Vuehistory模式刷新网页404级头

原创
小哥 3年前 (2022-11-02) 阅读数 85 #大杂烩

为什么它会出现?404

让我们先来看看我们给后端提供了什么。 dist 文件

可以看到dist只有一个 index.html 文件和一些静态资源,这是因为。 Vue 是一个单页应用程序(SPA),只有一个 index.html 作为一个条目文件,其他路线都是直通的。JS跳跃

那么让我们分析一下后端 nginx 的配置

server {
  // 监听80端口
  listen 80;
  // 定义您的站点名称
  server_name website.com;
  // 根据请求 URI 设置配置
  location / {
      // 站点根目录,在这里。 vue 已构建 dist 目录
      root   /www/dist;
      // 站点初始页面为index.html 或 index.htm
      index  index.html index.htm;
  }
}

我们现在可以依靠 nginx 当我们进入地址栏时,配置就会派生出来。 website.com 什么时候,这个时间会打开我们 dist 目录下的 index.html 文件,然后我们就进入跳跃路线了。 website.com/login

钥匙就在这里,当我们进去的时候。 website.com/login 该页面执行刷新操作, nginx location 没有相关的配置 ,所以它会出现在 404 的情况

为什么hash在模式下没有问题

router hash 我们都知道,图案使用的是符号。 # 表达,  website.com/#/login, hash 的值为 #/login

它的特点是:hash 虽然存在于 URL 但不会包括在 HTTP 在请求中,对服务端完全没有影响,所以改变了。 hash 将不会重新加载该页面

hash 模式,仅限 hash 符号之前的内容包括在请求中,例如。 website.com/#/login 只有 website.com 将包括在请求中 ,所以对于服务器端,即使没有配置也是如此。location,也不会回来404错误

单页应用(SPA)概念

我们前面有提到单页应用,那什么是一个单页应用程序呢?

单页应用

单页应用程序(single-page application),缩写SPA 是Web应用程序或网站的模型,它通过动态重写当前页面来与用户交互,而不是从服务器重新加载整个新页面。这种方法可以防止页面之间的切换干扰用户体验,并使应用程序更像桌面应用程序。在单页面应用程序中,所有必要的代码(HTML、JavaScript和CSS)通过加载单个页面来检索,或者根据需要动态加载适当的资源并将其添加到页面(通常响应于用户操作)。尽管您可以散列或HTML5历史API以提供对应用程序中各个逻辑页的感知和导航,但不会在该过程的任何点重新加载该页,也不会将控制权转移到其他页。

简单地说:

早上喝一杯牛奶,中午喝开水,晚上喝茶。我们可以发现,变化永远是内容,容器仍然是容器。

当然, 每种技术都有其优缺点,单页面应用程序也是如此

利:

  1. 无刷体验 ,这应该是最重要的一点,因为路线分发是直接在浏览器端完成的,页面不刷新,对用户的响应非常及时,从而提高了用户体验

  2. 完成前端组件化 ,前端开发不再基于页面,更多的是基于组件的思维,代码结构和组织更加规范,易于修改和调整

弊:

  1. 首屏较长 ,要在一个页面上为用户提供产品的所有功能,在加载这个页面时,必须先加载大量的静态资源,加载时间相对较长。

  2. 不利于 SEO ,单页,前端数据渲染,表示没有 SEO,否则需要解决方案。

Router的实现

为了让大家加深大家的了解 Router 理解,在这里我们实现一个最简明的 Router

hash 模式

通过倾听获得核心url中的hash要执行布线跳跃,请执行以下操作

// 定义 Router
class Router {
    constructor () {
        this.routes = {}; // 存放路由path及callback
        this.currentUrl = ;
        
        // 监听路由change调用对应的路由回调
        window.addEventListener(load, this.refresh, false);
        window.addEventListener(hashchange, this.refresh, false);
    }
    
    route(path, callback){
        this.routes[path] = callback;
    }
    
    push(path) {
        this.routes[path] && this.routes[path]()
    }
}

// 使用 router
window.miniRouter = new Router();
miniRouter.route(/, () => console.log(page1))
miniRouter.route(/page2, () => console.log(page2))

miniRouter.push(/) // page1
miniRouter.push(/page2) // page2

history 模式

history 模式核心借用 HTML5 history api,api 提供了丰富的 router 相关属性

首先了解几个相关的api

  • history.pushState 浏览器历史记录添加记录

  • history.replaceState 修改浏览器历史记录中的当前记录

  • history.popState 当 history 发生更改时触发

    // 定义 Router class Router {     constructor () {         this.routes = {};         this.listerPopState()     }          init(path) {         history.replaceState({path: path}, null, path);         this.routes[path] && this.routes[path]();     }          route(path, callback){         this.routes[path] = callback;     }          push(path) {         history.pushState({path: path}, null, path);         this.routes[path] && this.routes[path]();     }          listerPopState () {         window.addEventListener(popstate , e => {             const path = e.state && e.state.path;             this.routers[path] && this.routers[path]()         })     } }

    // 使用 Router

    window.miniRouter = new Router(); miniRouter.route(/, ()=> console.log(page1)) miniRouter.route(/page2, ()=> console.log(page2))

    // 跳转 miniRouter.push(/page2)  // page2

解决404

看到这里,我相信大多数学生都能想出解决问题的办法,

问题的实质是我们的路线已经通过了。JS为了执行视图切换,

进入子路由后刷新页面,web容器没有对应的页面,此时将显示该页面。404

因此,我们只需要配置以重定向任何页面 index.html,该路由被移交给前端进行处理。

还是以 nginx 例如,Everyone的更多版本可以https://router.vuejs.org/zh/guide/essentials/history-mode.html 查看

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

如果这是真的,这里有一个小细节。 404 页面在哪里?例如 website.com/notfound

因为这样做之后,您的服务器将不再返回 404 错误页,因为它为所有路径返回 index.html 档案。为了避免这种情况,您应该加入。 Vue 该应用程序涵盖所有路由情况,然后给出一个 404 页面

const router = new VueRouter({
  mode: history,
  routes: [
    { path: *, component: NotFoundComponent }
  ]
})
版权声明

所有资源都来源于爬虫采集,如有侵权请联系我们,我们将立即删除