Repository: palantir/tslint

Issue #3804: [Rule Request] no-promise-in-boolean-expressions
Created: 2018-04-02T11:40:40Z
We're working with a lot of async/await in our backend code, and the most frequent source of mistake I found in our code base has this shape:
if (user.pictures.exists()) doX()
whereas it should be
if (await user.pictures.exists()) doX()
I'm aware of the strict-boolean-expressions rule, but its ruleset is too strict for our code. So I'm suggesting to create a softer version which allows anything but promises in boolean expressions.

Duplicate issue #4115: no-floating-promises didn't catch an "error" that I think it should have .. 
Created: 2018-08-16T12:48:33Z
Bug Report

TSLint version:  5.11.0
TypeScript version:  2.9.2
Running TSLint via: (pick one) CLI / Node.js API / VSCode / grunt-tslint / Atom / Visual Studio / etc
via yarn script or within VSCode

TypeScript code being linted
async function passwordMatches(
  password: string,
  hashedPassword: string,
  hashType: EMemberHashType,
): Promise<boolean> {
  let doesPasswordMatch = false;
  ...const blah = await something();
  return doesPasswordMatch;
}

     // Do the basic password check
      if (!passwordMatches(password, member.password, hashType)) {
        authService.logger.trace(`user ${login} password did not match`);
        reject(new Error(INVALID_MESSAGE));
        return;
      }
with tslint.json configuration:
{
  "defaultSeverity": "error",
  "extends": [
    "tslint:recommended",
    "tslint-consistent-codestyle"
  ],
  "rules": {
    "eofline": true,
    "indent": [true, "spaces", 2],
    "quotemark": [true, "avoid-escape", "single"],
    "ban-types": [true, ["Object", "Use {} instead."], ["String", "Use string instead"], ["Number", "Use number instead"]],
    "member-access": [true, "no-public"],
    "no-inferrable-types": [true, "ignore-params"],
    "import-blacklist": [true, "lodash"],
    "no-internal-module": true,
    "no-non-null-assertion": true,
    "no-parameter-reassignment": true,
    "no-reference": true,
    "no-var-requires": true,
    "promise-function-async": true,
    "unified-signatures": true,
    "await-promise": true,
    "ban-comma-operator": true,
    "curly": true,
    "no-arg": true,
    "no-bitwise": true,
    "no-conditional-assignment": true,
    "no-construct": true,
    "no-console": [true, "log", "error"],
    "no-debugger": true,
    "no-duplicate-super": true,
    "no-duplicate-switch-case": true,
    "no-duplicate-variable": true,
    "no-empty": true,
    "no-eval": true,
    "no-floating-promises": true,
    "no-for-in-array": true,
    "no-inferred-empty-object-type": true,
    "no-invalid-template-strings": true,
    "no-misused-new": true,
    "no-object-literal-type-assertion": true,
    "no-return-await": true,
    "no-sparse-arrays": true,
    "no-string-literal": true,
    "no-string-throw": true,
    "no-switch-case-fall-through": true,
    "no-this-assignment": [true, { "allow-destructuring": true }],
    "no-unnecessary-class": [true, "allow-constructor-only"],
    "no-unsafe-any": true,
    "no-unused": true,
    "no-unused-expression": true,
    "no-use-before-declare": true,
    "no-var-keyword": true,
    "prefer-object-spread": true,
    "radix": true,
    "restrict-plus-operands": true,
    "triple-equals": true,
    "use-isnan": true,
    "cyclomatic-complexity": [true, 15],
    "deprecation": true,
    "linebreak-style": [true, "LF"],
    "max-classes-per-file": [true, 1],
    "max-file-line-count": [true, 300],
    "max-line-length": [true, 160],
    "no-duplicate-imports": true,
    "prefer-const": true,
    "trailing-comma": [true, {"multiline": "always", "singleline": "never"}],
    "arrow-return-shorthand": true,
    "class-name": true,
    "import-spacing": true,
    "interface-name": [true, "always-prefix"],
    "new-parens": true,
    "no-consecutive-blank-lines": true,
    "no-irregular-whitespace": true,
    "no-trailing-whitespace": true,
    "no-unnecessary-callback-wrapper": true,
    "one-variable-per-declaration": true,
    "prefer-method-signature": true,
    "prefer-template": true,
    "semicolon": [true, "always"],
    "space-before-function-paren": [true, {"asyncArrow": "always", "named": "never"}],
    "variable-name": [true, "ban-keywords", "check-format", "allow-leading-underscore"],
    "whitespace": [
        true,
        "check-branch",
        "check-decl",
        "check-module",
        "check-separator",
        "check-operator",
        "check-typecast",
        "check-rest-spread",
        "check-type",
        "check-typecast",
        "check-type-operator",
        "check-preblock"
    ]
  }
}
Actual behavior
No errors or warnings
Expected behavior
Some warning message about using a return of a Promise in a boolean expression?   This caused a large security hole not doing the await on the function ...

Closing comment (2018-09-03T12:39:02Z): Closing since this appears to be a dup of #3804 and #3983.