这可能是什么? [TsLint错误:"必须妥善处理承诺"]

时间:2017-05-15 12:57:56

标签: javascript typescript asynchronous exception tslint

我在TypeScript中使用async/await进行了一些基本的异步操作,但是TSLint正在为下面这两个函数抛出神秘的错误消息。有没有人遇到过这些错误?在错误输出上没有提到管理规则,所以我不明白造成这些规则的原因。任何想法都将不胜感激。

主要要求:

import * as rp from 'request-promise'

export function getRequest(address: rp.Options): rp.RequestPromise {
  return rp(address)
}

导出异步功能:

export async function getStatus(message: Message) {
  try {
    const res = await getRequest(address)
    if (res.ready) {
      message.reply('...')
    } else {
      message.reply('...')
    }
  } catch (err) {
    message.reply(err)
  }
}

第3行获得Promises must be handled appropriatelyawait of non-Promise

使用此导出的简单函数是:

client.on('message', message => {
  if (message.content === 'green') {
    getStatus(message)
  }
})

这也得到Promises must be handled appropriately

其他信息:

即使错误消息没有提及,这似乎是Promises must be handled appropriately的管理规则: https://palantir.github.io/tslint/rules/no-floating-promises/

此问题提及await of non-Promisehttps://github.com/palantir/tslint/issues/2661

6 个答案:

答案 0 :(得分:50)

这是一个糟糕的错误消息。一个更好的可能是,

Promise类型的每个表达式必须以调用.catch或使用拒绝处理程序调用{​​{1}} source)结束

所以,例如,如果你这样做

.then

那么你仍然会遇到一个tslint问题,因为PromiseFunction() .catch(err => handle(err)) .then(() => console.log('this will succeed')) 的类型是一个承诺,它必须以一个catch结束。修复程序将附加.then(...)子句,例如

.catch

或通过以下方式禁用该行的tslint:

PromiseFunction()
  .catch(err => handle(err))
  .then(() => console.log('this will succeed'))
  .catch(() => 'obligatory catch')

或者,您可以颠倒PromiseFunction() .catch(err => handle(err)) // tslint:disable-next-line:no-unsafe-any .then(() => console.log('this will succeed')) .then语句的顺序。但是,如果发生错误,则会阻止.catch执行,如果遇到此问题,您可能会想要这样做。

答案 1 :(得分:12)

有时您可能想称呼诺言,但是您不需要对响应做任何事情。路线更改或其他内容。

所以而不是:

promiseFunction().then().catch()
try/catch async/await

您可以这样做:

void promiseFunction();

答案 2 :(得分:4)

您的getStatus函数被定义为返回一个承诺:

// All functions marked as async returns a promise:
async function getStatus(message: Message) {/* ... */}

但你打电话给getStatus而没有打电话给他们:

getStatus(message)

因此编译器认为您忘记处理异步代码。您只需拨打.then()

即可
getStatus(message).then(() => console.log('done'));

答案 3 :(得分:2)

当我使用firebase-function

创建firebase-tool时,我遇到了同样的异常
const ref = admin.database().ref("path/to/database/object");

ref.once("value").catch(error =>{  // line 22
    response.send( error() );
}).then( snapshot =>{
    response.send( snapshot.val );
})

此代码未编译且return

ERROR: /src/index.ts[22, 5]: Promises must be handled appropriately

我更改了catchthen的位置。

ref.once(...).then(...).catch(...)

此代码有效,对不起,但我没有任何解释

当应用返回一些没有catch阻止的错误时,甚至根据firebase doc未提及catch是必需的。

答案 4 :(得分:1)

我认为这个问题可以通过等待getStatus函数来修复,因为它是一个异步函数。消息说清楚,但行号会引起混淆。说实话,我也花了一些时间。

您可以通过以下代码更改来解决此lint错误:

client.on('message', message => {
 if (message.content === 'green') {
   await getStatus(message)
}});

在我看来,关闭这些特定错误并不是一个好主意。它们很有用,因为在另一种方式中,您不会运行代码异步。

答案 5 :(得分:1)

如果您要使用typescript-eslint编写一个无效的异步函数,那么在不等待的情况下编写异步函数就会引起抱怨,这很容易忘记,尤其是对于函数的最后一行。

const sendSyncPlayCommandToWatchers = async (): Promise<void> => {
  ...
  someAsyncFunction()
}

你会得到

错误承诺必须得到适当处理@ typescript-eslint / no-floating-promises

您需要将await关键字添加到最后一行(或确保按照前面的答复中所述,使用try / catch来处理诺言

const sendSyncPlayCommandToWatchers = async () => {
  ...
  await someAsyncFunction()
}

我认为这也将有助于在调试时获得更好的堆栈跟踪。