数据 Mock
在目前互联网行业 web 产品开发中,前后端大部分都是分离开发的,前端开发过程中无法实时得到后端的数据。这种情况下,一般会使用三种方式:
- 模拟静态数据:即按照既定的数据格式,自己提供一些静态的JSON数据,用相关工具(如fis3)做接口来获取这些数据。该形式使用不比较简单的、只用 get 方法的场景,该项目不适用。
- 模拟动态接口:即自己用一个 web 框架,按照既定的接口和数据结构的要求,自己模拟后端接口的功能,让前端项目能顺利跑起来。该方式适用于新开发的项目,后端和前端同时开发,适用于该教程的项目。
- 转发线上接口:项目开发中,所有的接口直接用代理获取线上的数据,post 的数据也都直接提交到线上。该方式适用于成熟项目中,而该项目是新开发的,没有线上接口,不适用。
最后强调一下,该教程是一个前端教程,面向的是前端工程师,后端的开发和处理交给后端工程师来做。后端的业务处理和开发过程,不在本教程的讲解范围之内。
安装
这里我们使用目前比较流行的 koa 来做后端接口的模拟。因此要先安装 koa 极其相关的插件。执行npm install koa koa-body koa-router --save-dev
,注意这里使用--save-dev
,意思是我们只在开发过程中使用 koa ,项目发布之后 koa 就没用了。因为发布之后的项目,使用的就是后端工程师开发的线上的接口,而不是我们基于 koa 写的接口。
注意,该教程重点关注前端和 React,对于 koa 我们只介绍用到的常用功能。想学习可以去官网或者找相关教程。
模拟接口
我们将模拟接口的代码都写在./mock
目录下,接口文件是./mock/server.js
(目前只有这一个文件,真正开发项目时,应该会分不同模块)。
var app = require('koa')();
var router = require('koa-router')();
// router.get('/', function *(next) {
// this.body = 'hello koa !'
// });
// router.get('/api', function *(next) {
// this.body = 'test data'
// });
/ ./home/ad.js
// module.exports = [
// {
// title: '暑假5折',
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016191639092-2000037796.png',
// link: 'http://www.imooc.com/wap/index'
// },
// {
// title: '特价出国',
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016191648124-298129318.png',
// link: 'http://www.imooc.com/wap/index'
// },
// {
// title: '亮亮车',
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016191653983-1962772127.png',
// link: 'http://www.imooc.com/wap/index'
// },
// {
// title: '学钢琴',
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016191700420-1584459466.png',
// link: 'http://www.imooc.com/wap/index'
// },
// {
// title: '电影',
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016191706733-367929553.png',
// link: 'http://www.imooc.com/wap/index'
// },
// {
// title: '旅游热线',
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016191713186-495002222.png',
// link: 'http://www.imooc.com/wap/index'
// }
// ]
/// ./home/list.js
// module.exports = {
// hasMore: true,
// data: [
// {
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016201638030-473660627.png',
// title: '汉堡大大',
// subTitle: '叫我汉堡大大,还你多彩口味',
// price: '28',
// distance: '120m',
// mumber: '389'
// },
// {
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016201645858-1342445625.png',
// title: '北京开源饭店',
// subTitle: '[望京]自助晚餐',
// price: '98',
// distance: '140m',
// mumber: '689'
// },
// {
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016201652952-1050532278.png',
// title: '服装定制',
// subTitle: '原价xx元,现价xx元,可修改一次',
// price: '1980',
// distance: '160',
// mumber: '106'
// },
// {
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016201700186-1351787273.png',
// title: '婚纱摄影',
// subTitle: '免费试穿,拍照留念',
// price: '2899',
// distance: '160',
// mumber: '58'
// },
// {
// img: 'http://images2015.cnblogs.com/blog/138012/201610/138012-20161016201708124-1116595594.png',
// title: '麻辣串串烧',
// subTitle: '双人免费套餐等你抢购',
// price: '0',
// distance: '160',
// mumber: '1426'
// }
// ]
// }
// 首页 —— 广告(超值特惠)
var homeAdData = require('./home/ad.js')
router.get('/api/homead', function *(next) {
this.body = homeAdData
});
// 首页 —— 推荐列表(猜你喜欢)
var homeListData = require('./home/list.js')
router.get('/api/homelist/:city/:page', function *(next) {
// 参数
const params = this.params
const paramsCity = params.city
const paramsPage = params.page
console.log('当前城市:' + paramsCity)
console.log('当前页数:' + paramsPage)
this.body = homeListData
});
// 开始服务并生成路由
app.use(router.routes())
.use(router.allowedMethods());
app.listen(3000);
然后在./package.json
中增加如下代码,然后执行npm run mock
即可启动模拟的接口服务。
"scripts": {
"mock": "node --harmony ./mock/server.js",
},
启动之后,随便找一个 get 的接口,访问以下,例如http://localhost:3000/api/1
使用 webpack-dev-server 的代理
到这里你可能会有一个疑问————koa 接口的端口是3000
,而我们项目的接口是8080
,这样不就跨域了吗?————如果默认情况下,肯定是跨域了。此时就需要 webpack-dev-server 做一个代理的转发。配置代码在./webpack.config.js
中
devServer: {
proxy: {
// 凡是 `/api` 开头的 http 请求,都会被代理到 localhost:3000 上,由 koa 提供 mock 数据。
// koa 代码在 ./mock 目录中,启动命令为 npm run mock
'/api': {
target: 'http://localhost:3000',
secure: false
}
},
// ...省略若干代码...
}