详解react-router 4.0 下服务器如何配合BrowserRouter


Posted in Javascript onDecember 29, 2017

react-router作为react框架路由解决方案在react项目中举足轻重。

在react-router 4.0版本中,API与先前版本相比有了很大的修改,在2.0、3.0中常用的<Router>组件作为路由底层配置组件不再常用,取而代之的是四个各有不同的路由组件:

<BrowserRouter>, <HashRouter>, <MemoryRouter>, <StaticRouter>

其中<MemoryRouter>组件在内存中保存“URL”信息,不会修改浏览器的地址栏,往往用于React Native或测试环境等非浏览器环境。

而<StaticRouter>组件从名字能看出它从不修改路由,这在服务器端渲染时很有用。

<HashRouter>组件我们最为熟悉的路由组件不用再多赘述,这里来说说我在使用react-router推荐的<BrowserRouter>时遇到的坑。

<BrowserRouter>

<BrowserRouter>和<HashRouter>都可以实现前端路由的功能,区别是前者基于rul的pathname段,后者基于hash段。

前者:http://127.0.0.1:3000/article/num1

后者:http://127.0.0.1:3000/#/article/num1(不一定是这样,但#是少不了的)

这样的区别带来的直接问题就是当处于二级或多级路由状态时,刷新页面,<BrowserRouter>会将当前路由发送到服务器(因为是pathname),而<HashRouter>不会(因为是hash段)。

我们当然不希望前端路由被发送到后台。

在react-router 4.0 的文档中有这样一段话:

注意: 使用 hash 的方式记录导航历史不支持 location.key 和 location.state。 在以前的版本中,我们为这种行为提供了 shim,但是仍有一些问题我们无法解决。 任何依赖此行为的代码或插件都将无法正常使用。 由于该技术仅用于支持传统的浏览器,因此在用于浏览器时可以使用 <BrowserHistory> 代替。

这就要求服务器要配合前端做一些简单的修改。

修改的思想就是当收到请求的url不是功能性的,而是前端路由时,重新加载入口html文件(我的后台是nodejs)。

// catch 404 and forward to error handler
app.use(function(req, res, next) {
  //判断是主动导向404页面,还是传来的前端路由。
 //如果是前端路由则如下处理

  fs.readFile(__dirname + '/public/dist/index.html', function(err, data){
    if(err){
      console.log(err);
      res.send('后台错误');
    } else {
      res.writeHead(200, {
        'Content-type': 'text/html',
        'Connection':'keep-alive'
      });
      res.end(data);
    }
  })
});

此处踩坑无数,在网上搜索方法后换用nginx,使用try_files字段定向到入口html,但是重定向后,webpack打包的js文件没有执行。

在查看firebug时发现此次刷新的响应头中设置了"Connection":"keep-alive";

觉得问题应该出在这里,换用nodejs用200状态配合keep-alive果然解决了问题。

在react-router 4.0 多级路由下刷新页面不会再404,而是保存了前端状态。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
JavaScript 判断日期格式是否正确的实现代码
Jul 04 Javascript
JavaScript实现斗地主游戏的思路
Feb 29 Javascript
基于javascript bootstrap实现生日日期联动选择
Apr 07 Javascript
JavaScript绑定事件监听函数的通用方法
May 14 Javascript
KnockoutJS 3.X API 第四章之事件event绑定
Oct 10 Javascript
Bootstrap优化站点资源、响应式图片、传送带使用详解3
Oct 14 Javascript
根据Bootstrap Paginator改写的js分页插件
Dec 25 Javascript
原生js实现放大镜效果
Jan 11 Javascript
js阻止移动端页面滚动的两种方法
Jan 25 Javascript
angularjs的单选框+ng-repeat的实现方法
Sep 12 Javascript
了解重排与重绘
May 29 Javascript
Cordova(ionic)项目实现双击返回键退出应用
Sep 17 Javascript
浅谈react-router HashRouter和BrowserRouter的使用
Dec 29 #Javascript
javaScript 连接打印机,打印小票的实例
Dec 29 #Javascript
深入浅析vue组件间事件传递
Dec 29 #Javascript
详解Vue 事件修饰符capture 的使用
Dec 29 #Javascript
react-router browserHistory刷新页面404问题解决方法
Dec 29 #Javascript
node简单实现一个更改头像功能的示例
Dec 29 #Javascript
JavaScript 中使用 Generator的方法
Dec 29 #Javascript
You might like
THINKPHP+JS实现缩放图片式截图的实现
2010/03/07 PHP
php设计模式 Builder(建造者模式)
2011/06/26 PHP
PHP计算2点经纬度之间的距离代码
2013/08/12 PHP
php读取excel文件示例分享(更新修改excel)
2014/02/27 PHP
PHP获取当前页面URL函数实例
2014/10/22 PHP
JavaScript 编程引入命名空间的方法
2007/06/29 Javascript
js实现时间显示几天前、几小时前或者几分钟前的方法集锦
2015/05/29 Javascript
javascript实现鼠标放上后下边对应内容变换的效果
2015/08/06 Javascript
初识angular框架后的所思所想
2016/02/19 Javascript
利用JavaScript阻止表单提交的两种方法
2016/08/11 Javascript
微信小程序 开发工具快捷键整理
2016/10/31 Javascript
简单实现JS计算器功能
2016/12/21 Javascript
过期软件破解办法实例详解
2017/01/04 Javascript
深入理解React中何时使用箭头函数
2017/08/23 Javascript
React 组件转 Vue 组件的命令写法
2018/02/28 Javascript
Vue官方推荐AJAX组件axios.js使用方法详解与API
2018/10/09 Javascript
用Electron写个带界面的nodejs爬虫的实现方法
2019/01/29 NodeJs
Ant Design Pro 之 ProTable使用操作
2020/10/31 Javascript
JS时间戳与日期格式互相转换的简单方法示例
2021/01/30 Javascript
爬山算法简介和Python实现实例
2014/04/26 Python
详解Python里使用正则表达式的ASCII模式
2017/11/02 Python
在python中利用try..except来代替if..else的用法
2019/12/19 Python
CSS3 实现雷达扫描图的示例代码
2020/09/21 HTML / CSS
CSS代码检查工具stylelint的使用方法详解
2021/03/27 HTML / CSS
校园餐饮创业计划书
2014/01/10 职场文书
教导处工作制度
2014/01/18 职场文书
2014年社区重阳节活动策划方案
2014/09/16 职场文书
税务干部群众路线教育实践活动自我剖析材料
2014/09/21 职场文书
早读课迟到检讨书
2014/09/25 职场文书
美国旅游签证工作证明
2014/10/14 职场文书
习近平在党的群众路线教育实践活动总结大会上的讲话全文
2014/10/25 职场文书
2014年基层党支部工作总结
2014/12/04 职场文书
财务个人年度总结范文
2015/02/26 职场文书
2015年初中生自我评价范文
2015/03/03 职场文书
Windows Server 2019 安装DHCP服务及相关配置
2022/04/28 Servers
Mysql数据库事务的脏读幻读及不可重复读详解
2022/05/30 MySQL