框架提供了多種擴展點擴展自身的功能:
在開發(fā)中,我們既可以使用已有的擴展 API 來方便開發(fā),也可以對以上對象進(jìn)行自定義擴展,進(jìn)一步加強框架的功能。
app 對象指的是 Koa 的全局應(yīng)用對象,全局只有一個,在應(yīng)用啟動時被創(chuàng)建。
框架會把 app/extend/application.js 中定義的對象與 Koa Application 的 prototype 對象進(jìn)行合并,在應(yīng)用啟動時會基于擴展后的 prototype 生成 app 對象。
例如,我們要增加一個 app.foo() 方法:
// app/extend/application.js |
一般來說屬性的計算只需要進(jìn)行一次,那么一定要實現(xiàn)緩存,否則在多次訪問屬性時會計算多次,這樣會降低應(yīng)用性能。
推薦的方式是使用 Symbol + Getter 的模式。
例如,增加一個 app.bar 屬性 Getter:
// app/extend/application.js |
Context 指的是 Koa 的請求上下文,這是 請求級別 的對象,每次請求生成一個 Context 實例,通常我們也簡寫成 ctx。在所有的文檔中,Context 和 ctx 都是指 Koa 的上下文對象。
框架會把 app/extend/context.js 中定義的對象與 Koa Context 的 prototype 對象進(jìn)行合并,在處理請求時會基于擴展后的 prototype 生成 ctx 對象。
例如,我們要增加一個 ctx.foo() 方法:
// app/extend/context.js |
一般來說屬性的計算在同一次請求中只需要進(jìn)行一次,那么一定要實現(xiàn)緩存,否則在同一次請求中多次訪問屬性時會計算多次,這樣會降低應(yīng)用性能。
推薦的方式是使用 Symbol + Getter 的模式。
例如,增加一個 ctx.bar 屬性 Getter:
// app/extend/context.js |
Request 對象和 Koa 的 Request 對象相同,是 請求級別 的對象,它提供了大量請求相關(guān)的屬性和方法供使用。
ctx.request |
ctx 上的很多屬性和方法都被代理到 request 對象上,對于這些屬性和方法使用 ctx 和使用 request 去訪問它們是等價的,例如 ctx.url === ctx.request.url。
Koa 內(nèi)置的代理 request 的屬性和方法列表:Koa - Request aliases
框架會把 app/extend/request.js 中定義的對象與內(nèi)置 request 的 prototype 對象進(jìn)行合并,在處理請求時會基于擴展后的 prototype 生成 request 對象。
例如,增加一個 request.foo 屬性 Getter:
// app/extend/request.js |
Response 對象和 Koa 的 Response 對象相同,是 請求級別 的對象,它提供了大量響應(yīng)相關(guān)的屬性和方法供使用。
ctx.response |
ctx 上的很多屬性和方法都被代理到 response 對象上,對于這些屬性和方法使用 ctx 和使用 response 去訪問它們是等價的,例如 ctx.status = 404 和 ctx.response.status = 404 是等價的。
Koa 內(nèi)置的代理 response 的屬性和方法列表:Koa Response aliases
框架會把 app/extend/response.js 中定義的對象與內(nèi)置 response 的 prototype 對象進(jìn)行合并,在處理請求時會基于擴展后的 prototype 生成 response 對象。
例如,增加一個 response.foo 屬性 setter:
// app/extend/response.js |
就可以這樣使用啦:this.response.foo = 'bar';
Helper 函數(shù)用來提供一些實用的 utility 函數(shù)。
它的作用在于我們可以將一些常用的動作抽離在 helper.js 里面成為一個獨立的函數(shù),這樣可以用 JavaScript 來寫復(fù)雜的邏輯,避免邏輯分散各處。另外還有一個好處是 Helper 這樣一個簡單的函數(shù),可以讓我們更容易編寫測試用例。
框架內(nèi)置了一些常用的 Helper 函數(shù)。我們也可以編寫自定義的 Helper 函數(shù)。
通過 ctx.helper 訪問到 helper 對象,例如:
// 假設(shè)在 app/router.js 中定義了 home router |
框架會把 app/extend/helper.js 中定義的對象與內(nèi)置 helper 的 prototype 對象進(jìn)行合并,在處理請求時會基于擴展后的 prototype 生成 helper 對象。
例如,增加一個 helper.foo() 方法:
// app/extend/helper.js |
另外,還可以根據(jù)環(huán)境進(jìn)行有選擇的擴展,例如,只在 unittest 環(huán)境中提供 mockXX() 方法以便進(jìn)行 mock 方便測試。
// app/extend/application.unittest.js |
這個文件只會在 unittest 環(huán)境加載。
同理,對于 Application,Context,Request,Response,Helper 都可以使用這種方式針對某個環(huán)境進(jìn)行擴展,更多參見運行環(huán)境。
更多建議: