一,环境准备
- node -v 大于10.3及以上
- yarn 1.22.15
二,项目安装
- 新建文件夹,在该文件夹下打开终端,或者使用vscode在文件夹下打开终端
- 执行 yarn create @umijs/umi-app 创建项目
- 安装依赖 yran
- 启动项目 yarn start
三,如何使用
- 配置项目eslint
umi 维护了一个 prettier,eslint,stylelint 的配置文件合集 umi-fabric
我们使用该配置 安装umi-fabric yarn add @umijs/fabric -D
在项目根目录新建.eslintrc.js .stylelintrc.js .prettierrc.js 分别对应加上代码
//.eslintrc.js 配置
module.exports = {
extends: [require.resolve('@umijs/fabric/dist/eslint')],
// in antd-design-pro
globals: {
ANT_DESIGN_PRO_ONLY_DO_NOT_USE_IN_YOUR_PRODUCTION: true,
page: true,
},
rules: {
// your rules
'prefer-const': 0,
},
};
//.prettierrc.js
const fabric = require('@umijs/fabric')
module.exports = {
...fabric.prettier,
semi: false,
}
//.stylelintrc.js
const fabric = require('@umijs/fabric')
module.exports = {
...fabric.stylelint,
}
根目录新建eslint忽略文件 .eslintignore
.eslintrc.js
node_modules
在package.json 里面的lint-staged 新增 "eslint --fix"
"lint-staged": {
"*.{js,jsx,less,md,json}": [
"prettier --write"
],
"*.ts?(x)": [
"prettier --parser=typescript --write",
"eslint --fix"
]
},
最后要在vscode中安装插件eslint,prettier,stylelint , 尝试在任意tsx文件下修改
会提示 变量a 定义未使用
- 配置项目全局css
在项目src下新建 global.css文件
umi 中约定 src/global.css **为全局样式,如果存在此文件,会被自动引入到入口文件最前面。
在该文件下配置网站常用到的css或者reset css属性
- 配置文件
umi 在 .umirc.ts 或 config/config.ts 中配置项目和插件
使用config配置项的话必须删除项目根目录下的.umirc.ts, 不然以.umirc.ts中的配置项为最优配置(也就表示则 config下的任何配置都会无效)
后面部分我们会按照config的配置方式进行,所以删掉.umirc.ts文件
项目根目录新建config文件夹,目录中新建config.ts文件
把删掉的.umirc.ts文件的内容复制到config.ts中
import { defineConfig } from 'umi'
export default defineConfig({
nodeModulesTransform: {
type: 'none',
},
mfsu: {}, //热启动提升
//路由
routes: [{page:'/',component: '@/pages/index'}],
fastRefresh: {},
hash: true,//文件名哈希值 避免浏览器缓存
})
- 运行环境配置
可以通过环境变量 UMI_ENV 区分不同环境来指定配置。
这里我们使用第三方工具 cross-env来配置环境变量
安装 yarn add cross-env --dev
在package.json中修改script各个运行环境的配置
"start": "cross-env UMI_ENV=dev umi dev",
"build": "cross-env UMI_ENV=dev umi build",
"build:prod": "cross-env UMI_ENV=prod umi build",
在config中加入相对应环境的文件
config.dev.ts, config.prod.ts
//开发环境配置 config.dev.ts
import { defineConfig } from 'umi'
export default defineConfig({
// CurrentEnvironment 变量代表当前的环境,后面根据不同的环境配置不同的请求地址会用到
define: {
CurrentEnvironment: 'dev',
},
})
//生产环境配置 config.prod.ts
import { defineConfig } from 'umi'
export default defineConfig({
define: {
CurrentEnvironment: 'prod',
},
})
然后我们需要在根目录中的typings.d.ts 添加
declare const CurrentEnvironment: 'dev' | 'prod';
分别表示 当执行 yarn start 时 使用的是 config.dev.ts 配置文件中的配置项
当执行 yarn build:prod 时 使用的是 config.prod.ts 配置文件中的配置项
如果我们不想麻烦,可以直接删掉UMI_ENV=xxx 代码, 默认使用config.ts中的配置
- 自定义环境变量配置
有时候开发中,我们需要通过自定义的变量,去控制 在开发时和发布生产时的接口地址切换,或者版本控制等,
可以通过自定义环境变量方式 去控制
其实他跟上面的环境配置差不多,需要我们在package.json中script加入我们定义的变量
如: REACT_APP_ENV
"scripts": {
"start": "cross-env REACT_APP_ENV=reactDev umi dev",
"build": "cross-env REACT_APP_ENV=reactProd umi build",
"build:prod": "cross-env UMI_ENV=prod umi build",
"postinstall": "umi generate tmp",
"prettier": "prettier --write '**/*.{js,jsx,tsx,ts,less,md,json}'"
},
在config.ts中添加defind配置
define: {
//定义全局值 需要在package.json中script配置 REACT_APP_ENV 如
//"start": "cross-env REACT_APP_ENV=reactDev UMI_ENV=dev umi dev",
//还需要在typings.d.ts 中添加 declare const REACT_APP_ENV: string
REACT_APP_ENV: process.env.REACT_APP_ENV,
},
还需要在typings.d.ts 中添加 declare const REACT_APP_ENV: string
在需要使用到的地方 可以直接通过REACT_APP_ENV 方式获取
四,Umi中的路由使用
根据Umi文档介绍,umi的路由生成方式有两种,分别是'配置路由'和'约定式路由',用过vue的都知道,vue很多基本都是使用配置路由(除使用nuxt外)
4.1 约定式路由
- 基础配置
约定式路由也叫文件路由,就是不需要手写配置,文件系统即路由,通过目录和文件及其命名分析出路由配置。
白话的意思就是,你要根据umi事先约定好的约束去生成文件, umi就会为你自动生成路由
如果没有 routes 配置,Umi 会进入约定式路由模式,然后分析 src/pages 目录拿到路由配置。
生成路由中文档提及需要注意的地方及规则:
- 以 . 或 _ 开头的文件或目录
- 以 d.ts 结尾的类型定义文件
- 以 test.ts、spec.ts、e2e.ts 结尾的测试文件(适用于 .js、.jsx 和 .tsx 文件)
- components 和 component 目录
- utils 和 util 目录
- 不是 .js、.jsx、.ts 或 .tsx 文件
- 文件内容不包含 JSX 元素
- 动态路由
约定 [] (中括号)包裹的文件或文件夹为动态路由。
src/pages/users/[id].tsx 会成为 /users/:id
src/pages/users/[id]/settings.tsx 会成为 /users/:id/settings
//比如一下文件结构
└── pages
└── [post]
├── index.tsx
└── comments.tsx
└── users
└── [id].tsx
└── index.tsx
//会生成对应配置路由
[
{ exact: true, path: '/', component: '@/pages/index' },
{ exact: true, path: '/users/:id', component: '@/pages/users/[id]' },
{ exact: true, path: '/:post/', component: '@/pages/[post]/index' },
{
exact: true,
path: '/:post/comments',
component: '@/pages/[post]/comments',
},
];
- 动态可选路由
约定 [ $] 包裹的文件或文件夹为动态可选路由。
比如:
src/pages/users/[id$].tsx 会成为 /users/:id?
src/pages/users/[id$]/settings.tsx 会成为 /users/:id?/settings
- 嵌套路由
Umi 里约定目录下有 _layout.tsx 时会生成嵌套路由,以 _layout.tsx 为该目录的 layout。layout 文件需要返回一个 React 组件,并通过 props.children 渲染子组件。
比如以下目录结构,
└── pages
└── users
├── _layout.tsx
├── index.tsx
└── list.tsx
//会生成对应嵌套路由
[
{ exact: false, path: '/users', component: '@/pages/users/_layout',
routes: [
{ exact: true, path: '/users', component: '@/pages/users/index' },
{ exact: true, path: '/users/list', component: '@/pages/users/list' },
]
}
]
- 全局Layout
umi约定src/layouts/index.tsx 为全局路由. 返回一个React组件 并通过 props.children渲染子组件
//如当前文件目录结构
└── src
├── layouts
│ └── index.tsx
└── pages
├── index.tsx
└── users.tsx
//会生成对应路由
[
{ exact: false, path: '/', component: '@/layouts/index',
routes: [
{ exact: true, path: '/', component: '@/pages/index' },
{ exact: true, path: '/users', component: '@/pages/users' },
],
},
]
这个时候我们可以修改layouts中的index.tsx文件
import { NavLink } from 'umi'
export default (props) => {
return (
<div style={{ padding: 20 }}>
<h2>秀儿网</h2>
<ul>
<li>
<NavLink to="/">首页</NavLink>
</li>
<li>
<NavLink to="/users">用户中心</NavLink>
</li>
</ul>
{props.children}
</div>
)
}
更多可以查看umijs文档 约定式路由
4.2 配置路由
配置路由可以按照自己的风格,去定义自己的路由方式
回到config.ts配置文件,这个时候我们新起一个routes.ts文件 来单独处理我们的路由配置
export default [
{ exact: true, path: '/', component: '@/pages/index' },
{ exact: true, path: '/my', component: '@/pages/my' },
{
component: '@/pages/video',
path: '/video',
routes: [
{
path: '/video',
title: '视频教程',
routes: [
{ path: '/video', component: '@/pages/video/vue', title: 'vue视频' },
{ path: '/video/react', component: '@/pages/video/react', title: 'react视频' },
{ path: '/video/jq', component: '@/pages/video/jq', title: 'jq视频' },
],
},
],
},
]
在config.ts中引入
import { defineConfig } from 'umi'
import routes from './routes'
export default defineConfig({
nodeModulesTransform: {
type: 'none',
},
mfsu: {}, //热启动提升
define: {
REACT_APP_ENV: process.env.REACT_APP_ENV,
},
//路由
routes: routes,
fastRefresh: {},
hash: true,//文件名哈希值 避免浏览器缓存
})
生成对应文件
在pages/video/index.tsx中配置嵌套路由出口
import { NavLink } from 'umi'
export default (props: any ) => {
return (
<div style={{ padding: 20 }}>
<h2>视频教程</h2>
<ul>
<li>
<NavLink to="/video">vue视频</NavLink>
</li>
<li>
<NavLink to="/video/react">react视频</NavLink>
</li>
<li>
<NavLink to="/video/jq">jq视频</NavLink>
</li>
</ul>
{props.children}
</div>
)
}
效果
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。