前瞻
Express 框架和 Koa 框架都出自于同一个团队,可以说 Koa 框架是 Express 框架的衍生但有别于 Express 框架,因为 Koa 框架的核心代码仅有 1600+行,且由 TJ 大佬在维护。从架构设计上来说,Express 是完整和强大的,在其中帮助我们内置了很多好用的功能;而 Koa 则是简洁和自由的,毕竟核心代码只有 1600+行,完全称得上轻量级,它只包含最核心的功能,并不会对我们使用其他中间件进行任何的限制。两个框架的核心其实都是中间件,但两者的中间件执行机制是不同的,特别是针对某个中间件包含异步操作时,接下来会详细说说~
Express 与 Koa 的比较
创建服务器
静态资源服务器
-
Express 框架
Express 内置了 static 方法实现托管静态资源
-
Koa 框架
Koa 实现托管静态资源需使用第三方库:koa-static
创建中间件
中间件的本质就是一个回调函数
路由
-
Express 框架
Express 可以自动处理路径和 method 的匹配问题,如果两者同时匹配成功,则 Express 会将这次请求,转交给对应的中间件处理
模块化路由
-
Koa 框架
Koa 不能自动处理路径和 method 的匹配问题,但可以根据 request 自己来判断或使用第三方路由中间件(koa-router)
参数解析
-
Express 框架
-
Koa 框架
-
获取 URL 中携带的查询参数
请求地址:http://locahost:8000/login?username=licodeao&password=123
-
获取 URL 中的动态参数
请求地址:http://localhost:8000/users/123
-
解析 JSON 格式的数据
需要使用第三方库 koa-bodyparser
请求地址:http://localhost:8000/login
-
解析 URL-encoded 格式的数据
请求地址:http://localhost:8000/login
body 是 x-www-form-urlencoded 格式
获取数据和 json 一样,安装 koa-bodyparser
-
解析 form-data 格式的数据
需要使用 koa-multer 第三方库
-
文件上传
错误处理
-
Express 框架
-
Koa 框架
源码分析
Express 框架
-
调用 express()到底创建的是什么
调用 express()实际上是调用了 createApplication 函数
-
use 注册一个中间件
无论是 app.use 还是 app.methods 都会注册一个主路由
app 本质上会将所有的函数交给整个主路由来处理
-
一个请求过来,从哪里开始处理
从 app 函数被调用开始
-
router.handle 中做了什么事情
Koa 框架
-
require(‘koa’),导出的是什么
导出的是 Application 这个类
const Koa = require(‘koa’)
这也是为什么在创建实例时需要大写
-
Koa 中如何开启监听?
-
Koa 如何注册中间件?
-
监听回调
-
handleRequest 方法
-
compose 方法
中间件的执行顺序
对于某个中间件包含异步操作时,Express 框架和 Koa 框架的机制是不一样的
假设有三个中间件会在一次请求中匹配到,并且按照顺序执行
希望实现的结果是:
- 在 middleware1 中,在 req.message 中添加一个字符串 aaa
- 在 middleware2 中,在 req.message 中添加一个字符串 bbb
- 在 middleware3 中,在 req.message 中添加一个字符串 ccc
- 当所有的内容添加结束后,在 middleware1 中,通过 res 返回最终的结果
Express 同步数据的实现
Express 异步数据的实现
Express 异步数据的实现相较于 Koa 比较麻烦
Koa 同步数据的实现
实现原理图与 Express 同步数据的实现一致
Koa 异步数据的实现
Koa 异步数据的实现较为方便,是因为其内部返回了一个 Promise(详细可看上方源码)
值得注意的是:虽然上方的 Express 与 Koa 的异步实现看起来一样,但运行结果却大相径庭。
Express 异步得到的结果:aaabbb
Koa 异步得到的结果:aaabbb+axios 返回的数据
造成这样结果的原因,显然是因为 Express 框架和 Koa 框架的机制是不一样的,Koa 处理中间件时返回的是 Promise,所以一定会得到一个完整的结果。 而 Express 处理中间件是同步执行的,有异步操作时会得不到数据。所以上方 Express 异步数据的实现中的 async、await 相当于白加。
Koa 洋葱模型
来自 Koa 社区针对于中间件的盛行的说法
两层理解: