Using Async/Await with Mongoose

Queries in Mongoose 4.x have a .then() function, so you don't need any extra work to use mongoose with async/await:

const mongoose = require('mongoose');
async function run() {
  // No need to `await` on this, mongoose 4 handles connection buffering
  // internally
  mongoose.connect('mongodb://localhost:27017/test');
  await mongoose.connection.dropDatabase();
  const MyModel = mongoose.model('Test', new mongoose.Schema({ name: String }));
  await MyModel.create({ name: 'Val' });
  // Prints an array with 1 element, the above document
  console.log(await MyModel.find());
}
run().catch(error => console.error(error.stack));

Async/await makes interacting with mongoose cursors much more elegant. While you still can use cursors as a stream with async/await, it's much more elegant to use the next() function. Fundamentally, a mongoose cursor is an object with a next() function that returns a promise which resolves to the next document in the query result, or null if there are no more documents.

const mongoose = require('mongoose');
async function run() {
  mongoose.connect('mongodb://localhost:27017/test');
  await mongoose.connection.dropDatabase();
  const MyModel = mongoose.model('Test', new mongoose.Schema({ name: String }));
  await MyModel.create({ name: 'Val' }, { name: 'Varun' });
  // A cursor has a `.next()` function that returns a promise. The promise
  // will resolve to the next doc if there is one, or null if they are no
  // more results.
  const cursor = MyModel.find().sort({name: 1 }).cursor();
  for (let doc = await cursor.next(); doc != null; doc = await cursor.next()) {
    // Prints "Val" followed by "Varun"
    console.log(doc.name);
  }
}
run().catch(error => console.error(error.stack));

Mongoose cursors also have a neat eachAsync() function that lets you do some rudimentary functional programming with async/await. The eachAsync() function executes a (potentially async) function for each document that the cursor returns. If that function returns a promise, it will wait for that promise to resolve before getting the next document. This is the easiest way to exhaust a cursor in mongoose.

const mongoose = require('mongoose');
async function run() {
  mongoose.connect('mongodb://localhost:27017/test');
  await mongoose.connection.dropDatabase();
  const MyModel = mongoose.model('Test', new mongoose.Schema({ name: String }));
  await MyModel.create({ name: 'Val' }, { name: 'Varun' });
  // A cursor has a `.next()` function that returns a promise. The promise
  // will resolve to the next doc if there is one, or null if they are no
  // more results.
  const cursor = MyModel.find().sort({name: 1 }).cursor();
  let count = 0;
  console.log(new Date());
  await cursor.eachAsync(async function(doc) {
    // Wait 1 second before printing first doc, and 0.5 before printing 2nd
    await new Promise(resolve => setTimeout(() => resolve(), 1000 - 500 * (count++)));
    console.log(new Date(), doc);
  });
}
run().catch(error => console.error(error.stack));
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • NAME dnsmasq - A lightweight DHCP and caching DNS server....
    ximitc閱讀 2,997評論 0 0

友情鏈接更多精彩內(nèi)容