这篇文章将通过一个demo来描述,怎么在使用typeScript的项目里面,使用react-router和React.lazy来实现lazy loading来提升网页性能。
建议先读一下相关的React官方文档:https://reactjs.org/docs/code-splitting.html#suspense
首先这个demo共有4个页面,3个url
1 '/' -> Home Page
2 '/blogList' ->Blog List Page
3 '/blogDetails/:id' -> Blog Details Page
大家都知道对于Blog Details Page的页面,通常的做法是在url里面加变量,以此来区分,当前是哪篇博客。
在这个例子里,我们创建了2篇博客,所以页面总共算起来有4个,但是在代码去实现的时候,我们会有3个文件:HomePage.tsx, BlogDetailsPage.tsx, BlogDetailsPage.tsx.
下面是我们的4个页面,从这个页面上,就能看出来我们的user journey:
1:到了home page, 此上有个链接可以去到 blog list page
2: 到了blog list page, 从页面上有2篇博客链接
3:点击第一篇博客链接,进入第一篇博客的详情页面
4: 点击第二篇博客链接,进入第二篇博客的详情页面
安装react-router-dom && @types/react-router-dom
yarn add react-router-dom @types/react-router-dom
配置react-router
index.tsx
// index.tsx
import React from "react";
import ReactDOM from "react-dom";
import { BrowserRouter } from "react-router-dom";
import "./index.scss";
import App from "./App";
import * as serviceWorker from "./serviceWorker";
ReactDOM.render(
<BrowserRouter>
<App/>
</BrowserRouter>
, document.getElementById("root"));
// If you want your app to work offline and load faster, you can change
// unregister() to register() below. Note this comes with some pitfalls.
// Learn more about service workers: https://bit.ly/CRA-PWA
serviceWorker.unregister();
App.tsx
//App.tsx
import React, { Suspense, lazy } from "react";
import { Switch, Route } from "react-router-dom";
import HomePage from './pages/HomePage/HomePage'
const BlogListPage = lazy(()=> import('./pages/blogListPage/BlogListPage'));
const BlogDetailsPage = lazy(()=> import('./pages/blogDetailsPage/BlogDetailsPage'));
function WaitingComponent(Component: React.FC<any> ) {
return (props: any) => (
<Suspense fallback={<div>Loading...</div>}>
<Component {...props} />
</Suspense>
);
}
function App() {
return (
<Switch>
<Route path="/blogList" component={WaitingComponent(BlogListPage)} />
<Route path="/blogDetails/:id" component={WaitingComponent(BlogDetailsPage)} />
<Route path="/" exact component={HomePage} />
</Switch>
);
}
export default App;
HomePage.tsx
//HomePage.tsx
import React from "react";
import logo from "./images/logo.svg";
import pink from "./images/pink.png";
import "./HomePage.scss";
import {Link} from "react-router-dom";
function App() {
return (
<div className="App">
<header className="App-header">
<img src={logo} className="App-logo" alt="logo" />
<img src={pink} className="" alt="pink" />
<Link to="/blogList">Blog List Page</Link>
</header>
</div>
);
}
export default App;
BlogListPage.tsx
// BlogListPage.tsx
import React from "react";
import {RouteComponentProps} from "react-router";
import {Link} from "react-router-dom";
function BlogListPage() {
return (
<div className="BlogListPage">
<div>Blog List Page</div>
<ul>
<li>
<Link to="/blogDetails/1">First Blog</Link>
</li>
<li>
<Link to="/blogDetails/2">Second Blog</Link>
</li>
</ul>
</div>
);
}
export default BlogListPage;
BlogDetailsPage.tsx
//BlogDetailsPage.tsx
import React from "react";
import {RouteComponentProps, useParams} from 'react-router-dom'
type routerParams = {id: string}
function BlogDetailsPage(props: RouteComponentProps<routerParams>){
const {id} = useParams();
return (
<div className="BlogDetailsPage">
<div>Blog Details page</div>
<p>The id in the url is: {id}</p>
</div>
);
}
export default BlogDetailsPage;