react-router和react-router-dom的不同之处
Ubiregi Advent Calendar 2019 的第二天。第一天是周日休息的。
前端工程师柯加将承担此任务。他不仅作为前端工程师已有大约5个月的工作经验,也刚刚加入公司约5个月。
不知道已经是第几次了,我要发布一篇关于React-Router的文章。请温情地关注一下,不要欺负我。
React-router和React-router-dom的区别是什么?
React的Routing库有两个选项:react-router和react-router-dom。
「我也有这样的印象,react-router从v4开始进行了改名,变成了react-router-dom!」然而严格来说是不准确的。
因为在使用react-router进行谷歌搜索时,首篇文章突然让人迷惑,建议直接执行npm install –save react-router-dom。
不管怎样
让我们看一下说明书吧。目前版本是v5。
在这里写着react-router-dom是绑定到DOM的react-router。
React-Router 是 React 的声明式路由机制。
react-router-dom是React Router的DOM绑定。
顺便提一下,还有一个叫做react-router-native的东西。
请比较用法。
主页、关于、仪表板是事先准备好的组件。
react-router 反应路由
import React from 'react';
import ReactDOM from 'react-dom';
import { Router, Route, Switch } from 'react-router';
import { createBrowserHistory } from 'history';
import { Home, About, Dashboard } from './component';
const App = () => {
return (
<Router history={createBrowserHistory()}>
<div>{document.title}</div>
<Switch>
<Route exact path='/'><Home /></Route>
<Route path='/about'><About /></Route>
<Route path='/dashboard'><Dashboard /></Route>
</Switch>
<a href='/'>Back To Home</a>
</Router>
)
}
react-router-dom 可以改写成”应对路由器-多”。
import React from 'react';
import ReactDOM from 'react-dom';
import { BrowserRouter, Route, Switch, Link } from 'react-router-dom';
import { Home, About, Dashboard } from './component';
const App = () => {
return (
<BrowserRouter>
<div>{document.title}</div>
<Switch>
<Route exact path='/'><Home /></Route>
<Route path='/about'><About /></Route>
<Route path='/dashboard'><Dashboard /></Route>
</Switch>
<Link to='/'>Back To Home</Link>
</BrowserRouter>
)
}
一看之下,两者的区别如下:
1. react-router将history传递给组件。
2. react-router是使用a标签,而react-router-dom则使用组件。
我会优先查看关于2的API。
对于1,我会继续调查。
Router和BrowserRouter的区别
总的来说,这两者之间没有太大的区别。
我会看一下实施情况。
react-router/Router: 反应路由/路由器
react-router-dom/BrowserRouter: 反应路由-dom/浏览器路由器
如您所见,BrowserRouter在内部使用了Router,并将history作为props传递。它只是一个简单的包装器而已。
class BrowserRouter extends React.Component {
history = createHistory(this.props);
render() {
return <Router history={this.history} children={this.props.children} />;
}
}
在PropTypes中定义了一些可选参数,但是这些props都会被传递给history,因此在Router中通过使用createBrowserHistory来传递参数,也可以实现类似的功能。
BrowserRouter.propTypes = {
basename: PropTypes.string,
children: PropTypes.node,
forceRefresh: PropTypes.bool,
getUserConfirmation: PropTypes.func,
keyLength: PropTypes.number
};
以下是一个指定了basename和forceRefresh的例子。
const App = () => {
return (
<Router history={createBrowserHistory({ basename: '/', forceRefresh: true })}>
<div>{document.title}</div>
<Switch>
<Route exact path='/'><Home /></Route>
<Route path='/about'><About /></Route>
<Route path='/dashboard'><Dashboard /></Route>
</Switch>
<a href='/'>Back To Home</a>
</Router>
)
}
虽然不太不同……
如果只是用于“路由”,无论是react-router还是react-router-dom都可以使用。 react-router还实现了一些钩子,例如useHistory、useLocation、useParams和useRouteMatch。
然而,当然,单独使用react-router并不那么令人愉快,因为无法使用和等API。
的使用…?
让我们最后考虑一下的应用。如之前所述,BrowserRouter是Router的包装器,因此和等API也可以以相同的方式使用。
需要单独安装history,但也算是可以接受的。
Router和BrowserRouter的区别只有一个,就是可以从外部传递history。就是这样。
所以,我想结合ReactGA来进行跟踪…但是查找后发现已经有人在这样做了。更进一步说,他们都使用了useEffect来完成。
另外另外,官方还提供了使用useLocation的示例。
结论
不要猶豫,使用react-router-dom。
多余的部分
在我漫不经心地浏览react-router的问题时,看到了这样的讨论。
将react-router-dom更改为react-router/dom #6755。
当有另一个依赖于react-router的包,并且版本不一致时会产生冲突,所以可以将react-router-dom移到react-router的子包中,这样做感觉合理。因为react-router-native完全没有优势,并且react-router本身就不是直接依赖的东西,所以我觉得它不是一个积极的选择。