阅读 216

用koa的简单写一个接口[后面会更新]

koa 是非常精简的框架, 其中的精粹思想就是洋葱模型(中间件模型), koa 框架的中间件模型非常好用并且简洁, 但是也有自身的缺陷, 一旦中间件数组过于庞大, 性能会有所下降,我们需要结合自身的情况与业务场景作出最合适的选择.

* Node 主要用在开发 Web 应用,koa 是目前 node 里最流行的 web 框架。*

理解koa

1. 安装koa koa-router

npm install koa koa-router -S  
npm install nodemon -D 
复制代码
  • 使用 require() 引入 koa-router ,并且对其实例化(支持传递参数),然后使用获取到的路由实例 router 设置一个路径
  • Nodemon是一个实用程序,它将监视源中的任何更改并自动重新启动服务器

使用koa koa-body代码如下

// app.js

const Koa = require('koa'); // 引入koa
const Router = require('koa-router'); // 引入koa-router

const app = new Koa(); // 创建koa应用
const router = new Router(); // 创建路由,支持传递参数

// 调用router.routes()来组装匹配好的路由,返回一个合并好的中间件
// 调用router.allowedMethods()获得一个中间件,当发送了不符合的请求时,会返回 `405 Method Not Allowed` 或 `501 Not Implemented`
app.use(router.routes()); //拆分路由要用的  下面有提到
app.use(router.allowedMethods({ 
    // throw: true, // 抛出错误,代替设置响应头状态
    // notImplemented: () => '不支持当前请求所需要的功能',
    // methodNotAllowed: () => '不支持的请求方式'
}));  //拆分路由要用的  下面有提到

// 启动服务监听本地3000端口
app.listen(3000, () => {
    console.log('应用已经启动,http://localhost:3000');
})

复制代码

package.json需要添加一条nodemon的命令,第8行

"scripts":{
   "server":"nodemon app.js"
}
复制代码

2.使用 Koa-router (如果要拆分的话 需要注意注释的语句 )

拆分路由模块

创建一个routes的文件夹

创建一个user.js

Koa-router 请求方式: getputpostpatchdeletedel ,而使用方法就是 router.方式() ,比如 router.get()router.post() 。而 router.all() 会匹配所有的请求方法。

    const Router = require("koa-router");
    const router = new Router({ prefix: "/users" });
    const { register, login, find } = require("../controllers/user.js");

    // router.get("/test", (ctx) => {
    //   ctx.body = "我是test";
    // });

    router.post("/register", register); //登录接口
    
    router.post("/login", login);  //注册接口

    module.exports = router.routes();
复制代码

3 登录接口的内容 根目录新建一个controllers文件夹

 //controllers/users.js 路径
    
    const User = require("../models/Users.js");
const { encryptPW, isRightPW } = require("../config/utils.js");
const jwt = require("jsonwebtoken");
const { secretKEY } = require("../config/key.js");
class ginS {
  async register(ctx) {
    console.log(ctx.request.body);
    ctx.body = ctx.request.body;

    //存储到数据库
    const findResult = await User.find({ email: ctx.request.body.email });
    if (findResult.length > 0) {
      ctx.body = { msg: "邮箱已经存在!!!" };
    } else {
      //没查到
      const newUser = new User({
        name: ctx.request.body.name,
        email: ctx.request.body.email,
        password: encryptPW(ctx.request.body.password),
      });

      //存储到数据库
      await newUser
        .save()
        .then((res) => {
          ctx.body = newUser;
        })
        .catch((err) => {
          console.log(err);
        });
    }
  }

  async login(ctx) {
    const findResult = await User.find({ email: ctx.request.body.email });

    if (findResult.length === 0) {
      ctx.status = 404;
      ctx.body = { email: "用户不存在!!!" };
    } else {
      const user = findResult[0];
      const password = ctx.request.body.password;
      // 返回true和false
      const result = isRightPW(password, user.password);
      console.log(result);
      if (result) {
        // 返回token
        const userInfo = { id: user.id, name: user.name };
        //生成token
        const token = jwt.sign(userInfo, secretKEY, { expiresIn: "1h" });
        ctx.status = 200;
        ctx.body = { msg: "登录成功!!!", token: "Bearer " + token };
      } else {
        ctx.status = 400;
        ctx.body = { msg: "登录失败!!!" };
      }
    }
  }

  // 获取数据
  async find(ctx) {
    ctx.body = await User.find();
  }
  
}
module.exports = new ginS();

复制代码

4 需要引入的登录或数据的类型 根目录新建 models文件 /models/Users.js

const mongoose = require("mongoose");
const Schema = mongoose.Schema;

const UserChema = new Schema({
  name: { type: String, required: true },
  email: { type: String, required: true },
  password: { type: String, required: true },
  date: { type: Date, default: Date.now },
});

module.exports = mongoose.model("Admin", UserChema, "wens");
复制代码

5. 需要的话 还能设置路由前缀

可以通过调用 router.prefix(prefix) 来设置路由的前缀,也可以通过实例化路由的时候传递参数设置路由的前缀,比如在 RESTful 接口里面,往往会为接口设置一个 api 前缀,如:

router.prefix('/api')

// 或者
const router = new Router({
   prefix: '/api' 
})

复制代码

当然也支持设置参数:

router.prefix('/路径/:参数')
复制代码

**6. 还可以拆分路由 主文件app.js添加

//app.js
const Koa = require('koa'); // 引入koa
const Router = require('koa-router'); // 引入koa-router

+const routeing = require("./routers/index.js");  //创建的index.js文件夹  在 routers下面创建

+/*   index.js 的内容
const fs = require("fs");
module.exports = (router) => {
  fs.readdirSync(__dirname).forEach((file) => {
    if (file === "index.js") return false;
    const route = require(`./${file}`);
    router.use(route);
  });
};*/


const app = new Koa(); // 创建koa应用
const router = new Router(); // 创建路由,支持传递参数

//+ routeing(router);
app.use(router.routes()).use(router.allowedMethods());

// 启动服务监听本地3000端口
app.listen(3000, () => {
    console.log('应用已经启动,http://localhost:3000');
})
复制代码

7. 路由重定向

使用 router.redirect(source, destination, [code]) 可以对路由进行重定向,例子:

router.redirect('/login', 'sign-in');
复制代码

等价于:

router.all('/login', ctx => {
  ctx.redirect('/sign-in');
  ctx.status = 301;
});
复制代码

8. koa配合mongoose(数据库的操作)使用

安装

npm install mongoose --save
复制代码

可以在app.js引入

const mongoose = require("mongoose");
const { connectionStr } = require("./config/key.js");  //./config/key.js  链接数据库的文件
// 连接数据库
mongoose.connect(connectionStr, (err) => {
  if (err) console.log("mongonDB连接失败了");
  console.log("mongonDB连接成功了");
});`

复制代码

config/key.js

module.exports = {
    connectionStr:'这个主要是启动的下面的这个软件(mongoDB)'
  }
复制代码

8EPVUKZ453RI@S3$2VTGSCS.png

总结

koa 是非常精简的框架, 其中的精粹思想就是洋葱模型(中间件模型), koa 框架的中间件模型非常好用并且简洁, 但是也有自身的缺陷, 一旦中间件数组过于庞大, 性能会有所下降,我们需要结合自身的情况与业务场景作出最合适的选择.

文章分类
阅读
文章标签