vue-router启用history模式下的开发及非根目录部署方法


Posted in Javascript onDecember 23, 2018

 为什么要有 hash 和 history

对于 Vue 这类渐进式前端开发框架,为了构建 SPA(单页面应用),需要引入前端路由系统,这也就是 Vue-Router 存在的意义。前端路由的核心,就在于 —— 改变视图的同时不会向后端发出请求。

为了达到这一目的,浏览器当前提供了以下两种支持:

1.hash —— 即地址栏 URL 中的 # 符号(此 hash 不是密码学里的散列运算)。

比如这个 URL:http://www.abc.com/#/hello,hash 的值为 #/hello。它的特点在于:hash 虽然出现在 URL 中,“#”后面的内容不会被包括在 HTTP 请求中,对后端完全没有影响,因此改变 hash 不会重新加载页面。

2.history —— 利用了 HTML5 History Interface 中新增的 pushState() 和 replaceState() 方法。(需要特定浏览器支持)
这两个方法应用于浏览器的历史记录栈,在当前已有的 back、forward、go 的基础之上,它们提供了对历史记录进行修改的功能。只是当它们执行修改时,虽然改变了当前的 URL,但浏览器不会立即向后端发送请求。

因此可以说,hash 模式和 history 模式都属于浏览器自身的特性,Vue-Router 只是利用了这两个特性(通过调用浏览器提供的接口)来实现前端路由。

vue-router 的 history 模式是个提高颜值的好东西,没有了 hash 的路由看起来清爽许多。

开发的时候,如果我们使用 devServer 来启动服务,由于一般不共用端口,我们一般不存在非根目录的问题。

而刷新后 404 的问题可以借助 historyApiFallback 来解决。

但当我们项目对外开放时,往往无法在域名根目录下提供服务,这个时候资源的访问路径与开发时的根目录就有了区别。

首先,我们通过 webpack 来配置一下项目中所有资源的基础路径,让这份代码在开发和生产环境中都可以正确找到资源。

// config/index.js
module.exports = {
  dev: {
    ...
    // 开发环境根目录 - 服务根目录 - 绝对路径
    assetsPublicPath: '/'
    ...
  },
  build: {
    ...
    // 生产环境根目录 - 服务器访问路径 - 绝对路径
    assetsPublicPath: '/test/project1/'
    ...
  }
}

 
// build/webpack.common.conf.js
const config = require('../config')
module.exports = {
  output: {
    publicPath: process.env.NODE_ENV === 'production'
      ? config.build.assetsPublicPath
      : config.dev.assetsPublicPath
  }
}

// build/webpack.dev.conf.js
const common = require('./webpack.common')
module.exports = merge(common, {
  devServer: {
    historyApiFallback: true
  }
}

然后在提供服务的服务器配置中做如下配置(以 nginx 为例):

location /test/project1 {
    alias .../project1; // 项目的真实路径
    index index.html;
    try_files $uri $uri/ /test/project1/index.html;
}

try_files 会按顺序检查参数中的资源是否存在,并返回第一个找到的资源,如果都没有找到,它会让 nginx 内部重定向到会后一个参数。

对了,所以它的的作用是解决刷新 404 的问题。

这里值得注意的是 try_files 的参数是绝对路径。

至此,你开启 history 模式的项目就可以顺利的跑在任何路径了。

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

Javascript 相关文章推荐
jQuery之网页换肤实现代码
Apr 30 Javascript
EasyUI的treegrid组件动态加载数据问题的解决办法
Dec 11 Javascript
JS验证日期的格式YYYY-mm-dd 具体实现
Jun 29 Javascript
js获取当前月的第一天和最后一天的小例子
Nov 18 Javascript
jQuery响应enter键的实现思路
Apr 18 Javascript
jquery实现的导航固定效果
Apr 28 Javascript
JavaScript实现广告弹窗效果
Aug 09 Javascript
Bootstrap基本插件学习笔记之标签切换(17)
Dec 08 Javascript
AngularJS中的promise用法分析
May 19 Javascript
浅谈JavaScript作用域和闭包
Sep 18 Javascript
IntelliJ IDEA编辑器配置vue高亮显示
Sep 26 Javascript
react 路由Link配置详解
Nov 11 Javascript
小程序实现人脸识别功能(百度ai)
Dec 23 #Javascript
优雅的elementUI table单元格可编辑实现方法详解
Dec 23 #Javascript
基于webpack4.X从零搭建React脚手架的方法步骤
Dec 23 #Javascript
JavaScript基于数组实现的栈与队列操作示例
Dec 22 #Javascript
jQuery实现侧边栏隐藏与显示的方法详解
Dec 22 #jQuery
JavaScript时间日期操作实例小结【5个示例】
Dec 22 #Javascript
JavaScript文本特效实例小结【3个示例】
Dec 22 #Javascript
You might like
PHP求最大子序列和的算法实现
2011/06/24 PHP
magento后台无法登录解决办法的两种方法
2016/12/09 PHP
JavaScript基础篇之变量作用域、传值、传址的简单介绍与实例
2013/06/29 Javascript
js 判断浏览器使用的语言示例代码
2014/03/22 Javascript
深入理解JavaScript系列(46):代码复用模式(推荐篇)详解
2015/03/04 Javascript
javascript实现确定和取消提示框效果
2015/07/10 Javascript
详解AngularJS中自定义过滤器
2015/12/28 Javascript
JS中Json数据的处理和解析JSON数据的方法详解
2016/06/29 Javascript
微信小程序登录换取token的教程
2018/05/31 Javascript
详解npm 配置项registry修改为淘宝镜像
2018/09/07 Javascript
详解angular2.x创建项目入门指令
2018/10/11 Javascript
Vue.Draggable拖拽功能的配置使用方法
2020/07/29 Javascript
如何制作一个Node命令行图像识别工具
2018/12/12 Javascript
js继承的这6种方式!(上)
2019/04/23 Javascript
jQuery内容选择器与表单选择器实例分析
2019/06/28 jQuery
原生js实现瀑布流效果
2020/03/09 Javascript
Python格式化css文件的方法
2015/03/10 Python
用Python解析XML的几种常见方法的介绍
2015/04/09 Python
常见的python正则用法实例讲解
2016/06/21 Python
人工智能最火编程语言 Python大战Java!
2017/11/13 Python
Ubuntu下使用Python实现游戏制作中的切分图片功能
2018/03/30 Python
python实现合并多个list及合并多个django QuerySet的方法示例
2019/06/11 Python
python下PyGame的下载与安装过程及遇到问题
2019/08/04 Python
Mac中PyCharm配置Anaconda环境的方法
2020/03/04 Python
python语言中有算法吗
2020/06/16 Python
Python turtle库的画笔控制说明
2020/06/28 Python
丹尼尔惠灵顿手表天猫官方旗舰店:Daniel Wellington
2017/08/25 全球购物
新闻编辑求职信
2014/04/09 职场文书
党员批评与自我批评思想汇报(集锦)
2014/09/14 职场文书
四风问题对照检查材料整改措施
2014/09/27 职场文书
信用卡催款律师函
2015/05/27 职场文书
2016大学生社会实践心得体会范文
2016/01/14 职场文书
golang 如何通过反射创建新对象
2021/04/28 Golang
Pytorch 中net.train 和 net.eval的使用说明
2021/05/22 Python
MyBatis-Plus 批量插入数据的操作方法
2021/09/25 Java/Android
深入解析MySQL索引数据结构
2021/10/16 MySQL