This weekend my project ended up being "find a React/Rails gem that works." I administer a couple different Rails 6.0 projects with fairly vanilla configurations, so chances are that someone else is going to need to setup
react_on_rails and will find this useful.
Incidentally, we were migrating from
webpacker-react, which to this point I would tend to recommend over
react_on_rails for the cases where one doesn't need SSR. The docs and examples on the latter are great, but it has been further from a "Just Works" experience than
This was hard. As source I started with the very helpful project that shakacode set up as a proof-of-concept.
As best I can tell, keeping HMR functional with React and webpacker is a hot potato-type of project. There seem to be about five different approaches to realizing HMR, and most of those approaches call themselves deprecated (including the once-default npm package to get hot reloading). The latest heir to the title nobody seems to want is react-refresh-webpack-plugin, which still labels itself as "experimental" as of November 2020. Anyway, it seems to be the going default, and you can add it via
Remember to remove
react-hot-loader from your
packages.json directory if it had previously been included.
The shakacode HMR tutorial project adds the following line to it's babel.config.js:
I believe the
process.env.WEBPACK_DEV_SERVER ties into the many-config-file split SSR/client setup from the tutorial project. If not using that, I believe that
process.env.WEBPACK_DEV_SERVER would instead be
But that project makes a great number of changes to all of the default webpacker configuration files (one for each environment) and adds three new files on behalf of allowing a split compiling of SSR and non-SSR webpacker assets. Here is the directory in question where all of those config files reside. Since I'd like to have SSR, I emulated that project.
If you don't to add a bunch of tech debt-ish boilerplate to your config directory, and merely want to get HMR working, then adding this to
config/webpack/development.js ought to do the trick:
As far as
config/webpacker.yml, nothing in the tutorial project seems to be consequentially different from the default file provided by the Rails
webpacker gem. Just need to make sure
hmr: true and
inline: true in the
In one of my projects, even though the entire contents of
packs/application.js appeared to be commented out, I discovered that by including that pack tag, a second version of HMR was being imported that prevented the main HMR mechanism from functioning. I doubt others will experience this but leaving it here in case you followed all the steps above, HMR still doesn't work and you're low on ideas.
By default, React on Rails registers a pack by calling
In a file that resides within
ReactOnRails.register. I'm not sure how this could ever be true in medium-to-large projects -- it certainly wasn't for us. It was easy to work around though using this suggestion from this issue. Instead of starting your pack with
You can instead use
The ticket talks about splitting packs up not to have overlap, but I don't have time to explore that. This suggestion has managed to Just Work.
While loading components after xhr looks to "Just Work" in
webpacker-react, there's some heavy lifting involved to get it working smoothly with
react_on_rails. This issue (starting to sense a trend here?) describes how best to get this working:
[todo: finish figuring out]
For reasons that nobody has been able to figure out in three years, some Rails projects don't get access to the gem's included
react_component helper. I had this happen in one of my Rails projects. Resolved by adding the following to the end of the
ReactOnRails.configure do |config| in
For a use case that one assumes would be common (getting React to work on Rails), there's still a good amount of polish work that needs to be done around the edges to get access to all the best functionality. I suppose it is partly a reflection of how rapidly the space has moved forward. At any rate, even though there was a lot of tedious Googling that went into getting a working setup for us, it was certainly appreciated how many examples shakacode's Josh has provided for tinkerers like myself to be able to reverse-engineer how to get their own projects working. Thanks, Josh! We'll become customers soon enough if this setup continues to function smoothly for us.