路由
路由是根据不同的 url 地址展示不同的内容或页面。
在过去,服务器端处理来自浏览器的请求时,要根据不同的Url路由,拼接出对应的视图页面,通过Http返回给浏览器进行解析渲染。后端路由每次访问一个新页面的时候都要向服务器发送请求,然后服务器再响应请求,这个过程肯定会有延迟。
前端路由
前端路由就是把不同路由对应不同的内容或页面的任务交给前端来做。
前端路由在访问一个新页面的时候仅仅是变换了一下路径而已,没有了网络延迟,对于用户体验来说会有相当大的提升。
前端路由的实现由两种方式:
(1)通过改变hash值,监听onhashchange事件,这种方式的优点是可以兼容低版本浏览器
(2)通过H5的historyAPI,监听popState事件,用pushState和replaceState来实现
History API
两个新增的API history.pushState
和history.replaceState
相同之处是两个 API 都会操作浏览器的历史记录,而不会引起页面的刷新,这就是实现页面无刷新情况下改变 url
不同之处在于,pushState会增加一条新的历史记录,而replaceState则会替换当前的历史记录。
比如在百度页面的控制台输入:
window.history.pushState(null, null, "https://www.baidu.com/?name=orange");
运行
history.pushState()
方法,历史栈对应的纪录就会存入状态对象,我们可以随时主动调用历史条目。
官方文档提供了 popstate 事件,当我们在历史记录中切换时就会产生 popstate 事件。
onpopstate = function(event) {
setupPage(event.state);
}
hash
路由里的 # 不叫锚点,我们称之为 hash,大型框架的路由系统大多都是哈希实现的。
同样我们需要一个根据监听哈希变化触发的事件 —— hashchange 事件
Web 服务并不会解析 hash
,也就是说 #
后的内容 Web 服务都会自动忽略,但是JS是可以通过 window.location.hash
读取到的,读取到路径加以解析之后就可以响应不同路径的逻辑处理。
window.location
处理哈希的改变时不会重新渲染页面,而是当作新页面加到历史记录中,这样我们跳转页面就可以在 hashchange 事件中注册 ajax 从而改变页面内容。
同样在百度页面的控制台:
window.location.hash = '/234'
页面进入 https://www.baidu.com/#/234
切换时就会产生 hashchange 事件
onhashchange = function(){
alert(window.location);
}
前端路由的使用场景
前端路由更多用在单页应用上, 也就是SPA, 因为单页应用, 基本上都是前后端分离的, 后端自然也就不会给前端提供路由。
前端路由优缺点
优点:
1.从性能和用户体验的层面来比较的话,后端路由每次访问一个新页面的时候都要向服务器发送请求,然后服务器再响应请求,这个过程肯定会有延迟。而前端路由在访问一个新页面的时候仅仅是变换了一下路径而已,没有了网络延迟,对于用户体验来说会有相当大的提升。
2.在某些场合中,用ajax请求,可以让页面无刷新,页面变了但Url没有变化,用户就不能复制到想要的地址,用前端路由做单页面网页就很好的解决了这个问题
缺点:
使用浏览器的前进,后退键的时候会重新发送请求,没有合理地利用缓存,