React Router v4 URL问题

时间:2018-01-28 15:08:15

标签: node.js reactjs react-router react-router-v4

我们的react应用程序在开发模式(本地主机)中完美运行,但是当我们将它放到heroku服务器上时,我们无法直接访问路由。当我们将history.push({})写入我们的路径时,我们会得到一个404页面。

您可以在此处查看页面:placemate.herokuapp.com

重现步骤:转到上面的网址,看看它是否已加载。然后添加/登录到URL栏,您将看到显示404页面。但是,从标题中单击登录将指示您正确。

这是我们的路由器代码:

import React from 'react'
import { Switch, Route, Redirect } from 'react-router-dom'
import '../../App.css'
import Home from '../../scenes/general/home/Home'
import Login from '../../scenes/general/login/Login'
import Register from '../../scenes/general/register/Register'
import GuestHeader from '../../components/general/header/Header'

const Main = () => (
  <main className='main_app'>
      <GuestHeader />
      <Switch>
          <Route exact path='/' component={Home}/>
          <Route path='/login' component={Login}/>
          <Route path='/register' component={Register}/>
      </Switch>
    </main>
);

export default Main;

index.js文件:

ReactDOM.render(<BrowserRouter><App /></BrowserRouter>, document.getElementById('root'));
registerServiceWorker();

1 个答案:

答案 0 :(得分:4)

为何找不到404

这是因为当您在地址栏中放置任何路径时,其请求将被发送到Web服务器而不作出反应。如您所知,我们使用的react router负责根据路由显示正确的组件,但是因为您将路由传递给nginx / apache服务器而不是路由器;因此,您的Web服务器会尝试查找实际上不存在的www.example.com/login。因此,您找不到404。

<强>解决方案

尝试在Web服务器public html根目录中创建.htaccess文件。创建一些规则,以便始终从根路径转发请求。这将使反应进入画面,因此反应路由器可以抓取路径并渲染适当的组件。

例如,你可以创建类似这样的东西

对于Apache服务器

RewriteEngine On        
  # If an existing asset or directory is requested go to it as it is
  RewriteCond %{DOCUMENT_ROOT}%{REQUEST_URI} -f [OR]
  RewriteCond %{DOCUMENT_ROOT}%{REQUEST_URI} -d
  #RewriteCond %{SERVER_PORT} 80 
  #RewriteRule ^(.*)$ https://www.example.com/$1 [R,L]
  RewriteRule ^ - [L]

  # If the requested resource doesn't exist the serve index.html
  RewriteRule ^ ./index.html

对于Node.js

node.js express服务器的示例代码可以是这样的(存在于服务器实现的文件中,通常命名为server.js

const express = require('express');
const path = require('path');

const app = express();

if(process.env.NODE_ENV!== 'production'){
   //do something if you are in development environment

   //below lines only if you are using webpack based deployment

   const webpackMiddleware = require('webpack-dev-middleware');
   const webpack = require('webpack');
   const webpackConfig = require('./webpack.config.js');
   app.use(webpackMiddleware(webpack(webpackConfig)));
}
else{
  // in production env do following thing 
  app.use(express.static('public_html_folder'));//give user access to public assets

  //redirect all request to index.html for compatibality with react router
  app.get('*',(req,res)=>{
    res.sendFile(path.join(__dirname,'public_html_folder/index.html'));
  });
}

app.listen(process.env.PORT || 3050, () => console.log('Listening'));

我希望这可以解决您的问题或至少让您了解如果有不同的后端服务器该怎么做。