Node.js
Koa
Node.jsDay 15

そろそろkoa入門

More than 3 years have passed since last update.

koa.jsの出た当初はexpress.jsのほうが機能が優れていてあんまりやるぞーって気になってなかったのですが、

ネタ探しに調べてたら既にメジャーバージョンも出ているし

パッケージも豊富になっていたので

そろそろ大丈夫じゃないかなと思ったのでkoa.jsやってみます。


koa.jsとは

Node.jsの新しいWebFrameworkです。Node.jsのWebFrameworkといえばexpress.jsが有名ですがその開発メンバーが開発しているフレームワークです。

koaはgeneratorを使うことでコールバックをなくしエラーハンドリングが強化されています。

以下はhello worldです。


app.js


'use strict';

const koa = require('koa');
const app = module.exports = koa();

app.use(function *(){
this.body = 'Hello world';
});


これだけでは、ありがたみがわかりませんが以下の様なコードだともう少しわかりやすくなります。


app.js

'use strict'; 

const koa = require('koa');
const request = require('request-promise');
const app = module.exports = koa();

app.use(function *(){
let options = {
uri: 'https://github.com' + this.request.url
};

this.body = yield request(options);
});


これをexpressで書くと


app.js

app.get('/', function(req, res){

...
request(options).
then(function(body){
res.send(body);
}).
catche(...);
});

みたくPromiseを使ってもコールバックが2つはできてしまいます。

koaのほうが見通しのよいコードを書けます。


Cookie

Cookieの設定方法です。this.cookiesを使います。


app.js

'use strict'; 

const koa = require('koa');
const app = module.exports = koa();

app.use(function *(){
let count = ~~this.cookies.get('count') + 1;
this.cookies.set('count', count);
this.body = 'count: ' + count;
});


特に解説することもなく普通に使えますね。

署名もサポートされています。

app.keys = ['im a newer secret', 'i like corgi'];

setする時は次のような感じです。

this.cookies.set('name', 'koki_cheese', { signed: true });


Routing

ルーティングなどもMiddlewareとして別パッケージに分離されています。

この辺はexpress.jsもv4からそんな感じですね

ルーティングにはkoa-routeを使います


app.js

'use strict'; 

const koa = require('koa');
const _ = require('koa-route');
const app = module.exports = koa();

app.
use(_.get('/', function *(){
this.body = 'Hello world';
})).
use(_.get('/users/:name', function *(name){
this.body = 'Hello, ' + name + '!';
}));



Templates

テンプレートエンジンを利用するのにco-viewsを使います。

テンプレートエンジンはjadeを使います

package.jsonjadeがあればjadeを読み込んでくれるようになります。

npm install --save co-views jadeでインストールすると使えるようになります。


app.js

'use strict'; 

const koa = require('koa');
const _ = require('koa-route');
const views = require('co-views');
const app = module.exports = koa();

let render = views(__dirname + '/views', { ext: 'jade'});

let title = 'koa-example';

app.
use(_.get('/', function *(){
this.body = yield render('index', {
title: title
});
})).
use(_.get('/users/:name', function *(name){
this.body = yield render('user', {
title: name + ' - ' + title,
user: {
name: name
}
});
}));


app.jsと同じ位置にviewsでディレクトリを作成してその中にテンプレートを作成します。


layout.jade

doctype html

html
head
title= title
body
block body


index.jade

extends layout

block body
h1= title
a(href="/users/k2wanko") k2wanko



user.jade

extends layout

block body
h1 Hello #{user.name}!


という感じでレイアウトを書いてあげればHTMLの表示もらくらくできます。


Error Handling

エラーはイベントで通知されます。

この辺はNode.jsではおなじみですね。

app.on('error', function(err){

log.error('server error', err);
});


Stream

すみません 時間がなくて試せなかったので詳しくは書けませんでした。

この辺のサンプルを参考にしたかったのですが僕自身まだStreamを制しきれてないので時間が掛かってしまいました。


まとめ

コードは https://github.com/k2wanko/koa-example においています。

Node.js v5.1.1で試しました。

感想としては、機能面でもexpressに劣らないくらい色々充実してて良さそうだし

何かあっても本体はシンプルだし足りない機能は自分で簡単に作れそうです

あと一番はコードの見通しがよくなるのは最高ですね。