018 Umi 中使用 mockjs 完善前后端分离

简介: 018 Umi 中使用 mockjs 完善前后端分离

在现在习惯的开发流程中,特别是快速交付流程里面,我们通常会在开始动工之前通过约定好 API 接口,然后前端通过使用 Mock 数据在本地模拟出 API 返回的正确的数据结构,完成全部的前端逻辑开发,然后在项目上线前修改请求路径到后端,如果双方都严格按照最开始的约定进行,并且在此期间没有任何的业务流程修改的话,那前端可能只需要简单的请求路径,就可以完成前后端连调工作。


在上一节课的练习中,我们采用了更原始的方法,直接在代码中写死数据,还要是一个列表,我们可以通过循环的方式来取巧生成。但是如果是一个对象,并且是一个大对象的话,那我们要么都用“11111”来渲染我们的整个页面,要么就要花大量的时间去编写“假数据”。


Umi 提供了开箱即用的 Mock 功能,能够用方便简单的方式来完成 Mock 数据的设置。



Mock 约定目录

Umi 约定 /mock 目录下的所有文件为 Mock 文件,每一个 mock 文件都会返回一个 default 对象,例如这样的目录结构:

.
├── mock
    ├── todos.ts
    ├── items.ts
    └── users.ts
└── src
    └── pages
        └── index.tsx
复制代码


/mock 目录中的 todos.ts, items.tsusers.ts 就会被 Umi 视为 Mock 文件 来处理。

值得注意的是 mock 目录下的文件的文件名对真正的 mock 服务不会产生任何的影响,所以你可以仅仅从业务的分类的角度来组织他们,甚至你讲所有的 mock 服务放在同一个文件中存放也可以。



Mock 文件

Mock 文件默认导出一个对象,而对象的每个 Key 对应了一个 Mock 接口,值则是这个接口所对应的返回数据,例如这样的 Mock 文件:

// ./mock/users.ts
export default {
  // 返回值可以是数组形式
  'GET /api/users': [
    { id: 1, name: 'foo' },
    { id: 2, name: 'bar' }
  ],
  // 返回值也可以是对象形式
  'GET /api/users/1': { id: 1, name: 'foo' },
}
复制代码

就声明了两个 Mock 接口,透过 GET /api/users 可以拿到一个带有两个用户数据的数组,通过 GET /api/users/1 可以拿到某个用户的模拟数据。



请求方式

当 Http 的请求方式是 GET 时,可以省略方法部分,只需要路径即可,例如:

// ./mock/users.ts
export default {
  '/api/users': [
    { id: 1, name: 'foo' },
    { id: 2, name: 'bar' }
  ],
  '/api/users/1': { id: 1, name: 'foo' },
}
复制代码


也可以用不同的请求方法,例如 POSTPUTDELETE

// ./mock/users.ts
export default {
  'POST /api/users': { result: 'true' },
  'PUT /api/users/1': { id: 1, name: 'new-foo' },
}
复制代码



关闭 Mock

Umi 默认开启 Mock 功能,如果不需要的话可以从配置文件关闭:

// .umirc.ts
export default {
  mock: false,
};
复制代码


或是用环境变量的方式关闭:

MOCK=none umi dev
复制代码


以上的内容大部分你可以在官网中找到,以下的内容是开发中的一些小 tip。如果你看到这个文章的时间较晚,那可能也能在官网中看到,因为这个系列的所有文档,后面会尽量整理到官网的内容中。



取到请求的参数

其实 Umi 中提供的 Mock 能力,本质上是一个 express 的中间件,你可以通过 req 取到请求的入参和 header 等信息。

import { Request, Response } from 'express';
export default {
  'POST /api/list': (req: Request, res: Response) => {
    const { body } = req;
    const { pageSize, offset } = body;
    // 从这里取出 pageSize, offset
    return res.json({
      success:true
    });
  },
}
复制代码



引入 Mock.js

上节课中我们手写了一个数据,有时候很尴尬的是取名困难,要让数据看起来好看一点,就要让数据重复的更少。

{
      id: i,
      title: "卡片列表",
      description:
        "Umi@4 实战教程,专门针对中后台项目零基础的朋友,不管你是前端还是后端,看完这个系列你也有能力合理“抗雷”,“顶坑”",
    }
复制代码


这时候我们可以引入一些现在流行的 Mock 数据的生成工具,比如 Mock.js ,来帮我们方便的生成随机的模拟数据,会让我们的模拟数据看起来更加真实。

类似上节课的练习数据,我们可以这么写。


import mockjs from "mockjs";
export default {
  "GET /api/list": mockjs.mock({
    "data|10": [{ id: "@id", title: "@name", description: "@cparagraph(2)" }],
  }),
};
复制代码


