mock.js与Apifox在前端开发中的应用

487 阅读5分钟

在前端的需求开发中,可能会遇到后端已经输出接口文档,但是代码还没有实现完成的情况,前端不得不等后端接口写好后再请求数据,或者在js中手写死数据来模拟,这样效率会比较低而且浪费时间。在这种场景下,如果前端想要获取数据应用于开发的话,可以使用mock.js模拟一个mock接口去请求,来拦截ajax请求,生成伪数据。


mock.js的优点与缺点

优点: 配置简单、前后端分离、可随机生成大量的数据、数据类型丰富。

缺点: mock.js只是拦截地址,直接返回mock数据,并不会直接发送真实的请求,所以在控制台的network看不到请求,只能通过console打印查看数据(Apifox mock的接口可以看到network请求,详情在文末)。

mockjs官方网址: mockjs.com


mock.js在vue项目中的应用

首先安装mock.js

npm install mockjs

一般搭配axios发起网络请求

npm install axios

在项目中新建mock文件并初始化mock

可以在项目根目录创建mock文件夹,里面新建index.js文件,该文件中引入mock模块

import Mock from 'mockjs'    //引入mockMock.setup({    //设置拦截ajax请求的响应时间,若干时间后才会返回响应内容
    timeout:'200-600'
});
​
let configArray=[];
​
const files = require.context('.',true,/.js$/);    //使用webpack的require.context()遍历所有mock文件
files.keys().forEach((key) => {
    if(key==='./index.js'){
        return
    }
    configArray=configArray.concat(files(key).default)
});
​
configArray.forEach((item)=>{    //注册所有的mock服务
    for(let[path,target] of Object.entries(item)){
        let protocol=path.split('|');
        Mock.mock(new RegExp('^' + protocol[1]),protocol[0],target)
    }
})

在入口文件main.js(next-cli项目为pages下的index.js)中导入mock文件

import './mock/index.js'

在mock文件夹中新建mockApi.js单独存放需要模拟的接口数据

最常用接口数据为json结构,用mock定义需要模拟的json数据结构,并随机生成若干条,并通过export暴露出来模拟的接口路径与请求方式

import Mock from 'mockjs'let userList = {
    code: 200,
    message:'success',
    data:{
        total:100,
        'userInfo|100':[{
            id:'@guid',
            date:'@date(yyyy-MM-dd hh:mm)',
            name:'@cname',
            'age|20-35':1,
            address:'@city(true)',
            'job|1':['前端开发工程师','后端开发工程师','UI设计师','测试工程师'],
            "position|1-5":1
        }]
    }
};
​
export default {
    'get|/queryUserList':userList
}

用axios调用该接口获取数据

为方便管理与防止冗余过多,可以封装axios调用的接口:

  • 在根目录新建api文件夹,并在其中创建index.js文件
import axios from 'axios'
export const Api = new (class { //定义Api类并暴露出来
    constructor() { //单独管理接口路径
        this.userListApi = '/queryUserList'
    }
    getUserList() { //定义调用接口的方法,返回axios调用接口的结果
        return axios.get('/queryUserList').then((res) => res.data)
    }
})()

调用接口获取数据:

  • 1.在指定场景调用对应接口的方法,如组件进入时,在mounted生命周期调用
mounted(){
      Api.getUserList().then((res) => {
            this.realList=res.data.userInfo
            this.tableLength=res.data.total
        })
    }

控制台打印返回的res数据: userInfo中为mock随机生成的数据:

  • 2.将获取到的数据渲染在页面上
