最近学习了egg.js,发现以前用express开发的node项目真的是惨不忍睹,所以根据之前的express项目进行改造和对比,列一下egg有哪些优势解决了哪些问题。
- log
- swagger自动生成
- validate 参数校验
- 异常处理,统一拦截
- 免router配置
- sequelize降低前端写sql语句门槛
- jwt鉴权
文章步骤中隐去部分代码,便于展示,文章最后会放上完整的demo
项目结构
首先展示下,搭建完基础的内容的项目结构
app
├─router.js // 路由 不过通过JSDoc自动生成了,可以不用
├─throw
| └index.js // 异常处理枚举值和一些基本方法
├─service
| ├─actionToken.js // jwt创建授权service类
| ├─common.js // 通用类,封装 getCurrentModel方法
| └member.js // 实际的service类
├─public // 存放公共资源
├─postgres // 在config.default.js配置sequelize的datasource的时候配置的目录,存放model
| ├─member.js // 成员model
| ├─project.js // 项目model
| └task.js // 任务model
├─middleware // 存放各种中间件, egg会自动加载,如果需要修改中间件加载顺序到config.default.js修改
| └error_handler.js // 统一异常处理
├─extend // egg会把当前目录的文件绑定到ctx 如ctx.helper
| └helper.js // 提供基本工具支持
├─controller // 接口入口
| └user.js
├─contract // 接口出入参描述
| ├─index.js // 通用参数
| └user.js
config
├─config.default.js // egg各种配置
└plugin.js // egg使用的插件列表
开发步骤
创建项目
npm i egg-init -g
egg-init egg-server --type=simple
cd egg-server
npm i
启动项目
npm run dev
open localhost:7001
debug方式启动项目,并且再vscode直接调试
- 在根目录添加.vscode目录,并且添加launch.json文件
{
"version": "0.2.0",
"configurations": [
{
"name": "Launch Egg",
"type": "node",
"request": "launch",
"cwd": "${workspaceRoot}/egg/egg-server",
"runtimeExecutable": "npm",
"windows": {
"runtimeExecutable": "npm.cmd"
},
"runtimeArgs": [
"run",
"debug"
],
"console": "integratedTerminal",
"protocol": "auto",
"restart": true,
"port": 9999,
"autoAttachChildProcesses": true
}
]
}
2. 在vscode按F5启动项目,这样就能愉快的在vscode上面调试啦
创建controller文件,并且自动生成swagger文档
- 安装依赖包
npm install egg-swagger-doc-feat -s
- 配置文件添加配置
// config/plugin.js
swaggerdoc : {
enable: true,
package: 'egg-swagger-doc-feat',
}
// config.default.js
config.swaggerdoc = {
dirScanner: './app/controller',
apiInfo: {
title: 'swagger',
description: 'swagger-ui for egg',
version: '1.0.0',
},
schemes: ['http', 'https'],
consumes: ['application/json'],
produces: ['application/json'],
enableSecurity: false,
enableValidate: true, // 这个后续validate会用到
routerMap: true,
enable: true,
}
- 添加contoller文件,并且编写JSDoc
controller文件
const {
Controller } = require('egg');
class UserController extends Controller {
constructor(ctx) {
super(ctx);
}
/**
* @summary 登录
* @description 登录
* @router get /api/current/{id}
* @respone 200 baseResponse 登录成功
* @request path string *id
* @request body loginRequest *body
* @request query string *id
* @request header string *Authorization eg:Bearer +token
*/
async current() {
}
}
module.exports = UserController;
- contract文件(出入参描述,后续使用egg-validate插件进行参数校验)
// app/contract/xx.js
module.exports = {
loginRequest: {
name: {
type: 'string', required: true, description: '成员名', example: 'ldy' },
id: {
type: 'string', required: true, description: 'id', example: '' }, // 这里还可以使用正则匹配 format: /^1[34578]\d{9}$/
}
};
至此,再浏览器访问 http://localhost:7001/swagger-ui.html就能够看到swagger自动生成的文档,如下图
参数说明
自动生成swagger和router的JSDoc说明
/**
* @summary 登录
* @description 登录
* @router get /api/current/{id}
* @respone 200 baseResponse 登录成功
* @request path string *id
* @request body loginRequest *body
* @request query string *id
* @request header string *Authorization eg:Bearer +token
*/
async current() {
}
- @summary 接口标题 <