http内置模块,Node框架Express和Koa
http模块
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
| const http = require('http');
// 创建一个web服务器 const server = http.createServer((req, res) => { res.end("Hello Server"); });
// 启动服务器,并且制定端口号和主机 server.listen(8888, '0.0.0.0', () => { console.log("服务器启动成功~"); });
如果没有输入端口号,可以通过server.address().port获取 server.listen(() => { console.log("服务器启动成功~"); console.log(server.address().port) });
listen函数有三个参数 端口port,可以不穿,系统默认分配 主机host,通常是localhost,ip127.0.0.1,或者0.0.0.0,默认是0.0.0.0 localhost本质上是一个域名会被解析成127.0.0.1 127.0.0.1是回环地址,自己主机发出去的包自己解析,在应用层 => 传输层 => 网络层 => 链路层 => 物理层 在网络层就会被获取,不会经过链路层是物理层 0.0.0.0监听所有IP地址,再根据端口找到不同的应用程序
|
req
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53
| request包含请求路径,方法和头等 const server = http.createServer((req, res) => { console.log(requrl) console.log(req.ethod) console.log(req.eaders) res.end("Hello Server"); });
url const server = http.createServer((req, res) => { if(req.url== '/login') res.end("请登录") }else if(req.url=='/register'){ res.end("请注册") } });
如果访问地址携带参数,利用url模块和qs模块,明文传输方式 const url = require('url') const qs = require('querystring'); const { pathname, query } = url.parse(req.url); if (pathname === '/login') { console.log(qs.parse(query)); const { username, password } = qs.parse(query); console.log(username, password); res.end("请求结果~"); }
method 拿到通过post请求发送的json数据,不在地址栏 const server = http.createServer((req, res) => { console.log(req.method) if(req.methdos == 'POST'){ //获取body数据 req.setEncoding('utf-8') //设置数据编码 如果是音频和其他文件就是其他编码 req.on('data',(data)=>{ console.log(data.toString()) //字符串类型 {username:"',age:"'} 转换成js对象 const { username, age } = JSON.parse(data.toString()) }) } });
headers console.log(req.headers) contenttype:数据类型 content-length:文件长度 connection:keep-alive保持连接 accept-encoding:告知服务器,客户端支持的文件压缩格式,比如js文件可以使用gzip编码。对应.gz文件 accept:告知服务器科技接收的文件格式 user-agent:客户端相关信息
|
res
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
| response const server = http.createServer((req, res) => { 1:res.end("响应结果") 2:res.write("响应结果") res.end() });
响应状态码 1:需要后续操作 2:OK,成功 3:重定向 4:客户端 5:服务端
状态码设置方式 res.statusCode = 404 res.writeHead(404,{ 可以传入header相关的事情 })
设置头方式 1:res.setHeader("content-type", "text/plain") 2:res.writeHead(200, { "content-type":"text/plain" })
|
http发送网络请求
axios在前端使用时,基于xhr,在node端使用时是基于http模块
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
| const http = require('http') http.get('...',(res)=>{ res.on('data',(data)+>{ console.log(data) //结果 }) })
发送post const req = http.request({ method:'POST', host:'localhost', port:8888 },(res)=>{ res.on('data',(data)=>{ console.log('结果') }) res.on('end',()=>{ console.log('获取到了所有结果') }) })
req.end() //必须,否则请求停滞
|
http方式原生的文件上传
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48
| const http = require('http'); const fs = require('fs'); const qs = require('querystring');
const server = http.createServer((req, res) => { if (req.url === '/upload') { if (req.method === 'POST') { //必须,图片编码必须设置为binary req.setEncoding('binary');
let body = ''; const totalBoundary = req.headers['content-type'].split(';')[1]; const boundary = totalBoundary.split('=')[1];
req.on('data', (data) => { body += data; });
req.on('end', () => { console.log(body); // 处理body // 1.获取image/png的位置 const payload = qs.parse(body, "\r\n", ": "); const type = payload["Content-Type"];
// 2.开始在image/png的位置进行截取 const typeIndex = body.indexOf(type); const typeLength = type.length; let imageData = body.substring(typeIndex + typeLength);
// 3.将中间的两个空格去掉 imageData = imageData.replace(/^\s\s*/, '');
// 4.将最后的boundary去掉 imageData = imageData.substring(0, imageData.indexOf(`--${boundary}--`));
fs.writeFile('./foo.png', imageData, 'binary', (err) => { res.end("文件上传成功~"); }) }) } } });
server.listen(8000, () => { console.log("文件上传服务器开启成功~"); })
|
Express
基本使用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
| //安装方式 1 脚手架安装 npm install express-generator -g expres demo npm install node bin/www // 默认启动是loaclhost:3000
// 2自己从0实现 npm install express // 引入 const express = require('express'); // 返回app const app = express() //监听请求路径 app.get('/',(req,res,next)=>{ res.end('hello get') }) app.post('/',(req,res,next)=>{ res.end('hello post') })
app.listen(5000,()=>{ console.log('开启') })
|
express的中间件,中间件就是回调函数,接受req,res,next,next是执行下一个中间件的方法,express本质上是中间件的调用
中间件中可以执行任何代码,更改请求和响应对象,结束请求,响应周期,返回数据,调用栈中的下一个中间件
如果没有res.end就需要next传递给下一个中间件,否则请求会被挂起,不会结束
express提供了两种方式将中间件应用与程序中,app/router.use和app/router.methods
可以是app,也可以是router,methods是指常用的请求方式app.get或者app.post
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68
| 中间件类型1//最普通的中间件 app.use((req,res,next)=>{ console.log('注册了第一个普通中间件') }) 只会执行一个中间件 app.use((req,res,next)=>{ console.log('注册了第一个普通中间件') res.end() // 想要让第二个中间件执行得 next() })
app.use((req,res,next)=>{ console.log('注册了第二个普通中间件') res.end() // 报错 不能在end之后再end,end只能有一个 })
中间件类型2//path匹配中间件 app.use(path,callback) app.use('/home',(req,res,next)=>{ console.log('匹配到了/home') res.end('end') } 如果有相同的path匹配中间件,永远只会调用第一个中间件,除非使用next
中间件类型3//path和method匹配中间件 app.get('/home',(req.res,next)=>{ })
中间件类型4//注册多个中间件 app.get('/home',(req,res,next)=>{
},(req,res,next)=>{
},(req,res,next)=>{
})
//使用express解析req.body很轻松 解析json app.use(express.json())
// true是使用qs解析,false那么就是使用node中的queryString进行解析 解析urlencoded app.use(express.urlencoded({extended:true}))
// 解析formdata npm install multer const upload = require('multer') app.use(multer.any()) // 上穿文件 设置上传路径 const multer = multer({ dest:'./uploads/' // 上传文件保存位置, }) const path = require('path' const storage = muliter.diskStorge({ destintion: (req,res,cb)=>{ cb(null,'./uploads/') }//目的地, filename: (req,res,cb)=>{ cb(null, Date.now() + path.extname(file.originalname)) } }) upload.single 上传单个文件 upload.array 上传多个文件 可以传递一个key值表示具体处理哪个数据 app.post('/upload',upload.single('') ,(req,res,next)=>{ console.log(req.files) res.end('上传成功') }) // 默认没有后缀名
|
中间件用法
json解析
express内置一些request解析的中间件 ,当客户端发送请求post请求时,会把数据放到req.body中
客户端可以通过json也可以通过form表单的方式传递
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42
| post 发送username和age
自己写的 // app.use((req, res, next) => { // if (req.headers["content-type"] === 'application/json') { // req.on('data', (data) => { // const info = JSON.parse(data.toString()); // req.body = info; // }) // req.on('end', () => { // next(); // }) // } else { // next(); // } // })
使用express // 使用express提供给我们的body解析 // body-parser: express3.x 内置express框架 // body-parser: express4.x 被分离出去 // body-parser类似功能: express4.16.x 内置成函数 app.use(express.json()); //传送数据为json格式时 application/json // extended // true: 那么对urlencoded进行解析时, 它使用的是第三方库: qs // false: 那么对urlencoded进行解析时, 它使用的是Node内置模块: querystring app.use(express.urlencoded({extended: true}));//传送数据解析application/x-www-form-urlencoded 后续可直接通过打印req.body方式获取传送数据 app.post('/login', (req, res, next) => { console.log(req.body); res.end("Coderwhy, Welcome Back~"); });
app.post('/products', (req, res, next) => { console.log(req.body); res.end("Upload Product Info Success~"); });
app.listen(8000, () => { console.log("express初体验服务器启动成功~"); });
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
| npm install multer
const express = require('express'); const multer = require('multer');
const app = express();
app.use(express.json()); app.use(express.urlencoded({ extended: true }));
const upload = multer();
app.use(upload.any());
app.post('/login', (req, res, next) => { console.log(req.body); res.end("用户登录成功~") });
app.listen(8000, () => { console.log("form-data解析服务器启动成功~") });
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46
| const path = require('path');
const express = require('express'); const multer = require('multer');
const app = express();
app.use(express.json()); app.use(express.urlencoded({ extended: true }));
//自定义的文件信息 const storage = multer.diskStorage({ destination: (req, file, cb) => { cb(null, './uploads/'); }, filename: (req, file, cb) => { cb(null, Date.now() + path.extname(file.originalname)); } })
const upload = multer({ // dest: './uploads/' //文件存储路径 storage //自定义文件存储信息 });
app.post('/login', upload.any(), (req, res, next) => { console.log(req.body); res.end("用户登录成功~") });
上传单个文件 app.post('/upload', upload.single('file'), (req, res, next) => { console.log(req.files); res.end("文件上传成功~"); });
上传多个文件 app.post('/upload', upload.array('file'), (req, res, next) => { console.log(req.files); res.end("文件上传成功~"); });
app.listen(8000, () => { console.log("form-data解析服务器启动成功~") });
|
保存日志信息
使用express开发的第三方中间件,morgan,需要单独安装
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
| const fs = require('fs');
const express = require('express'); const morgan = require('morgan');
const app = express();
const writerStream = fs.createWriteStream('./logs/access.log', { flags: "a+" }) //combined是保存的日志格式, app.use(morgan("combined", {stream: writerStream}));
app.get('/home', (req, res, next) => { res.end("Hello World"); })
app.listen(8000, () => { console.log("express初体验服务器启动成功~"); });
|
request参数解析
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| const express = require('express');
const app = express();
app.get('/products/:id/:name', (req, res, next) => { console.log(req.params); // req.params => 在数据库中查询真实的商品数据 res.end("商品的详情数据~"); })
app.get('/login', (req, res, next) => { console.log(req.query); res.end("用户登录成功~"); })
app.listen(8000, () => { console.log("普通中间件服务器启动成功~"); });
|
response响应结果解析
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38
| const express = require('express'); const router = require('./routers/users');
const app = express();
app.get('/products/:id/:name', (req, res, next) => { console.log(req.params); // req.params => 在数据库中查询真实的商品数据 res.end("商品的详情数据~"); })
app.get('/login', (req, res, next) => { console.log(req.query);
// 设置响应吗 res.status(204);
// res.type("application/json"); // res.end(JSON.stringify({name: "why", age: 18})); // res.json({name: "why", age: 18}) // 设置内容 res.json(["abc", "cba", "abc"]); });
/** * 举个例子: * 请求所有的用户信息: get /users * 请求所有的某个用户信息: get /users/:id * 请求所有的某个用户信息: post /users body {username: passwod:} * 请求所有的某个用户信息: delete /users/:id * 请求所有的某个用户信息: patch /users/:id {nickname: } */
app.listen(8000, () => { console.log("普通中间件服务器启动成功~"); });
|
路由的使用
如果将所有代码放在app中,那么app会越来越复杂,可以使用express.Router创建一个路由处理程序,一个路由实例拥有完整的中间件和路由系统,因此也被称为迷你应用程序
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41
| const express = require('express'); const userRouter = require('./routers/users'); const productRouter = require('./routers/products');
const app = express();
app.use("/users", userRouter); app.use("/products", productRouter);
app.listen(8000, () => { console.log("路由服务器启动成功~"); });
routers/users /** * 举个例子: * 请求所有的用户信息: get /users * 请求所有的某个用户信息: get /users/:id * 请求所有的某个用户信息: post /users body {username: passwod:} * 请求所有的某个用户信息: delete /users/:id * 请求所有的某个用户信息: patch /users/:id {nickname: } */
const express = require('express');
const router = express.Router();
router.get('/', (req, res, next) => { res.json(["why", "kobe", "lilei"]); });
router.get('/:id', (req, res, next) => { res.json(`${req.params.id}用户的信息`); });
router.post('/', (req, res, next) => { res.json("create user success~"); });
module.exports = router;
|
静态服务器
express提供了部署静态资源的方法
1 2 3 4 5 6 7 8 9 10
| const express = require('express');
const app = express();
app.use(express.static('./build')); //.build中是打包后的文件 npm run build
app.listen(8000, () => { console.log("路由服务器启动成功~"); });
|
express的错误处理
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58
| const express = require('express');
const app = express();
const USERNAME_DOES_NOT_EXISTS = "USERNAME_DOES_NOT_EXISTS"; const USERNAME_ALREADY_EXISTS = "USERNAME_ALREADY_EXISTS";
app.post('/login', (req, res, next) => { // 加入在数据中查询用户名时, 发现不存在 const isLogin = false; if (isLogin) { res.json("user login success~"); } else { // res.type(400); // res.json("username does not exists~") next(new Error(USERNAME_DOES_NOT_EXISTS)); } })
app.post('/register', (req, res, next) => { // 加入在数据中查询用户名时, 发现不存在 const isExists = true; if (!isExists) { res.json("user register success~"); } else { // res.type(400); // res.json("username already exists~") next(new Error(USERNAME_ALREADY_EXISTS)); } });
app.use((err, req, res, next) => { let status = 400; let message = ""; console.log(err.message);
switch(err.message) { case USERNAME_DOES_NOT_EXISTS: message = "username does not exists~"; break; case USERNAME_ALREADY_EXISTS: message = "USERNAME_ALREADY_EXISTS~" break; default: message = "NOT FOUND~" }
res.status(status); res.json({ errCode: status, errMessage: message }) })
app.listen(8000, () => { console.log("路由服务器启动成功~"); });
|
更多细节察看expressjs.com.cn
部分原理
调用express创建的是什么
ap.listen如何结合原生启动服务器
listen在createApplication中表面上看不出来,实际上在mixin(app。proto,false)中
调用了原生的http创建服务器启动监听
loading……
app.use发生了什么
用户发送网络请求如何执行中间件回调
next为什么会执行下一个中间件
Koa
koa自称是node.js的下一代框架,koa是和express同一个团队开发的框架
koa旨在为web应用程序和api提供更小,更丰富和强大的能力
相对于express具有更强大的异步处理能力
koa的核心代码只有一千多行,很清凉
我们可以根据需要考虑安装中间件
1 2 3 4 5 6 7 8 9 10 11 12
| const Koa = require('koa');
const app = new Koa(); //ctx = context 上下文对象 包含request和response app.use((ctx, next) => { ctx.response.body = "Hello World"; });
app.listen(8000, () => { console.log("koa初体验服务器启动成功~"); });
|
注册中间件
koa并没有提供methods,path和连续注册的方式注册中间件
只能通过app.use(()=>{})
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
| const Koa = require('koa');
const app = new Koa();
// use注册中间件 app.use((ctx, next) => { if (ctx.request.url === '/login') { if (ctx.request.method === 'GET') { console.log("来到了这里~"); ctx.response.body = "Login Success~"; } } else { ctx.response.body = "other request~"; } });
// 没有提供下面的注册方式 // methods方式: app.get()/.post // path方式: app.use('/home', (ctx, next) => {}) // 连续注册: app.use((ctx, next) => { // }, (ctx, next) => { // })
app.listen(8000, () => { console.log("koa初体验服务器启动成功~"); });
|
路由的使用
需要安装第三方库 koa-router
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34
| const Koa = require('koa');
const userRouter = require('./router/user');
const app = new Koa();
app.use((ctx, next) => { // ctx.response.body = "Hello World"; next(); });
app.use(userRouter.routes()); app.use(userRouter.allowedMethods()); //如果访问了错误的地址和方式
app.listen(8000, () => { console.log("koa路由服务器启动成功~"); });
//routers const Router = require('koa-router');
const router = new Router({prefix: "/users"});
router.get('/', (ctx, next) => { ctx.response.body = "User Lists~"; });
router.put('/', (ctx, next) => { ctx.response.body = "put request~"; });
module.exports = router;
|
参数解析query,params
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25
| const Koa = require('koa');
const app = new Koa(); const Router = require('koa-router');
const userRouter = new Router({prefix: '/users'});
userRouter.get('/:id', (ctx, next) => { console.log(ctx.request.params); console.log(ctx.request.query); })
// app.use((ctx, next) => { // console.log(ctx.request.url); // console.log(ctx.request.query); // console.log(ctx.request.params); // ctx.response.body = "Hello World"; // });
app.use(userRouter.routes());
app.listen(8000, () => { console.log("参数处理服务器启动成功~"); });
|
npm install koa-bodyparser koa-multer
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22
| const Koa = require('koa'); const bodyParser = require('koa-bodyparser'); //json,urlencoded const multer = require('koa-multer'); //form-data const Router = require('koa-router');
const app = new Koa();
const upload = multer();
app.use(bodyParser()); app.use(upload.any());
app.use((ctx, next) => { console.log(ctx.request.body); console.log(ctx.req.body); //multer塞进去的 ctx.response.body = "Hello World"; });
app.listen(8000, () => { console.log("koa初体验服务器启动成功~"); });
|
文件上传
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
| const Koa = require('koa'); const Router = require('koa-router'); const multer = require('koa-multer');
const app = new Koa(); const uploadRouter = new Router({prefix: '/upload'});
// const storage = multer.diskStorage({ // destination, // filename, // })
const upload = multer({ dest: './uploads/' });
uploadRouter.post('/avatar', upload.single('avatar'), (ctx, next) => { console.log(ctx.req.file); ctx.response.body = "上传头像成功~"; });
app.use(uploadRouter.routes());
app.listen(8000, () => { console.log("koa初体验服务器启动成功~"); });
|
koa响应内容
body将相应主体分为
string
Buffer
Stream
Object/Array
null
如果response.status未设置,koa自动设置状态为200或者204 //有内容200,没内容返回null和204
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
| const Koa = require('koa');
const app = new Koa();
app.use((ctx, next) => { // ctx.request.query // ctx.query
// 设置内容 // ctx.response.body // ctx.response.body = "Hello world~" // ctx.response.body = { // name: "coderwhy", // age: 18, // avatar_url: "https://abc.png" // }; // 设置状态码 // ctx.response.status = 400; // ctx.response.body = ["abc", "cba", "nba"];
// ctx.response.body = "Hello World~"; ctx.status = 404; ctx.body = "Hello Koa~"; });
app.listen(8000, () => { console.log("koa初体验服务器启动成功~"); });
|
部署静态资源
npm Install koa-static
1 2 3 4 5 6 7 8 9 10 11
| const Koa = require('koa'); const staticAssets = require('koa-static');
const app = new Koa();
app.use(staticAssets('./build'));
app.listen(8000, () => { console.log("koa初体验服务器启动成功~"); });
|
错误处理
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| const Koa = require('koa');
const app = new Koa();
app.use((ctx, next) => { const isLogin = false; if (!isLogin) { ctx.app.emit('error', new Error("您还没有登录~"), ctx); } });
app.on('error', (err, ctx) => { ctx.status = 401; ctx.body = err.message; })
app.listen(8000, () => { console.log("koa初体验服务器启动成功~"); });
|
express和koa的区别
express比较完整,koa比较自由简洁只包含核心功能,我们需要自己安装使用
两者核心都是中间件
express同步数据
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
| const express = require('express');
const app = express();
const middleware1 = (req, res, next) => { req.message = "aaa"; next(); res.end(req.message); }
const middleware2 = (req, res, next) => { req.message += "bbb"; next(); }
const middleware3 = (req, res, next) => { req.message += "ccc"; }
app.use(middleware1, middleware2, middleware3);
app.listen(8000, () => { console.log("服务器启动成功~"); })
|
express异步数据
express处理异步数据非常麻烦,只能单独抽离函数await
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
| const express = require('express'); const axios = require('axios');
const app = express();
const middleware1 = async (req, res, next) => { req.message = "aaa"; await next(); res.end(req.message); }
const middleware2 = async (req, res, next) => { req.message += "bbb"; await next(); }
const middleware3 = async (req, res, next) => { const result = await axios.get('http://123.207.32.32:9001/lyric?id=167876'); req.message += result.data.lrc.lyric; }
app.use(middleware1, middleware2, middleware3);
app.listen(8000, () => { console.log("服务器启动成功~"); })
|
koa同步数据
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
| const Koa = require('koa');
const app = new Koa();
const middleware1 = (ctx, next) => { ctx.message = "aaa"; next(); ctx.body = ctx.message; }
const middleware2 = (ctx, next) => { ctx.message += "bbb"; next(); }
const middleware3 = (ctx, next) => { ctx.message += "ccc"; }
app.use(middleware1); app.use(middleware2); app.use(middleware3);
app.listen(8000, () => { console.log("服务器启动成功~"); })
|
koa异步数据
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29
| const Koa = require('koa'); const axios = require('axios');
const app = new Koa();
const middleware1 = async (ctx, next) => { ctx.message = "aaa"; await next(); next(); ctx.body = ctx.message; }
const middleware2 = async (ctx, next) => { ctx.message += "bbb"; await next(); }
const middleware3 = async (ctx, next) => { const result = await axios.get('http://123.207.32.32:9001/lyric?id=167876'); ctx.message += result.data.lrc.lyric; }
app.use(middleware1); app.use(middleware2); app.use(middleware3);
app.listen(8000, () => { console.log("服务器启动成功~"); })
|
洋葱模型
……
学无止境,结束意味着新的开始
loading……