Closed yongzhihuang closed 8 years ago
It's really easy, take a look at server/app.js
:
const app = express();
// ...
// Add anything you want before '*'
app.get('/api/v1/test', (req, res) => {
res.json({
staus: 200
});
});
app.use(express.static(path.resolve(__dirname, '..', 'build')));
app.get('*', (req, res) => {
res.sendFile(path.resolve(__dirname, '..', 'build', 'index.html'));
});
module.exports = app;
Hmm, I did that but that route is still being handled by react router it seems...
Oh now I get your question.
The react development server runs at port 3000 (npm start
), but the express.js server runs at port 9000 and it only returns the compiled react app (`npm run start:server).
Performing a GET request with fetch works fine:
class App extends Component {
// ...
state = {}
componentWillMount() {
fetch('http://localhost:9000/api/v1/test')
.then(result => result.json())
.then(response => this.setState({ response }));
}
render() {
// ...
}
}
But it is necessary to allow CORS because in development we have two apps on different ports:
const cors = require('cors');
const app = express();
if (process.env.NODE_ENV !== 'production') {
app.use(cors());
}
it would be necessary to build the app (npm run build
) each time to make it work at port 9000.
Ah makes sense now, thank you very much!
Hi,
I'm running into a similar issue. I'm doing OAuth authentication with github and I redirect to the github page from the server side. My server.js looks like this:
//... authentication logic with passport.js ... //
app.get('auth/github',
passport.authenticate('github', {scope: ['user', 'public_repo']})
);
app.use(express.static(path.join(__dirname, '/lemon/build')));
app.get('*',
function(req, res) {
res.sendFile(path.join(__dirname+'/lemon/build/index.html'));
});
My React App is as follows:
// ... importing modules ... //
ReactDOM.render(
<Provider store={store}>
<Router history={browserHistory}>
<Route path="/" component={LandingPage} />
<Route path="/announcements" component={AnnouncementsContainer} />
<Route path="/courses" component={CoursesContainer} />
<Route path="/community" component={CommunityContainer} />
<Route path="/404" component={NotFoundPage} />
</Router>
</Provider>,
document.getElementById('root')
);
I build the react app and serve it statically. I want the user to be able to navigate to localhost:3001/auth/github (server running on port 3001) which would redirect the user to github to login. However, instead it renders an empty page (index.html from my static files).
What I don't seem to understand is why the middleware is not being applied in order. That is why is the url redirected to the static files and not the auth/github routing which is specified first? I think it has to do with browser caching, but I tried disabling caching and that didn't help:
app.use(express.static(path.join(__dirname, '/lemon/build'), { etag: false }));
Any help would be really appreciated.
Probably you are missing the callback route:
const middleware = passport.authenticate('github', {
failureRedirect: '/login', // clientside route
});
app.get('/auth/github/callback', middleware, (req, res) => {
res.redirect('/'); // clientside route
});
No I do have that part but I didn't include it in the earlier comment. Here is what it looks like:
app.get('auth/github/callback',
passport.authenticate('github', { failureRedirect: '/' }),
function(req, res) {
console.log('Successful login!');
res.redirect('/announcements');
}
);
The issue is that localhost:3001/auth/github will not redirect to github and would render my static files. It redirects if I comment out the middleware handling serving the static assets. Any thoughts on why that could be the case?
Hi!
Awesome project btw. I would like to set up certain routes in express and have express handle them rather than React Router, how would I go about doing this?
Example:
Thanks!