Skip to content

Instantly share code, notes, and snippets.

@blackfry
Last active May 22, 2017 08:31
Show Gist options
  • Save blackfry/36659ed6a16aa161063c8d1e0efa288d to your computer and use it in GitHub Desktop.
Save blackfry/36659ed6a16aa161063c8d1e0efa288d to your computer and use it in GitHub Desktop.
server rendered with react router
import React from 'react';
import {renderToString} from 'react-dom/server';
import {StaticRouter} from 'react-router-dom';
import {createStore} from 'redux';
import {Provider}
import 'react-redux';
import reducer from 'reducer.js';
import App from 'App.js';
const app = new Express()
const port = 3000;
app.get(/^\/.*/, (req, res) => {
let config = buildAPIConfig(req);
// component doesn't get rendered until fetch promise is resolved with initial data
getAsyncData(config)
.then(apiResult => {
const context = {};
let preloadedState = apiResult;
const store = createStore(reducer, preloadedState);
const html = renderToString(
<Provider store={store}>
<StaticRouter
location={req.url}
context={context}>
<App/>
</StaticRouter>
</Provider>
);
if (context.url) {
res.writeHead(301, {
Location: context.url
});
res.end()
} else {
const finalState = store.getState();
res.set('content-type', 'text/html');
res.send(renderFullPage(html, finalState));
}
})
.catch(err => res.writeHead(400, {
Location: context.url
}))
});
app.listen(port, (error) => {
if (error) {
console.error(error)
} else {
console.info(`Listening on port ${port}. Open up http://localhost:${port}/ in your browser.`)
}
});
const getAsyncData = config => {
return fetch(config.route, config.options)
};
const buildAPIConfig = req => {
return {
route: req.route,
options: {
method: 'GET',
header: {
//
}
}
}
};
const renderFullPage = (html, finalState) => {
return `
<!doctype html>
<html>
<head>
<title>Redux Universal Example</title>
</head>
<body>
<div id="root">${html}</div>
<script>
// WARNING: See the following for security issues around embedding JSON in HTML:
// http://redux.js.org/docs/recipes/ServerRendering.html#security-considerations
window.__PRELOADED_STATE__ = ${JSON.stringify(finalState).replace(/</g, '\\u003c')}
</script>
<script src="/static/bundle.js"></script>
</body>
</html>
`
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment