我正在使用React-router,当我点击链接按钮时,它工作得很好,但当我刷新我的网页时,它没有加载我想要的东西。

例如,我在localhost/joblist和一切都很好,因为我到达这里按下一个链接。但如果我刷新网页,我会得到:

Cannot GET /joblist

默认情况下,它不是这样工作的。最初我有我的URL localhost/#/和localhost/#/joblist,他们工作得很好。但我不喜欢这种类型的URL,所以试图删除#,我写道:

Router.run(routes, Router.HistoryLocation, function (Handler) {
 React.render(<Handler/>, document.body);
});

这个问题不会发生在localhost/,这个总是返回我想要的。

这个应用程序是单页的,所以/joblist不需要向任何服务器询问任何事情。

我的整个路由器。

var routes = (
    <Route name="app" path="/" handler={App}>
        <Route name="joblist" path="/joblist" handler={JobList}/>
        <DefaultRoute handler={Dashboard}/>
        <NotFoundRoute handler={NotFound}/>
    </Route>
);

Router.run(routes, Router.HistoryLocation, function (Handler) {
  React.render(<Handler/>, document.body);
});

当前回答

我也遇到过同样的问题,这个解决方案对我们很有效……

背景:

我们在同一台服务器上托管多个应用程序。当我们刷新服务器时,它不知道该在目标文件夹的哪个位置查找特定应用程序的索引。上面的链接将把你带到我们的工作…

我们正在使用:

文件package.json:

"dependencies": {
  "babel-polyfill": "^6.23.0",
  "ejs": "^2.5.6",
  "express": "^4.15.2",
  "prop-types": "^15.5.6",
  "react": "^15.5.4",
  "react-dom": "^15.5.4",
  "react-redux": "^5.0.4",
  "react-router": "^3.0.2",
  "react-router-redux": "^4.0.8",
  "redux": "^3.6.0",
  "redux-persist": "^4.6.0",
  "redux-thunk": "^2.2.0",
  "webpack": "^2.4.1"
}

我的webpack.config.js文件:

/* eslint-disable */
const path = require('path');
const webpack = require('webpack');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const babelPolyfill = require('babel-polyfill');
const HTMLWebpackPluginConfig = new HtmlWebpackPlugin({
  template: __dirname + '/app/views/index.html',
  filename: 'index.html',
  inject: 'body'
});

module.exports = {
  entry: [
    'babel-polyfill', './app/index.js'
  ],
  output: {
    path: __dirname + '/dist/your_app_name_here',
    filename: 'index_bundle.js'
  },
  module: {
    rules: [{
      test: /\.js$/,
      loader: 'babel-loader',
      query : {
          presets : ["env", "react", "stage-1"]
      },
      exclude: /node_modules/
    }]
  },
  plugins: [HTMLWebpackPluginConfig]
}

我的index.js文件

import React from 'react'
import ReactDOM from 'react-dom'
import Routes from './Routes'
import { Provider } from 'react-redux'
import { createHistory } from 'history'
import { useRouterHistory } from 'react-router'
import configureStore from './store/configureStore'
import { syncHistoryWithStore } from 'react-router-redux'
import { persistStore } from 'redux-persist'

const store = configureStore();

const browserHistory = useRouterHistory(createHistory) ({
  basename: '/your_app_name_here'
})
const history = syncHistoryWithStore(browserHistory, store)

persistStore(store, {blacklist: ['routing']}, () => {
  console.log('rehydration complete')
})
// persistStore(store).purge()

ReactDOM.render(
    <Provider store={store}>
      <div>
        <Routes history={history} />
      </div>
    </Provider>,
  document.getElementById('mount')
)

我的app.js文件:

var express = require('express');
var app = express();

app.use(express.static(__dirname + '/dist'));
// app.use(express.static(__dirname + '/app/assets'));
app.set('views', __dirname + '/dist/your_app_name_here');
app.engine('html', require('ejs').renderFile);
app.set('view engine', 'html');

app.get('/*', function (req, res) {
    res.render('index');
});

app.listen(8081, function () {
  console.log('MD listening on port 8081!');
});

其他回答

如果你有一个回退到你的index.html,确保在你的index.html文件中你有这个:

<script>
  System.config({ baseURL: '/' });
</script>

这可能因项目而异。

用Laravel在React中实现JavaScript SPA的解决方案

公认的答案是对为什么会发生这样的问题的最好解释。如前所述,您必须同时配置客户端和服务器端。

在你的blade模板中,包括JavaScript绑定文件,确保像这样使用URL外观:

<script src="{{ URL::to('js/user/spa.js') }}"></script>

在路由中,确保将此添加到刀片模板所在的主端点。例如,

Route::get('/setting-alerts', function () {
   return view('user.set-alerts');
});

以上是刀片模板的主要端点。现在再添加一条可选路线,

