Skip to content

Latest commit

 

History

History
70 lines (52 loc) · 2.33 KB

使用koa管理类server调用.md

File metadata and controls

70 lines (52 loc) · 2.33 KB
date tags
2022-01-24
nodejs

tldr:

  • 如果架构内部可抽象出client server模式,都可以用过koa-composekoa-router管理。
  • koa-composekoa-router都可以脱离http这一套逻辑独立运行,这点有别于koa(koa就是http框架)。

koa这一套前端太熟悉了,它能轻易的实现

  • 中间件模型
  • api的分组和嵌套,按组指定中间件

在面向http的koa应用中,原生node提供最原始的req和res,由koa把它们包装成ctx并提供一些语法糖,中间件机制则是有koa-compose提供,经历过中间件的处理后回到koa源码,用原生node处理res。

在koa体系的两个关键组件中,koa-compose完全可以脱离koa,而koa-router则是依赖几个固定的ctx成员,包括:method,path,request。这些本应来自http的成员并不影响我们的使用,我们可以包装自己的ctx,轻易兼容koa-router,demo如下:

const compose = require('koa-compose')
const Router = require('koa-router')

const router = new Router()

router.get('/xiaoA', async (ctx, next) => {
    ctx.body += 'xiaoA'
});

router.get('/xiaoB', async (ctx, next) => {
    ctx.body += 'xiaoB'
});

const delay = ms => new Promise(resolve => setTimeout(resolve, ms))

const asyncCall = compose([
    async (ctx, next) => {
        ctx.body = 'hello '
        await delay(1000)
        await next()
    },
    router.routes(),
])
  
// 包装ctx
const ctxA = { path: '/xiaoA', method: 'GET', request: {} /* just mock兜底 */, body: '' }
asyncCall(ctxA).then(() => {
    console.log(ctxA.body) // hello xiaoA
}).catch(e => {
    console.log(e)
});

// 包装ctx
const ctxB = { path: '/xiaoB', method: 'GET', request: {} /* just mock兜底 */, body: '' }
asyncCall(ctxB).then(() => {
    console.log(ctxB.body) // hello xiaoB
}).catch(e => {
    console.log(e)
});

如上我们脱离了koa和http这一套使用了koa-compose和koa-router,可以在哪些场景应用呢?

  • 架构上明显分层,如需要ipc(electron,chrome extension,jsBridge)
  • 大型应用的内部分层
  • server client同构

通过包装ctx轻易的兼容了koa-router,使其能脱离http场景,或许其他koa生态组件也可以?

把一个熟悉的模式应用到不同的场景,感觉还是不错的。这种模式脱离场景的思考方式也值得在其他地方应用。