React单页应用程序与浏览器历史是否可能



我一直在使用hashHistoryreact-router构建一个react单页应用程序,在我决定删除URL中的尾部代码之前,一切都很顺利:#/?_k=ncbx6v

我遇到的推荐解决方案是转换到browserHistory,但我注意到所有的示例和解决方案都需要使用webpack-dev-serverhistory-api-fallback设置为true。我尝试了这种方法,它起了作用(通过localhost),但曾经起作用的独立bundle.js文件+index.html不再起作用。

当我运行webpack并打开html文件时,我在控制台中收到以下错误:Warning: [react-router] Location "/Users/mike/project/index.html" did not match any routes

我不熟悉这个问题背后的机制,但我很好奇是否有我不熟悉的解决方案。

这是我的webpack文件:

const {resolve} = require('path')
module.exports = () => {
return {
context: resolve('src'),
entry: './app',
output: {
path: resolve('public'),
filename: 'bundle.js',
publicPath: '/public/'
},
resolve: {
extensions: ['.js', '.jsx', '.json']
},
stats: {
colors: true,
reasons: true,
chunks: false
},
module: {
rules: [
{enforce: 'pre', test: /.jsx?$/, loader: 'eslint-loader', exclude: [/node_modules/]},
{test: /.jsx?$/,loader: 'babel-loader', include: /src/, exclude: /node_modules/
},
{test: /.json$/, loader: 'json-loader'},
{test: /(.css)$/, loaders: ['style-loader', 'css-loader']},
{test: /.eot(?v=d+.d+.d+)?$/, loader: "file-loader"},
{test: /.(woff|woff2)$/, loader: "url-loader?prefix=font/&limit=5000"},
{test: /.ttf(?v=d+.d+.d+)?$/, loader: "url-loader?limit=10000&mimetype=application/octet-stream"},
{test: /.svg(?v=d+.d+.d+)?$/, loader: "url-loader?limit=10000&mimetype=image/svg+xml"}
]
}
}
}

这是我的app.js:

'use strict'
import React from 'react'
import ReactDOM from 'react-dom'
import Layout from './components/common/Layout'
import { Router, Route, IndexRoute, browserHistory } from 'react-router'
import configureStore from './store/configureStore'
import { Provider } from 'react-redux'
const store = configureStore()
class App extends React.Component {
render () {
return (
<Provider store={store}>
<Router history={browserHistory}>
<Route path='/' component={Layout}></Route>
</Router>
</Provider>
)
}
}
ReactDOM.render(<App />, document.getElementById('app'))

为了使用浏览器历史记录,您需要一个能够处理所有可能路由的后端。如果你不打算有一个可以支持路由的后端(例如,你将提供静态文件),你应该坚持哈希历史记录。

浏览器历史记录如何工作的基本解释是,它查看当前URL的pathname,并尝试将其与已知路由相匹配。在包含的错误中,您的pathname/Users/mike/project/index.html。这意味着,为了让React Router匹配该URL,您必须将<Route>path(或具有一系列嵌套的<Route>)定义为/Users/mike/project/index.html

<Route path='Users/mike/project/index.html' component={App} />

哈希历史记录适用于静态文件,因为它只是在pathname之后添加一个哈希符号,并根据之后的内容确定路由。

如果您的问题只是不喜欢使用查询关键字(?_k=jkadjlkd),那么您可以指定在创建history实例时不应包含该关键字。URL仍将包括#,但不再附加密钥"垃圾邮件"。

import { Router, useRouterHistory } from 'react-router'
import { createHashHistory } from 'history'
const appHistory = useRouterHistory(createHashHistory)({ queryKey: false })
<Router history={appHistory} />

相关内容

最新更新