Koa2

1、技术分析

  • RESTFul理论
  • Koa2
  • Postman
  • MongoDB
  • jwt认证原理
  • 数据库设计
  • 线上部署

2、RESTFul Api

GitHub REST API

符合REST架构风格的Api

RESTFul长什么样子?

image.png

请求设计规范

image.png

响应设计规范

  • 查询
  • 分页
  • 字段过滤
  • 状态码
  • 错误处理

安全

  • HTTPS
  • 鉴权
  • 限流

3、Koa简介

Koa

一句话简介

基于Node.js平台的下一代web开发框架

官网简介

  • 由Express膜厚原班人马打造
  • Web应用和Api开发领域
  • 更小、更富有变现力、更健壮
  • 利用async函数,丢弃回调函数
  • 增强错误处理: try catch
  • 没有捆绑任何中间件

4、项目搭建

初始化项目

  1. npm init

安装Koa

  1. npm i koa --save

编写Hello Word

  1. const Koa = require('koa');
  2. const app = new Koa();
  3. app.use((ctx) => {
  4. ctx.body = 'Hello .. Word!'
  5. });
  6. app.listen(3000);

自动重启

  1. npm i nodemon --save
  1. "start": "nodemon index.js"

5、中间件和洋葱模式

中间件

就是一个函数

  1. /**
  2. * 中间件1
  3. */
  4. app.use(async (ctx, next) => {
  5. // 有多个中间件的时候,先执行这个中间件,再去执行下个中间件,
  6. // 此处应该执行next,next返回的是一个Promise
  7. await next();
  8. // 下一个中间件执行完成,这也就是所谓的洋葱模式
  9. console.log(1);
  10. ctx.body = 'Hello .. Word!'
  11. });

洋葱模式image.png

Reguest
Response
RegistryManager
StatusCodeRedirect
ErrorHandler
CacheMiddleware
SessionMiddleware
RoutesMiddleware
PylonsApp
image.png
image.png

6、路由

koa-router

  1. const Router = require('koa-router');
  2. // 实例化路由
  3. const router = new Router({
  4. // 加路由前缀
  5. refix: '/users
  6. })
  7. // 注册路由
  8. app.use(router.routes());

路由前缀

  1. // 添加路由前缀
  2. router.prefix('/api/photo');

多中间件

  1. router.get('/users/:id',()=>{}, ()=>{}, ()=> {}, (ctx) => {
  2. ctx.body = `用户id: ${ctx.params.id}`;
  3. });

options请求方法

预检请求

  • 检测服务器支持哪些请求方法
  • 支持cors的预检请求

allowedMethods

响应options请求

  1. // 注册路由
  2. app.use(router.routes());
  3. app.use(router.allowedMethods()); // 响应options请求

7、控制器

类+类方法的方式组织控制器

断点调试

  • 调试
  • 监控变量

获取HTTP请求参数

Query String,如:name=name(可选)

ctx.query.name

Router Params,如:/users/:name(必选)

ctx.params.name

Body,如{name: ‘name’}

ctx.request.body.name

Header,如Accept、Cookie

ctx.header.token

发送HTTP响应

发送Status,如:200

  1. ctx.status = 200;

发送Body,如:{name: ‘name’}

  1. ctx.body = {
  2. id: ctx.params.id,
  3. name: '马化腾',
  4. };

发送Header,如:Allow、Content-Type

  1. ctx.set('Allow', 'GET, POST');

处理业务逻辑

控制器处理业务逻辑
路由引入对应的操作

8、错误处理

处理软件或者程序出现的异常状况

运行时错误,

500

逻辑错误,

404,423,422

为什么错误处理?

  • 防止程序挂掉
  • 高速用户错误信息
  • 便于开发者调试

koa错误处理

  • 抛出错误

    1. row(412, '先决条件失败');
  • 错误的处理

    image.png

错误处理中间件

安装koa-json-error

  1. npm i koa-json-error --save-dev

错误处理配置(环境区分)

生产环境禁用打印堆栈信息

  1. // 错误处理
  2. app.use(koaJsonError({
  3. postFormat: (e, {
  4. stack,
  5. ...rest
  6. }) => {
  7. return process.env.NODE_ENV === 'production' ? rest : {
  8. stack,
  9. ...rest
  10. }
  11. }
  12. }));

统一环境变量的库

  1. "start": "cross-env NODE_ENV=production node index.js"

koa参数校验

image.png

  • 使用
    1. ctx.verifyParams({
    2. userName: {
    3. type: 'string',
    4. required: true,
    5. },
    6. userPwd: {
    7. type: 'string',
    8. required: true,
    9. },
    10. });

