関数doRequest(options)
があるとします。これはHTTPリクエストを実行することになっており、そのためにhttp.request()
を使用します。
doRequest()
がループ内で呼び出される場合、次の要求が前の完了(シリアル実行、次々に)の後に行われるようにします。コールバックとPromiseを混乱させないために、async/awaitパターンを使用します(Node 6+)で実行するBabel.jsでコンパイルされます)。
ただし、応答オブジェクトがさらに処理されるのを待つ方法と、doRequest()
の結果としてそれを返す方法は、私には不明です。
_var doRequest = async function (options) {
var req = await http.request(options);
// do we need "await" here somehow?
req.on('response', res => {
console.log('response received');
return res.statusCode;
});
req.end(); // make the request, returns just a boolean
// return some result here?!
};
_
HTTPリクエストにさまざまなオプションを使用してmochaを使用して現在のコードを実行すると、すべてのリクエストが同時に行われるようです。おそらくdoRequest()
が実際には何も返さないため、これらはすべて失敗します。
_describe('Requests', function() {
var t = [ /* request options */ ];
t.forEach(function(options) {
it('should return 200: ' + options.path, () => {
chai.assert.equal(doRequest(options), 200);
});
});
});
_
async/await
promiseで動作します。 async
関数であるawait
ingがPromiseを返す場合にのみ機能します。
問題を解決するには、request-promise
などのライブラリを使用するか、doRequest
関数からプロミスを返すことができます。
後者を使用したソリューションを次に示します。
function doRequest(options) {
return new Promise ((resolve, reject) => {
let req = http.request(options);
req.on('response', res => {
resolve(res);
});
req.on('error', err => {
reject(err);
});
});
}
describe('Requests', function() {
var t = [ /* request options */ ];
t.forEach(function(options) {
it('should return 200: ' + options.path, async function () {
try {
let res = await doRequest(options);
chai.assert.equal(res.statusCode, 200);
} catch (err) {
console.log('some error occurred...');
}
});
});
});
it関数にdoneを渡すことができるはずです。次に、非同期の要求が完了したら、アサートの後にdone()行を追加します。エラーがある場合は、done(myError)のように完了関数に渡します