前回に引き続き、今回も、JavaScriptのPromise関連の記事です。
今回は、JavaScriptライブラリのbluebirdを使って、コールバックで非同期処理を行う関数を簡単にPromiseを返す関数に変換する方法を紹介します。
bluebirdとは
bluebirdとは、Promiseを実装したJavaScriptのライブラリです。現在、多くのブラウザやNode.jsなどのJavaScript実行環境では、Promiseが標準で対応されていますが、IEなどの未対応の環境でも、bluebirdを利用することでPromiseを使えるようになります。それだけでなく、bluebirdにはES2015の標準の仕様にない便利な関数があり、Promiseに対応している環境でも便利なライブラリです。
bluebirdのpromisify、promisifyAllでPromiseを返す関数を作る
promisifyはひとつの関数を対象として、Promiseを返す関数を生成します。以下のような、Node.jsの標準ライブラリによくある、引数の末尾でコールバック関数を渡す形式の関数が対象となります。
1 2 3 4 |
fs.readFile( "myfile.txt", function ( error, data ) { if ( error ) throw error; console.log( data ); } ); |
以下のようにすることで、簡単にPromiseを返す関数を生成することができます。
ベタ書きでも書けないことはないですが、Promise化する度に似たことを書くのであれば、冗長なので、用意された関数を使いましょう。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
const Promise = require( "bluebird" ); const fs = require( "fs" ); // promisifyを使えば、Promiseを返す関数を1行で作成できる const readFile = Promise.promisify( fs.readFile ); // 同じ関数を手書きで作成すると・・・ function myReadFile( ...args ) { return new Promise( function ( resolve, reject ) { fs.readFile( ...args, function ( error, data ) { if ( error ) reject( error ); else resolve( data ); } ); } ); } readFile( "myfile.txt", "utf8" ).then( function( data ) { console.log( data ); } ); |
また、ひとつのオブジェクトに含まれるすべての関数を一度にPromiseを返す関数にする、promisifyAllという関数もあります。
Node.jsではコールバック関数で結果を返す関数が多いため、一気に変換できるのは便利です。
1 2 3 4 5 6 7 8 |
const Promise = require( "bluebird" ); const fs = Promise.promisifyAll( require( "fs" ) ); // デフォルトではAsyncというサフィックスでPromiseを返す関数が追加される // オプションでサフィックスは変更可能 fs.readFileAsync( "myfile.txt", "utf8" ).then( function( data ) { console.log( data ); } ); |
以下のように、予めpromisifyAllしたソースを用意しておくと、毎回しなくて良いので楽です。
1 2 |
const Promise = require( "bluebird" ); module.exports = Promise.promisifyAll( require( "fs" ) ); |
promisify、promisifyAllの詳しい説明は、以下からご覧になれます。
キー・ポイントでは、どんどん便利な書き方を取り入れるエンジニアを募集しています。