eslint-plugin-code-style 1.0.10 → 1.0.14
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/README.md +993 -157
- package/index.js +110 -10
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
[](https://github.com/Mohamed-Elhawary/eslint-plugin-code-style/blob/main/LICENSE)
|
|
8
8
|
|
|
9
9
|
[](https://eslint.org/)
|
|
10
|
-
[](https://nodejs.org/)
|
|
11
11
|
[](https://react.dev/)
|
|
12
12
|
|
|
13
13
|
[](https://github.com/Mohamed-Elhawary/eslint-plugin-code-style/stargazers)
|
|
@@ -17,20 +17,69 @@
|
|
|
17
17
|
|
|
18
18
|
**A powerful ESLint plugin for enforcing consistent code formatting and style rules in React/JSX projects.**
|
|
19
19
|
|
|
20
|
-
*
|
|
20
|
+
*47 auto-fixable rules to keep your codebase clean and consistent*
|
|
21
|
+
|
|
22
|
+
</div>
|
|
23
|
+
|
|
24
|
+
<br />
|
|
25
|
+
|
|
26
|
+
## 🎯 Why This Plugin?
|
|
27
|
+
|
|
28
|
+
This plugin provides **rules that don't exist in ESLint's built-in rule set** and are **not available in popular third-party ESLint packages**. These are the style requirements that teams often check manually, making them easy to miss and hard to enforce consistently.
|
|
29
|
+
|
|
30
|
+
**Key Benefits:**
|
|
31
|
+
- **Fills the gaps** — Covers formatting rules that ESLint and other plugins miss
|
|
32
|
+
- **Works alongside existing tools** — Complements ESLint's built-in rules and packages like `eslint-plugin-react`, `eslint-plugin-import`, etc.
|
|
33
|
+
- **Consistency at scale** — Reduces code-style differences between team members by enforcing uniform formatting across your projects
|
|
34
|
+
- **Fully automated** — All 47 rules support auto-fix, eliminating manual style reviews
|
|
35
|
+
|
|
36
|
+
When combined with ESLint's native rules and other popular plugins, this package helps create a **complete code style solution** that keeps your codebase clean and consistent.
|
|
37
|
+
|
|
38
|
+
<div align="center">
|
|
21
39
|
|
|
22
40
|
<br />
|
|
23
41
|
|
|
24
42
|
[Installation](#-installation) •
|
|
25
43
|
[Quick Start](#-quick-start) •
|
|
44
|
+
[Recommended Configs](#-recommended-configurations) •
|
|
26
45
|
[Rules](#-rules-reference) •
|
|
27
|
-
[Examples](#-examples) •
|
|
28
46
|
[Contributing](#-contributing)
|
|
29
47
|
|
|
30
48
|
</div>
|
|
31
49
|
|
|
32
50
|
<br />
|
|
33
51
|
|
|
52
|
+
## 📁 Recommended Configurations
|
|
53
|
+
|
|
54
|
+
We provide **ready-to-use ESLint flat configuration files** that combine `eslint-plugin-code-style` with carefully selected third-party plugins and ESLint built-in rules. These configurations represent our battle-tested setup that reduces code-style differences by ~95%.
|
|
55
|
+
|
|
56
|
+
### 💡 Why Use These Configs?
|
|
57
|
+
|
|
58
|
+
- **Complete Coverage** — Combines ESLint built-in rules, third-party plugins, and all 47 code-style rules
|
|
59
|
+
- **Ready-to-Use** — Copy the config file and start linting immediately
|
|
60
|
+
- **Battle-Tested** — These configurations have been refined through real-world usage
|
|
61
|
+
- **Fully Documented** — Each config includes detailed instructions and explanations
|
|
62
|
+
|
|
63
|
+
### 📋 Available Configurations
|
|
64
|
+
|
|
65
|
+
| Configuration | Description | Link |
|
|
66
|
+
|---------------|-------------|------|
|
|
67
|
+
| **React** | React.js projects (JavaScript, JSX) | [View Config](./recommended-configs/react/) |
|
|
68
|
+
| **React + TS + Tailwind** | React + TypeScript + Tailwind CSS | *Coming Soon* |
|
|
69
|
+
| **Next.js + TS + Tailwind** | Next.js + TypeScript + Tailwind CSS | *Coming Soon* |
|
|
70
|
+
|
|
71
|
+
### ⚡ Quick Start with Recommended Config
|
|
72
|
+
|
|
73
|
+
1. Navigate to the [recommended-configs](./recommended-configs/) folder
|
|
74
|
+
2. Choose the configuration for your project type
|
|
75
|
+
3. Follow the installation instructions in the README
|
|
76
|
+
4. Copy the `eslint.config.js` to your project root
|
|
77
|
+
5. Run `eslint src/ --fix`
|
|
78
|
+
|
|
79
|
+
> **Note:** Each configuration includes a detailed README with installation commands, plugin explanations, and rule documentation.
|
|
80
|
+
|
|
81
|
+
<br />
|
|
82
|
+
|
|
34
83
|
---
|
|
35
84
|
|
|
36
85
|
<br />
|
|
@@ -41,13 +90,13 @@
|
|
|
41
90
|
<tr>
|
|
42
91
|
<td width="50%">
|
|
43
92
|
|
|
44
|
-
### Auto-Fixable Rules
|
|
45
|
-
All **
|
|
93
|
+
### 🔧 Auto-Fixable Rules
|
|
94
|
+
All **47 rules** support automatic fixing with `eslint --fix`. No manual code changes needed.
|
|
46
95
|
|
|
47
96
|
</td>
|
|
48
97
|
<td width="50%">
|
|
49
98
|
|
|
50
|
-
### React & JSX Support
|
|
99
|
+
### ⚛️ React & JSX Support
|
|
51
100
|
Built specifically for React projects with comprehensive JSX formatting rules.
|
|
52
101
|
|
|
53
102
|
</td>
|
|
@@ -55,13 +104,13 @@ Built specifically for React projects with comprehensive JSX formatting rules.
|
|
|
55
104
|
<tr>
|
|
56
105
|
<td width="50%">
|
|
57
106
|
|
|
58
|
-
### ESLint v9+ Ready
|
|
107
|
+
### ✅ ESLint v9+ Ready
|
|
59
108
|
Designed for ESLint's new flat config system. Modern and future-proof.
|
|
60
109
|
|
|
61
110
|
</td>
|
|
62
111
|
<td width="50%">
|
|
63
112
|
|
|
64
|
-
### Zero Dependencies
|
|
113
|
+
### 📭 Zero Dependencies
|
|
65
114
|
Lightweight plugin with no external dependencies. Fast and efficient.
|
|
66
115
|
|
|
67
116
|
</td>
|
|
@@ -83,12 +132,12 @@ pnpm add eslint-plugin-code-style -D
|
|
|
83
132
|
yarn add eslint-plugin-code-style -D
|
|
84
133
|
```
|
|
85
134
|
|
|
86
|
-
### Requirements
|
|
135
|
+
### 📋 Requirements
|
|
87
136
|
|
|
88
137
|
| Dependency | Version |
|
|
89
138
|
|------------|---------|
|
|
90
139
|
| **ESLint** | `>= 9.0.0` |
|
|
91
|
-
| **Node.js** | `>=
|
|
140
|
+
| **Node.js** | `>= 18.0.0` |
|
|
92
141
|
|
|
93
142
|
<br />
|
|
94
143
|
|
|
@@ -126,25 +175,27 @@ eslint src/ --fix
|
|
|
126
175
|
|
|
127
176
|
```javascript
|
|
128
177
|
rules: {
|
|
129
|
-
"code-style/absolute-imports-only": "error",
|
|
130
178
|
"code-style/array-items-per-line": "error",
|
|
131
179
|
"code-style/array-objects-on-new-lines": "error",
|
|
132
180
|
"code-style/arrow-function-block-body": "error",
|
|
133
181
|
"code-style/arrow-function-simple-jsx": "error",
|
|
134
182
|
"code-style/arrow-function-simplify": "error",
|
|
183
|
+
"code-style/curried-arrow-same-line": "error",
|
|
135
184
|
"code-style/assignment-value-same-line": "error",
|
|
136
185
|
"code-style/block-statement-newlines": "error",
|
|
137
186
|
"code-style/comment-spacing": "error",
|
|
138
|
-
"code-style/curried-arrow-same-line": "error",
|
|
139
|
-
"code-style/export-format": "error",
|
|
140
187
|
"code-style/function-call-spacing": "error",
|
|
141
188
|
"code-style/function-naming-convention": "error",
|
|
142
189
|
"code-style/function-params-per-line": "error",
|
|
143
190
|
"code-style/hook-callback-format": "error",
|
|
144
191
|
"code-style/hook-deps-per-line": "error",
|
|
145
192
|
"code-style/if-statement-format": "error",
|
|
193
|
+
"code-style/multiline-if-conditions": "error",
|
|
194
|
+
"code-style/absolute-imports-only": "error",
|
|
195
|
+
"code-style/export-format": "error",
|
|
146
196
|
"code-style/import-format": "error",
|
|
147
197
|
"code-style/import-source-spacing": "error",
|
|
198
|
+
"code-style/module-index-exports": "error",
|
|
148
199
|
"code-style/jsx-children-on-new-line": "error",
|
|
149
200
|
"code-style/jsx-closing-bracket-spacing": "error",
|
|
150
201
|
"code-style/jsx-element-child-new-line": "error",
|
|
@@ -155,9 +206,7 @@ rules: {
|
|
|
155
206
|
"code-style/jsx-string-value-trim": "error",
|
|
156
207
|
"code-style/jsx-ternary-format": "error",
|
|
157
208
|
"code-style/member-expression-bracket-spacing": "error",
|
|
158
|
-
"code-style/module-index-exports": "error",
|
|
159
209
|
"code-style/multiline-argument-newline": "error",
|
|
160
|
-
"code-style/multiline-if-conditions": "error",
|
|
161
210
|
"code-style/multiple-arguments-per-line": "error",
|
|
162
211
|
"code-style/nested-call-closing-brackets": "error",
|
|
163
212
|
"code-style/no-empty-lines-in-function-calls": "error",
|
|
@@ -178,237 +227,1024 @@ rules: {
|
|
|
178
227
|
|
|
179
228
|
<br />
|
|
180
229
|
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
> All rules are **auto-fixable** using `eslint --fix`
|
|
230
|
+
---
|
|
184
231
|
|
|
185
|
-
|
|
232
|
+
## 📖 Rules Summary
|
|
186
233
|
|
|
187
|
-
|
|
234
|
+
> All **47 rules** are auto-fixable. See detailed examples for each rule in the [Rules Reference](#-rules-reference) section below.
|
|
235
|
+
>
|
|
236
|
+
> Rules marked with ⚙️ support customization options (e.g., extending default folder lists).
|
|
188
237
|
|
|
189
238
|
| Rule | Description |
|
|
190
239
|
|------|-------------|
|
|
191
|
-
| `
|
|
192
|
-
| `
|
|
240
|
+
| `array-items-per-line` | Enforce array formatting: 3 or less items on one line, more than 3 each on new line |
|
|
241
|
+
| `array-objects-on-new-lines` | Enforce array of objects to have each object on a new line |
|
|
242
|
+
| `arrow-function-block-body` | Enforce parentheses for arrow functions with multiline expressions |
|
|
243
|
+
| `arrow-function-simple-jsx` | Simplify arrow functions returning simple JSX to single line |
|
|
244
|
+
| `arrow-function-simplify` | Simplify arrow functions in JSX props with single statement block body |
|
|
245
|
+
| `curried-arrow-same-line` | Enforce curried arrow function to start on same line as `=>` |
|
|
246
|
+
| `assignment-value-same-line` | Enforce assignment value on same line as equals sign |
|
|
247
|
+
| `block-statement-newlines` | Enforce newlines after opening brace and before closing brace |
|
|
248
|
+
| `comment-spacing` | Enforce comment spacing and formatting |
|
|
249
|
+
| `function-call-spacing` | Enforce no space between function name and opening parenthesis |
|
|
250
|
+
| `function-naming-convention` | Enforce function naming conventions (camelCase, verb prefix) |
|
|
251
|
+
| `function-params-per-line` | Enforce function parameters on separate lines when multiline |
|
|
252
|
+
| `hook-callback-format` | Enforce consistent formatting for React hooks callbacks |
|
|
253
|
+
| `hook-deps-per-line` | Enforce each hook dependency on its own line when more than 2 |
|
|
254
|
+
| `if-statement-format` | Ensure if statement has proper formatting |
|
|
255
|
+
| `multiline-if-conditions` | Enforce multiline if conditions when there are multiple operands |
|
|
256
|
+
| `absolute-imports-only` | Enforce absolute imports using `@/` alias instead of relative paths ⚙️ |
|
|
257
|
+
| `export-format` | Format exports: collapse 1-3 specifiers, multiline for 4+ |
|
|
258
|
+
| `import-format` | Format imports: collapse 1-3 specifiers, multiline for 4+ |
|
|
193
259
|
| `import-source-spacing` | Enforce no extra spaces inside import path quotes |
|
|
194
|
-
| `
|
|
195
|
-
| `
|
|
260
|
+
| `module-index-exports` | Enforce proper exports in index files ⚙️ |
|
|
261
|
+
| `jsx-children-on-new-line` | Enforce JSX children on separate lines from parent tags |
|
|
262
|
+
| `jsx-closing-bracket-spacing` | No space before `>` or `/>` in JSX tags |
|
|
263
|
+
| `jsx-element-child-new-line` | JSX element children must be on new lines |
|
|
264
|
+
| `jsx-logical-expression-simplify` | Simplify logical expressions in JSX |
|
|
265
|
+
| `jsx-parentheses-position` | Enforce opening parenthesis position for JSX in arrow functions |
|
|
266
|
+
| `jsx-prop-naming-convention` | Enforce JSX prop naming conventions (camelCase) |
|
|
267
|
+
| `jsx-simple-element-one-line` | Simple JSX elements with single child on one line |
|
|
268
|
+
| `jsx-string-value-trim` | Disallow leading/trailing whitespace in JSX string values |
|
|
269
|
+
| `jsx-ternary-format` | Enforce consistent formatting for JSX ternary expressions |
|
|
270
|
+
| `member-expression-bracket-spacing` | Enforce no spaces inside brackets for member expressions |
|
|
271
|
+
| `multiline-argument-newline` | Enforce newlines for function calls with multiline arguments |
|
|
272
|
+
| `multiple-arguments-per-line` | Enforce multiple arguments to each be on their own line |
|
|
273
|
+
| `nested-call-closing-brackets` | Enforce nested function call closing brackets on same line |
|
|
274
|
+
| `no-empty-lines-in-function-calls` | Disallow empty lines in function calls |
|
|
275
|
+
| `no-empty-lines-in-function-params` | Disallow empty lines in function parameters |
|
|
276
|
+
| `no-empty-lines-in-jsx` | Disallow empty lines inside JSX elements |
|
|
277
|
+
| `no-empty-lines-in-objects` | Disallow empty lines inside objects |
|
|
278
|
+
| `no-empty-lines-in-switch-cases` | Prevent empty lines at the beginning of switch case logic |
|
|
279
|
+
| `object-property-per-line` | Enforce each property on its own line when object has 2+ properties |
|
|
280
|
+
| `object-property-value-brace` | Enforce opening brace on same line as colon for object values |
|
|
281
|
+
| `object-property-value-format` | Enforce property value on same line as colon |
|
|
282
|
+
| `opening-brackets-same-line` | Enforce opening brackets on same line for function calls |
|
|
283
|
+
| `simple-call-single-line` | Simplify simple function calls with arrow function to single line |
|
|
284
|
+
| `single-argument-on-one-line` | Enforce single simple argument calls to be on one line |
|
|
285
|
+
| `string-property-spacing` | Enforce no extra spaces inside string property keys |
|
|
286
|
+
| `variable-naming-convention` | Enforce variable naming conventions (camelCase, UPPER_CASE, PascalCase) |
|
|
196
287
|
|
|
197
288
|
<br />
|
|
198
289
|
|
|
199
|
-
|
|
290
|
+
---
|
|
200
291
|
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
| `arrow-function-simplify` | Simplify arrow functions returning simple JSX to single line |
|
|
205
|
-
| `arrow-function-simple-jsx` | Simplify arrow functions in JSX props with single statement block body |
|
|
206
|
-
| `function-call-spacing` | Enforce no space between function name and opening parenthesis |
|
|
207
|
-
| `function-naming-convention` | Enforce function naming conventions (camelCase) |
|
|
208
|
-
| `function-params-per-line` | Enforce function parameters on separate lines when more than 2 |
|
|
209
|
-
| `curried-arrow-same-line` | Enforce curried arrow function to start on same line as `=>` |
|
|
292
|
+
## 📖 Rules Reference
|
|
293
|
+
|
|
294
|
+
> All rules are **auto-fixable** using `eslint --fix`
|
|
210
295
|
|
|
211
296
|
<br />
|
|
212
297
|
|
|
213
|
-
|
|
298
|
+
## 📚 Array Rules
|
|
214
299
|
|
|
215
|
-
|
|
216
|
-
|------|-------------|
|
|
217
|
-
| `object-property-per-line` | Enforce each property on its own line when object has 2+ properties |
|
|
218
|
-
| `object-property-value-format` | Enforce property value on same line as colon with proper spacing |
|
|
219
|
-
| `object-property-value-brace` | Enforce opening brace on same line as colon for object property values |
|
|
220
|
-
| `no-empty-lines-in-objects` | Disallow empty lines inside objects |
|
|
221
|
-
| `string-property-spacing` | Enforce no extra spaces inside string property keys |
|
|
300
|
+
### `array-items-per-line`
|
|
222
301
|
|
|
223
|
-
|
|
302
|
+
Enforce array formatting based on item count. 3 or less items on one line, more than 3 items each on its own line.
|
|
224
303
|
|
|
225
|
-
|
|
304
|
+
```javascript
|
|
305
|
+
// Good
|
|
306
|
+
const arr = [1, 2, 3];
|
|
307
|
+
const arr = [
|
|
308
|
+
item1,
|
|
309
|
+
item2,
|
|
310
|
+
item3,
|
|
311
|
+
item4,
|
|
312
|
+
];
|
|
226
313
|
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
314
|
+
// Bad
|
|
315
|
+
const arr = [1, 2, 3, 4, 5];
|
|
316
|
+
const arr = [item1,
|
|
317
|
+
item2, item3];
|
|
318
|
+
```
|
|
319
|
+
|
|
320
|
+
---
|
|
321
|
+
|
|
322
|
+
### `array-objects-on-new-lines`
|
|
323
|
+
|
|
324
|
+
In arrays of objects, each object should start on a new line for better readability.
|
|
325
|
+
|
|
326
|
+
```javascript
|
|
327
|
+
// Good
|
|
328
|
+
const items = [
|
|
329
|
+
{ id: 1, name: "first" },
|
|
330
|
+
{ id: 2, name: "second" },
|
|
331
|
+
];
|
|
332
|
+
|
|
333
|
+
// Bad
|
|
334
|
+
const items = [{ id: 1, name: "first" },
|
|
335
|
+
{ id: 2, name: "second" }];
|
|
336
|
+
```
|
|
231
337
|
|
|
232
338
|
<br />
|
|
233
339
|
|
|
234
|
-
|
|
340
|
+
## ➡️ Arrow Function Rules
|
|
235
341
|
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
342
|
+
### `arrow-function-block-body`
|
|
343
|
+
|
|
344
|
+
Arrow functions with complex logic should use block body. Ensures consistent formatting when function body needs multiple statements or complex expressions.
|
|
345
|
+
|
|
346
|
+
```javascript
|
|
347
|
+
// Good
|
|
348
|
+
() => {
|
|
349
|
+
doSomething();
|
|
350
|
+
return value;
|
|
351
|
+
}
|
|
352
|
+
|
|
353
|
+
// Bad
|
|
354
|
+
() => (doSomething(), value)
|
|
355
|
+
```
|
|
356
|
+
|
|
357
|
+
---
|
|
358
|
+
|
|
359
|
+
### `arrow-function-simple-jsx`
|
|
360
|
+
|
|
361
|
+
Simplify arrow functions returning simple JSX to single line by removing unnecessary parentheses and line breaks.
|
|
362
|
+
|
|
363
|
+
```javascript
|
|
364
|
+
// Good
|
|
365
|
+
export const X = ({ children }) => <Sidebar>{children}</Sidebar>;
|
|
366
|
+
|
|
367
|
+
// Bad
|
|
368
|
+
export const X = ({ children }) => (
|
|
369
|
+
<Sidebar>{children}</Sidebar>
|
|
370
|
+
);
|
|
371
|
+
```
|
|
372
|
+
|
|
373
|
+
---
|
|
374
|
+
|
|
375
|
+
### `arrow-function-simplify`
|
|
376
|
+
|
|
377
|
+
Simplify arrow functions that have a single return statement by using implicit return instead of block body.
|
|
378
|
+
|
|
379
|
+
```javascript
|
|
380
|
+
// Good
|
|
381
|
+
() => value
|
|
382
|
+
(x) => x * 2
|
|
383
|
+
items.map(item => item.name)
|
|
384
|
+
|
|
385
|
+
// Bad
|
|
386
|
+
() => { return value; }
|
|
387
|
+
(x) => { return x * 2; }
|
|
388
|
+
items.map(item => { return item.name; })
|
|
389
|
+
```
|
|
390
|
+
|
|
391
|
+
---
|
|
392
|
+
|
|
393
|
+
### `curried-arrow-same-line`
|
|
394
|
+
|
|
395
|
+
Curried arrow function body must start on the same line as the arrow (=>), not on a new line.
|
|
396
|
+
|
|
397
|
+
```javascript
|
|
398
|
+
// Good
|
|
399
|
+
const fn = () => async (dispatch) => {
|
|
400
|
+
dispatch(action);
|
|
401
|
+
};
|
|
402
|
+
|
|
403
|
+
// Bad
|
|
404
|
+
const fn = () =>
|
|
405
|
+
async (dispatch) => {
|
|
406
|
+
dispatch(action);
|
|
407
|
+
};
|
|
408
|
+
```
|
|
248
409
|
|
|
249
410
|
<br />
|
|
250
411
|
|
|
251
|
-
|
|
412
|
+
## 📐 Spacing & Formatting Rules
|
|
252
413
|
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
414
|
+
### `assignment-value-same-line`
|
|
415
|
+
|
|
416
|
+
The value in an assignment should start on the same line as the equals sign, not on a new line.
|
|
417
|
+
|
|
418
|
+
```javascript
|
|
419
|
+
// Good
|
|
420
|
+
const name = "John";
|
|
421
|
+
const data = {
|
|
422
|
+
key: "value",
|
|
423
|
+
};
|
|
424
|
+
|
|
425
|
+
// Bad
|
|
426
|
+
const name =
|
|
427
|
+
"John";
|
|
428
|
+
const data =
|
|
429
|
+
{
|
|
430
|
+
key: "value",
|
|
431
|
+
};
|
|
432
|
+
```
|
|
433
|
+
|
|
434
|
+
---
|
|
435
|
+
|
|
436
|
+
### `block-statement-newlines`
|
|
437
|
+
|
|
438
|
+
Block statements should have proper newlines after the opening brace and before the closing brace.
|
|
439
|
+
|
|
440
|
+
```javascript
|
|
441
|
+
// Good
|
|
442
|
+
if (condition) {
|
|
443
|
+
doSomething();
|
|
444
|
+
}
|
|
445
|
+
|
|
446
|
+
// Bad
|
|
447
|
+
if (condition) { doSomething(); }
|
|
448
|
+
if (condition) {doSomething();}
|
|
449
|
+
```
|
|
450
|
+
|
|
451
|
+
---
|
|
452
|
+
|
|
453
|
+
### `comment-spacing`
|
|
454
|
+
|
|
455
|
+
Comments should have proper spacing: a space after the opening delimiter (// or block comment opener), and proper blank lines around comment blocks.
|
|
456
|
+
|
|
457
|
+
```javascript
|
|
458
|
+
// Good
|
|
459
|
+
// This is a comment
|
|
460
|
+
/* This is a block comment */
|
|
461
|
+
|
|
462
|
+
// Bad
|
|
463
|
+
//This is a comment (missing space)
|
|
464
|
+
/*No space after opener*/
|
|
465
|
+
```
|
|
466
|
+
|
|
467
|
+
---
|
|
468
|
+
|
|
469
|
+
### `member-expression-bracket-spacing`
|
|
470
|
+
|
|
471
|
+
No spaces inside brackets in computed member expressions. The property name should touch both brackets.
|
|
472
|
+
|
|
473
|
+
```javascript
|
|
474
|
+
// Good
|
|
475
|
+
arr[value]
|
|
476
|
+
obj[key]
|
|
477
|
+
|
|
478
|
+
// Bad
|
|
479
|
+
arr[ value ]
|
|
480
|
+
obj[ key ]
|
|
481
|
+
```
|
|
482
|
+
|
|
483
|
+
---
|
|
484
|
+
|
|
485
|
+
### `no-empty-lines-in-function-params`
|
|
486
|
+
|
|
487
|
+
Function parameter lists should not contain empty lines between parameters or after opening/before closing parens.
|
|
488
|
+
|
|
489
|
+
```javascript
|
|
490
|
+
// Good
|
|
491
|
+
function test(
|
|
492
|
+
param1,
|
|
493
|
+
param2,
|
|
494
|
+
) {}
|
|
495
|
+
|
|
496
|
+
// Bad
|
|
497
|
+
function test(
|
|
498
|
+
param1,
|
|
499
|
+
|
|
500
|
+
param2,
|
|
501
|
+
) {}
|
|
502
|
+
```
|
|
503
|
+
|
|
504
|
+
---
|
|
505
|
+
|
|
506
|
+
### `variable-naming-convention`
|
|
507
|
+
|
|
508
|
+
Variable names should follow naming conventions: camelCase for regular variables, UPPER_CASE for constants, and PascalCase for React components.
|
|
509
|
+
|
|
510
|
+
```javascript
|
|
511
|
+
// Good
|
|
512
|
+
const userName = "John";
|
|
513
|
+
const MAX_RETRIES = 3;
|
|
514
|
+
const UserProfile = () => <div />;
|
|
515
|
+
const useCustomHook = () => {};
|
|
516
|
+
|
|
517
|
+
// Bad
|
|
518
|
+
const user_name = "John";
|
|
519
|
+
const maxretries = 3;
|
|
520
|
+
const userProfile = () => <div />;
|
|
521
|
+
```
|
|
262
522
|
|
|
263
523
|
<br />
|
|
264
524
|
|
|
265
|
-
|
|
525
|
+
## ⚡ Function Rules
|
|
266
526
|
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
527
|
+
### `function-call-spacing`
|
|
528
|
+
|
|
529
|
+
No space between function name and opening parenthesis.
|
|
530
|
+
|
|
531
|
+
```javascript
|
|
532
|
+
// Good
|
|
533
|
+
useDispatch()
|
|
534
|
+
myFunction(arg)
|
|
535
|
+
|
|
536
|
+
// Bad
|
|
537
|
+
useDispatch ()
|
|
538
|
+
myFunction (arg)
|
|
539
|
+
```
|
|
540
|
+
|
|
541
|
+
---
|
|
542
|
+
|
|
543
|
+
### `function-naming-convention`
|
|
544
|
+
|
|
545
|
+
Function names should follow naming conventions: camelCase, starting with a verb, and handlers ending with "Handler".
|
|
546
|
+
|
|
547
|
+
```javascript
|
|
548
|
+
// Good
|
|
549
|
+
function getUserData() {}
|
|
550
|
+
function handleClick() {}
|
|
551
|
+
function isValidEmail() {}
|
|
552
|
+
const submitHandler = () => {}
|
|
553
|
+
|
|
554
|
+
// Bad
|
|
555
|
+
function GetUserData() {}
|
|
556
|
+
function user_data() {}
|
|
557
|
+
function click() {}
|
|
558
|
+
```
|
|
559
|
+
|
|
560
|
+
---
|
|
561
|
+
|
|
562
|
+
### `function-params-per-line`
|
|
563
|
+
|
|
564
|
+
When function parameters span multiple lines, each parameter should be on its own line with consistent indentation.
|
|
565
|
+
|
|
566
|
+
```javascript
|
|
567
|
+
// Good
|
|
568
|
+
function test(
|
|
569
|
+
param1,
|
|
570
|
+
param2,
|
|
571
|
+
param3,
|
|
572
|
+
) {}
|
|
573
|
+
|
|
574
|
+
// Bad
|
|
575
|
+
function test(param1,
|
|
576
|
+
param2, param3) {}
|
|
577
|
+
```
|
|
271
578
|
|
|
272
579
|
<br />
|
|
273
580
|
|
|
274
|
-
|
|
581
|
+
## 🪝 React Hooks Rules
|
|
275
582
|
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
583
|
+
### `hook-callback-format`
|
|
584
|
+
|
|
585
|
+
Enforce consistent formatting for React hooks like useEffect, useCallback, useMemo with callback and dependency array.
|
|
586
|
+
|
|
587
|
+
```javascript
|
|
588
|
+
// Good
|
|
589
|
+
useEffect(
|
|
590
|
+
() => { doSomething(); },
|
|
591
|
+
[dep1, dep2],
|
|
592
|
+
);
|
|
593
|
+
|
|
594
|
+
// Bad
|
|
595
|
+
useEffect(() => { doSomething(); }, [dep1, dep2]);
|
|
596
|
+
```
|
|
597
|
+
|
|
598
|
+
---
|
|
599
|
+
|
|
600
|
+
### `hook-deps-per-line`
|
|
601
|
+
|
|
602
|
+
React hook dependency arrays with more than 2 dependencies should have each dependency on its own line.
|
|
603
|
+
|
|
604
|
+
```javascript
|
|
605
|
+
// Good
|
|
606
|
+
useEffect(() => {}, [dep1, dep2])
|
|
607
|
+
useEffect(() => {}, [
|
|
608
|
+
dep1,
|
|
609
|
+
dep2,
|
|
610
|
+
dep3,
|
|
611
|
+
])
|
|
612
|
+
|
|
613
|
+
// Bad
|
|
614
|
+
useEffect(() => {}, [dep1, dep2, dep3, dep4])
|
|
615
|
+
```
|
|
281
616
|
|
|
282
617
|
<br />
|
|
283
618
|
|
|
284
|
-
|
|
619
|
+
## 🔀 Control Flow Rules
|
|
285
620
|
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
621
|
+
### `if-statement-format`
|
|
622
|
+
|
|
623
|
+
If statements should have consistent formatting with the opening brace on the same line as the condition and else on the same line as the closing brace.
|
|
624
|
+
|
|
625
|
+
```javascript
|
|
626
|
+
// Good
|
|
627
|
+
if (condition) {
|
|
628
|
+
doSomething();
|
|
629
|
+
} else {
|
|
630
|
+
doOther();
|
|
631
|
+
}
|
|
632
|
+
|
|
633
|
+
// Bad
|
|
634
|
+
if (condition)
|
|
635
|
+
{
|
|
636
|
+
doSomething();
|
|
637
|
+
}
|
|
638
|
+
else
|
|
639
|
+
{
|
|
640
|
+
doOther();
|
|
641
|
+
}
|
|
642
|
+
```
|
|
643
|
+
|
|
644
|
+
---
|
|
645
|
+
|
|
646
|
+
### `multiline-if-conditions`
|
|
647
|
+
|
|
648
|
+
When an if statement has multiple conditions that span multiple lines, each condition should be on its own line.
|
|
649
|
+
|
|
650
|
+
```javascript
|
|
651
|
+
// Good
|
|
652
|
+
if (
|
|
653
|
+
conditionA &&
|
|
654
|
+
conditionB &&
|
|
655
|
+
conditionC
|
|
656
|
+
) {}
|
|
657
|
+
|
|
658
|
+
// Bad
|
|
659
|
+
if (conditionA &&
|
|
660
|
+
conditionB && conditionC) {}
|
|
661
|
+
```
|
|
662
|
+
|
|
663
|
+
---
|
|
664
|
+
|
|
665
|
+
### `no-empty-lines-in-switch-cases`
|
|
666
|
+
|
|
667
|
+
Switch case blocks should not have empty lines at the beginning of the case logic or between consecutive cases.
|
|
668
|
+
|
|
669
|
+
```javascript
|
|
670
|
+
// Good
|
|
671
|
+
switch (value) {
|
|
672
|
+
case 1:
|
|
673
|
+
return "one";
|
|
674
|
+
case 2:
|
|
675
|
+
return "two";
|
|
676
|
+
}
|
|
677
|
+
|
|
678
|
+
// Bad
|
|
679
|
+
switch (value) {
|
|
680
|
+
case 1:
|
|
681
|
+
|
|
682
|
+
return "one";
|
|
683
|
+
|
|
684
|
+
case 2:
|
|
685
|
+
return "two";
|
|
686
|
+
}
|
|
687
|
+
```
|
|
294
688
|
|
|
295
689
|
<br />
|
|
296
690
|
|
|
297
|
-
##
|
|
691
|
+
## 📥 Import/Export Rules
|
|
692
|
+
|
|
693
|
+
### `absolute-imports-only`
|
|
298
694
|
|
|
299
|
-
|
|
695
|
+
Enforce absolute imports from index files only for local paths. Local paths (starting with @/) should only import from folder-level index files.
|
|
300
696
|
|
|
301
697
|
```javascript
|
|
302
|
-
//
|
|
303
|
-
import {
|
|
698
|
+
// Good
|
|
699
|
+
import { Button } from "@/components";
|
|
700
|
+
import { useAuth } from "@/hooks";
|
|
304
701
|
|
|
305
|
-
//
|
|
306
|
-
import {
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
702
|
+
// Bad
|
|
703
|
+
import { Button } from "@/components/buttons/primary-button";
|
|
704
|
+
import { useAuth } from "@/hooks/auth/useAuth";
|
|
705
|
+
```
|
|
706
|
+
|
|
707
|
+
**Default Allowed Folders:**
|
|
708
|
+
`actions`, `apis`, `assets`, `atoms`, `components`, `constants`, `contexts`, `data`, `hooks`, `layouts`, `middlewares`, `providers`, `reducers`, `redux`, `requests`, `routes`, `schemas`, `services`, `store`, `styles`, `theme`, `thunks`, `types`, `utils`, `views`
|
|
709
|
+
|
|
710
|
+
**Customization Options:**
|
|
711
|
+
|
|
712
|
+
| Option | Type | Description |
|
|
713
|
+
|--------|------|-------------|
|
|
714
|
+
| `extraAllowedFolders` | `string[]` | Add extra folders to the default list |
|
|
715
|
+
| `extraReduxSubfolders` | `string[]` | Add extra redux subfolders (default: `actions`, `reducers`, `store`, `thunks`, `types`) |
|
|
716
|
+
| `extraDeepImportFolders` | `string[]` | Add extra folders that allow deep imports (default: `assets`) |
|
|
717
|
+
| `aliasPrefix` | `string` | Change the import alias prefix (default: `@/`) |
|
|
718
|
+
| `allowedFolders` | `string[]` | Replace default folders entirely |
|
|
719
|
+
| `reduxSubfolders` | `string[]` | Replace default redux subfolders entirely |
|
|
720
|
+
| `deepImportFolders` | `string[]` | Replace default deep import folders entirely |
|
|
721
|
+
|
|
722
|
+
```javascript
|
|
723
|
+
// Example: Add custom folders to the defaults
|
|
724
|
+
"code-style/absolute-imports-only": ["error", {
|
|
725
|
+
extraAllowedFolders: ["features", "modules", "lib"],
|
|
726
|
+
extraDeepImportFolders: ["images", "fonts"]
|
|
727
|
+
}]
|
|
728
|
+
```
|
|
729
|
+
|
|
730
|
+
---
|
|
731
|
+
|
|
732
|
+
### `export-format`
|
|
733
|
+
|
|
734
|
+
Export statements should have consistent formatting with proper spacing. Collapse 1-3 specifiers on one line, use multiline for 4+ specifiers.
|
|
735
|
+
|
|
736
|
+
```javascript
|
|
737
|
+
// Good
|
|
738
|
+
export { a, b, c };
|
|
739
|
+
export {
|
|
740
|
+
a,
|
|
741
|
+
b,
|
|
742
|
+
c,
|
|
743
|
+
d,
|
|
744
|
+
};
|
|
745
|
+
|
|
746
|
+
// Bad
|
|
747
|
+
export {a,b,c};
|
|
748
|
+
export { a, b, c, d, e };
|
|
749
|
+
```
|
|
750
|
+
|
|
751
|
+
---
|
|
312
752
|
|
|
313
|
-
|
|
753
|
+
### `import-format`
|
|
754
|
+
|
|
755
|
+
Import statements should have consistent formatting with proper spacing. Collapse 1-3 specifiers on one line, use multiline for 4+ specifiers.
|
|
756
|
+
|
|
757
|
+
```javascript
|
|
758
|
+
// Good
|
|
759
|
+
import { a, b, c } from "module";
|
|
314
760
|
import {
|
|
315
|
-
|
|
761
|
+
a,
|
|
762
|
+
b,
|
|
763
|
+
c,
|
|
764
|
+
d,
|
|
765
|
+
} from "module";
|
|
766
|
+
|
|
767
|
+
// Bad
|
|
768
|
+
import {a,b,c} from "module";
|
|
769
|
+
import { a, b, c, d, e } from "module";
|
|
316
770
|
```
|
|
317
771
|
|
|
318
|
-
|
|
772
|
+
---
|
|
773
|
+
|
|
774
|
+
### `import-source-spacing`
|
|
319
775
|
|
|
320
|
-
|
|
776
|
+
No spaces inside import path quotes. The module path should not have leading or trailing whitespace.
|
|
321
777
|
|
|
322
778
|
```javascript
|
|
323
|
-
//
|
|
324
|
-
|
|
779
|
+
// Good
|
|
780
|
+
import { Button } from "@mui/material";
|
|
325
781
|
|
|
326
|
-
//
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
782
|
+
// Bad
|
|
783
|
+
import { Button } from " @mui/material ";
|
|
784
|
+
```
|
|
785
|
+
|
|
786
|
+
---
|
|
787
|
+
|
|
788
|
+
### `module-index-exports`
|
|
789
|
+
|
|
790
|
+
Ensure module folders have index files that export all contents. Each module folder must have an index file that exports all subfolders and files in the module.
|
|
791
|
+
|
|
792
|
+
```javascript
|
|
793
|
+
// Good
|
|
794
|
+
// index.js
|
|
795
|
+
export { Button } from "./Button";
|
|
796
|
+
export { Input } from "./Input";
|
|
797
|
+
|
|
798
|
+
// Bad
|
|
799
|
+
// Missing exports in index.js
|
|
800
|
+
```
|
|
801
|
+
|
|
802
|
+
**Default Module Folders:**
|
|
803
|
+
`apis`, `assets`, `atoms`, `components`, `constants`, `contexts`, `data`, `hooks`, `layouts`, `middlewares`, `providers`, `redux`, `requests`, `routes`, `schemas`, `services`, `styles`, `theme`, `utils`, `views`
|
|
804
|
+
|
|
805
|
+
**Customization Options:**
|
|
806
|
+
|
|
807
|
+
| Option | Type | Description |
|
|
808
|
+
|--------|------|-------------|
|
|
809
|
+
| `extraModuleFolders` | `string[]` | Add extra module folders to the default list |
|
|
810
|
+
| `extraLazyLoadFolders` | `string[]` | Add extra lazy load folders (default: `views`) |
|
|
811
|
+
| `extraIgnorePatterns` | `string[]` | Add extra ignore patterns (supports wildcards like `*.stories.js`) |
|
|
812
|
+
| `moduleFolders` | `string[]` | Replace default module folders entirely |
|
|
813
|
+
| `lazyLoadFolders` | `string[]` | Replace default lazy load folders entirely |
|
|
814
|
+
| `ignorePatterns` | `string[]` | Replace default ignore patterns entirely |
|
|
815
|
+
|
|
816
|
+
**Default Ignore Patterns:**
|
|
817
|
+
`index.js`, `index.jsx`, `index.ts`, `index.tsx`, `.DS_Store`, `__tests__`, `__mocks__`, `*.test.js`, `*.test.jsx`, `*.spec.js`, `*.spec.jsx`
|
|
332
818
|
|
|
333
|
-
|
|
334
|
-
|
|
819
|
+
```javascript
|
|
820
|
+
// Example: Add custom folders and patterns to the defaults
|
|
821
|
+
"code-style/module-index-exports": ["error", {
|
|
822
|
+
extraModuleFolders: ["features", "modules", "lib"],
|
|
823
|
+
extraLazyLoadFolders: ["pages"],
|
|
824
|
+
extraIgnorePatterns: ["*.stories.js", "*.mock.js"]
|
|
825
|
+
}]
|
|
335
826
|
```
|
|
336
827
|
|
|
337
828
|
<br />
|
|
338
829
|
|
|
339
|
-
|
|
830
|
+
## ⚛️ JSX Rules
|
|
831
|
+
|
|
832
|
+
### `jsx-children-on-new-line`
|
|
833
|
+
|
|
834
|
+
When a JSX element has multiple children, each child should be on its own line with proper indentation.
|
|
340
835
|
|
|
341
836
|
```javascript
|
|
342
|
-
//
|
|
343
|
-
|
|
837
|
+
// Good
|
|
838
|
+
<Container>
|
|
839
|
+
<Header />
|
|
840
|
+
<Content />
|
|
841
|
+
<Footer />
|
|
842
|
+
</Container>
|
|
843
|
+
|
|
844
|
+
// Bad
|
|
845
|
+
<Container><Header /><Content />
|
|
846
|
+
<Footer /></Container>
|
|
847
|
+
```
|
|
848
|
+
|
|
849
|
+
---
|
|
850
|
+
|
|
851
|
+
### `jsx-closing-bracket-spacing`
|
|
852
|
+
|
|
853
|
+
No space before > or /> in JSX tags. The closing bracket should be directly after the last attribute or tag name.
|
|
854
|
+
|
|
855
|
+
```javascript
|
|
856
|
+
// Good
|
|
857
|
+
<Button />
|
|
858
|
+
<Button className="primary">
|
|
859
|
+
|
|
860
|
+
// Bad
|
|
861
|
+
<Button / >
|
|
862
|
+
<Button className="primary" >
|
|
863
|
+
```
|
|
864
|
+
|
|
865
|
+
---
|
|
344
866
|
|
|
345
|
-
|
|
346
|
-
|
|
867
|
+
### `jsx-element-child-new-line`
|
|
868
|
+
|
|
869
|
+
JSX element children (nested JSX elements) must be on their own line, not on the same line as the opening tag.
|
|
870
|
+
|
|
871
|
+
```javascript
|
|
872
|
+
// Good
|
|
873
|
+
<Button>
|
|
874
|
+
<Icon />
|
|
875
|
+
</Button>
|
|
876
|
+
|
|
877
|
+
// Bad
|
|
878
|
+
<Button><Icon /></Button>
|
|
879
|
+
```
|
|
880
|
+
|
|
881
|
+
---
|
|
882
|
+
|
|
883
|
+
### `jsx-logical-expression-simplify`
|
|
884
|
+
|
|
885
|
+
Simplify JSX logical expressions by removing unnecessary parentheses around conditions and JSX elements.
|
|
886
|
+
|
|
887
|
+
```javascript
|
|
888
|
+
// Good
|
|
889
|
+
{condition && <Component />}
|
|
890
|
+
{isVisible && <Modal />}
|
|
891
|
+
|
|
892
|
+
// Bad
|
|
893
|
+
{(condition) && (<Component />)}
|
|
894
|
+
{(isVisible) && (<Modal />)}
|
|
895
|
+
```
|
|
896
|
+
|
|
897
|
+
---
|
|
898
|
+
|
|
899
|
+
### `jsx-parentheses-position`
|
|
900
|
+
|
|
901
|
+
JSX return parentheses should be on the same line as the arrow or return keyword, not on a new line.
|
|
902
|
+
|
|
903
|
+
```javascript
|
|
904
|
+
// Good
|
|
905
|
+
const Component = () => (
|
|
906
|
+
<div>content</div>
|
|
907
|
+
);
|
|
908
|
+
return (
|
|
909
|
+
<div>content</div>
|
|
910
|
+
);
|
|
911
|
+
|
|
912
|
+
// Bad
|
|
913
|
+
const Component = () =>
|
|
914
|
+
(
|
|
915
|
+
<div>content</div>
|
|
916
|
+
);
|
|
917
|
+
return
|
|
918
|
+
(
|
|
919
|
+
<div>content</div>
|
|
920
|
+
);
|
|
921
|
+
```
|
|
922
|
+
|
|
923
|
+
---
|
|
924
|
+
|
|
925
|
+
### `jsx-prop-naming-convention`
|
|
926
|
+
|
|
927
|
+
Enforce camelCase naming for JSX props. Allows PascalCase for component reference props, and kebab-case for data-* and aria-*.
|
|
928
|
+
|
|
929
|
+
```javascript
|
|
930
|
+
// Good
|
|
931
|
+
<Button onClick={handler} />
|
|
932
|
+
<Input data-testid="input" />
|
|
933
|
+
<Modal ContentComponent={Panel} />
|
|
934
|
+
|
|
935
|
+
// Bad
|
|
936
|
+
<Button on_click={handler} />
|
|
937
|
+
<Input test_id="input" />
|
|
938
|
+
```
|
|
939
|
+
|
|
940
|
+
---
|
|
941
|
+
|
|
942
|
+
### `jsx-simple-element-one-line`
|
|
943
|
+
|
|
944
|
+
Simple JSX elements with only a single text or expression child should be collapsed onto a single line.
|
|
945
|
+
|
|
946
|
+
```javascript
|
|
947
|
+
// Good
|
|
948
|
+
<Button>{buttonLinkText}</Button>
|
|
949
|
+
<Title>Hello</Title>
|
|
950
|
+
|
|
951
|
+
// Bad
|
|
952
|
+
<Button>
|
|
953
|
+
{buttonLinkText}
|
|
954
|
+
</Button>
|
|
955
|
+
```
|
|
956
|
+
|
|
957
|
+
---
|
|
958
|
+
|
|
959
|
+
### `jsx-string-value-trim`
|
|
960
|
+
|
|
961
|
+
JSX string attribute values should not have leading or trailing whitespace inside the quotes.
|
|
962
|
+
|
|
963
|
+
```javascript
|
|
964
|
+
// Good
|
|
965
|
+
className="button"
|
|
966
|
+
title="Hello World"
|
|
967
|
+
|
|
968
|
+
// Bad
|
|
969
|
+
className=" button "
|
|
970
|
+
title=" Hello World "
|
|
971
|
+
```
|
|
972
|
+
|
|
973
|
+
---
|
|
974
|
+
|
|
975
|
+
### `jsx-ternary-format`
|
|
976
|
+
|
|
977
|
+
Format ternary expressions in JSX with proper structure. Simple branches stay on one line, complex branches get parentheses with proper indentation.
|
|
978
|
+
|
|
979
|
+
```javascript
|
|
980
|
+
// Good
|
|
981
|
+
{condition ? <Simple /> : <Other />}
|
|
982
|
+
{condition ? <Simple /> : (
|
|
347
983
|
<Complex>
|
|
348
|
-
<
|
|
984
|
+
<Child />
|
|
349
985
|
</Complex>
|
|
350
|
-
) : (
|
|
351
|
-
<Alternative>
|
|
352
|
-
<Content />
|
|
353
|
-
</Alternative>
|
|
354
986
|
)}
|
|
355
987
|
|
|
356
|
-
//
|
|
357
|
-
{condition
|
|
988
|
+
// Bad
|
|
989
|
+
{condition
|
|
990
|
+
? <Simple />
|
|
991
|
+
: <Other />}
|
|
992
|
+
```
|
|
358
993
|
|
|
359
|
-
|
|
994
|
+
---
|
|
360
995
|
|
|
361
|
-
|
|
996
|
+
### `no-empty-lines-in-jsx`
|
|
362
997
|
|
|
363
|
-
|
|
998
|
+
JSX elements should not contain empty lines between children or after opening/before closing tags.
|
|
364
999
|
|
|
365
|
-
|
|
1000
|
+
```javascript
|
|
1001
|
+
// Good
|
|
1002
|
+
<div>
|
|
1003
|
+
<span>text</span>
|
|
1004
|
+
<span>more</span>
|
|
1005
|
+
</div>
|
|
1006
|
+
|
|
1007
|
+
// Bad
|
|
1008
|
+
<div>
|
|
1009
|
+
|
|
1010
|
+
<span>text</span>
|
|
1011
|
+
|
|
1012
|
+
<span>more</span>
|
|
1013
|
+
|
|
1014
|
+
</div>
|
|
366
1015
|
```
|
|
367
1016
|
|
|
368
1017
|
<br />
|
|
369
1018
|
|
|
370
|
-
|
|
1019
|
+
## 📞 Call Expression Rules
|
|
1020
|
+
|
|
1021
|
+
### `multiline-argument-newline`
|
|
1022
|
+
|
|
1023
|
+
When function arguments span multiple lines, each argument should start on its own line with consistent indentation.
|
|
371
1024
|
|
|
372
1025
|
```javascript
|
|
373
|
-
//
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
1026
|
+
// Good
|
|
1027
|
+
fn(
|
|
1028
|
+
arg1,
|
|
1029
|
+
arg2,
|
|
1030
|
+
)
|
|
1031
|
+
|
|
1032
|
+
// Bad
|
|
1033
|
+
fn(arg1,
|
|
1034
|
+
arg2)
|
|
1035
|
+
```
|
|
1036
|
+
|
|
1037
|
+
---
|
|
1038
|
+
|
|
1039
|
+
### `multiple-arguments-per-line`
|
|
1040
|
+
|
|
1041
|
+
When a function call has 2+ arguments, each argument should be on its own line with proper indentation.
|
|
1042
|
+
|
|
1043
|
+
```javascript
|
|
1044
|
+
// Good
|
|
1045
|
+
setValue(
|
|
1046
|
+
"numberOfCopies",
|
|
1047
|
+
null,
|
|
1048
|
+
)
|
|
1049
|
+
|
|
1050
|
+
// Bad
|
|
1051
|
+
setValue("numberOfCopies", null)
|
|
1052
|
+
```
|
|
1053
|
+
|
|
1054
|
+
---
|
|
1055
|
+
|
|
1056
|
+
### `nested-call-closing-brackets`
|
|
1057
|
+
|
|
1058
|
+
Nested function calls (like styled-components) should have closing brackets on the same line: }));
|
|
1059
|
+
|
|
1060
|
+
```javascript
|
|
1061
|
+
// Good
|
|
1062
|
+
styled(Card)(({ theme }) => ({
|
|
1063
|
+
color: theme.color,
|
|
1064
|
+
}));
|
|
1065
|
+
|
|
1066
|
+
// Bad
|
|
1067
|
+
styled(Card)(({ theme }) => ({
|
|
1068
|
+
color: theme.color,
|
|
1069
|
+
})
|
|
379
1070
|
);
|
|
1071
|
+
```
|
|
380
1072
|
|
|
381
|
-
|
|
382
|
-
useEffect(() => doSomething(), []);
|
|
1073
|
+
---
|
|
383
1074
|
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
1075
|
+
### `no-empty-lines-in-function-calls`
|
|
1076
|
+
|
|
1077
|
+
Function call arguments should not have empty lines between them or after opening/before closing parentheses.
|
|
1078
|
+
|
|
1079
|
+
```javascript
|
|
1080
|
+
// Good
|
|
1081
|
+
fn(
|
|
1082
|
+
arg1,
|
|
1083
|
+
arg2,
|
|
1084
|
+
)
|
|
1085
|
+
|
|
1086
|
+
// Bad
|
|
1087
|
+
fn(
|
|
1088
|
+
arg1,
|
|
1089
|
+
|
|
1090
|
+
arg2,
|
|
1091
|
+
)
|
|
1092
|
+
```
|
|
1093
|
+
|
|
1094
|
+
---
|
|
1095
|
+
|
|
1096
|
+
### `opening-brackets-same-line`
|
|
1097
|
+
|
|
1098
|
+
Opening brackets should be on the same line as function/method calls. This applies to objects, arrays, and arrow function parameters.
|
|
1099
|
+
|
|
1100
|
+
```javascript
|
|
1101
|
+
// Good
|
|
1102
|
+
fn({ prop: value })
|
|
1103
|
+
.map(({ x }) => x)
|
|
1104
|
+
fn([1, 2, 3])
|
|
1105
|
+
|
|
1106
|
+
// Bad
|
|
1107
|
+
fn(
|
|
1108
|
+
{ prop: value }
|
|
1109
|
+
)
|
|
1110
|
+
.map(
|
|
1111
|
+
({ x }) => x
|
|
1112
|
+
)
|
|
1113
|
+
```
|
|
1114
|
+
|
|
1115
|
+
---
|
|
1116
|
+
|
|
1117
|
+
### `simple-call-single-line`
|
|
1118
|
+
|
|
1119
|
+
Simple function calls with an arrow function containing a simple call expression should be on a single line.
|
|
1120
|
+
|
|
1121
|
+
```javascript
|
|
1122
|
+
// Good
|
|
1123
|
+
fn(() => call(arg))
|
|
1124
|
+
lazy(() => import("./module"))
|
|
1125
|
+
|
|
1126
|
+
// Bad
|
|
1127
|
+
fn(
|
|
1128
|
+
() => call(arg),
|
|
1129
|
+
)
|
|
1130
|
+
```
|
|
1131
|
+
|
|
1132
|
+
---
|
|
1133
|
+
|
|
1134
|
+
### `single-argument-on-one-line`
|
|
1135
|
+
|
|
1136
|
+
Function calls with a single simple argument (literal, identifier, member expression) should be on one line.
|
|
1137
|
+
|
|
1138
|
+
```javascript
|
|
1139
|
+
// Good
|
|
1140
|
+
fn(arg)
|
|
1141
|
+
getValue("key")
|
|
1142
|
+
obj.method(value)
|
|
1143
|
+
|
|
1144
|
+
// Bad
|
|
1145
|
+
fn(
|
|
1146
|
+
arg,
|
|
1147
|
+
)
|
|
388
1148
|
```
|
|
389
1149
|
|
|
390
1150
|
<br />
|
|
391
1151
|
|
|
392
|
-
|
|
1152
|
+
## 📦 Object Rules
|
|
1153
|
+
|
|
1154
|
+
### `no-empty-lines-in-objects`
|
|
1155
|
+
|
|
1156
|
+
Object literals should not contain empty lines between properties or after opening/before closing braces.
|
|
393
1157
|
|
|
394
1158
|
```javascript
|
|
395
|
-
//
|
|
396
|
-
|
|
1159
|
+
// Good
|
|
1160
|
+
{
|
|
1161
|
+
a: 1,
|
|
1162
|
+
b: 2,
|
|
1163
|
+
}
|
|
397
1164
|
|
|
398
|
-
//
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
1165
|
+
// Bad
|
|
1166
|
+
{
|
|
1167
|
+
a: 1,
|
|
1168
|
+
|
|
1169
|
+
b: 2,
|
|
1170
|
+
}
|
|
1171
|
+
```
|
|
1172
|
+
|
|
1173
|
+
---
|
|
1174
|
+
|
|
1175
|
+
### `object-property-per-line`
|
|
1176
|
+
|
|
1177
|
+
When an object has 2 or more properties and spans multiple lines, each property should be on its own line.
|
|
1178
|
+
|
|
1179
|
+
```javascript
|
|
1180
|
+
// Good
|
|
1181
|
+
{
|
|
1182
|
+
name: "John",
|
|
1183
|
+
age: 30,
|
|
1184
|
+
}
|
|
1185
|
+
|
|
1186
|
+
// Bad
|
|
1187
|
+
{ name: "John",
|
|
1188
|
+
age: 30 }
|
|
1189
|
+
```
|
|
1190
|
+
|
|
1191
|
+
---
|
|
1192
|
+
|
|
1193
|
+
### `object-property-value-brace`
|
|
1194
|
+
|
|
1195
|
+
Opening brace of an object value should be on the same line as the colon, not on a new line.
|
|
1196
|
+
|
|
1197
|
+
```javascript
|
|
1198
|
+
// Good
|
|
1199
|
+
"& a": { color: "red" }
|
|
1200
|
+
|
|
1201
|
+
// Bad
|
|
1202
|
+
"& a":
|
|
1203
|
+
{ color: "red" }
|
|
1204
|
+
```
|
|
1205
|
+
|
|
1206
|
+
---
|
|
1207
|
+
|
|
1208
|
+
### `object-property-value-format`
|
|
405
1209
|
|
|
406
|
-
|
|
407
|
-
|
|
1210
|
+
Object property values should be on the same line as the colon with proper spacing for simple values.
|
|
1211
|
+
|
|
1212
|
+
```javascript
|
|
1213
|
+
// Good
|
|
1214
|
+
{
|
|
1215
|
+
name: "John",
|
|
1216
|
+
age: 30,
|
|
1217
|
+
}
|
|
1218
|
+
|
|
1219
|
+
// Bad
|
|
1220
|
+
{
|
|
1221
|
+
name:
|
|
1222
|
+
"John",
|
|
1223
|
+
age:
|
|
1224
|
+
30,
|
|
1225
|
+
}
|
|
1226
|
+
```
|
|
1227
|
+
|
|
1228
|
+
---
|
|
1229
|
+
|
|
1230
|
+
### `string-property-spacing`
|
|
1231
|
+
|
|
1232
|
+
String property keys should not have extra leading or trailing spaces inside the quotes.
|
|
1233
|
+
|
|
1234
|
+
```javascript
|
|
1235
|
+
// Good
|
|
1236
|
+
{ "& a": value }
|
|
1237
|
+
{ "selector": value }
|
|
1238
|
+
|
|
1239
|
+
// Bad
|
|
1240
|
+
{ " & a ": value }
|
|
1241
|
+
{ " selector ": value }
|
|
408
1242
|
```
|
|
409
1243
|
|
|
410
1244
|
<br />
|
|
411
1245
|
|
|
1246
|
+
---
|
|
1247
|
+
|
|
412
1248
|
## 🔧 Auto-fixing
|
|
413
1249
|
|
|
414
1250
|
All rules support auto-fixing. Run ESLint with the `--fix` flag:
|