目录结构

  1. app
  2. ├── api # api
  3. ├── cms # 关于 cms api
  4. ├── admin.js
  5. ├── log.js
  6. ├── test.js
  7. └── user.js
  8. └── v1 # 普通api
  9. └── book.js
  10. ├── config # 配置文件目录
  11. ├── code-message.js # 返回成功码错误码和返回信息配置
  12. ├── log.js # 日志配置文件
  13. ├── secure.js # 安全性配置文件
  14. └── setting.js # 普通配置文件
  15. ├── dao # 数据库操作
  16. ├── admin.js
  17. ├── book.js
  18. ├── log.js
  19. └── user.js
  20. ├── extension # 扩展目录
  21. ├── lib # 其它类库
  22. ├── db.js # Sequelize 实例
  23. ├── exception.js # 异常类库
  24. ├── type.js # 枚举
  25. └── util.js # 助手函数
  26. ├── middleware # 中间件目录
  27. ├── jwt.js
  28. └── logger.js
  29. ├── model # 模型层
  30. ├── book.js
  31. ├── file.js
  32. ├── group-permission.js
  33. ├── group.js
  34. ├── log.js
  35. ├── permission.js
  36. ├── user-group.js
  37. └── user.js
  38. ├── plugin # 插件目录
  39. ├── validator # 校验层
  40. ├── admin.js # 校验器模块
  41. ├── book.js
  42. ├── common.js
  43. ├── log.js
  44. └── user.js
  45. ├── app.js # 创建koa实例及应用扩展
  46. └── starter.js # 程序的启动文件

9、字段过滤

请求

  1. http://127.0.0.1:3000/cms/users/id?fields=user_pwd;gender;headline;

接口过滤

  1. // 查询特定
  2. async findOne(ctx) {
  3. const {
  4. fields = ''
  5. } = ctx.query;
  6. // 过滤字段的参数
  7. let selectFields = fields.split(';').filter(field => field).map(field => ' +' + field).join('');
  8. let res = await User.findOne({
  9. _id: ctx.params.id
  10. }).select(selectFields); // 字段过滤
  11. if (!res) {
  12. ctx.throw(404, '该用户不存在')
  13. } else {
  14. ctx.body = res;
  15. }
  16. }

10、上传图片的实现

功能点

  • 基础功能

上传图片、生成图片链接

  • 附加功能

限制上传图片的大小与类型、生成高中低三种分辨率的图片链接、生成CDN

技术方案

  • 阿里云OSS等云服务(推荐生产使用)
  • 直接上传到服务器(不推荐生产使用,适合学习使用)

操作步骤

安装koa-body,替换 koa-bodyparser

  1. npm i koa-bodyparser --save

设置图片上传目录

  1. // 请求体解析
  2. app.use(koaBody({
  3. multipart: true, // 启动文件
  4. formidable: {
  5. uploadDir: path.join(__dirname, '/public/uploads'), // 文件存放目录
  6. keepExtensions: true, // 保留扩展名
  7. }
  8. }));
  9. const koaBody = require('koa-body');

获取上传图片

  1. upload (ctx) {
  2. const file = ctx.request.files.file;
  3. ctx.body = {
  4. path: file.path
  5. }
  6. }

生成上传图片链接

image.png

  1. upload (ctx) {
  2. // 上传的文件
  3. const file = ctx.request.files.file;
  4. // 获取文件名
  5. const basename = path.basename(file.path);
  6. // 生成上传后的图片链接
  7. const url = `${ctx.origin}/uploads/${basename}`;
  8. ctx.body = {
  9. url
  10. }
  11. }

11、二级嵌套路由的设计

a、前缀

  1. const router = new Router({ prefix: '/questions/:questionId/answers' });

b、获取参数

  1. ctx.params.questionId

12、koa应用的部署

登录服务器:

  1. ssh -p 22 root@106.12.182.39

安装Git,并下载项目

使用Git并clone代码至服务器,并安装Node

可以npm run start 测试下项目能不能跑起来

  1. npm install

但是,当我们退出服务器后,node的进程也就关了,服务也就没了,

所以我们需要 pm2 来守护进程

pm2使用

守护进程,后台运行

安装

  1. npm install pm2 -g

安装完成后云服务切换到你项目所在路径

启动并监听服务:

  1. pm2 start ./bin/www --watch
  2. ## --watch参数,koa2应用代码发生变化时,pm2会帮你重启服务。

启动之后,显示如下:说明启动成功!

Koa学习 - 图12

pm2更多用法

pm2 reload ./bin/www // 开启
pm2 start ./bin/www // 开启
pm2 stop ./bin/www // 关闭
pm2 list //查看所用已启动项目:

pm2列表查看,pm2 list

Koa学习 - 图13

输入 pm2 show 0 对应上图中的id = 0

image.png

关闭进程
www 对应list的name

  1. pm2 stop www

pm2杀死进程,pm2 kill

Koa学习 - 图15

nginx使用

常用命令

  • 安装
  1. yum install nginx
  • 查看版本号
  1. nginx -v
  • 重启nginx
  1. nginx -s reload
  • 验证配置是否正确
  1. ./nginx -t
  • Nginx正常启动:
  1. nginx
  • 快速停止或关闭Nginx
  1. ./nginx -s stop
  • 正常停止或关闭Nginx
  1. ./nginx -s quit
  • 配置文件修改重装载命令
  1. ./nginx -s reload

查看配置

检查配置,并查看配置文件位置。

  1. nginx -t
  2. [root@VM_0_17_centos nginx]# nginx -t
  3. nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
  4. nginx: configuration file /etc/nginx/nginx.conf test is successful

修改配置

  1. vim /etc/nginx/nginx.conf

image.png

设置转发并重启

  1. server {
  2. listen 443 ssl;
  3. server_name forguo.cn www.forguo.cn;
  4. location /api/ {
  5. ## api转发到内网3333端口
  6. proxy_pass http://127.0.0.1:3333/api/;
  7. }
  8. }

重启:service nginx reload

加密

拓展

  • 使用企业级Node.js框架 ——Egg.js
  • 掌握多进程编程知识
  • 学习使用日志和性能监控