会自动生成类似如下数据,太长了,我这里摘录了两段,实际上生成了 10 个数据,这是通过 data|10 来指定的,你在表格数据中,可以给一个比较大的值来渲染一个超长列表。


{
  "data": [
    {
      "id": "810000197712245720",
      "title": "David Lewis",
      "description": "理史率能厂响命热么克积深先片。每号公状志山织声具接度通满被准。"
    },
    {
      "id": "230000199101266590",
      "title": "Sharon White",
      "description": "是石来验关且公决器重调受白设。农队战社五点团持老了取装场。"
    }
  ]
}
复制代码



实战

在上节课的技术上我们继续今天的实战。如果你不是每节课都看的朋友,你可以下载上节课的 源码归档



安装依赖

pnpm i mockjs @alita/plugins
复制代码


安装类型包

pnpm i @types/mockjs --D
复制代码


因为今天 Umi@4 正式发布,所以我们同步升级到 Umi@4

修改 packages.json 文件

- "@umijs/plugins": "4.0.0-rc.20",
+ "@umijs/plugins": "4.0.0",
- "umi": "4.0.0-rc.20"
+ "umi": "4.0.0"
复制代码

修改后,重新执行 pnpm i



新建 Mock 文件

新建 mock/list.ts,并写入如下内容:

import mockjs from "mockjs";
export default {
  "GET /api/list": mockjs.mock({
    success: true,
    "data|10": [
      {
        id: "@id",
        title: "@name",
        description: "@cparagraph(2)",
      },
    ],
  }),
};
复制代码



引入请求

详细内容在 14 课中已讲解,这里直接写使用。

修改配置文件 config/config.ts

import { defineConfig } from "umi";
export default defineConfig({
  // 最终值在插件中设置,所以这里不用写
  //   title: "Hello Umi",
  plugins: [
    require.resolve("@umijs/plugins/dist/model"),
    require.resolve("@umijs/plugins/dist/antd"),
+   require.resolve("@alita/plugins/dist/request"),
  ],
  model: {},
+ request: {},
  antd: {},
});
复制代码


src/pages/listcard/index.tsx 中引入请求,通过日志查看数据结构

import { useRequest, request } from "umi";
// 文件中原有内容略
const ListCard = () => {
  const { data } = useRequest(() => request("/api/list"));
  console.log(data);
  return (
  );
};
export default ListCard;
复制代码
{
    "data":[]
}
复制代码


修改原有的代码将 dataSource={[{}, ...data?.data]}data 作为 ListdataSource


image.png

源码归档



目录
相关文章
电力规约DL/T 654 2007多功能电表通信协议 调试工具
电力规约DL/T 654 2007多功能电表通信协议 调试工具
256 1
|
JSON 开发工具 git
精通 Prettier:进阶配置与最佳实践
【10月更文挑战第18天】Prettier 是一款流行的代码格式化工具,它能够帮助开发者保持代码风格的一致性,减少因代码风格争议而产生的争论。本文将深入探讨如何根据项目需求进行详细的配置选项调整,并分享一些使用 Prettier 的最佳实践,包括如何通过 Git 钩子自动化代码格式化过程以及如何解决常见的配置冲突问题。
770 5
|
8月前
|
人工智能 自动驾驶 物联网
5G到底有多牛?一文看懂它的原理与优势!
5G到底有多牛?一文看懂它的原理与优势!
487 19
|
存储 人工智能 JSON
|
前端开发 JavaScript 虚拟化
React 树形组件 Tree View
本文从零开始构建了一个简单的React树形组件,介绍了环境准备、项目创建、基础组件构建等步骤,并探讨了常见问题及解决方案,包括层次嵌套过深、状态管理复杂、事件处理不当和样式问题,帮助读者在实际项目中更好地应用树形组件。
577 3
|
设计模式 人工智能 前端开发
七大设计原则之开闭原则应用
七大设计原则之开闭原则应用
291 0
|
数据采集 存储 监控
CDGA|数据治理:让数据与业务伴生的实践路径
在数据驱动的时代,数据已成为企业宝贵资产,蕴含推动业务增长与创新的无限可能。数据治理通过科学策略挖掘、整合、保护数据,成为企业数字化转型的核心驱动力。本文阐述了数据治理的定义、重要性及其实践路径,强调跨部门协作与全员参与,确保数据质量、安全及合规性,支持企业战略目标实现。通过明确数据战略、建立管理体系、推动数据共享和持续优化,数据治理助力企业实现数据与业务的伴生共长。
1185 0
|
网络协议 数据处理 C++
LabVIEW与Simulink的通信及调用方式
LabVIEW与Simulink的通信及调用方式
400 1
|
SQL 前端开发 Java
实现数据的搜索( 筛选 )功能
实现数据的搜索( 筛选 )功能