Skip to content

/* eslint-expect-error */ — continuous verification of eslint config #14212

@jtbandes

Description

@jtbandes

(Forgive me if this has been discussed before, but I didn't find any issues or discussions about it.)

The problem you want to solve.

I'd like to be able to write examples of bad code in my project, and enforce that they continue to be rejected by eslint, to guard against accidental changes to eslint configs/rule implementations.

I'm not proposing this as a rule, because of the "atomic" requirement in the core rule guidelines. It's more of a meta-feature that lives outside the realm of specific rules, similar to existing ignore-directives.

Your take on the correct solution to problem.

A comment would be the simplest way to annotate expected warnings/errors, and would match nicely with the existing comments for eslint-disable:

a == b // eslint-expect-error             <-- expect any error to be raised
a == b // eslint-expect-error eqeqeq      <-- expect an error to be raised from a specific rule
a == b // eslint-expect-warning eqeqeq    <-- expect a warning to be raised
let a == b // eslint-expect-error eqeqeq, prefer-const   <-- expect two errors to be raised

// eslint-expect-error-next-line eqeqeq
a == b
// eslint-expect-warning-next-line eqeqeq
a == b

I think it would also be valuable to allow these assertions to mention the specific error message. This could be done with strings or regular expressions:

a == b // eslint-expect-error /^Expected '===' and instead saw '=='\.$/   <-- regex match
a == b // eslint-expect-error "Expected '==='"                            <-- substring match

It doesn't make as much sense to have an expected error at the whole file level; I think "same line" and "next line" options would be sufficient.

These checks would be run as part of the normal eslint execution. If an error/warning would normally be emitted that matches the expectation comment, instead nothing would be emitted (the check would be considered a success). If the expected error/warning was not raised on the indicated line, then an error would be emitted.

Variations/alternatives to consider

  • There could be a config option to choose whether expectation failures are errors or just warnings. Since this guards against configuration changes, I don't personally see much value in making errors a warning
  • There could also be a "no warning" comment, such as // eslint-expect-no-warning. I think this option would only be useful when applied to warnings — since "expect no error" is already how eslint behaves.
  • Instead of running during normal execution, there could be a separate --verify mode. Since it's likely that these expect-error comments would only be used in non-production code, it could make sense for the verification step to be a separate kind of eslint invocation. However, I thought this was a needlessly complicated design.

Prior art

  • TypeScript has // ts-expect-error comments (documentation, implementing PR). These are a part of the normal TS compilation process, not a separate mode. They don't allow you to specify exactly which error is expected, though that enhancement has been requested by the community.

  • The clang compiler has a -verify mode which uses special comments to indicate which diagnostic output is expected. A substring or regular expression can be used to match against the error text. For example:

    int A = B; // expected-error {{use of undeclared identifier 'B'}}

    Clang's verify mode also has some advanced features such as custom prefixes, which allows the same source file to provide test cases for different compiler invocations.

Are you willing to submit a pull request to implement this change?

If the team/community can agree on the details of the design, I'd be open to implementing this, though I would also like some guidance on where to make the changes.

Metadata

Metadata

Assignees

No one assigned

    Labels

    archived due to ageThis issue has been archived; please open a new issue for any further discussioncoreRelates to ESLint's core APIs and featuresenhancementThis change enhances an existing feature of ESLint

    Type

    No type

    Projects

    Status

    Complete

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions