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

前端路由详解 #4

Open
joinmouse opened this issue Apr 16, 2019 · 0 comments
Open

前端路由详解 #4

joinmouse opened this issue Apr 16, 2019 · 0 comments

Comments

@joinmouse
Copy link
Owner

一、后端路由

路由这个概念最先是后端出现的。在前后端还没分离的架构下,用后端语言的一些模板引擎开发页面时, 经常会看到:

https://www.xxx.com/login
https://www.xxx.com/settings

大致上后端路由解析的过程可以分为
1、用户点击页面跳转,浏览器发出请求
2、服务端通过监听80/443端口有请求过来,解析url路径
3、依据服务器的路由配置,返回信息(html/json/图片等资源)
4、浏览器根据数据包的 Content-Type 来决定如何解析数据

基本上路由就是用来跟后端服务器进行交互的一种方式, 根据不同的路径,后端服务器返回不同的资源, 当我们每次切换不同的页面的时候就会向服务端发出请求。

二、前端路由

随着 ajax 的流行,异步数据请求交互运行在不刷新浏览器的情况下进行。而异步交互体验的更高级版本就是 SPA —— 单页应用。单页应用不仅仅是在页面交互是无刷新的,连页面跳转都是无刷新的,为了实现单页应用,所以就有了前端路由。 类似于服务端路由,前端路由实现起来其实也很简单,就是匹配不同的 url 路径,进行解析,然后动态的渲染出区域 html 内容。

1、hash模式

http://www.xxx.com/#/login

这种包含#号的url,就是hash路由,#后面的路径值发生变化,并不会像服务端发送请求,,当每次#后面的hash值发生比变化,我们可以通过监听hashchange这个事件,来更新页面的内容,这样无需刷新就可以实现页面的变化, 这也是现在流行单页应用(SPA)的由来。

function matchAndUpdate () {
   // 匹配 hash 更换页面内容
}

window.addEventListener('hashchange', matchAndUpdate)

2、history模式

随着HTML5的发布,新增了两个API: pushState 和 replaceState,通过这两个API可以改变URL而不发起请求,我们可以通过调用histroy.pushState()或者history.replaceState()来改变页面的URL,如:

http://www.xxx.com/login.html页面中执行了以下JS代码

let stateObj = {
    page: "bar",
};

history.pushState(stateObj, "page", "bar.html");

页面就会跳转到http://www.xxx.com/bar.html,但浏览器并不会去加载bar.html,像服务端去请求这个资源,甚至不会检查bar.html 是否存在。
同时还要提及的有popstate 事件.调用history.pushState()或者history.replaceState()不会触发popstate事件. popstate事件只会在浏览器某些行为下触发, 比如点击后退、前进按钮(或者在JavaScript中调用history.back()、history.forward()、history.go()方法)

使用history的模式整个url没有了hash显的更加美观,实现的思路和hash类似,但是以上面的例子为例,假设用户自己刷新http://www.xxx.com/bar.html页面,浏览器就会向服务端请求资源而出错,所以history需要服务端的支持,讲所有的路由都重定向到根页面 以nginx配置为例

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

参考:
MDN Manipulating the browser history
Vue router文档
前端路由的简介

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

No branches or pull requests

1 participant