4 React项目架构 - 目录划分 & Router配置
Sat, Sep 22, 2018
0x0 目录划分
目录划分介绍
views文件夹
- 存放项目功能模块
- App.jsx
- 需要根据路由配置,分割子级目录
- 如列表页:
- index.jsx为这个页面的出口,向外抛出去
- 列表每一项都会建一个组件
- 如:titlebar会建一个组件
- 这些东西会放入同一个文件夹里,因为属于同一个页面嘛
config文件夹
- 放app的配置 & 第三方类库的引用
- router.jsx 路由的配置、映射和跳转等
store文件夹
- 存放数据管理的文件夹(包括数据的获取和封装)
- 如用户登录的信息
- 全局类信息需要存起来,就存在store中的某个地方
- 是web app单页应用开发新增的功能
- 需要单独拿出来
components
- 非业务型通用组件
- 很多view里都用到,和业务无关
- 如:
- 下拉组件 - drop down
- 更高级的通用组件封装,会打包到npm上,如Ant Design组件库
0x1 Router的简单实现
1 文件调整
/client/views/topic-list/index.jsx
import React from 'react' export default class TopicList extends React.Component { componentDidMount() { // placeholder } render() { return ( <div>ㄟ...这里是to...topic li..li..list(。•́-ก̀。)</div> ) } } |
/client/views/topic-detail/index.jsx
import React from 'react' export default class TopicDetail extends React.Component { componentDidMount() { // placeholder } render() { return ( <div>喂喂喂,这里是topic detail!(o˘д˘)o有人在吗?</div> ) } } |
2 配置路由
路由:区分一个网站不同功能模块的地址
- 浏览器通过不同的地址访问不同的功能
- 也让开发者区分需要返回的页面
前端路由:
- 原理:html的history api
- url变化的时候,js代码可以监听到这个事件
- 阻止浏览器刷新页面的行为
- 在js代码中执行需要的操作
- 一般是渲染一个新页面出来
- 同时请求数据填充进去
react-router:
- react中好用的路由控制插件
- 写JSX组件一样,控制路由跳转
- 安装:`npm i react-router react-router-dom -S`
client/config/router.jsx
import React from 'react' import { Route, } from 'react-router-dom' import TopicList from '../views/topic-list' import TopicDetail from '../views/topic-detail' export default () => [ <Route path="/" component={TopicList} exact />, <Route path="/detail" component={TopicDetail} exact />, ] |
说明:
- Route - 用来指定哪个url对应哪个组件
- 如果不写exact,访问/detail的时候,/也会被匹配到
- 就像写一般的标签一样...
client/views/App.jsx
import React from 'react' import Routers from '../config/router' export default class App extends React.Component { componentDidMount() { // placeholder } render() { return [ <div>初次见面,请多关照嘿嘿嘿~(๑^ں^๑)</div>, <Routers />, ] } } |
说明:
- Routers的使用方法(和使用普通的标签一样...)
client/app.js
需要在整个app外面,包裹一层<BrowserRouter>,便于整体控制
... import { BrowserRouter } from 'react-router-dom' ... const render = (Component) => { ReactDOM.hydrate( <AppContainer> <BrowserRouter> <Component /> </BrowserRouter> </AppContainer>, root, ) }; ... |
webpack.config.base.js
小调整:修改webpack的配置文件,让webpack在import没有后缀文件类型的js和jsx文件的时候,也能找到它们
resolve: { extensions: ['.js', '.jsx'] }, |
效果
3 使用Link做点击跳转
App.jsx
... import { Link } from 'react-router-dom' ... export default class App extends React.Component { ... render() { return [ <div> <div>初次见面,请多关照嘿嘿嘿~(๑^ں^๑)</div> <Link to="/">⌲ 列表页</Link> <br /> <Link to="/detail">⌲ 详情页</Link> </div>, <Routers />, ] } } |
效果
- 切换页面后,浏览器没有刷新,但是页面内容已经改变了
4 Redirect页面重定向
client/config/router.jsx
import React from 'react' import { Route, Redirect, } from 'react-router-dom' ... export default () => [ <Route path="/" render={() => <Redirect to="/list" />} exact />, <Route path="/list" component={TopicList} />, <Route path="/detail" component={TopicDetail} />, ] |
说明:
- Redirect:做页面跳转 - 访问「/」直接跳转到「/list」
- 效果和服务端返回302是一样的