Context
Koa里的context,即上下文,是一个封装了response,request等属性和方法的对象。每一次请求都会生产一个新的context。
在Koa1中,每个请求func中的this即使一个context:
app.use(function *(){
this; // Context
this.request; // koa Request
this.response; // koa Response
});
而在Koa2中,context对象直接就在回调函数里:
app.use((ctx, next) => {
ctx; // Context
ctx.request; // koa Request
ctx.response; // koa Response
})
handle error
// 监听error,自定义错误处理逻辑
app.on('error', (err) => {
log.error('server error', err);
});
当 request/response 中出现任何错误且无法响应客户端时,Koa 会把 ctx 实例作为第二个参数:
app.on('error', (err, ctx) => {
log.error('server error', err, ctx);
});
context.request
request.header/request.headers请求头对象request.length以数字(或undefined)的形式返回Content-Lengthrequest.type获取请求的Content-Typerequest.is(type)判断Content-Type是否是is中期待的值。如果没有 request body,返回 undefined; 如果没有 content type,或者匹配失败,返回 false; 否则返回匹配的 content-type
// With Content-Type: text/html; charset=utf-8
request.is('html'); // => 'html'
request.is('text/html'); // => 'text/html'
request.is('text/*', 'text/html'); // => 'text/html'
// When Content-Type is application/json
request.is('json', 'urlencoded'); // => 'json'
request.is('application/json'); // => 'application/json'
request.is('html', 'application/*'); // => 'application/json'
request.is('html'); // => false
// usage
if (request.is('image/*')) {
// process
} else {
ctx.throw(415, 'images only!');
}
request.accepts(types)检查给定的类型 types(s) 是否可被接受,当为 true 时返回最佳匹配,否则返回 false。参数可以是字符串或者数组
// Accept: text/html
this.accepts('html');
// => "html"
// Accept: text/*, application/json
this.accepts('html');
// => "html"
this.accepts('text/html');
// => "text/html"
this.accepts('json', 'text');
// => "json"
this.accepts('application/json');
// => "application/json"
// Accept: text/*, application/json
this.accepts('image/png');
this.accepts('png');
// => false
// Accept: text/*;q=.5, application/json
this.accepts(['html', 'json']);
this.accepts('html', 'json');
// => "json"
// No Accept header
this.accepts('html', 'json');
// => "html"
this.accepts('json', 'html');
// => "json"
request.method请求方法request.method=设置请求的方法request.url请求的URLrequest.url=设置请求的URLrequest.path获取请求路径request.path=设置请求路径(保留请求参数)request.search获取请求的查询参数字符串,包含?request.search=设置请求的查询参数字符串,不需要加?request.querystring获取请求的查询参数字符串,不包含?request.querystring=设置请求的查询参数字符串,需要加上?request.query以对象的形式获取请求参数,不支持嵌套对象request.query=以对象的形式设置请求参数,不支持嵌套对象
// example
const about = async (ctx, next) => {
const request = ctx.request;
console.log('request query');
console.log(request.query);
await ctx.render('home/about', {
title: 'about page',
content: 'this is about page'
});
};
// visit /about?a=1&b=2
// result:
// {a: 1, b: 2}
context.response
response.status响应的状态值,没有默认值response.status=设置响应的状态值response.message获取响应消息。默认情况下和response.status相关联response.message=response.body获取响应体response.body=stringwrittenBufferwrittenStreampipedObjectjson-stringifiednullno content response
response.get(field)获取 response header 中某字段的值response.set(field, value)设置 response header 中某字段的值response.set(fields)设置 response header 中字段的值,参数为Objectresponse.is(types...)response.redirect(url, [alt])
context.cookies
Koa的cookie处理底层是通过cookies模块来实现的。
ctx.cookies.set
ctx.cookies.set(name, value, [options])
// options
{
maxAge, // 从 Date.now() 开始的过期时间,以毫秒作为单位
signed, // 是否签名
expires, // 通过 Date 表示的 cookie 过期日期
path: "/", // cookie path
domain, // cookie 的域
secure, // cookie 发送方式。false 表示 cookie 通过 HTTP 协议发送,true 表示 cookie 通过 HTTPS 发送
httpOnly: true, // true 表示 cookie 只能通过 HTTP 协议发送
overwrite: false // 对于重名的 cookie 是否覆盖
}
ctx.cookies.get
ctx.cookies.get(name, [options])
// options
{
signed // 是否签名
}
// example
router.get('/', async (ctx, next) => {
ctx.cookies.set('username', 'ecmadao');
await ctx.render('home/index', {
title: 'home page',
content: 'this is home page'
});
});
router.get('about', async (ctx, next) => {
console.log('ctx cookies');
console.log(`log: ${ctx.cookies.get('username')}`);
await ctx.render('home/about', {
title: 'about page',
content: 'this is about page'
});
});
// visit /
// then visit /about
// result:
// log: ecmadao
context.throw
Koa是封装了http-assert模块,来进行错误的抛出。
通过throw抛出一个包含status属性的Error对象。默认情况下这个Error的status为500:
ctx.throw([msg], [status], [properties])
// examples
ctx.throw(403);
ctx.throw('name required', 400);
ctx.throw(400, 'name required');
ctx.throw('something exploded');
ctx.throw('something exploded');
// 相当于
var err = new Error('something exploded');
err.status = 400;
throw err;