【问题标题】:Resolve promise inside another promise在另一个 Promise 中解决 Promise
【发布时间】:2023-03-31 21:33:01
【问题描述】:

我是 Promise 的新手,在掌握如何将两个 Promise 组合在一起时遇到了一些麻烦。我有一个函数可以解决一个承诺并执行一些任务:

loginService (context, credentials) {
  context.$http.post(LOGIN_URL, credentials, { emulateJSON: true}).then(response => {
    this.user.authenticated = true
    localStorage.setItem(TOKEN_STORAGE_NAME, response.body[TOKEN_NAME])
  }).catch(response => {
    context.error = response.body
  })
},

我想修改上面的代码,以便我可以执行以下操作:

login () {
  this.submitButtonLoading = true
  loginService(this, this.credentials).then(response => {
    this.submitButtonLoading = false
    // Do something else here.
  }).catch(response => {
    this.submitButtonLoading = false
    // Do something else here.
  })
}

处理这个问题的正确方法是什么?

【问题讨论】:

  • 你的函数需要return语句。

标签: javascript promise es6-promise vuejs2 vue-resource


【解决方案1】:

要让 loginService 成为一个承诺,只需在函数内返回一个 Promise。确保在您的功能完成时调用resolve 和/或reject。

在您的示例中,您可以:

var loginService = function(context, credentials) {
  return new Promise( (resolve, reject) => {
    context.$http.post(LOGIN_URL, credentials, {emlateJSON: true})
      .then(response => {
        if (success) {
          this.user.authenticated = true
          resolve(this.user)
        } else {
          reject(new Error('Log in failed'))
        }
      })
      .catch(err => {
        reject(err)
      })
    })
 }

现在可以了。

请注意,整个函数实际上只是返回一个很大的 Promise。还要注意成功或失败是如何解决或拒绝的。

【讨论】:

  • $http.post 方法似乎已经返回了一个承诺,这将使它成为一种反模式。
  • 谢谢@Traktor53 我开始沿着这条路线走,并意识到它可能是。
【解决方案2】:

从loginService返回promise,然后你可以继续链接:

loginService (context, credentials) {
  return context.$http.post(LOGIN_URL, credentials, { emulateJSON: true})
    .then(response => {
      this.user.authenticated = true
      localStorage.setItem(TOKEN_STORAGE_NAME, response.body[TOKEN_NAME])
    })
    .catch(response => {
      context.error = response.body
    })
}

login () {
  this.submitButtonLoading = true
  loginService(this, this.credentials)
    .then(_ => {
      this.submitButtonLoading = false
      // ...
    })
}

注意login中的then()函数,无论调用成功与否,都会一直执行。

【讨论】:

  • 完美,谢谢!我曾尝试过,但无法区分它是否成功。有没有办法处理它是否存在?
  • @hatzipani 是一个在 Promise 链中任何地方抛出的未捕获的错误,如果存在,将直接传播到 catch 处理程序。否则错误会被默默吞下,所以请始终使用catch。
  • @JaredSmith 谢谢!能发个例子吗?
  • 要修复只调用login 中的then 处理程序,请在第一个catch 处理程序中重新抛出错误以触发login 中的第二个catch。换句话说,尝试在context.error=response.body; 之后插入throw response;
  • 太棒了!这正是我想要的。太感谢了。现在去研究一下这一切的内部运作。
猜你喜欢
  • 2019-08-03
  • 1970-01-01
  • 2018-01-24
  • 1970-01-01
  • 1970-01-01
  • 2019-07-05
  • 2017-06-21
  • 2018-02-06
相关资源
最近更新 更多