<div class="table-area">
            <el-table :data="realList.slice((this.currentPage - 1) * this.pageSize, this.currentPage * this.pageSize)" stripe style="width: 100%" border>
                <el-table-column prop="name" label="姓名" width="180"></el-table-column>
                <el-table-column prop="date" label="入职日期" width="180"></el-table-column>
                <el-table-column prop="age" label="年龄" width="180"></el-table-column>
                <el-table-column prop="address" label="户籍地址"></el-table-column>
                <el-table-column prop="job" label="职位"></el-table-column>
                <el-table-column prop="position" label="职级">
                    <template #default="scope">
                        <div v-if="scope.row.position == 5">
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                        </div>
                        <div v-if="scope.row.position == 4">
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-off"></i>
                        </div>
                        <div v-if="scope.row.position == 3">
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-off"></i>
                            <i class="el-icon-star-off"></i>
                        </div>
                        <div v-if="scope.row.position == 2">
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-off"></i>
                            <i class="el-icon-star-off"></i>
                            <i class="el-icon-star-off"></i>
                        </div>
                        <div v-if="scope.row.position == 1">
                            <i class="el-icon-star-on"></i>
                            <i class="el-icon-star-off"></i>
                            <i class="el-icon-star-off"></i>
                            <i class="el-icon-star-off"></i>
                            <i class="el-icon-star-off"></i>
                        </div>
                    </template>
                </el-table-column>
            </el-table>
            <el-pagination
                @size-change="handleSizeChange"
                @current-change="handleCurrentChange"
                :current-page="currentPage"
                :page-sizes="[10, 20, 50, 100]"
                :page-size="10"
                layout="total, sizes, prev, pager, next, jumper"
                :total="tableLength"
            ></el-pagination>
        </div>
  • 3.运行效果:

mock.js常用语法

// 定义数据类型
var data = Mock.mock({
    // 自动生成20条数据
    "data|20": [{
      // 从ID为1开始,每条数据ID自动加1
      "ID|+1": 1,
      // 随机生成一个中文名
      'name': "@cname",
      // 随机生成数组中的1项
      'type|1': ["美的","集团","电商"],
      // 随机生成包含5-20个中文的字符串
      'text|5-20': '@cword',
      // 随机生成一个范围0-10的数字
      'account|0-10': 1,
      // 随机生成一个日期时间,括号内为时间戳格式
      "date":"@date('yyyy-MM-dd HH:mm:ss')"
      // 随机生成一个日期,举例:2023-02-03
      "date":"@date"
      // 随机生成一个大小100×100,颜色随机,格式为png的图片地址
      "imgUrl": "@Image('100x100','@color','png')",
      // 随机生成一个颜色,结果为16进制色值代码
      "color": "@color",
      // 随机生成一个布尔值,true或false
      "is": "@boolean",
      // 随机生成一个英文名
      "name": "@name",
      // 随机生成一个市
      "ccity":"@city"
    }]
  })



便捷的接口Mock工具:Apifox

如果想要在network中查看mock接口的请求,可以使用Apifox

Apifox的优点:

根据json数据可以自动生成mock模拟的数据,内置mock的服务器对AJAX的请求进行拦截,不需要在前端的项目中添加mock.js的代码,减少了代码量,适合团队开发使用

Apifox的使用方法:

1.UniAccess安全助手的软件商城里有Apifox,可在软件商城直接安装:

2.安装后登录软件Apifox,进行如下操作:

3.填写接口信息,请求方式、接口路径、服务类型、返回响应是必填项,在返回响应中用mock.js语法配置调用接口后期望的返回数据:

4.运行配置好的接口,检验返回接口是否正确,Apifox涵盖Postman的功能,也可以在Apifox中调试接口:

5.在项目中的API配置中直接调用Apifox生成的mock接口路径,接口的请求可以在network中查看到:

import axios from 'axios'
export const Api = new (class {
    constructor() {
        this.userListApi = 'http://127.0.0.1:4523/mock/2253158/queryuserlist'   //Apifox mock的接口路径
    }
    getUserList() {
        return axios.get(this.userListApi).then((res) => res)
    }
})()
​

6.接口获取到的数据渲染在页面上:

Apifox是一个功能相对齐全的接口软件,拥有Postman、Swagger、Mock、JMeter的基本功能,在前后端开发步调不一致,后端接口没开发完成的情况下,前端可用Mock工具模拟接口调用,来保证开发进度与实现效果,提高开发效率