Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

vue 路由配置 history 模式 #7

Open
huangshuwei opened this issue Dec 5, 2017 · 2 comments
Open

vue 路由配置 history 模式 #7

huangshuwei opened this issue Dec 5, 2017 · 2 comments
Labels

Comments

@huangshuwei
Copy link
Owner

huangshuwei commented Dec 5, 2017

前言

这里记录下 vue 路由配置成 history 模式的过程。

路由 hash 模式

vue 路由默认是 hash 模式。使用这种模式url 地址上模式会有一个路由标识 ‘#’,乍一看以为是锚点。
这种模式存在以下缺点:

1、本身与锚点冲突,导致页面需要用到锚点定位时比较困难
2、路由切换滚动行为还原困难,当然可以通过其他方式实现,参考这里
3、不利于 SEO
4、url 丑(哈哈,别当真)

既然用hash 模式不爽,那我们就改成 history 模式。

vue 路由配置修改

就是在这里改下

const router = new VueRouter({
  mode: 'history',
  routes: [...]
})

这时候我们重启将项目运行起来,不错,就是这个效果。对比下url地址
hash 模式: 协议://域名:端口/index.html#/home
history 模式: 协议://域名:端口/home

会看到将 index.html# 省略掉了。

webpack 热启动配置 history 模式

我们通过webpack 热启动(webpack-dev-server)路由切换正常访问,但是当刷新页面,或者点击浏览器回退的时候提示找不到了,这是因为使用了 history 模式,webpack 热启动也需要对应的配置。
怎么配置呢,有两种方式,也可参考webpack官网配置

方式1 通过命令行的方式,形如 webpack-dev-server --history-api-fallback,不过一般都是放到 'scripts'节点下,如:

// package.json
 "scripts": {
    "dev": "webpack-dev-server  --env.dev --history-api-fallback"
  }

方式2 在 webpack 配置文件的devServer配置:

// webpack.config.js
devServer:{
  ...
 historyApiFallback: true
}

如果是使用了 webpack 的 ‘webpack-dev-middleware’,你可能需要配合connect-history-api-fallback插件达到页面刷新回退不报错的目的,这里不多说了(因为我用的不是这种方式😂)

webpack history 模式发布

通过history 模式发布后,也是刷新以及页面回退都会出现找不到的问题,这时候需要对应的站点服务器处理了。

IIS 服务环境安装

因为我们的站点放到IIS 上的,下面以IIS 环境为例。

其他平台 history 模式的设置官网有说明

1、安装 IIS UrlRewrite

2、安装完成后,在你的网站根目录中创建一个 web.config 文件,然后进行以下配置

<?xml version="1.0" encoding="UTF-8"?>
<configuration>
  <system.webServer>
    <rewrite>
      <rules>
        <rule name="Handle History Mode and custom 404/500" stopProcessing="true">
            <match url="(.*)" />
            <conditions logicalGrouping="MatchAll">
              <add input="{REQUEST_FILENAME}" matchType="IsFile" negate="true" />
              <add input="{REQUEST_FILENAME}" matchType="IsDirectory" negate="true" />
            </conditions>
          <action type="Rewrite" url="/" />
        </rule>
      </rules>
    </rewrite>
  </system.webServer>
</configuration>

这里配置的目的就是把包含 .*的路径名称 替换成 '/'。

这时候再去打开部署好的站点,无论是页面刷新还是回退操作一切正常。

注意:单页应用的入口命名一定要是 index.html 否则页面刷新后会报错

Q&A(自问自答)

  • 单页应用的入口文件必须是index.html 吗?
    如果入口文件不是index.html, 调试模式(webpack-dev-server) , 刷新会报错,回退可以。
    发布后部署在iis 上也是一样的问题,不能刷新。所以入口文件必须是index.html

  • 单页应用与多页应用通过webpack 统一管理的项目会有问题吗?
    我已经在项目中使用过,history 模式 只会作用在单页应用上,对多页应用无影响,访问多页应用依旧通过 ~*.html 方式

  • 我用 nginx 作为负载均衡,还需 nginx 配置后端url 重写规则吗?
    不需要,只有nginx 作为 http 服务器的时候才需要。nginx 作为负载均衡时只要每个站点配置即可。

待解决的问题

  • 开启 history 模式后层级目录没了?
    资源路径改为绝对路径

参考

https://docs.microsoft.com/zh-cn/iis/extensions/url-rewrite-module/using-the-url-rewrite-module

--完?--

@MrErHu
Copy link

MrErHu commented May 9, 2019

不错!清晰明了

@hanguangpeng
Copy link

我改了两处,一个是devserver的historyApiFallback,还有一个就是mode从hash改成了history,为什么页面没有加载出来呢,直接白屏了

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

3 participants