Vue Router (历史模式)

前言:

历史模式" ​ 指的是 Vue Router(vue-router) ​ 提供的一种 路由模式 ,它使用 浏览器的 HTML5 History API ​ 来管理前端路由,让单页应用(SPA)的 URL 看起来更自然、更像是传统的多页应用,没有难看的 #(井号)。

1、vue 的主要路由模式

| 名称 | 是否使用 # | 是否需要服务器配置 | 对应的 History 对象 | 推荐使用场景 |
|--------------------|-------------|-------------------|----------------|-------------------------------------------------------|---------------------|
| 1. Hash 模式​ | hash模式 | ✅ 使用(如 /#/home) | ❌ 不需要 | window.location.hash | 兼容性好,快速开发,不需要服务器配置 |
| 2. History 模式​ | history模式 | ❌ 不使用(如 /home) | ✅ 需要 | HTML5 History API ​ (pushState, replaceState) | URL 更美观,适合正式环境、生产部署 |

1.1 Hash 模式

1.1.1 定义

Hash 模式 ​ 是 Vue Router 使用 URL 中的 hash(#)部分 ​ 来管理路由的一种方式,它通过监听 window.location.hash的变化来实现前端路由的切换,无需服务器端的特殊配置,并且兼容所有的浏览器(包括 IE9)。

1.1.2 URL样式

路由配置 实际访问的 URL
/(首页) http://localhost:3000/#/或 http://example.com/#/
/about http://localhost:3000/#/about
/user/123 http://localhost:3000/#/user/123
  • URL 中包含一个 #(井号) ,#后面的部分(如 /about)被称为 hash 路由

  • hash 部分的变化不会向服务器发送请求,所以不会导致页面刷新

  • 适合用于 单页应用(SPA)

1.1.3 如何启用

通过 createWebHashHistory()来启用 Hash 模式。

复制代码
// router/index.js 或 router/index.ts
import { createRouter, createWebHashHistory } from 'vue-router'

const router = createRouter({
  history: createWebHashHistory(), // ✅ 启用 Hash 模式
  routes: [
    { path: '/', component: Home },
    { path: '/about', component: About },
    { path: '/user/:id', component: UserDetail }
  ]
})

export default router

1.1.4 工作原理

  • Vue Router 会监听浏览器 URL 中 #(hash)后面的部分 ​ 的变化,例如从 #/变成 #/about

  • 当 hash 发生变化时,不会向服务器发送请求,而是通过 JavaScript 控制显示哪个组件

  • 通过 window.onhashchange或类似机制,Vue Router 能够响应路由变化并渲染对应的页面内容

1.1.5 Hash 模式的特点总结

特性 说明
✅ URL 示例​ http://example.com/#/about
✅ 是否需要服务器配置​ ❌ 不需要(推荐用于静态托管、快速开发)
✅ 兼容性​ ✅ 支持所有浏览器,包括 IE9 及更早版本
✅ 是否美观​ ❌ URL 中有 #,不够简洁(但功能完整)
✅ 是否支持前端路由​ ✅ 完全支持,无刷新切换页面
✅ SEO 友好性​ ❌ 不友好(搜索引擎通常忽略 #后面的内容)
✅ 适用场景​ 本地开发、快速原型、静态网站、兼容旧浏览器

1.2 Memory 模式

1.2.1 定义

Memory 模式不会假定自己处于浏览器环境,因此不会与 URL 交互也不会自动触发初始导航 。这使得它非常适合 Node 环境和 SSR。它是用 createMemoryHistory() 创建的,并且需要你在调用 app.use(router) 之后手动 push 到初始导航。

1.2.2 URL样式

重要:Memory 模式下,没有真实的 URL 变化!

  • 它 不会修改浏览器地址栏

  • 它 不会使用 #(hash)

  • 它 不会产生可被收藏或分享的真实路径

  • 它的"路由"完全运行在 JavaScript 内存中

1.2.3 如何启用

复制代码
import { createRouter, createMemoryHistory } from 'vue-router'
const router = createRouter({
  history: createMemoryHistory(),
  routes: [
    //...
  ],
})
  • Memory 模式不会自动触发初始导航(即不会根据当前"假想"的 URL 自动跳转页面)

  • 你需要在调用 app.use(router)挂载路由后,手动调用 router.push('/')或其他路径,来初始化当前路由状态

  • 它没有浏览器历史记录,因此用户无法使用前进 / 后退按钮导航(除非你手动实现)

复制代码
import { createApp } from 'vue'
import App from './App.vue'
import router from './router'

const app = createApp(App)

app.use(router)

// 手动设置初始路由(比如跳转到首页)
router.push('/') // 必须手动触发,Memory 模式不会自动导航

app.mount('#app')

1.2.4 工作原理

createMemoryHistory()创建了一个 "内存中的 History 实现" ,它维护了一个 路由栈(history stack)和当前路由状态,类似于浏览器中的 History API,但是:

  • 不依赖 window.history

  • 不修改真实的 URL

  • 不触发浏览器的前进/后退行为(除非你手动模拟)

1.2.5 Memory 模式特点总结

特性 说明 适用场景
1. 不依赖浏览器环境​ 不使用 window.location、不操作 URL、不依赖 history.pushState Node.js、SSR、测试环境
2. 不修改浏览器地址栏​ URL 不会变化,用户看不到路由切换 后台逻辑、无 UI 路由
3. 路由信息保存在内存中​ 包括当前路径、路由栈等,都存在于内存,不持久化 测试、服务端、CLI 工具
4. 不会自动导航​ 需要手动调用 router.push()初始化路由状态 手动控制路由初始化
5. 没有内置历史记录​ 无法使用浏览器的前进 / 后退按钮(除非你手动维护栈) 不适合需要用户导航感知的场景
6. 可用于 SSR / 测试​ 是服务端渲染和单元测试中常用的路由模式 Jest、Vue Test Utils、Nuxt、SSR

1.3 History 模式(HTML5 模式)

1.3.1 定义

History 模式 ,也叫 HTML5 模式 ,是 Vue Router 提供的一种不依赖 URL 中的 #(hash),而是利用浏览器原生 history.pushStateAPI 来管理前端路由 的模式。它让前端路由的 URL 看起来和传统多页应用(MPA)一样干净、专业(没有 #),但需要服务器端做相应的配置支持,否则直接访问子路由可能导致 404。

1.3.2 URL样式

功能 Hash 模式 URL History 模式 URL​
首页 http://example.com/#/ http://example.com/
关于页 http://example.com/#/about http://example.com/about
用户详情 http://example.com/#/user/123 http://example.com/user/123
  • 没有 #,URL 更加简洁、专业,和传统网站一致

  • 看起来就像是一个普通的多页网站,但实际上是由前端路由控制的单页应用(SPA)

  • 但必须由服务器正确配置,否则用户刷新页面或直接访问子路由(如 /about)时,服务器可能返回 404

1.3.3 如何启用

使用 createWebHistory()来启用 HTML5 / History 模式:

复制代码
// router/index.js 或 router/index.ts
import { createRouter, createWebHistory } from 'vue-router'

const router = createRouter({
  history: createWebHistory(), // ✅ 启用 HTML5 / History 模式
  routes: [
    { path: '/', component: Home },
    { path: '/about', component: About },
    { path: '/user/:id', component: UserDetail }
  ]
})

export default router

注意:

History 模式不会自动处理 404 页面的服务器响应,你需要确保:

  • 服务器(如 Nginx、Apache、Netlify、Vercel 等)将 所有路由请求都重定向或返回 index.html

  • 否则,当用户直接访问 /about或刷新页面时,服务器可能找不到对应文件,返回 404 错误

1.3.4 工作原理

核心机制:利用浏览器的 History API

Vue Router 的 History 模式​ 基于以下浏览器提供的 API:

  • history.pushState(state, title, url):无刷新地添加一条新的历史记录,并更新地址栏 URL

  • history.replaceState(state, title, url):替换当前历史记录,不新增记录

  • popstate事件:当用户点击浏览器的前进/后退按钮时触发

工作流程简述:

  1. 初始化:

    • Vue Router 通过 **createWebHistory()**创建一个 基于 HTML5 History API 的路由实例

    • 路由匹配规则由你定义(如 /, /about, /user/:id)

  2. 导航(如点击 <router-link>或调用 router.push('/about')):

    • Vue Router 使用 history.pushState()更新 URL ,不会刷新页面

    • 同时根据路由规则,渲染对应的组件

  3. 浏览器前进 / 后退:

    • 用户点击前进/后退时,触发 popstate事件

    • Vue Router 监听到该事件,解析当前 URL,匹配对应路由,渲染相应组件

  4. 直接访问或刷新页面(如输入 /about后回车):

    • 浏览器会向服务器请求 /about这个路径

    • 如果服务器没有配置返回 index.html,就会返回 404

    • 正确配置后,服务器返回 index.html,然后 Vue Router 根据 URL 渲染对应页面

1.3.5 HTML5 模式特点总结

特性 说明 适用场景
1. URL 无 #,更加美观专业​ URL 如 /about,不像 Hash 模式有 #/about 面向用户的产品、正式官网、商业项目
2. 基于浏览器 History API​ 使用 pushState/ replaceState,无刷新切换路由 现代浏览器(IE10+)
3. 需要服务器端配置支持​ 所有路由请求必须返回 index.html,否则刷新/直接访问子路由会 404 需要后端或部署平台配合
4. 支持浏览器前进/后退​ ✅ 支持,且体验流畅 用户习惯性导航
5. 兼容性​ ✅ 支持现代浏览器(IE10 及以上) 不支持 IE9 及以下(如需兼容,请用 Hash 模式)
6. SEO 友好性相对更好​ 搜索引擎爬虫更容易抓取无 #的 URL(但仍建议搭配 SSR 更佳) 对 SEO 有基本要求的场景
7. 不依赖 Hash,更接近传统网站​ 用户和开发者都更容易理解与接受 专业产品、正式发布环境

1.4 三种模式的对比

Vue Router 提供了三种路由模式:Hash 模式(带 #,兼容性好,无需配置)、History 模式(无 #,专业美观,但需要服务器配置)、Memory 模式(无浏览器,用于测试/SSR)。根据你的项目需求、部署环境和目标用户,选择最适合的路由模式。

对比维度 Hash 模式 ​ (createWebHashHistory()) History 模式 ​ (createWebHistory()) Memory 模式 ​ (createMemoryHistory())
**是否依赖 #**​ ✅ 依赖(如 #/home) ❌ 不依赖(如 /home) ❌ 不依赖
URL 是否美观​ ❌ 有 #,不够简洁专业 ✅ 无 #,和普通网站一样 ❌ 无 URL(内存中维护)
是否需要服务器配置​ ❌ 不需要 ✅ 必须配置(所有路由返回 index.html) ❌ 不需要
兼容性​ ✅ 所有浏览器,包括 IE9+ ✅ 现代浏览器(IE10+) ✅ 无浏览器限制(用于非浏览器环境)
是否支持前进/后退​ ✅ 支持(hashchange 事件) ✅ 支持(popstate 事件) ✅ 支持(内存维护)
能否直接部署在静态托管上​ ✅ 可以(如 GitHub Pages) ❌ 通常不行(需服务器支持) ✅ 可以(但一般不用)
SEO 友好性​ ❌ 不友好(搜索引擎忽略 #后内容) ⚠️ 相对较好(但仍建议 SSR) ❌ 无 URL,不涉及 SEO
典型使用场景​ 静态网站、原型、兼容旧浏览器、快速开发 正式产品、商业网站、美观 URL、可配服务器 测试、SSR、无浏览器环境、命令行工具等
推荐程度​ ⭐⭐⭐(适合简单项目、静态托管) ⭐⭐⭐⭐(推荐用于正式线上项目) ⭐(特殊用途,一般开发者很少直接使用)

2、常见服务器的配置方法

2.1 Nginx 服务器配置

适用于:部署在 Linux 服务器、VPS、Docker 容器等环境

复制代码
server {
    listen 80;
    server_name yourdomain.com;

    root /path/to/your/dist;  # Vue 打包后的文件夹,通常是 dist
    index index.html;

    location / {
        try_files $uri $uri/ /index.html;
    }
}

try_files $uri $uri/ /index.html;表示:如果请求的路径不是真实文件或目录,就返回 index.html,让前端路由处理。

2.2 Apache 服务器配置

适用于:传统 Apache 托管环境

在网站根目录下创建或修改 .htaccess文件,添加如下内容:

复制代码
<IfModule mod_rewrite.c>
  RewriteEngine On
  RewriteBase /
  RewriteRule ^index\.html$ - [L]
  RewriteCond %{REQUEST_FILENAME} !-f
  RewriteCond %{REQUEST_FILENAME} !-d
  RewriteRule . /index.html [L]
</IfModule>

当请求的不是真实文件(-f)或目录(-d)时,重写到 /index.html,保 Apache 已启用 mod_rewrite模块。

2.3 Node.js 服务器(如 Express)配置示例

如果你是自己用 Node.js 搭的服务,可以这样配置:

复制代码
const express = require('express')
const path = require('path')
const app = express()

// 静态文件托管(Vue 打包后的 dist 目录)
app.use(express.static(path.join(__dirname, 'dist')))

// 所有路由都返回 index.html,由 Vue Router 接管
app.get('*', (req, res) => {
  res.sendFile(path.join(__dirname, 'dist', 'index.html'))
})

app.listen(3000, () => {
  console.log('Server is running on http://localhost:3000')
})

2.4 Vercel 平台配置

Vercel 是一个流行的前端静态站点托管平台,支持 SPA。

方法一:自动支持(通常可以)

Vercel 对单页应用有默认支持,但如果你遇到刷新 404,可以手动配置:

方法二:使用 vercel.json

创建 vercel.json文件,内容如下:

复制代码
{
  "rewrites": [{ "source": "/(.*)", "destination": "/index.html" }]
}

这会确保所有路径都返回 index.html,由 Vue 接管路由。

2.5 Netlify 平台配置

Netlify 也支持 SPA,默认情况下可能已经可以工作,但如果遇到刷新 404,可以:

方法一:使用 _redirects文件

在项目根目录(或打包后的 dist目录)创建一个名为 _redirects的文件,内容为:

复制代码
/* /index.html 200
方法二:使用 netlify.toml
复制代码
[[redirects]]
  from = "/*"
  to = "/index.html"
  status = 200

2.6 注意

这有一个注意事项。你的服务器将不再报告 404 错误,因为现在所有未找到的路径都会显示你的 index.html 文件。为了解决这个问题,你应该在你的 Vue 应用程序中实现一个万能的路由来显示 404 页面。

复制代码
const router = createRouter({
  history: createWebHistory(),
  routes: [{ path: '/:pathMatch(.*)', component: NotFoundComponent }],
})

另外,如果你使用的是 Node.js 服务器,你可以通过在服务器端使用路由器来匹配传入的 URL,如果没有匹配到路由,则用 404 来响应,从而实现回退。查看 Vue 服务器端渲染文档了解更多信息。

相关推荐
仿生狮子38 分钟前
OpenAI 攻下千禧年难题之后,开发者似乎无动于衷
前端·数学·vibecoding
夏幻灵4 小时前
JavaScript this 面试:五种绑定规则、优先级与常见面试陷阱
开发语言·javascript·面试
Lvan的前端笔记4 小时前
docker:每个前端项目一个 Nginx 容器还是只有一个Nginx容器
前端·nginx·docker
三天不学习4 小时前
Egg.js 4 突然爆火,原因是否归结于AI 原生落地需求爆发?
前端·javascript·全栈·egg.js
xcs194055 小时前
前端 vue 的前端页面debugger 进不去
前端·javascript·vue.js
明月_清风6 小时前
Deno 终局来了:从挑战 Node 到被 Cloudflare 收编
前端·后端·node.js
Csvn7 小时前
框架性能优化
前端
雪芽蓝域zzs9 小时前
第 5 节:Marker 点击弹出 InfoWindow 信息窗口
vue.js
回眸&啤酒鸭9 小时前
【回眸】OpenSwarm 多智能体协作系统实战指南
大数据·前端·人工智能
用户69371750013849 小时前
2026,程序员的时代拐点到了
android·前端·后端