Isomorphic React in Three Simple Steps
2 min readNov 17, 2015
An isomorphic react app has three basic parts:
- You generate a html file using react-dom/server’s reactDOM.renderToString()
- This is then served along with the client javascript file —
- — which is pretty much the same as the server-side code, except that it uses reactDOM.render()
The code we’re interested in on the server is:
app.use(function *() {
var splitURL = this.url.split('/');
splitURL.shift();
var username = splitURL.shift();
var id = splitURL.shift();
var user = yield fetchUser(username).then((user) => {
if ((id) && (user.posts.indexOf(id) > 0)) {
user.posts.splice(user.posts.indexOf(id), 1);
user.posts.unshift(id);
}
var promiseArr = user.posts.map(id => fetchPost(username, id));
return Promise.all(promiseArr).then((data) => {
user.posts = data;
return user;
});
});
this.body = generateHTML(user);
});
We’re still serving static files off the public directory, which brings us to the client code:
var splitPathname = window.location.pathname.split('/');
splitPathname.shift();
let username = splitPathname.shift();
let id = splitPathname.shift();function load(username, id) {
return fetchUser(username).then((user) => {
if ((id) && (user.posts.indexOf(id) > 0)) {
user.posts.splice(user.posts.indexOf(id), 1);
user.posts.unshift(id);
}
var promiseArr = user.posts.map(id => fetchPost(username, id));
Promise.all(promiseArr).then((data) => {
user.posts = data;
let mountNode = document.getElementById(“react-mount”);
React.render(React.createElement(views.User, user), mountNode);
});
});
}
Pretty similar, huh? The file is bundled using webpack and put in the public directory using this webpack.config.js:
var path = require('path');
var webpack = require('webpack');
module.exports = {
entry: [
'./main.js'
],
output: {
path: path.join(__dirname, 'public'),
filename: 'main.js',
},
module: {
loaders: [{loader: ‘uglify’}, {
exclude: /node_modules/,
loader: 'babel'
}]
},
plugins: [
new webpack.ProvidePlugin({
‘fetch’: ‘imports?this=>global!exports?global.fetch!whatwg-fetch’
})
]
};
Note that we’re using whatwg-fetch to support the fetch api on older browsers. We can run webpack using an npm post install script in our package.json:
"scripts": {
"start": "node index.js",
"postinstall": "webpack -p"
}
To recap, we have
- Server code that generates html and
- Serves both the html and the client code
- Which is pretty much the same as the server code
And that’s about it! Congratulations, you’ve made an isomorphic react app!