使用 knex 的异步子查询

asynchronous sub-queries with knex

这里的问题不在于 knex,而是在于将它与 async/await 一起使用。顺便说一句,这是一个简单的例子:

const subquery = catchAsync(async () => {
  const res = await knex("author").select("id").where("id", ">", 1);

  return res;
});

const knexQuery = catchAsync(async () => {
  const res = await knex("author").where("id", "in", await subquery());

  return res;
});

const test = catchAsync(async (knexQuery) => {
  const res = await knexQuery();

  console.log(res)

  knex.destroy();
});

我不知道如何将 subquery 传递给 knexQuery 所以它会在适当的时候解决。目前它返回一个空数组,这里是调试日志:

{
  method: 'select',
  options: {},
  timeout: false,
  cancelOnTimeout: false,
  bindings: [ 1 ],
  __knexQueryUid: '00baf1e0-81a5-11ea-9b17-3bbd9f85a577',
  sql: 'select `id` from `author` where `id` > ?'
}
{
  method: 'select',
  options: {},
  timeout: false,
  cancelOnTimeout: false,
  bindings: [ { id: 2 }, { id: 3 }, { id: 4 } ],
  __knexQueryUid: '00bc7880-81a5-11ea-9b17-3bbd9f85a577',
  sql: 'select * from `author` where `id` in (?, ?, ?)'
}
(empty array)

我认为我 await 在所有正确的地方。显然我没有。我错过了什么?

注意:我特别感兴趣的是在这里使用 async/await,而不是承诺。

如果您需要 return 来自异步函数的查询构建器而不触发查询,您需要将构建器包装到一个对象中。

这里有一些链接,指向 knex 问题中一些相关的讨论 https://github.com/knex/knex/pull/2226#issuecomment-329589115

像这样:

const subquery = catchAsync(async () => {
  return {
    subQuery: knex("author").select("id").where("id", ">", 1)
  };
});

const knexQuery = catchAsync(async () => {
  const res = await knex("author").where("id", "in", (await subquery()).subQuery);

  return res;
});

const test = catchAsync(async (knexQuery) => {
  const res = await knexQuery();

  console.log(res)

  await knex.destroy();
});