@utilfirst/eslint-plugin 0.2.0 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/LICENSE CHANGED
@@ -22,8 +22,9 @@ SOFTWARE.
22
22
 
23
23
  Third-party notices
24
24
 
25
- The files under `src/rules/` other than `consistent-blank-lines.ts` and the
26
- files under `src/shared/` include adapted work from anti-slop:
25
+ Portions of this software are adapted from anti-slop
26
+ (https://github.com/dmmulroy/anti-slop) and are used under the following
27
+ license:
27
28
 
28
29
  MIT License
29
30
 
package/README.md CHANGED
@@ -37,6 +37,10 @@ export default [
37
37
  "error",
38
38
  { internalModulePrefixes: ["@workspace/"] },
39
39
  ],
40
+ "utilfirst/require-repository-test-subject": [
41
+ "error",
42
+ { internalModulePrefixes: ["@workspace/"] },
43
+ ],
40
44
  "utilfirst/no-positional-boolean-parameters": [
41
45
  "error",
42
46
  { allowFunctionNames: ["protocolCallback"] },
@@ -54,97 +58,79 @@ export default [
54
58
  ];
55
59
  ```
56
60
 
57
- - `internalModulePrefixes` marks package-style import prefixes as repository-owned for `no-module-mocking`.
61
+ - `internalModulePrefixes` marks package-style import prefixes as repository-owned for `no-module-mocking` and `require-repository-test-subject`.
58
62
  - `allowFunctionNames` preserves named functions whose positional boolean or multi-input signature is fixed by an external protocol.
59
63
  - `allowParameterNames` preserves `unknown` parameters whose names identify an externally fixed callback or interface signature.
60
64
 
61
- ```jsonc
62
- // .oxlintrc.json
63
- {
64
- "jsPlugins": [
65
- {
66
- "name": "utilfirst",
67
- "specifier": "@utilfirst/eslint-plugin",
68
- },
69
- ],
70
- "rules": {
71
- "utilfirst/consistent-blank-lines": "error",
72
- "utilfirst/no-chained-type-assertions": "error",
73
- "utilfirst/no-conditional-undefined-properties": "error",
74
- "utilfirst/no-enum-declarations": "error",
75
- "utilfirst/no-known-value-widening": "error",
76
- "utilfirst/no-module-mocking": [
77
- "error",
78
- { "internalModulePrefixes": ["@workspace/"] },
79
- ],
80
- "utilfirst/no-object-parameters": "error",
81
- "utilfirst/no-positional-boolean-parameters": [
82
- "error",
83
- { "allowFunctionNames": ["protocolCallback"] },
84
- ],
85
- "utilfirst/no-reflect-apply": "error",
86
- "utilfirst/no-reflect-get": "error",
87
- "utilfirst/no-unknown-parameters": [
88
- "error",
89
- { "allowParameterNames": ["externalPayload"] },
90
- ],
91
- "utilfirst/no-unknown-returns": "error",
92
- "utilfirst/no-unknown-type-aliases": "error",
93
- "utilfirst/no-unsafe-dictionary-type": "error",
94
- "utilfirst/no-unhandled-detached-promises": "error",
95
- "utilfirst/no-widen-then-assert": "error",
96
- "utilfirst/prefer-options-parameter": [
97
- "error",
98
- { "allowFunctionNames": ["protocolCallback"] },
99
- ],
100
- "utilfirst/prefer-switch-discriminator-chain": "error",
101
- "utilfirst/prefer-top-level-function-declarations": "error",
102
- "utilfirst/require-lint-suppression-reason": "error",
103
- "utilfirst/require-safety-comment-for-type-assertion": "error",
104
- },
105
- }
65
+ For Oxlint TypeScript configuration, import the canonical shared policy and layer repository and platform boundaries after it:
66
+
67
+ ```ts
68
+ // oxlint.config.ts
69
+ import { defineConfig } from "oxlint";
70
+ import { oxlintBaseConfig } from "@utilfirst/eslint-plugin/oxlint";
71
+
72
+ export default defineConfig({
73
+ extends: [oxlintBaseConfig],
74
+ ignorePatterns: ["dist/**", "node_modules/**"],
75
+ options: { reportUnusedDisableDirectives: "error" },
76
+ plugins: ["jsx-a11y", "nextjs", "node"],
77
+ });
106
78
  ```
107
79
 
80
+ The base config owns shared categories, environment defaults, plugins, compiler-diagnostic overrides, React settings, native rules, and every exported custom rule. Repositories retain root-only unused-disable reporting, ignore paths, platform plugins, platform environments, generated-file treatment, and reasoned exceptions.
81
+
108
82
  ## Rules
109
83
 
110
84
  [`docs/rules.md`](./docs/rules.md) explains the policy boundary and expected replacement for every rule. The implementations and colocated tests remain the executable behavior owners.
111
85
 
112
- | Rule | Description |
113
- | --------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------- |
114
- | [`consistent-blank-lines`](./docs/rules/consistent-blank-lines.md) | Insert blank lines between statement-list and JSXChild items that start a new thought |
115
- | [`no-chained-type-assertions`](./docs/rules.md#type-evidence) | Reject chained TypeScript assertions |
116
- | [`no-conditional-undefined-properties`](./docs/rules.md#object-and-api-construction) | Reject conditional undefined object properties |
117
- | [`no-enum-declarations`](./docs/rules.md#object-and-api-construction) | Reject repository-owned enums other than ambient declarations |
118
- | [`no-known-value-widening`](./docs/rules.md#type-evidence) | Reject known values widened into broad target types |
119
- | [`no-module-mocking`](./docs/rules.md#ownership-and-tests) | Reject Vitest and Jest mocking of repository-owned modules |
120
- | [`no-object-parameters`](./docs/rules.md#boundary-contracts) | Reject `object` function parameters |
121
- | [`no-positional-boolean-parameters`](./docs/rules.md#object-and-api-construction) | Reject positional boolean flags on named functions and methods |
122
- | [`no-reflect-apply`](./docs/rules.md#object-and-api-construction) | Reject `Reflect.apply` |
123
- | [`no-reflect-get`](./docs/rules.md#object-and-api-construction) | Reject `Reflect.get` |
124
- | [`no-unknown-parameters`](./docs/rules.md#boundary-contracts) | Keep explicit `unknown` parameters at decoding boundaries |
125
- | [`no-unknown-returns`](./docs/rules.md#boundary-contracts) | Reject `unknown` return contracts |
126
- | [`no-unknown-type-aliases`](./docs/rules.md#boundary-contracts) | Reject type aliases that resolve to `unknown` |
127
- | [`no-unsafe-dictionary-type`](./docs/rules.md#boundary-contracts) | Reject dictionary contracts with broad value types |
128
- | [`no-unhandled-detached-promises`](./docs/rules.md#async-errors) | Require rejection handling on `void`-marked detached call chains |
129
- | [`no-widen-then-assert`](./docs/rules.md#type-evidence) | Reject const flows that widen a known value before narrowing it |
130
- | [`prefer-options-parameter`](./docs/rules.md#object-and-api-construction) | Require options objects for named functions and methods with three or more inputs |
131
- | [`prefer-switch-discriminator-chain`](./docs/rules.md#object-and-api-construction) | Require a switch for four or more equality branches on one discriminator |
132
- | [`prefer-top-level-function-declarations`](./docs/rules.md#object-and-api-construction) | Require declarations for direct top-level function bindings and default exports |
133
- | [`require-lint-suppression-reason`](./docs/rules.md#lint-policy) | Require a forcing reason on lint disable directives |
134
- | [`require-safety-comment-for-type-assertion`](./docs/rules.md#type-evidence) | Require one `SAFETY:` comment for each outermost non-const assertion |
86
+ | Rule | Description |
87
+ | --------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------- |
88
+ | [`consistent-blank-lines`](./docs/rules/consistent-blank-lines.md) | Apply tight, separate, or preserved gaps between statements and JSX children |
89
+ | [`no-call-count-only-test`](./docs/rules.md#ownership-and-tests) | Reject tests supported only by mock call counts or omission |
90
+ | [`no-chained-type-assertions`](./docs/rules.md#type-evidence) | Reject chained TypeScript assertions |
91
+ | [`no-conditional-undefined-properties`](./docs/rules.md#object-and-api-construction) | Reject conditional undefined object properties |
92
+ | [`no-enum-declarations`](./docs/rules.md#object-and-api-construction) | Reject repository-owned enums other than ambient declarations |
93
+ | [`no-imported-constant-restatement`](./docs/rules.md#ownership-and-tests) | Require behavior evidence instead of imported constant restatements |
94
+ | [`no-known-value-widening`](./docs/rules.md#type-evidence) | Reject known values widened into broad target types |
95
+ | [`no-module-mocking`](./docs/rules.md#ownership-and-tests) | Reject Vitest and Jest mocking of repository-owned modules |
96
+ | [`no-negated-throw-assertion`](./docs/rules.md#ownership-and-tests) | Replace negated throw assertions with direct execution |
97
+ | [`no-object-parameters`](./docs/rules.md#boundary-contracts) | Reject `object` function parameters |
98
+ | [`no-positional-boolean-parameters`](./docs/rules.md#object-and-api-construction) | Reject positional boolean flags on directly named callable contracts |
99
+ | [`no-promise-settlement-only-assertion`](./docs/rules.md#ownership-and-tests) | Require a promise assertion to describe its result or specific failure |
100
+ | [`no-reflect-apply`](./docs/rules.md#object-and-api-construction) | Reject `Reflect.apply` |
101
+ | [`no-reflect-get`](./docs/rules.md#object-and-api-construction) | Reject `Reflect.get` |
102
+ | [`no-test-snapshots`](./docs/rules.md#ownership-and-tests) | Require explicit observable assertions instead of snapshots |
103
+ | [`no-truthy-falsy-assertion`](./docs/rules.md#ownership-and-tests) | Require exact expected values instead of truthiness |
104
+ | [`no-uncontrolled-time-in-test`](./docs/rules.md#ownership-and-tests) | Require clock control in each owning test or setup scope |
105
+ | [`no-unknown-parameters`](./docs/rules.md#boundary-contracts) | Keep `unknown` inputs at declared or input-consuming decoder boundaries |
106
+ | [`no-unknown-returns`](./docs/rules.md#boundary-contracts) | Reject `unknown` return contracts |
107
+ | [`no-unknown-type-aliases`](./docs/rules.md#boundary-contracts) | Reject type aliases that resolve to `unknown` |
108
+ | [`no-unsafe-dictionary-type`](./docs/rules.md#boundary-contracts) | Reject object and Map dictionary contracts with broad value types |
109
+ | [`no-unhandled-detached-promises`](./docs/rules.md#async-errors) | Require terminal rejection handling on `void`-marked detached chains |
110
+ | [`no-widen-then-assert`](./docs/rules.md#type-evidence) | Reject const flows that widen a known value before narrowing it |
111
+ | [`prefer-forwarded-props-order`](./docs/rules.md#react-source-form) | Put forwarded props before component-controlled JSX attributes |
112
+ | [`prefer-hook-order`](./docs/rules.md#react-source-form) | Order built-in hooks by context, state, derivation, and effect role |
113
+ | [`prefer-jsx-boolean-and`](./docs/rules.md#jsx-conditionals) | Require boolean JSX guards and normalize null-branch conditionals |
114
+ | [`prefer-options-parameter`](./docs/rules.md#object-and-api-construction) | Require options objects for named callable contracts with three or more inputs |
115
+ | [`prefer-react-props-reference`](./docs/rules.md#react-source-form) | Keep React props behind canonical access and bounded destructuring |
116
+ | [`prefer-switch-discriminator-chain`](./docs/rules.md#object-and-api-construction) | Require a switch for four or more equality branches on one discriminator |
117
+ | [`prefer-top-level-function-declarations`](./docs/rules.md#object-and-api-construction) | Require declarations for direct top-level function bindings and default exports |
118
+ | [`require-lint-suppression-reason`](./docs/rules.md#lint-policy) | Require a forcing reason on lint disable directives |
119
+ | [`require-repository-test-subject`](./docs/rules.md#ownership-and-tests) | Require behavioral tests to import repository-owned code |
120
+ | [`require-safety-comment-for-type-assertion`](./docs/rules.md#type-evidence) | Require one `SAFETY:` comment for each outermost non-const assertion |
121
+ | [`require-special-comment-tag`](./docs/rules.md#comments) | Require canonical uppercase tags and colons on special comments |
135
122
 
136
123
  ## Attribution
137
124
 
138
- The rules other than `consistent-blank-lines`, `no-conditional-undefined-properties`, `no-enum-declarations`, `no-positional-boolean-parameters`, `no-unhandled-detached-promises`, `prefer-options-parameter`, and `require-lint-suppression-reason`, along with their helpers, are adapted from [dmmulroy/anti-slop](https://github.com/dmmulroy/anti-slop/) under the MIT License. The package's [LICENSE](./LICENSE) retains the copyright and permission notice.
125
+ The rules other than `consistent-blank-lines`, `no-call-count-only-test`, `no-conditional-undefined-properties`, `no-enum-declarations`, `no-imported-constant-restatement`, `no-negated-throw-assertion`, `no-positional-boolean-parameters`, `no-promise-settlement-only-assertion`, `no-test-snapshots`, `no-truthy-falsy-assertion`, `no-uncontrolled-time-in-test`, `no-unhandled-detached-promises`, `prefer-forwarded-props-order`, `prefer-hook-order`, `prefer-jsx-boolean-and`, `prefer-options-parameter`, `prefer-react-props-reference`, `require-lint-suppression-reason`, `require-repository-test-subject`, and `require-special-comment-tag`, along with their helpers, are adapted from [dmmulroy/anti-slop](https://github.com/dmmulroy/anti-slop/) under the MIT License. The package's [LICENSE](./LICENSE) retains the copyright and permission notice.
139
126
 
140
127
  ## Develop
141
128
 
142
129
  ```sh
143
130
  pnpm install
144
- pnpm run setup-hooks # one-time: wire pre-commit via simple-git-hooks
145
- pnpm test # unit, dual-runtime, and packed-artifact tests
146
- pnpm run build # tsdown dist/
147
- pnpm run lint # oxlint + prettier + publint
131
+ pnpm test # unit, dual-runtime, and packed-artifact tests
132
+ pnpm run build # tsdown dist/
133
+ pnpm run lint # oxlint + prettier + publint
148
134
  ```
149
135
 
150
136
  ## License