node.js - Hur man hittar saknad Await på Async-funktionsanrop i Node+Typescript+VSCode?


Vi har släppt buggar i vår node-app eftersom vi glömde att prefixa async-funktionsanrop med "await".

Exempel :

const getUsers = async () => db.query('SELECT * from Users');

const testMissingAwait = async () => {
  const users = getUsers(); // <<< missing await
  console.log(users.length);
};

testMissingAwait();

Finns det ett enkelt sätt att hitta asynkrona funktionsanrop som saknar await-nyckelordet?

Om det misslyckas, hur mycket arbete skulle det vara att skriva ett Visual Studio Code-tillägg som automatiskt markerar dessa? (Jag är redo att ta itu med det om någon kan peka mig i rätt riktning).

Svar #1

TypeScript-kompilatorn erbjuder inte ett kompilatoralternativ för det. Däremot erbjuder TSLint 4.4 ett alternativ för att upptäcka flytande promises. Du kan läsa detta blogginlägg för ett mer detaljerat svar: Detect missing await in typescript

Ladda ner TSLint:

npm install -g tslint typescript

Konfigurera TSLint:

{
    "extends": "tslint:recommended",
    "rules": {
        "no-floating-promises": true
    }
}

Kör TSLint:

tslint --project tsconfig.json

Om det finns flytande löften i din kod bör du se följande fel:

FEL: F:/Samples/index.ts[12, 5]: Löften måste hanteras på rätt sätt

Svar #2

tslint är föråldrat men typescript-eslint har en regel för detta: no-floating-promises

Denna regel förbjuder användning av Promise-liknande värden i satser utan att hantera deras fel på ett lämpligt sätt ... Giltiga sätt att hantera en sats med ett Promise-värde inkluderar att awaita, returnera, och antingen anropa .then() med två argument eller .catch() med ett argument.

För att använda det behöver du konfigurera typescript-eslint:

  1. Installera beroenden

    npm install --save-dev eslint @typescript-eslint/parser @typescript-eslint/eslint-plugin
    
  2. Ändra din .eslintrc-fil

    Detta är de minsta nödvändiga inställningarna; se dokumentationen för fler alternativ (https://typescript-eslint.io/docs/linting/linting):

    {
      "parser": "@typescript-eslint/parser",
      "parserOptions": { "project": "./tsconfig.json" },
      "plugins": ["@typescript-eslint"],
      "rules": {
        "@typescript-eslint/no-floating-promises": ["error"]
      }
    }
    

Om det finns platser där du vill kalla en asynkron funktion utan att använda await, kan du antingen:

  • Använd void-operatorn som nämnts i dokumentationen för regeln, t.ex.

    void someAsyncFunction();
    
  • Eller ändra bara error till warn i .eslintrc-konfigurationen ovan

Nästa gång du kör eslint bör du se regeln tillämpas:

npm run lint
...
./src/database/database.ts
  219:7  warning  Promises must be awaited, end with a call to .catch, end with a call to .then with a rejection handler or be explicitly marked as ignored with the `void` operator  @typescript-eslint/no-floating-promises

Eftersom du nämnde VS Code specifikt, integreras detta också utmärkt med ESLint-pluginen:

Relaterade artiklar