前端路由的实现原理 #125
zhangyu1818
announced in
zh-cn
前端路由的实现原理
#125
Replies: 0 comments
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
-
像
react-router
这样的库,核心实现依赖的是一个名为history
的库。history
库其实就是对于window.history
的一个封装,是基于原生API实现的。window.history API
window.history
提供了5个方法。go
,到指定页面,参数为数字,go(1)
前进1个页面,go(-1)
后退1个页面back
,后退,等同于go(-1)
forward
,前进,等同于go(1)
pushState
,添加1条记录replaceState
,替换1条记录我们主要会是用
pushState
和replaceState
。pushState
pushState
方法接收3个参数state
对象。url
,这个参数会实时的显示在浏览器的地址栏上。state
对象我们可以通过window.history.state
来获取,默认情况下值为null
。在当前页面打开控制台
输入
window.history.pushState({state:0},"","/page")
,可以看到浏览器的地址变成了/page
。在控制台输入
window.history.state
,可以获取到当前的{state: 0}
。输入
window.history.back()
,即可返回之前到上一个页面。replaceState
replaceState
和pushState
不同的地方在于它会替换掉当前的历史记录。打开控制台,输入
window.history.replaceState({state:1},"","/replace")
,可以看到浏览器的地址变成了/replace
。在控制台输入
window.history.state
,可以获取到当前的{state: 1}
。输入
window.history.back()
,回到的是上上个页面,因为上一个页面被我们替换掉了。监听历史记录的变化
浏览器提供了一个
popstate
的事件来监听历史记录的变化,不过它不能监听pushState
和replaceState
的变化,也无法知道当前是前进还是后退,只能监听go
、back
、forward
,和手动点击浏览器前进和后退按钮发生的历史记录变化。history源码浅析
由于原生的监听略有缺陷,所以
history
这个库就解决了原生的问题。它将API统一到一个
history
对象,同时自行实现listener
的功能,在调用push
、replace
函数时也会触发事件回调函数,同时会将当前是前进还是后退传入给函数。可以看到,只是创建了一个自己的
listeners
,在push
和replace
的时候在手动调用一下,就解决了原生不触发的问题。createHashHistory
和createBrowserHistory
基本一致,只是额外增加了hashchange
的事件监听。手写React Router
基于上面的原理,其实我们已经可以简单的写一个路由了。
下面是一个很简单的20行实现的例子。
其实简单来说就是根据不同的
pathname
展示不同的元素了,不过在react-router
里没有这么简单,里面有一些复杂的判断,过段时间再对它写一篇源码浅析。Beta Was this translation helpful? Give feedback.
All reactions