Koa 是一个全新的 web 框架,由 Express 幕后的原班人马打造,致力于成为 web 应用和 API 开发领域中的一个更小、更富有表现力、更健壮的基石。 通过使用异步函数,Koa 帮你丢弃回调函数,并有力地增强错误处理能力。 Koa 并没有捆绑任何中间件,而是提供了一套优雅的方法,帮助您快速而愉快地编写服务端应用程序。

使用

npm init -y//初始化并创建package。json
npm install koa -s//安装Koa

koa-router//koa路由
koa-body//koa默认无法处理post请求体,需要第三方包
nodemon//node的热重载

//如果是ts需要安装以下包
typescript
ts-node
@types/koa
@types/koa-router
JavaScript

使用koa创建node服务器

const Koa = require('koa'); //引入koa构造函数
const app = new Koa(); //创建应用

app.use(async(ctx) => { //中间件函数,在页面响应之前加载
    ctx.body = 'hello,koa';
})
app.listen(3000, () => { //监听端口
    console.log('服务器正在3000端口运行...');
})
JavaScript

路由

const Koa = require('koa'); //引入koa构造函数
const router = require('koa-router')() //引入并执行koa-router函数

const app = new Koa(); //创建应用

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

app.use(router.routes()); //将router作为中间件引入app

app.listen(3000, () => { //监听端口
    console.log('服务器正在3000端口运行...');
})
JavaScript

获取请求

import Koa from 'koa'
import Router from 'koa-router'
import koaBody from 'koa-body'

const app=new Koa()
const router=new Router({
    prefix:'/user'
})

router.get('/',async(ctx)=>{
    ctx.body="user home"
})
router.post('/add',async(ctx)=>{
    const bdy=ctx.request.body
    console.log(bdy)
    ctx.body="user add"
})

app.use(koaBody({
    json: true,
}))//这里有顺序要求,必须在Router前面
app.use(router.routes())

app.listen(3000,()=>{
    console.log("服务运行中……,本地预览:http://localhost:3000")
})

增删改查

import Koa from 'koa'
import Router from 'koa-router'
import koaBody from 'koa-body'

const app=new Koa()
const router=new Router({
    prefix:'/user'
})

const userList=[{
    id:1,
    name:"zhangsan",
    pass:"333"
},{
    id:2,
    name:"lisi",
    pass:"444"
}
]
//增
router.post('/add',async(ctx)=>{
    const newUser=ctx.request.body
    userList.push(newUser)
    ctx.body="add user success"
})
//删,
//通常DELETE请求不会携带请求体(body),而是使用URL中的查询字符串(query string)或URL路径中的动态段(如/delete/:id)来传递需要删除的用户ID
router.delete('/delete/:id',async(ctx)=>{
    const delId=parseInt(ctx.params.id)
    const index=userList.findIndex(user=>user.id==delId)
    //在数组中查找给定元素的第一个出现的索引。如果找到了这个元素,则返回该元素的索引(即位置,从 0 开始计数);如果没有找到,则返回 -1
    if(index!=-1){
        userList.splice(index, 1)
        //array.splice(从哪里开始删,删几个,要添加进数组的元素,从 start 位置开始(可选))
        ctx.body=`delete user: ${delId} success`
    }else{
        ctx.body="no user"
    }
})
//改
router.put('/put',async(ctx)=>{
    const {newId,newName,newPass}=ctx.request.body
    const index=userList.findIndex(user=>user.id==newId)//
    if(index!=-1){
        userList[index]={
            id:newId,
            name:newName,
            pass:newPass
        }
        ctx.body="put user success"
    }else{
        ctx.body="no user"
    }

})
//查
router.get('/list',async(ctx)=>{
    ctx.body=userList
})


app.use(koaBody({
    json: true,
}))//这里有顺序要求,必须在前面
app.use(router.routes())

app.listen(3000,()=>{
    console.log("服务运行中……,本地预览:http://localhost:3000")
})

错误处理

npm i koa-json-error

参数校验

//使用joi进行参数验证
npm i joi --dev
//不需要安装@type/joi,因为已经内置
import Router from 'koa-router'
import Joi from 'joi'

const router = new Router({
    prefix: '/user'
})

const userList = [{
    id: 1,
    name: "zhangsan",
    pass: "333"
}, {
    id: 2,
    name: "lisi",
    pass: "444"
}]

const addUserSchema = Joi.object({
    id: Joi.number().integer().required(),
    name: Joi.string().required(),
    pass: Joi.string().required()
});
const updateUserSchema = Joi.object({
    newId: Joi.number().integer().required(),
    newName: Joi.string().required(),
    newPass: Joi.string().required()
});

const deleteUserSchema = Joi.object({
    id: Joi.number().integer().required()
});

//增
router.post('/add', async (ctx) => {
    const { error, value } = addUserSchema.validate(ctx.request.body);
    if (error) {
      ctx.status = 400;
      ctx.body = { error: error.details[0].message };
      return;
    }
    userList.push(value);
    ctx.body = "add user success";
})
//删
router.delete('/delete/:id', async (ctx) => {
    const { error, value } = deleteUserSchema.validate({ id: parseInt(ctx.params.id) });
    if (error) {
      ctx.status = 400;
      ctx.body = { error: error.details[0].message };
      return;
    }
    const delId = value.id;
    const index = userList.findIndex(user => user.id === delId);
    if (index !== -1) {
      userList.splice(index, 1);
      ctx.body = `delete user: ${delId} success`;
    } else {
      ctx.status = 404;
      ctx.body = "no user";
    }
  });
  
//改
router.put('/put', async (ctx) => {
    const { error, value } = updateUserSchema.validate(ctx.request.body);
    if (error) {
      ctx.status = 400;
      ctx.body = { error: error.details[0].message };
      return;
    }
  
    const { newId, newName, newPass } = value;
    const index = userList.findIndex(user => user.id === newId);
    if (index !== -1) {
      userList[index] = { id: newId, name: newName, pass: newPass };
      ctx.body = "put user success";
    } else {
      ctx.status = 404;
      ctx.body = "no user";
    }
  });
//查
router.get('/list', async (ctx) => {
    ctx.body = userList
})

export default router

定义验证 schema:

  • addUserSchema 用于验证 POST /add 请求体中的用户数据。
  • updateUserSchema 用于验证 PUT /put 请求体中的用户数据。
  • deleteUserSchema 用于验证 DELETE /delete/:id 路径参数中的用户 ID。

验证请求:

  • 对于 POST 和 PUT 请求,使用 Joi.validate() 来验证 ctx.request.body
  • 对于 DELETE 请求,验证路径参数中的 id

错误处理:

  • 如果验证失败,设置响应状态为 400 Bad Request 并返回错误消息。
  • 如果用户找不到,设置响应状态为 404 Not Found