facebook/create-react-app

How to publish components without ejecting

robcaldecott opened this issue · 11 comments

I hope others find this useful.

I have a project built using CRA that includes some components I wish to publish on npm. In order to do that I need to use babel to transpile the code to ES5.

Out of the box, babel is not available from a package.json script and I really don't want to eject. So I made this work by npm installing babel-cli and babel-preset-react-app and then adding a compile script that looks something like this:

set NODE_ENV=production&&babel -d lib/ src/ --presets react-app

This seems to work, plus all the CRA scripts (start, test and build) seem unaffected.

So if you need to do this, it looks like you can achieve it without having to eject. Which is a nice surprise.

Would you like to add Using the Babel Preset to the User Guide?

I think that would be really useful.

It would indeed be useful. I used your setup myself and it works great. But I have a problem with CSS.

I have a few stylesheets (one per component) that I import via Webpack (as described in the User guide). However, the stylesheets are not copied into lib when using Babel. So I had to extract the stylesheets in an index.css file and npm install postcss-cli, cssnano and autoprefixer. I then added a new compile step which gives us the following result:

"compile": "npm run compile:js && npm run compile:css",
"compile:js": "NODE_ENV=production babel src/orb -d lib --presets react-app",
"compile:css": "postcss --use autoprefixer --use cssnano src/orb/index.css > lib/index.css"

It works but it does require putting all your css in one file. I don't know how to do better.

@gaearon Could create-react-app generate .babelrc file with { "presets": ["react-app"] } (or to package.json)? It would make all babel scripts work out of the box..

@sheerun

We want to hide dev dependencies and their versions, so I would like to avoid that. I understand the motivation in this issue but it's a slightly more advanced use case, and so we don't have a clean support for it.

I think that after we implement #741, we might take a look at supporting building/publishing components with that package structure.

@emilebres, is the idea that you're putting everything into one CSS file to simplify consumption, since only one CSS file has to be imported in addition to the code itself?

That's certainly one advantage yes.
Although these days I tend not to style the components directly (colour, font) but rather to expose classes that the user can use to customise the components as she wishes. And I use inline styles for the absolutely necessary CSS (position, sizes).

Thanks @emilebres, good to know.

The problem I'm facing is that the components I want to compile are using CSS modules, which creates its own additional set of problems. I'm more & more preferring the atomic functional CSS approach over both style-in-js and CSS Modules, since it solves this and many other styling & theming related issues.

I would love to contribute to this, as I will have to do a POC in implementing thing like this for my new project. http://github.com/mappmechanic/codelab-book

@gaearon - Please do guide me if I should do a Prototype with that Babel Preset thing or some other approach.

I'll close as this is currently out of scope of the project.

I recommend nwb for publishing components.

For a very simple start to uncompiled typescript components, this might make a good read.

Its done for vanilla Typescript components but principles should cross over to TSX

https://medium.com/@quantumjs/combining-webpack-and-typescript-to-publish-component-libraries-over-npm-d22c3201ab22

If anyone wants I can look at TSX.