首页 > 解决方案 > pg-promise:链接条件查询

问题描述

我正在尝试找到链接条件查询的正确方法。

这是一些伪代码来说明我的情况:

check whether the an item exists;
  if no:
    reply with status 404;
  if yes:
    check whether the user owns the item;
      if no:
        redirect to another page;
      if yes:
        retrieve the information about the item and render the page;

我的第一个直觉是使用任务来重用相同的连接,但由于可能的结果不同,我很难弄清楚如何正确处理承诺:

db.task(t => {
  return t.items.exists(itemId)
    .then(exists => {
      if (!exists) { // item does not exist
        // 404
      }

      return t.items.isOwner(itemId, userId)
        .then(isOwner => {
          if (!isOwner) {
            // redirect to some other page
          }

          return t.items.getById(itemId);
        })
    })
})
.then(data => {
  // OK, process data and render
})
.catch(console.error); // unexpected errors

例如,如果我尝试重定向到 404 页面,承诺仍将在之后得到解决。另一种方法是具有以下内容:

if (!exists) { // item does not exist
  return Promise.reject('404');
}

...

.then(data => {
  // OK, process data and render
}, reason => {
  // KO, conditions were not met to resolve
})

哪个“有效”,但同时捕获错误和未满足的条件。我希望有一个专门的“未满足条件”处理程序。

我想到的另一种方法:

var p = db.task(t => {
  return t.items.exists(itemId)
    .then(exists => {
      if (!exists) { // item does not exist
        //  resolve p (and break promise chain) with something like
        //  p.resolve(() => {
        //    return res.redirect...
        //  });
      }

      // else we can go on with the queries
      return t.items.isOwner(itemId, userId);
    }
    .then(isOwner => {
      if (!isOwner) {
        // resolve p and redirect to some other page
      }

      return t.items.getById(itemId);
    })
    .then(item => {
      // everything OK, resolve with a handler to render the page
    });
})
.then(action => {
  action();
})
.catch(console.error); // unexpected errors

但我看不出有什么办法可以解决pPromise.resolve(...)在嵌套的 Promise 中调用会在通过p's之前解决下一个 Promise 本身then

pg-promise在关注性能的同时链接条件查询和处理不同结果的推荐方法是什么?

标签: javascriptexpressbluebirdpg-promise

解决方案


看看这是否适合你。

这仍然需要项目通过每个承诺,直到它到达最后一个then块或catch块。

// First Condition
const input = 'test input'
Promise.resolve({ item: input })



  // Repeat this for different condition on `item.item` and change `X`
  /* REPEAT START */
  .then(data => {
    if (data.hitCondition != null && data.hitCondition !== '') {
      return data;
    }

    if (conditionX(data)) {
      return Object.assign({}, data, { 
        hitCondition: 'conditionX'
      });
    }

    return data;
  })
  /* REPEAT END */




  ...



  .then(result => {
    const { item, hitCondition } = result
    if (hitCondition != null && hitCondition !== '') {
      // at least one condition is met
      // check hitCondition to see which condition is hit
    } else {
      // none of the conditions are met
    }
  })
  .catch(error => {
    // Some error happened somewhere
    console.error(error);
  });


推荐阅读