Skip to content

About

Node.js 全栈开发之 Midway.js 最佳实践

Topics

Resources

Stars

216 stars

Watchers

4 watching

Forks

Latest commit

 

History

438 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

FSD Service

FSD Logo

FSD (Full Stack Develop) Service - Midway.js 的最佳实践

codecov GitHub Actions status codebeat badge Codacy Badge GitHub license PRs Welcome Gitpod Ready-to-Code

Sonar Cloud

项目导览

在这个项目中,你会看到以下基于 Midway 的实践案例 (上层使用 egg.js )

我们正在做以下工程实践例子,大家你遇到什么问题,或者希望追加什么功能,或者学习内部实现。

可以关注我们的仓库(点赞,分享...三连)在 issue 留言,我们会征集你的意见,带来最干货的案例。

帮你扫清学习障碍,让你用起 Midway 来更加得心应手,提升能效,找回编码的乐趣。

所有代码均已经过工程师的测试请放心使用!!!

能力栏目 名称 进度
概述
控制器(Controller) ✓
服务和注入 ✓
请求、响应和应用 ✓
Web 中间件 ✓
启动和部署 ✓
基础能力
依赖注入 ✓
运行环境 ✓
多环境配置 ✓
参数校验和转换 ✓
生命周期 ✓
使用组件 ✓
日志 ✓
本地调试 ✓
测试 ✓
增强
代码流程控制
方法拦截器(切面)
缓存(Cache)(目前直接使用 Redis) ✓
Database(TypeORM) ✓
MongoDB
Swagger ✓
一体化研发
开发一体化项目
非 Serverless 环境使用一体化
Web技术
Cookies
Session
跨域 CORS ✓
微服务
gRPC
RabbitMQ (生产者) ✓
RabbitMQ (消费者)
Consul
WebSocket
SocketIO
常用能力
Admin 登录 ✓
普通用户登录-账户密码
OAuth 2.0
日志监控
本地上传文件服务
鉴权中间件 ✓
接口响应统计中间件 ✓
统一错误处理 ✓
SnowFlake 雪花算法生成分布式ID ✓
Jaeger 链路追踪 ✓
业务能力
权限管理 ✓
角色管理 ✓
管理员管理 ✓
菜单管理 ✓
日志(操作日志,记录管理用户的实际操作) ✓

使用项目

查看 Midway docs 获取更多信息.

运行该项目需要以下环境支持

  • Mysql
  • Redis
  • Jeager

目前该项目已经集成 Docker 环境,按以下步骤可以自动配置以上依赖。docker-compose 相关文档请查看这里

  • 1.确保机器已经安装 Docker。
  • 2.在项目目录运行 docker-compose up -d
  • 3.停止服务 docker-compose down

如果没有数据库 GUI 工具,可按照下面步骤进行数据库初始化

  • $ docker ps // 查看容器ID
  • $ docker exec -it <mysql 容器 ID> /bin/bash // 进入容器
  • $ mysql shop_development < /data/database/init.sql -uroot -ppassword // 初始化数据库

Development

先将 database 目录下到 sql 文件迁移到数据库,修改默认的config配置文件

$ npm i
$ npm run dev
$ open http://localhost:7001/

Redis

  • 使用 Redis 作为用户登录凭证存取的地方
  • RTS 收集统计数据 (开发中)

Redis划分

建议使用 Redis 的时候,对所有 key 做好命名空间划分,便于管理。可把 scope 写到对照表中。

借助 jwt 插件做签名校验,管理员的 token 中会包含 id 字段。

所有 admin 相关的缓存数据都放在 admin:xxxx 下面。

  • admin:accessToken:${id} 缓存管理员 Token 信息
  • admin:userinfo:${id} 缓存管理员基本信息

数据库

所有实体表均有 deleted_at 字段(目前基础模块不使用软删除),用于软删除。

如果要关闭软删除,将deletedAt字段注释即可

进行软删除的时候,关系表的数据不做改动。

后期根据需要,用脚本定期清理软删除的数据。

以下模块未使用软删除:

  • 权限管理
  • 角色管理
  • 菜单管理
  • 管理员管理

查询注意事项

业务软删除单独写一个 BaseModel,其他实体继承该 Model 即可

  • 实体查询,继承 BaseModel 的实体会自带软删除判断,例子查看src/app/model/base.ts
  • 在做关系查询的时候,关系表需要手动加软删除判断 IS NULL,如下:
      /**
       * 根据菜单id获取数据
       * @param id 菜单id
       */
      async getAdminMenuById(id: string) {
        const row = await this.adminMenuModel
          .createQueryBuilder()
          .select()
          .leftJoinAndSelect(
            'AdminMenuModel.roles',
            'role',
            'role.deletedAt IS NULL'
          )
          .where({ id: id })
          .getOne();
        return row;
      }

Jaeger 链路追踪

Jaeger 是 OpenTracing 的一个实现,链路追踪是一个比较复杂的话题,关于 Jaeger 的具体用法请参考它的官方文档

本实现基于 ctx 机制,结合 midway 的依赖注入可实现无侵入式 spanContext 传递

  • 默认实现接口级别的采样
  • 若需小颗粒度采样,可手动管理 span
    ctx.tracerManager.startSpan('SpanName1')
    await doSomethine()
    ctx.tracerManager.finishSpan() // 别忘记关闭

接口响应统计中间件(设计)

做接口响应数据统计的出发点,有两点(即使有类似的第三方包,但还是自己实现以下):

  • 帮助排查线上接口响应问题
  • 监控系统实时状态

虽然框架本身已经有日志功能,但是很多场景下,我们可能需要看下各个接口服务的响应状态

是在正常服务,还是已经出现问题。在有监控的帮助下,可以快速帮我们定位日志排查问题。

是对应统计实时数据而言,这里我们会使用 RTS 的技术方案,会用到 RabbitMQ 和 Redis

RabbitMQ 作用在于把统计的计算异步化,从而不影响正常的业务请求处理

(消费者的逻辑代码,需要写在单独一个工程,独立部署)

大致流程如下,手绘的,工具简陋,姑且看一下。 IMG_5365 HEIC

Test 单元测试

单元测试框架采用 Mocha , 支持对 case 进行 .skip() .only() 的随意组合以及快速实现, 适合在包含复杂、耦合的业务项目场景

注意事项:

  • 单测文件不支持 nullish 链式操作符,比如
    assert(res?.body) // 不支持
    assert(res && res.body) // 可行

拓展阅读

答疑

群里会有热心的朋友,也会有新版本发布推送。钉钉扫码加入答疑群

二群

一群(已满)

License

我们的代码使用 MIT 协议,请放心使用。

About

Node.js 全栈开发之 Midway.js 最佳实践

Topics

Resources

Stars

216 stars

Watchers

4 watching

Forks

Releases

Packages

Used by

Contributors

Languages