Skip to content

Commit a3b6695

Browse files
authored
feat: add should-be-fine support for flat configs (#343)
1 parent 622c191 commit a3b6695

File tree

5 files changed

+156
-44
lines changed

5 files changed

+156
-44
lines changed

.eslint-doc-generatorrc.js

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
/** @type {import('eslint-doc-generator').GenerateOptions} */
2+
const config = {
3+
ignoreConfig: [
4+
'all',
5+
'flat/all',
6+
'flat/recommended',
7+
],
8+
};
9+
10+
module.exports = config;

README.md

+26-2
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,17 @@ This library has a required `peerDependencies` listing for [`ESLint`](https://es
4747

4848
## Usage
4949

50+
> [!NOTE]
51+
>
52+
> `eslint.config.js` is supported, though most of the plugin documentation still
53+
> currently uses `.eslintrc` syntax; compatible versions of configs are available
54+
> prefixed with `flat/` and may be subject to small breaking changes while ESLint
55+
> v9 is being finalized.
56+
>
57+
> Refer to the
58+
> [ESLint documentation on the new configuration file format](https://eslint.org/docs/latest/use/configure/configuration-files-new)
59+
> for more.
60+
5061
Add `jest-dom` to the plugins section of your `.eslintrc.js` configuration file.
5162
You can omit the `eslint-plugin-` prefix:
5263

@@ -78,8 +89,7 @@ This plugin exports a recommended configuration that enforces good `jest-dom`
7889
practices _(you can find more info about enabled rules in
7990
[Supported Rules section](#supported-rules))_.
8091

81-
To enable this configuration use the `extends` property in your `.eslintrc.js`
82-
config file:
92+
To enable this configuration with `.eslintrc`, use the `extends` property:
8393

8494
```javascript
8595
module.exports = {
@@ -90,6 +100,20 @@ module.exports = {
90100
};
91101
```
92102

103+
To enable this configuration with `eslint.config.js`, use
104+
`jestDom.configs['flat/recommended']`:
105+
106+
```javascript
107+
module.exports = [
108+
{
109+
files: [
110+
/* glob matching your test files */
111+
],
112+
...require("eslint-plugin-jest-dom").configs["flat/recommended"],
113+
},
114+
];
115+
```
116+
93117
## Supported Rules
94118

95119
<!-- begin auto-generated rules list -->

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@
3131
"scripts": {
3232
"build": "kcd-scripts build",
3333
"pregenerate-readme-table": "npm run build",
34-
"generate-readme-table": "eslint-doc-generator --ignore-config all",
34+
"generate-readme-table": "eslint-doc-generator",
3535
"lint": "kcd-scripts lint",
3636
"lint:generate-readme-table": "npm run generate-readme-table -- --check",
3737
"setup": "npm install && npm run validate -s",

src/__tests__/index.test.js

+74-15
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,81 @@
1-
import { generateRecommendedConfig, rules } from "../";
1+
import plugin, { configs, rules } from "../";
2+
3+
it("includes the configs and rules on the plugin", () => {
4+
expect(plugin).toHaveProperty("configs", configs);
5+
expect(plugin).toHaveProperty("rules", rules);
6+
});
27

38
it("should have all the rules", () => {
4-
expect(Object.keys(rules).length).toBeGreaterThan(0);
9+
expect(Object.keys(rules)).toHaveLength(11);
510
});
611

7-
it.each(Object.keys(rules))("%s should export required fields", (ruleName) => {
8-
const rule = rules[ruleName];
9-
expect(rule).toHaveProperty("create", expect.any(Function));
10-
expect(rule.meta.docs.url).not.toBe("");
11-
expect(rule.meta.docs.category).toBe("Best Practices");
12-
expect(rule.meta.docs.description).not.toBe("");
12+
it.each(Object.entries(rules))(
13+
"%s should export required fields",
14+
(name, rule) => {
15+
expect(rule).toHaveProperty("create", expect.any(Function));
16+
expect(rule.meta.docs.url).not.toBe("");
17+
expect(rule.meta.docs.category).toBe("Best Practices");
18+
expect(rule.meta.docs.description).not.toBe("");
19+
}
20+
);
21+
22+
it("has the expected recommended config", () => {
23+
expect(configs.recommended).toMatchInlineSnapshot(`
24+
Object {
25+
plugins: Array [
26+
jest-dom,
27+
],
28+
rules: Object {
29+
jest-dom/prefer-checked: error,
30+
jest-dom/prefer-empty: error,
31+
jest-dom/prefer-enabled-disabled: error,
32+
jest-dom/prefer-focus: error,
33+
jest-dom/prefer-in-document: error,
34+
jest-dom/prefer-required: error,
35+
jest-dom/prefer-to-have-attribute: error,
36+
jest-dom/prefer-to-have-class: error,
37+
jest-dom/prefer-to-have-style: error,
38+
jest-dom/prefer-to-have-text-content: error,
39+
jest-dom/prefer-to-have-value: error,
40+
},
41+
}
42+
`);
1343
});
1444

15-
it("should have a recommended config with recommended rules", () => {
16-
expect(
17-
generateRecommendedConfig({
18-
good: { meta: { docs: { recommended: true } } },
19-
bad: { meta: { docs: { recommended: false } } },
20-
})
21-
).toEqual({ "jest-dom/good": "error" });
45+
it("has the expected recommended flat config", () => {
46+
const expectJestDomPlugin = expect.objectContaining({
47+
meta: {
48+
name: "eslint-plugin-jest-dom",
49+
version: expect.any(String),
50+
},
51+
});
52+
53+
expect(configs["flat/recommended"]).toMatchInlineSnapshot(
54+
{ plugins: { "jest-dom": expectJestDomPlugin } },
55+
`
56+
Object {
57+
plugins: Object {
58+
jest-dom: ObjectContaining {
59+
meta: Object {
60+
name: eslint-plugin-jest-dom,
61+
version: Any<String>,
62+
},
63+
},
64+
},
65+
rules: Object {
66+
jest-dom/prefer-checked: error,
67+
jest-dom/prefer-empty: error,
68+
jest-dom/prefer-enabled-disabled: error,
69+
jest-dom/prefer-focus: error,
70+
jest-dom/prefer-in-document: error,
71+
jest-dom/prefer-required: error,
72+
jest-dom/prefer-to-have-attribute: error,
73+
jest-dom/prefer-to-have-class: error,
74+
jest-dom/prefer-to-have-style: error,
75+
jest-dom/prefer-to-have-text-content: error,
76+
jest-dom/prefer-to-have-value: error,
77+
},
78+
}
79+
`
80+
);
2281
});

src/index.js

+45-26
Original file line numberDiff line numberDiff line change
@@ -8,39 +8,58 @@
88
//------------------------------------------------------------------------------
99

1010
import requireIndex from "requireindex";
11+
import {
12+
name as packageName,
13+
version as packageVersion,
14+
} from "../package.json";
1115

1216
//------------------------------------------------------------------------------
1317
// Plugin Definition
1418
//------------------------------------------------------------------------------
1519

16-
// import all rules in src/rules
20+
// import all rules in src/rules and re-export them for .eslintrc configs
1721
export const rules = requireIndex(`${__dirname}/rules`);
1822

19-
export const generateRecommendedConfig = (allRules) =>
20-
Object.entries(allRules).reduce(
21-
(memo, [name, rule]) => ({
22-
...memo,
23-
...(rule.meta.docs.recommended ? { [`jest-dom/${name}`]: "error" } : {}),
24-
}),
25-
{}
26-
);
27-
28-
export const generateAllRulesConfig = (allRules) =>
29-
Object.entries(allRules).reduce(
30-
(memo, [name]) => ({
31-
...memo,
32-
...{ [`jest-dom/${name}`]: "error" },
33-
}),
34-
{}
35-
);
36-
37-
export const configs = {
38-
recommended: {
39-
plugins: ["jest-dom"],
40-
rules: generateRecommendedConfig(rules),
23+
const allRules = Object.entries(rules).reduce(
24+
(memo, [name]) => ({
25+
...memo,
26+
...{ [`jest-dom/${name}`]: "error" },
27+
}),
28+
{}
29+
);
30+
31+
const recommendedRules = allRules;
32+
33+
const plugin = {
34+
meta: {
35+
name: packageName,
36+
version: packageVersion,
4137
},
42-
all: {
43-
plugins: ["jest-dom"],
44-
rules: generateAllRulesConfig(rules),
38+
configs: {
39+
recommended: {
40+
plugins: ["jest-dom"],
41+
rules: recommendedRules,
42+
},
43+
all: {
44+
plugins: ["jest-dom"],
45+
rules: allRules,
46+
},
4547
},
48+
rules,
49+
};
50+
51+
plugin.configs["flat/recommended"] = {
52+
plugins: { "jest-dom": plugin },
53+
rules: recommendedRules,
4654
};
55+
plugin.configs["flat/all"] = {
56+
plugins: { "jest-dom": plugin },
57+
rules: allRules,
58+
};
59+
60+
export default plugin;
61+
62+
// explicitly export config to allow using this plugin in CJS-based
63+
// eslint.config.js files without needing to deal with the .default
64+
// and also retain backwards compatibility with `.eslintrc` configs
65+
export const configs = plugin.configs;

0 commit comments

Comments
 (0)