Route::get('/setting-alerts/{spa?}', function () {
  return view('user.set-alerts');
});

发生的问题是,首先加载刀片模板,然后加载React路由器。当你加载'/setting-alerts'时,它会加载HTML内容和JavaScript代码。

但是当你加载'/setting-alerts/about'时,它首先在服务器端加载。因为它在服务器端,所以这个位置上没有任何东西,并且它返回not found。当你有可选的路由器时,它加载同一个页面,React路由器也被加载,然后React加载器决定显示哪个组件。

如果您在谷歌桶上运行它,简单的解决方案是考虑'index.html'为错误(404 not found)页面。

这样做:

在桶的列表中,找到您创建的桶。 单击桶关联的桶溢出菜单(…),选择“编辑网站配置”。 在网站配置对话框中,将主页也指定为错误页面。

我也遇到过同样的问题,这个解决方案对我们很有效……

背景:

我们在同一台服务器上托管多个应用程序。当我们刷新服务器时,它不知道该在目标文件夹的哪个位置查找特定应用程序的索引。上面的链接将把你带到我们的工作…

我们正在使用:

文件package.json:

"dependencies": {
  "babel-polyfill": "^6.23.0",
  "ejs": "^2.5.6",
  "express": "^4.15.2",
  "prop-types": "^15.5.6",
  "react": "^15.5.4",
  "react-dom": "^15.5.4",
  "react-redux": "^5.0.4",
  "react-router": "^3.0.2",
  "react-router-redux": "^4.0.8",
  "redux": "^3.6.0",
  "redux-persist": "^4.6.0",
  "redux-thunk": "^2.2.0",
  "webpack": "^2.4.1"
}

我的webpack.config.js文件:

/* eslint-disable */
const path = require('path');
const webpack = require('webpack');
const HtmlWebpackPlugin = require('html-webpack-plugin');
const babelPolyfill = require('babel-polyfill');
const HTMLWebpackPluginConfig = new HtmlWebpackPlugin({
  template: __dirname + '/app/views/index.html',
  filename: 'index.html',
  inject: 'body'
});

module.exports = {
  entry: [
    'babel-polyfill', './app/index.js'
  ],
  output: {
    path: __dirname + '/dist/your_app_name_here',
    filename: 'index_bundle.js'
  },
  module: {
    rules: [{
      test: /\.js$/,
      loader: 'babel-loader',
      query : {
          presets : ["env", "react", "stage-1"]
      },
      exclude: /node_modules/
    }]
  },
  plugins: [HTMLWebpackPluginConfig]
}

我的index.js文件

import React from 'react'
import ReactDOM from 'react-dom'
import Routes from './Routes'
import { Provider } from 'react-redux'
import { createHistory } from 'history'
import { useRouterHistory } from 'react-router'
import configureStore from './store/configureStore'
import { syncHistoryWithStore } from 'react-router-redux'
import { persistStore } from 'redux-persist'

const store = configureStore();

const browserHistory = useRouterHistory(createHistory) ({
  basename: '/your_app_name_here'
})
const history = syncHistoryWithStore(browserHistory, store)

persistStore(store, {blacklist: ['routing']}, () => {
  console.log('rehydration complete')
})
// persistStore(store).purge()

ReactDOM.render(
    <Provider store={store}>
      <div>
        <Routes history={history} />
      </div>
    </Provider>,
  document.getElementById('mount')
)

我的app.js文件:

var express = require('express');
var app = express();

app.use(express.static(__dirname + '/dist'));
// app.use(express.static(__dirname + '/app/assets'));
app.set('views', __dirname + '/dist/your_app_name_here');
app.engine('html', require('ejs').renderFile);
app.set('view engine', 'html');

app.get('/*', function (req, res) {
    res.render('index');
});

app.listen(8081, function () {
  console.log('MD listening on port 8081!');
});

这里有一个简单、清晰和更好的解决方案。如果你使用网络服务器,它就可以工作。

每个web服务器都有能力在出现HTTP 404时将用户重定向到错误页面。要解决此问题,需要将用户重定向到索引页。

如果您使用Java基础服务器(Tomcat或任何Java应用程序服务器),解决方案可能如下:

web . xml:

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
         version="3.1">

    <!-- WELCOME FILE LIST -->
    <welcome-file-list>
        <welcome-file>index.jsp</welcome-file>
    </welcome-file-list>

    <!-- ERROR PAGES DEFINITION -->
    <error-page>
        <error-code>404</error-code>
        <location>/index.jsp</location>
    </error-page>

</web-app>

例子:

得到http://example.com/about web服务器抛出HTTP 404,因为此页面在服务器端不存在 错误页面配置通知服务器将index.jsp页面发送回用户 那么JavaScript将在客户端完成剩下的工作,因为客户端的URL仍然是http://example.com/about。

就是这样。不再需要魔法:)