Koa2框架"另类学习"

最近做了个图书分享的小程序项目,后台用的腾讯云管理后台下的demo,看了看源码是Koa2的代码,下面的是个人的拙见,自己构建了koa,来更好的理解koa.
可能很多地方不对,希望各位大佬看到的给指正,本人就是一个还没毕业的菜鸟而已…,别让我走太多弯路

首先介绍一下koa:(下面的话你们可能不想听,但我还是要说)
Koa 是一个新的 web 框架,由 Express 幕后的原班人马打造, 致力于成为 web 应用和 API 开发领域中的一个更小、更富有表现力、更健壮的基石。 通过利用 async 函数,Koa 帮你丢弃回调函数,并有力地增强错误处理。 Koa 并没有捆绑任何中间件, 而是提供了一套优雅的方法,帮助您快速而愉快地编写服务端应用程序。
在这里插入图片描述

let’s go!!

Step1:浅层封装http模块

【node需要是7.6+版本之上,安装了nodemon最好不过,本人就是使用nodemon运行的】
1.我们先来看一下原生node的对http模块以及创建服务的过程
上代码:

//引入nodejs自带的http模块
const http = require('http');
//创建服务
//req:request请求
//res:response相应
//创建服务传入的回调中的两个参数
const server = http.createServer((req,res)=>{
    //重写响应头
    res.writeHead(200);
    //打印到页面
    //注意:创建的服务中必须有一个end,里面的内容会打印到页面上去
    res.end("hello PG13");
}); 
//监听端口9090,监听成功后可以传递一个回调函数,当然参数是可选的
server.listen(9090,()=>{
    console.log("9090正在被监听");
})

使用nodemon编译运行的结果截图:
运行结果

页面上会打印一个hello PG13

然后我们自己实现一个koa的http模块,创建一个服务
新建一个application.js
代码如下:

const http = require('http');

class Application{
    constructor(){
        this.callback = ()=>{

        }
    }
    use(callback){
        this.callback = callback;
    }
    listen(...args){
        const server = http.createServer((req,res)=>{
            this.callback(req,res);
        });
        server.listen(...args);
    }
}

module.exports = Application;

我们将sever.js改造一下:

const koaPG13 = require('./application');
const app = new koaPG13();

app.use((req,res)=>{
    res.writeHead(200);
    res.end("hello PG13");
});
app.listen(9090,()=>{
    console.log("9090正在被监听");
})

执行以后,页面上也会正常显示’hello PG13’

Step2:封装Ctx对象

application.js中代码:

const http = require('http');

let request = {
    get url(){
        return this.req.url
    }
}

let response = {
    get body(){
        return this._body
    },
    set body(val){
        this._body = val 
    }
}

let context =  {
    get url(){
        return this.request.url
    },
    get body(){
        return this.response.body
    },
    set body(val){
        this.response.body= val
    }
}

class Application{
    constructor(){
        this.callback = ()=>{

        },
        this.context = context;
        this.request = request;
        this.response = response;
    }
    use(callback){
        this.callback = callback;
    }
    listen(...args){
        const server = http.createServer(async (req,res)=>{
            let ctx = this.createCtx(req,res);
            await this.callback(ctx);
            ctx.res.end(ctx.body);
            // this.callback(req,res);
        });
        server.listen(...args);
    }
    createCtx(req,res){
        let ctx = Object.create(this.context);
        ctx.request = Object.create(this.request);
        ctx.response = Object.create(this.response);
        ctx.req = ctx.request.req = req;
        ctx.res = ctx.response.res = res;
        return ctx;
    }
}

module.exports = Application;

server.js:

const koaPG13 = require('./application');
const app = new koaPG13();
// app.use((req,res)=>{
//     res.writeHead(200);
//     res.end("hello PG13");
// });
app.use(async ctx=>{
    ctx.body = 'hello koaPG13'+ctx.url
})
app.listen(9090,()=>{
    console.log("9090正在被监听");
})

执行编译后,页面会打印成:
编译结果

Step3 实现中间件机制

解释中间件机制的模型图
在这里插入图片描述

实现一个同步的compose

function add(x,y){
    return x+y
  }
  function double(z){
    return z*2
  }
  const middlewares = [add, double]   //中间件:两个函数
  let len = middlewares.length   //2
  function compose(midds){
    console.log(midds);
    return (...args)=>{
      // 初始值
      console.log(...args);
      let res = midds[0](...args)
      for(let i=1;i<len;i++){
        res = midds[i](res)
      }
      return res
    }
  }
  const fn = compose(middlewares)
  const res = fn(1,2);
  console.log(res)

打印为6

Step4 实现精简版Koa

实现next 异步的中间件

async function fn1(next){
    console.log('fn1')
    await next()
    console.log('end fn1')
  }
  
  async function fn2(next){
    console.log('fn2')
    await delay()
    await next()
    console.log('end fn2')
  }
  function fn3(next){
    console.log('fn3')
  }
  
  function delay(){
    return new Promise((reslove,reject)=>{
      setTimeout(()=>{
        reslove()
      },2000)
    })
  }
  
  function compose (middlewares){
    return function(){
      return dispatch(0)
      function dispatch(i){
        let fn = middlewares[i]
        if(!fn){
          return Promise.resolve()
        }
        return Promise.resolve(fn(function next(){
          return dispatch(i+1)
        }))
      }
    }
  }

会以洋葱圈的形式执行!

over!
比较糙,见谅,更多的是我自己做的笔记

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值