mirror of
https://github.com/oxc-project/oxc.git
synced 2026-11-04 10:29:58 +00:00
feat(oxlint): support allow option for prefer-promise-reject-errors (#20934)
Add the TypeScript rule config surface for the new `allow` specifier option and extend the oxlint CLI fixture to verify the option end to end. Tested with: - `cargo test -p oxc_linter prefer_promise_reject_errors -- --nocapture` - `cargo test -p oxlint test_tsgolint_rule_options -- --nocapture` - `node --run fmt` AI usage disclosure: Codex was used to implement the config support, add the CLI fixture coverage, and prepare this PR. The changes were reviewed in the local workspace before submission.
This commit is contained in:
1 parent
a04f405cbe
commit
0b84de1c1a
4 files changed
+85
-51
No files matched your search
@@ -32,6 +32,16 @@
|
||||
]
|
||||
}
|
||||
],
|
||||
"typescript/prefer-promise-reject-errors": [
|
||||
"error",
|
||||
{
|
||||
"allow": [
|
||||
{ "from": "file", "name": "AllowedRejection" }
|
||||
],
|
||||
"allowThrowingAny": false,
|
||||
"allowThrowingUnknown": false
|
||||
}
|
||||
],
|
||||
"typescript/no-unnecessary-type-assertion": [
|
||||
"error",
|
||||
{
|
||||
|
||||
@@ -46,6 +46,16 @@ const allowedSpread = { ...allowedFunc };
|
||||
// This SHOULD error because notAllowedFunc is NOT in the allow list
|
||||
const notAllowedSpread = { ...notAllowedFunc };
|
||||
|
||||
// Test prefer-promise-reject-errors with allow option
|
||||
class AllowedRejection {}
|
||||
class NotAllowedRejection {}
|
||||
|
||||
// This should NOT error because AllowedRejection is in the allow list
|
||||
Promise.reject(new AllowedRejection());
|
||||
|
||||
// This SHOULD error because NotAllowedRejection is NOT in the allow list
|
||||
Promise.reject(new NotAllowedRejection());
|
||||
|
||||
// Test no-unnecessary-type-assertion with checkLiteralConstAssertions option
|
||||
// When checkLiteralConstAssertions is true, this SHOULD error
|
||||
const literalConst = 'hello' as const;
|
||||
|
||||
+58
-50
@@ -23,97 +23,105 @@ working directory: fixtures/cli/tsgolint_rule_options
|
||||
`----
|
||||
help: Did you forget to call the function?
|
||||
|
||||
x typescript-eslint(prefer-promise-reject-errors): Expected the Promise rejection reason to be an Error.
|
||||
,-[test.ts:57:1]
|
||||
56 | // This SHOULD error because NotAllowedRejection is NOT in the allow list
|
||||
57 | Promise.reject(new NotAllowedRejection());
|
||||
: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
58 |
|
||||
`----
|
||||
|
||||
x typescript-eslint(no-unsafe-member-access): Unsafe member access .bar on an `any` value.
|
||||
,-[test.ts:58:31]
|
||||
57 | // This SHOULD error because it's not using optional chaining
|
||||
58 | const unsafeAccess = anyValue.bar;
|
||||
,-[test.ts:68:31]
|
||||
67 | // This SHOULD error because it's not using optional chaining
|
||||
68 | const unsafeAccess = anyValue.bar;
|
||||
: ^^^
|
||||
59 |
|
||||
69 |
|
||||
`----
|
||||
|
||||
x typescript-eslint(no-base-to-string): 'unknownValue' may use Object's default stringification format ('[object Object]') when stringified.
|
||||
,-[test.ts:63:20]
|
||||
62 | // This SHOULD error because checkUnknown is true
|
||||
63 | const unknownStr = unknownValue.toString();
|
||||
,-[test.ts:73:20]
|
||||
72 | // This SHOULD error because checkUnknown is true
|
||||
73 | const unknownStr = unknownValue.toString();
|
||||
: ^^^^^^^^^^^^
|
||||
64 |
|
||||
74 |
|
||||
`----
|
||||
help: Consider picking a property (e.g. `user.name`), using a formatter (or `JSON.stringify`), or implementing a custom `toString()`/`toLocaleString()` on the type.
|
||||
|
||||
x typescript-eslint(no-unnecessary-condition): Unnecessary conditional, value is always truthy.
|
||||
,-[test.ts:68:5]
|
||||
67 | // This SHOULD error because this object is always truthy
|
||||
68 | if (alwaysTruthyObject) {
|
||||
,-[test.ts:78:5]
|
||||
77 | // This SHOULD error because this object is always truthy
|
||||
78 | if (alwaysTruthyObject) {
|
||||
: ^^^^^^^^^^^^^^^^^^
|
||||
69 | result += 1;
|
||||
79 | result += 1;
|
||||
`----
|
||||
|
||||
x typescript-eslint(consistent-type-exports): Type export ExportOnlyType is not a value and should be exported using `export type`.
|
||||
,-[test.ts:81:1]
|
||||
80 | // This SHOULD error because ExportOnlyType is only used as a type.
|
||||
81 | export { ExportOnlyType, exportOnlyValue };
|
||||
,-[test.ts:91:1]
|
||||
90 | // This SHOULD error because ExportOnlyType is only used as a type.
|
||||
91 | export { ExportOnlyType, exportOnlyValue };
|
||||
: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
82 |
|
||||
92 |
|
||||
`----
|
||||
|
||||
x typescript-eslint(strict-void-return): Value returned in a context where a void return is expected.
|
||||
,-[test.ts:89:25]
|
||||
88 | // This SHOULD error because returning string is not allowed in a void callback
|
||||
89 | takesVoidCallback(() => 'not-void');
|
||||
: ^^^^^^^^^^
|
||||
90 |
|
||||
`----
|
||||
,-[test.ts:99:25]
|
||||
98 | // This SHOULD error because returning string is not allowed in a void callback
|
||||
99 | takesVoidCallback(() => 'not-void');
|
||||
: ^^^^^^^^^^
|
||||
100 |
|
||||
`----
|
||||
|
||||
x typescript-eslint(prefer-readonly-parameter-types): Parameter should be a readonly type.
|
||||
,-[test.ts:92:27]
|
||||
91 | // Test prefer-readonly-parameter-types options
|
||||
92 | function takesAllowedType(input: RegExp): void {
|
||||
: ^^^^^^^^^^^^^
|
||||
93 | console.log(input.source);
|
||||
`----
|
||||
,-[test.ts:102:27]
|
||||
101 | // Test prefer-readonly-parameter-types options
|
||||
102 | function takesAllowedType(input: RegExp): void {
|
||||
: ^^^^^^^^^^^^^
|
||||
103 | console.log(input.source);
|
||||
`----
|
||||
|
||||
x typescript-eslint(prefer-readonly-parameter-types): Parameter should be a readonly type.
|
||||
,-[test.ts:101:32]
|
||||
100 | // This SHOULD error because parameter type is mutable
|
||||
101 | function takesMutableParameter(input: MutableParameter): void {
|
||||
,-[test.ts:111:32]
|
||||
110 | // This SHOULD error because parameter type is mutable
|
||||
111 | function takesMutableParameter(input: MutableParameter): void {
|
||||
: ^^^^^^^^^^^^^^^^^^^^^^^
|
||||
102 | console.log(input.value);
|
||||
112 | console.log(input.value);
|
||||
`----
|
||||
|
||||
x typescript-eslint(prefer-readonly): Member 'handler' is never reassigned; mark it as `readonly`.
|
||||
,-[test.ts:107:3]
|
||||
106 | class PreferReadonlyOptionExample {
|
||||
107 | private handler = () => 1;
|
||||
,-[test.ts:117:3]
|
||||
116 | class PreferReadonlyOptionExample {
|
||||
117 | private handler = () => 1;
|
||||
: ^^^^^^^^^^^^^^^
|
||||
108 | getValue() {
|
||||
118 | getValue() {
|
||||
`----
|
||||
|
||||
x typescript-eslint(prefer-string-starts-ends-with): Use 'String#startsWith' method instead.
|
||||
,-[test.ts:118:28]
|
||||
117 | // This SHOULD error because startsWith is preferred here
|
||||
118 | const boundarySliceMatch = boundaryText.slice(0, 3) === 'foo';
|
||||
,-[test.ts:128:28]
|
||||
127 | // This SHOULD error because startsWith is preferred here
|
||||
128 | const boundarySliceMatch = boundaryText.slice(0, 3) === 'foo';
|
||||
: ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
119 |
|
||||
129 |
|
||||
`----
|
||||
|
||||
x typescript-eslint(consistent-return): Function 'maybeReturnValue' expected a return value.
|
||||
,-[test.ts:126:3]
|
||||
125 | // This SHOULD be treated as an unspecified return with the option enabled
|
||||
126 | return undefined;
|
||||
,-[test.ts:136:3]
|
||||
135 | // This SHOULD be treated as an unspecified return with the option enabled
|
||||
136 | return undefined;
|
||||
: ^^^^^^^^^^^^^^^^^
|
||||
127 | }
|
||||
137 | }
|
||||
`----
|
||||
|
||||
x typescript-eslint(dot-notation): ["name"] is better written in dot notation.
|
||||
,-[test.ts:145:19]
|
||||
144 | // This SHOULD error because static property access should use dot notation
|
||||
145 | dotNotationSimple['name'];
|
||||
,-[test.ts:155:19]
|
||||
154 | // This SHOULD error because static property access should use dot notation
|
||||
155 | dotNotationSimple['name'];
|
||||
: ^^^^^^
|
||||
146 |
|
||||
156 |
|
||||
`----
|
||||
|
||||
Found 0 warnings and 13 errors.
|
||||
Finished in <variable>ms on 1 file with 15 rules using 1 threads.
|
||||
Found 0 warnings and 14 errors.
|
||||
Finished in <variable>ms on 1 file with 16 rules using 1 threads.
|
||||
----------
|
||||
CLI result: LintFoundErrors
|
||||
----------
|
||||
@@ -2,7 +2,10 @@ use oxc_macros::declare_oxc_lint;
|
||||
use schemars::JsonSchema;
|
||||
use serde::{Deserialize, Serialize};
|
||||
|
||||
use crate::rule::{DefaultRuleConfig, Rule};
|
||||
use crate::{
|
||||
rule::{DefaultRuleConfig, Rule},
|
||||
utils::TypeOrValueSpecifier,
|
||||
};
|
||||
|
||||
#[derive(Debug, Default, Clone, Deserialize)]
|
||||
pub struct PreferPromiseRejectErrors(Box<PreferPromiseRejectErrorsConfig>);
|
||||
@@ -10,6 +13,9 @@ pub struct PreferPromiseRejectErrors(Box<PreferPromiseRejectErrorsConfig>);
|
||||
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, JsonSchema, Default)]
|
||||
#[serde(rename_all = "camelCase", default, deny_unknown_fields)]
|
||||
pub struct PreferPromiseRejectErrorsConfig {
|
||||
/// An array of type or value specifiers for additional types that are allowed
|
||||
/// as Promise rejection reasons.
|
||||
pub allow: Vec<TypeOrValueSpecifier>,
|
||||
/// Whether to allow calling `Promise.reject()` with no arguments.
|
||||
pub allow_empty_reject: bool,
|
||||
/// Whether to allow rejecting Promises with values typed as `any`.
|
||||
|
||||
Reference in new issue
Block a user