Skip to content

Commit

Permalink
WIP2
Browse files Browse the repository at this point in the history
  • Loading branch information
justin808 committed Mar 8, 2020
1 parent 2da3029 commit 58daa51
Show file tree
Hide file tree
Showing 5 changed files with 95 additions and 49 deletions.
11 changes: 7 additions & 4 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,21 +17,24 @@ Changes since last non-beta release.
*Please add entries here for your pull requests that are not yet released.*
### [11.4.0] - 2020-01-19
#### Changed
- Changes enable hashing of the server bundle so that it's in the manifest. This is important
because the `assets:clean` "enhancement" of rails/webpacker deletes any files that are not
in the `manifest.json`. Thus, it's critical to fingerprint the server bundle and adding it to
the manifest.

- Added configuration option `same_bundle_for_client_and_server` with default `false` because

1. Production applications would typically have a server bundle that differs from the client bundle
2. This change only affects trying to use HMR with react_on_rails with rails/webpacker.

The previous behavior was to always go to the webpack-dev-server for the server bundle if the
webpack-dev-server was running _and_ the server bundle was found in the `manifest.json`. Because
the `assets:clean` enhancement of rails/webpacker deletes any files that are not in the `manifest.json`,
we recommend fingerprinting the server bundle and adding it to the manifest.
webpack-dev-server was running _and_ the server bundle was found in the `manifest.json`.

If you are using the **same bundle for client and server rendering**, then set this configuration option
to `true`. By [justin808](https://github.com/justin808/1240).

#### Improved
- Removed unnecessary restriction to keep the server bundle in the same directory with the client bundles. Rails/webpacker 4 has an advanced cleanup that will remove any files in the directory of other webpack files. Removing this restriction allows the server bundle to be created in a sibling directory. Note, the rails/webpacker cleanup will remove any files in child directories. By [justin808](https://github.com/justin808/1240).
- The gem execjs no longer needs to be explicitly included. When Rails is installed without `Sprockets`, `ExecJS` was not required, resulting in the error: `uninitialized constant #<Class:0x00007fc487215bf8>::ExecJS`

### [11.3.0] - 2019-05-24
#### Added
Expand Down
61 changes: 60 additions & 1 deletion docs/tutorial.md
Original file line number Diff line number Diff line change
Expand Up @@ -111,21 +111,59 @@ First, check that the `hmr` option is `true` in your `config/webpacker.yml` file

The basic setup will have HMR working with the default webpacker setup. However, the basic will cause a full page refresh each time you save a file.

To have proper React hot loading:


1. Add the `react-hot-loader` and ` @hot-loader/react-dom` npm packages.
```sh
yarn add --dev react-hot-loader @hot-loader/react-dom
```

2. Add changes like this to your entry points

```diff
// app/javascript/packs/hello_react.jsx

import React from 'react';
+ import { hot } from 'react-hot-loader/root';
```

```diff
- export default HelloWorld;
+ export default hot(HelloWorld);
```

3. Adjust your webpack configuration for development so that `sourceMapContents` option for the sass
loader is `false`

```diff
// config/webpack/development.js

process.env.NODE_ENV = process.env.NODE_ENV || 'development'

const environment = require('./environment')

// allows for editing sass/scss files directly in browser
+ if (!module.hot) {
+ environment.loaders.get('sass').use.find(item => item.loader === 'sass-loader').options.sourceMapContents = false
+ }
+
module.exports = environment.toWebpackConfig()
```

4. Adjust your `config/webpack/environment.js` for a

```diff
// config/webpack/environment.js

// ...

// Fixes: React-Hot-Loader: react-🔥-dom patch is not detected. React 16.6+ features may not work.
// https://github.com/gaearon/react-hot-loader/issues/1227#issuecomment-482139583
+ environment.config.merge({ resolve: { alias: { 'react-dom': '@hot-loader/react-dom' } } });

module.exports = environment;
```



Expand Down Expand Up @@ -272,7 +310,9 @@ and you will see your live app and you can share this URL with your friends. Con

## Turning on Server Rendering

You can turn on server rendering by simply changing the `prerender` option to `true`:
You can turn on server rendering by:

1. Changing the `prerender` option to `true`:

```erb
<%= react_component("HelloWorld", props: @hello_world_props, prerender: true) %>
Expand All @@ -288,6 +328,25 @@ If you want to test this out with HMR, then you also need to add this line to yo
More likely, you will create a different build file for server rendering. However, if you want to
use the same file from the webpack-dev-server, you'll need to add that line.





PUT IN THE CHANGES TO ALLOW FOR creating different server and client bundles














Then push to Heroku:

```
Expand Down
Original file line number Diff line number Diff line change
@@ -1,45 +1,27 @@
import PropTypes from 'prop-types';
import React from 'react';
import React, { useState} from 'react';

export default class HelloWorld extends React.Component {
static propTypes = {
name: PropTypes.string.isRequired, // this is passed from the Rails view
};
const HelloWorld = (props) => {
const [name, setName] = useState(props.name);

/**
* @param props - Comes from your rails view.
*/
constructor(props) {
super(props);
return (
<div>
<h3>
Hello, {name}!
</h3>
<hr />
<form >
<label htmlFor="name">
Say XXXXX to:
</label>
<input
id="name"
type="text"
value={name}
onChange={(e) => setName(e.target.value)}
/>
</form>
</div>
);
};

// How to set initial state in ES6 class syntax
// https://reactjs.org/docs/state-and-lifecycle.html#adding-local-state-to-a-class
this.state = { name: this.props.name };
}

updateName = (name) => {
this.setState({ name });
};

render() {
return (
<div>
<h3>
Hello, {this.state.name}!
</h3>
<hr />
<form >
<label htmlFor="name">
Say hello to:
</label>
<input
id="name"
type="text"
value={this.state.name}
onChange={(e) => this.updateName(e.target.value)}
/>
</form>
</div>
);
}
}
export default HelloWorld;
3 changes: 3 additions & 0 deletions lib/react_on_rails/helper.rb
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
require "react_on_rails/utils"
require "react_on_rails/json_output"
require "active_support/concern"
require "execjs"

module ReactOnRails
module Helper
Expand Down Expand Up @@ -258,6 +259,8 @@ def server_render_js(js_expression, options = {})
html = result["html"]
console_log_script = result["consoleLogScript"]
raw("#{html}#{render_options.replay_console ? console_log_script : ''}")

# TODO, this error is probably different for mini_racer
rescue ExecJS::ProgramError => err
raise ReactOnRails::PrerenderError, component_name: "N/A (server_render_js called)",
err: err,
Expand Down
3 changes: 1 addition & 2 deletions lib/tasks/assets.rake
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,7 @@ if defined?(Sprockets)
# Note, it's not possible to refer to ReactOnRails configuration values at this point.
Rake::Task["assets:precompile"]
.clear_prerequisites
.enhance([:environment, "react_on_rails:assets:compile_environment"])
.enhance do
.enhance([:environment, "react_on_rails:assets:compile_environment"]) do
Rake::Task["react_on_rails:assets:symlink_non_digested_assets"].invoke
Rake::Task["react_on_rails:assets:delete_broken_symlinks"].invoke
end
Expand Down

0 comments on commit 58daa51

Please sign in to comment.