@lvce-editor/eslint-plugin-virtual-dom 17.1.0 → 17.3.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/dist/index.js +666 -53
- package/package.json +1 -1
package/dist/index.js
CHANGED
|
@@ -52,8 +52,19 @@ const getProperty = (node, name) => {
|
|
|
52
52
|
const hasProperty = (node, name) => {
|
|
53
53
|
return Boolean(getProperty(node, name));
|
|
54
54
|
};
|
|
55
|
+
const virtualDomElementNames = new Set(['A', 'Abbr', 'Article', 'Aside', 'Audio', 'Br', 'Button', 'Cite', 'Code', 'Col', 'ColGroup', 'Data', 'Dd', 'Del', 'Div', 'Dl', 'Dt', 'Figcaption', 'Figure', 'Footer', 'H1', 'H2', 'H3', 'H4', 'H5', 'H6', 'Header', 'Hr', 'I', 'Img', 'Input', 'Ins', 'Kbd', 'Label', 'Li', 'Nav', 'Ol', 'Option', 'P', 'Pre', 'Reference', 'Root', 'Search', 'Section', 'Select', 'Span', 'Table', 'TBody', 'Td', 'Text', 'TextArea', 'Tfoot', 'Th', 'THead', 'Time', 'Tr', 'Ul', 'Video']);
|
|
56
|
+
const getVirtualDomElementName = node => {
|
|
57
|
+
if (!isMemberExpressionNode(node) || node.computed || !isIdentifierNode(node.object) || !isIdentifierNode(node.property) || !node.object.name.endsWith('Elements') || !virtualDomElementNames.has(node.property.name)) {
|
|
58
|
+
return undefined;
|
|
59
|
+
}
|
|
60
|
+
return node.property.name;
|
|
61
|
+
};
|
|
55
62
|
const isVirtualDomNode = node => {
|
|
56
|
-
|
|
63
|
+
if (!isObjectExpressionNode(node)) {
|
|
64
|
+
return false;
|
|
65
|
+
}
|
|
66
|
+
const typeProperty = getProperty(node, 'type');
|
|
67
|
+
return Boolean(typeProperty && (hasProperty(node, 'childCount') || getVirtualDomElementName(typeProperty.value)));
|
|
57
68
|
};
|
|
58
69
|
const isTextCall = node => {
|
|
59
70
|
return isCallExpressionNode(node) && isIdentifierNode(node.callee) && node.callee.name === 'text';
|
|
@@ -77,7 +88,67 @@ const isStringLiteral = node => {
|
|
|
77
88
|
return isLiteralNode(node) && typeof node.value === 'string';
|
|
78
89
|
};
|
|
79
90
|
|
|
80
|
-
const
|
|
91
|
+
const controlsRequiringDirectName = new Set(['Input', 'TextArea']);
|
|
92
|
+
const controlsAllowingChildren = new Set(['A', 'Button']);
|
|
93
|
+
const hasDirectName = node => {
|
|
94
|
+
return Boolean(getProperty(node, 'ariaLabel') || getProperty(node, 'ariaLabelledBy') || getProperty(node, 'title'));
|
|
95
|
+
};
|
|
96
|
+
const meta$p = {
|
|
97
|
+
docs: {
|
|
98
|
+
description: 'Require a statically determinable accessible name for virtual-dom controls'
|
|
99
|
+
},
|
|
100
|
+
messages: {
|
|
101
|
+
accessibleControlName: 'Add an accessible name to this virtual-dom `{{name}}` control.'
|
|
102
|
+
},
|
|
103
|
+
type: 'problem'
|
|
104
|
+
};
|
|
105
|
+
const create$p = context => {
|
|
106
|
+
return {
|
|
107
|
+
ObjectExpression(node) {
|
|
108
|
+
if (!isVirtualDomNode(node) || hasDirectName(node)) {
|
|
109
|
+
return;
|
|
110
|
+
}
|
|
111
|
+
const typeProperty = getProperty(node, 'type');
|
|
112
|
+
const elementName = typeProperty && getVirtualDomElementName(typeProperty.value);
|
|
113
|
+
if (!elementName) {
|
|
114
|
+
return;
|
|
115
|
+
}
|
|
116
|
+
if (controlsRequiringDirectName.has(elementName)) {
|
|
117
|
+
context.report({
|
|
118
|
+
data: {
|
|
119
|
+
name: elementName
|
|
120
|
+
},
|
|
121
|
+
messageId: 'accessibleControlName',
|
|
122
|
+
node
|
|
123
|
+
});
|
|
124
|
+
return;
|
|
125
|
+
}
|
|
126
|
+
if (!controlsAllowingChildren.has(elementName)) {
|
|
127
|
+
return;
|
|
128
|
+
}
|
|
129
|
+
const childCountProperty = getProperty(node, 'childCount');
|
|
130
|
+
const childCount = childCountProperty && getStaticNumberValue(childCountProperty.value);
|
|
131
|
+
if (childCount !== 0) {
|
|
132
|
+
return;
|
|
133
|
+
}
|
|
134
|
+
context.report({
|
|
135
|
+
data: {
|
|
136
|
+
name: elementName
|
|
137
|
+
},
|
|
138
|
+
messageId: 'accessibleControlName',
|
|
139
|
+
node
|
|
140
|
+
});
|
|
141
|
+
}
|
|
142
|
+
};
|
|
143
|
+
};
|
|
144
|
+
|
|
145
|
+
const accessibleControlName = {
|
|
146
|
+
__proto__: null,
|
|
147
|
+
create: create$p,
|
|
148
|
+
meta: meta$p
|
|
149
|
+
};
|
|
150
|
+
|
|
151
|
+
const meta$o = {
|
|
81
152
|
docs: {
|
|
82
153
|
description: 'Require an explicit role on clickable virtual-dom div nodes'
|
|
83
154
|
},
|
|
@@ -86,7 +157,7 @@ const meta$c = {
|
|
|
86
157
|
},
|
|
87
158
|
type: 'problem'
|
|
88
159
|
};
|
|
89
|
-
const create$
|
|
160
|
+
const create$o = context => {
|
|
90
161
|
return {
|
|
91
162
|
ObjectExpression(node) {
|
|
92
163
|
if (!isVirtualDomNode(node)) {
|
|
@@ -108,11 +179,11 @@ const create$c = context => {
|
|
|
108
179
|
|
|
109
180
|
const clickableDivNeedsRole = {
|
|
110
181
|
__proto__: null,
|
|
111
|
-
create: create$
|
|
112
|
-
meta: meta$
|
|
182
|
+
create: create$o,
|
|
183
|
+
meta: meta$o
|
|
113
184
|
};
|
|
114
185
|
|
|
115
|
-
const meta$
|
|
186
|
+
const meta$n = {
|
|
116
187
|
docs: {
|
|
117
188
|
description: 'Require static virtual-dom nodes created inside functions to be hoisted to module scope'
|
|
118
189
|
},
|
|
@@ -223,7 +294,7 @@ const isStaticExpression = (sourceCode, node) => {
|
|
|
223
294
|
return false;
|
|
224
295
|
}
|
|
225
296
|
};
|
|
226
|
-
const create$
|
|
297
|
+
const create$n = context => {
|
|
227
298
|
return {
|
|
228
299
|
ObjectExpression(node) {
|
|
229
300
|
if (!isVirtualDomElement(node)) {
|
|
@@ -248,11 +319,52 @@ const create$b = context => {
|
|
|
248
319
|
|
|
249
320
|
const hoistStaticNodes = {
|
|
250
321
|
__proto__: null,
|
|
251
|
-
create: create$
|
|
252
|
-
meta: meta$
|
|
322
|
+
create: create$n,
|
|
323
|
+
meta: meta$n
|
|
253
324
|
};
|
|
254
325
|
|
|
255
|
-
const meta$
|
|
326
|
+
const meta$m = {
|
|
327
|
+
docs: {
|
|
328
|
+
description: 'Disallow conditional spreads in virtual-dom arrays'
|
|
329
|
+
},
|
|
330
|
+
messages: {
|
|
331
|
+
noConditionalSpread: 'Move conditional virtual-dom children into a helper function and spread the helper result.'
|
|
332
|
+
},
|
|
333
|
+
type: 'suggestion'
|
|
334
|
+
};
|
|
335
|
+
const isConditionalSpread = node => {
|
|
336
|
+
return node?.type === 'SpreadElement' && node.argument.type === 'ConditionalExpression';
|
|
337
|
+
};
|
|
338
|
+
const isVirtualDomArray$1 = node => {
|
|
339
|
+
return isArrayExpressionNode(node) && node.elements.some(element => isVirtualDomNode(element) || isTextCall(element));
|
|
340
|
+
};
|
|
341
|
+
const addsVirtualDomChildren = spread => {
|
|
342
|
+
return isVirtualDomArray$1(spread.argument.consequent) || isVirtualDomArray$1(spread.argument.alternate);
|
|
343
|
+
};
|
|
344
|
+
const create$m = context => {
|
|
345
|
+
return {
|
|
346
|
+
ArrayExpression(node) {
|
|
347
|
+
const conditionalSpreads = node.elements.filter(isConditionalSpread);
|
|
348
|
+
if (!isVirtualDomArray$1(node) && !conditionalSpreads.some(addsVirtualDomChildren)) {
|
|
349
|
+
return;
|
|
350
|
+
}
|
|
351
|
+
for (const spread of conditionalSpreads) {
|
|
352
|
+
context.report({
|
|
353
|
+
messageId: 'noConditionalSpread',
|
|
354
|
+
node: spread
|
|
355
|
+
});
|
|
356
|
+
}
|
|
357
|
+
}
|
|
358
|
+
};
|
|
359
|
+
};
|
|
360
|
+
|
|
361
|
+
const noConditionalSpread = {
|
|
362
|
+
__proto__: null,
|
|
363
|
+
create: create$m,
|
|
364
|
+
meta: meta$m
|
|
365
|
+
};
|
|
366
|
+
|
|
367
|
+
const meta$l = {
|
|
256
368
|
docs: {
|
|
257
369
|
description: 'Disallow empty ARIA values in virtual-dom nodes'
|
|
258
370
|
},
|
|
@@ -264,7 +376,7 @@ const meta$a = {
|
|
|
264
376
|
const isAriaProperty = name => {
|
|
265
377
|
return /^aria[A-Z]/.test(name);
|
|
266
378
|
};
|
|
267
|
-
const create$
|
|
379
|
+
const create$l = context => {
|
|
268
380
|
return {
|
|
269
381
|
ObjectExpression(node) {
|
|
270
382
|
if (!isVirtualDomNode(node)) {
|
|
@@ -289,11 +401,11 @@ const create$a = context => {
|
|
|
289
401
|
|
|
290
402
|
const noEmptyAria = {
|
|
291
403
|
__proto__: null,
|
|
292
|
-
create: create$
|
|
293
|
-
meta: meta$
|
|
404
|
+
create: create$l,
|
|
405
|
+
meta: meta$l
|
|
294
406
|
};
|
|
295
407
|
|
|
296
|
-
const meta$
|
|
408
|
+
const meta$k = {
|
|
297
409
|
docs: {
|
|
298
410
|
description: 'Disallow empty className values in virtual-dom nodes'
|
|
299
411
|
},
|
|
@@ -302,7 +414,7 @@ const meta$9 = {
|
|
|
302
414
|
},
|
|
303
415
|
type: 'problem'
|
|
304
416
|
};
|
|
305
|
-
const create$
|
|
417
|
+
const create$k = context => {
|
|
306
418
|
return {
|
|
307
419
|
ObjectExpression(node) {
|
|
308
420
|
if (!isVirtualDomNode(node)) {
|
|
@@ -322,11 +434,11 @@ const create$9 = context => {
|
|
|
322
434
|
|
|
323
435
|
const noEmptyClassName = {
|
|
324
436
|
__proto__: null,
|
|
325
|
-
create: create$
|
|
326
|
-
meta: meta$
|
|
437
|
+
create: create$k,
|
|
438
|
+
meta: meta$k
|
|
327
439
|
};
|
|
328
440
|
|
|
329
|
-
const meta$
|
|
441
|
+
const meta$j = {
|
|
330
442
|
docs: {
|
|
331
443
|
description: 'Disallow inline event handlers in virtual-dom nodes'
|
|
332
444
|
},
|
|
@@ -341,7 +453,7 @@ const isEventPropertyName = name => {
|
|
|
341
453
|
const isInlineEventHandler = node => {
|
|
342
454
|
return isStringLiteral(node) || isTemplateLiteralNode(node) || isArrowFunctionExpressionNode(node) || isFunctionExpressionNode(node);
|
|
343
455
|
};
|
|
344
|
-
const create$
|
|
456
|
+
const create$j = context => {
|
|
345
457
|
return {
|
|
346
458
|
ObjectExpression(node) {
|
|
347
459
|
if (!isVirtualDomNode(node)) {
|
|
@@ -366,11 +478,11 @@ const create$8 = context => {
|
|
|
366
478
|
|
|
367
479
|
const noInlineEventHandlers = {
|
|
368
480
|
__proto__: null,
|
|
369
|
-
create: create$
|
|
370
|
-
meta: meta$
|
|
481
|
+
create: create$j,
|
|
482
|
+
meta: meta$j
|
|
371
483
|
};
|
|
372
484
|
|
|
373
|
-
const meta$
|
|
485
|
+
const meta$i = {
|
|
374
486
|
docs: {
|
|
375
487
|
description: 'Disallow inline style attributes in virtual-dom nodes'
|
|
376
488
|
},
|
|
@@ -379,7 +491,7 @@ const meta$7 = {
|
|
|
379
491
|
},
|
|
380
492
|
type: 'problem'
|
|
381
493
|
};
|
|
382
|
-
const create$
|
|
494
|
+
const create$i = context => {
|
|
383
495
|
return {
|
|
384
496
|
ObjectExpression(node) {
|
|
385
497
|
if (!isVirtualDomNode(node)) {
|
|
@@ -399,11 +511,59 @@ const create$7 = context => {
|
|
|
399
511
|
|
|
400
512
|
const noInlineStyle = {
|
|
401
513
|
__proto__: null,
|
|
402
|
-
create: create$
|
|
403
|
-
meta: meta$
|
|
514
|
+
create: create$i,
|
|
515
|
+
meta: meta$i
|
|
404
516
|
};
|
|
405
517
|
|
|
406
|
-
const
|
|
518
|
+
const ignoredProperties$1 = new Set(['childCount', 'type']);
|
|
519
|
+
const isOptionalExpression = node => {
|
|
520
|
+
return typeof node === 'object' && node !== null && ('type' in node && node.type === 'ChainExpression' || 'optional' in node && node.optional === true);
|
|
521
|
+
};
|
|
522
|
+
const isNullish = node => {
|
|
523
|
+
return isLiteralNode(node) && node.value === null || isIdentifierNode(node) && node.name === 'undefined' || isOptionalExpression(node);
|
|
524
|
+
};
|
|
525
|
+
const meta$h = {
|
|
526
|
+
docs: {
|
|
527
|
+
description: 'Disallow nullish virtual-dom attribute values'
|
|
528
|
+
},
|
|
529
|
+
messages: {
|
|
530
|
+
noNullishAttributeValue: 'Omit `{{name}}` instead of assigning a nullish value.'
|
|
531
|
+
},
|
|
532
|
+
type: 'problem'
|
|
533
|
+
};
|
|
534
|
+
const create$h = context => {
|
|
535
|
+
return {
|
|
536
|
+
ObjectExpression(node) {
|
|
537
|
+
if (!isVirtualDomNode(node)) {
|
|
538
|
+
return;
|
|
539
|
+
}
|
|
540
|
+
for (const property of node.properties) {
|
|
541
|
+
if (!isPropertyNode(property)) {
|
|
542
|
+
continue;
|
|
543
|
+
}
|
|
544
|
+
const name = getStaticPropertyName(property);
|
|
545
|
+
if (!name || ignoredProperties$1.has(name) || !isNullish(property.value)) {
|
|
546
|
+
continue;
|
|
547
|
+
}
|
|
548
|
+
context.report({
|
|
549
|
+
data: {
|
|
550
|
+
name
|
|
551
|
+
},
|
|
552
|
+
messageId: 'noNullishAttributeValue',
|
|
553
|
+
node: property.value
|
|
554
|
+
});
|
|
555
|
+
}
|
|
556
|
+
}
|
|
557
|
+
};
|
|
558
|
+
};
|
|
559
|
+
|
|
560
|
+
const noNullishAttributeValues = {
|
|
561
|
+
__proto__: null,
|
|
562
|
+
create: create$h,
|
|
563
|
+
meta: meta$h
|
|
564
|
+
};
|
|
565
|
+
|
|
566
|
+
const meta$g = {
|
|
407
567
|
docs: {
|
|
408
568
|
description: 'Disallow object-like attribute values in virtual-dom nodes'
|
|
409
569
|
},
|
|
@@ -416,7 +576,7 @@ const ignoredProperties = new Set(['childCount', 'type']);
|
|
|
416
576
|
const isObjectLikeAttributeValue = node => {
|
|
417
577
|
return isObjectExpressionNode(node) || isArrayExpressionNode(node) || isArrowFunctionExpressionNode(node) || isFunctionExpressionNode(node);
|
|
418
578
|
};
|
|
419
|
-
const create$
|
|
579
|
+
const create$g = context => {
|
|
420
580
|
return {
|
|
421
581
|
ObjectExpression(node) {
|
|
422
582
|
if (!isVirtualDomNode(node)) {
|
|
@@ -441,11 +601,45 @@ const create$6 = context => {
|
|
|
441
601
|
|
|
442
602
|
const noObjectAttributeValues = {
|
|
443
603
|
__proto__: null,
|
|
444
|
-
create: create$
|
|
445
|
-
meta: meta$
|
|
604
|
+
create: create$g,
|
|
605
|
+
meta: meta$g
|
|
446
606
|
};
|
|
447
607
|
|
|
448
|
-
const meta$
|
|
608
|
+
const meta$f = {
|
|
609
|
+
docs: {
|
|
610
|
+
description: 'Disallow positive virtual-dom tabIndex values'
|
|
611
|
+
},
|
|
612
|
+
messages: {
|
|
613
|
+
noPositiveTabIndex: 'Use a `tabIndex` of 0 or -1 instead of a positive value.'
|
|
614
|
+
},
|
|
615
|
+
type: 'problem'
|
|
616
|
+
};
|
|
617
|
+
const create$f = context => {
|
|
618
|
+
return {
|
|
619
|
+
ObjectExpression(node) {
|
|
620
|
+
if (!isVirtualDomNode(node)) {
|
|
621
|
+
return;
|
|
622
|
+
}
|
|
623
|
+
const tabIndexProperty = getProperty(node, 'tabIndex');
|
|
624
|
+
const tabIndex = tabIndexProperty && getStaticNumberValue(tabIndexProperty.value);
|
|
625
|
+
if (!tabIndexProperty || tabIndex === undefined || tabIndex <= 0) {
|
|
626
|
+
return;
|
|
627
|
+
}
|
|
628
|
+
context.report({
|
|
629
|
+
messageId: 'noPositiveTabIndex',
|
|
630
|
+
node: tabIndexProperty.value
|
|
631
|
+
});
|
|
632
|
+
}
|
|
633
|
+
};
|
|
634
|
+
};
|
|
635
|
+
|
|
636
|
+
const noPositiveTabIndex = {
|
|
637
|
+
__proto__: null,
|
|
638
|
+
create: create$f,
|
|
639
|
+
meta: meta$f
|
|
640
|
+
};
|
|
641
|
+
|
|
642
|
+
const meta$e = {
|
|
449
643
|
docs: {
|
|
450
644
|
description: 'Disallow raw string children in virtual-dom arrays'
|
|
451
645
|
},
|
|
@@ -457,7 +651,7 @@ const meta$5 = {
|
|
|
457
651
|
const isVirtualDomArray = node => {
|
|
458
652
|
return isArrayExpressionNode(node) && node.elements.some(element => isVirtualDomNode(element) || isTextCall(element));
|
|
459
653
|
};
|
|
460
|
-
const create$
|
|
654
|
+
const create$e = context => {
|
|
461
655
|
return {
|
|
462
656
|
ArrayExpression(node) {
|
|
463
657
|
if (!isVirtualDomArray(node)) {
|
|
@@ -478,16 +672,93 @@ const create$5 = context => {
|
|
|
478
672
|
|
|
479
673
|
const noRawTextChildren = {
|
|
480
674
|
__proto__: null,
|
|
481
|
-
create: create$
|
|
482
|
-
meta: meta$
|
|
675
|
+
create: create$e,
|
|
676
|
+
meta: meta$e
|
|
483
677
|
};
|
|
484
678
|
|
|
485
|
-
const meta$
|
|
679
|
+
const meta$d = {
|
|
680
|
+
docs: {
|
|
681
|
+
description: 'Require each virtual-dom event listener to call its dedicated handler'
|
|
682
|
+
},
|
|
683
|
+
messages: {
|
|
684
|
+
noSharedEventListenerHandler: 'Use the dedicated handler `{{name}}` as the first event listener parameter instead of `{{handler}}`.'
|
|
685
|
+
},
|
|
686
|
+
type: 'problem'
|
|
687
|
+
};
|
|
688
|
+
const create$d = context => {
|
|
689
|
+
return {
|
|
690
|
+
ObjectExpression(node) {
|
|
691
|
+
if (!isObjectExpressionNode(node)) {
|
|
692
|
+
return;
|
|
693
|
+
}
|
|
694
|
+
const nameProperty = getProperty(node, 'name');
|
|
695
|
+
const paramsProperty = getProperty(node, 'params');
|
|
696
|
+
if (!nameProperty || !paramsProperty || !isStringLiteral(nameProperty.value) || !isArrayExpressionNode(paramsProperty.value)) {
|
|
697
|
+
return;
|
|
698
|
+
}
|
|
699
|
+
const name = nameProperty.value.value;
|
|
700
|
+
const firstParameter = paramsProperty.value.elements[0];
|
|
701
|
+
if (!name.startsWith('handle') || !isStringLiteral(firstParameter) || firstParameter.value === name) {
|
|
702
|
+
return;
|
|
703
|
+
}
|
|
704
|
+
context.report({
|
|
705
|
+
data: {
|
|
706
|
+
handler: firstParameter.value,
|
|
707
|
+
name
|
|
708
|
+
},
|
|
709
|
+
messageId: 'noSharedEventListenerHandler',
|
|
710
|
+
node: firstParameter
|
|
711
|
+
});
|
|
712
|
+
}
|
|
713
|
+
};
|
|
714
|
+
};
|
|
715
|
+
|
|
716
|
+
const noSharedEventListenerHandlers = {
|
|
717
|
+
__proto__: null,
|
|
718
|
+
create: create$d,
|
|
719
|
+
meta: meta$d
|
|
720
|
+
};
|
|
721
|
+
|
|
722
|
+
const meta$c = {
|
|
723
|
+
docs: {
|
|
724
|
+
description: 'Prefer constants for single literal virtual-dom class names'
|
|
725
|
+
},
|
|
726
|
+
messages: {
|
|
727
|
+
preferClassNameConstant: 'Use a `ClassNames.*` constant instead of a literal `className`.'
|
|
728
|
+
},
|
|
729
|
+
type: 'suggestion'
|
|
730
|
+
};
|
|
731
|
+
const create$c = context => {
|
|
732
|
+
return {
|
|
733
|
+
ObjectExpression(node) {
|
|
734
|
+
if (!isVirtualDomNode(node)) {
|
|
735
|
+
return;
|
|
736
|
+
}
|
|
737
|
+
const classNameProperty = getProperty(node, 'className');
|
|
738
|
+
if (!classNameProperty || !isStringLiteral(classNameProperty.value) || classNameProperty.value.value === '' || /\s/.test(classNameProperty.value.value)) {
|
|
739
|
+
return;
|
|
740
|
+
}
|
|
741
|
+
context.report({
|
|
742
|
+
messageId: 'preferClassNameConstant',
|
|
743
|
+
node: classNameProperty.value
|
|
744
|
+
});
|
|
745
|
+
}
|
|
746
|
+
};
|
|
747
|
+
};
|
|
748
|
+
|
|
749
|
+
const preferClassNameConstants = {
|
|
750
|
+
__proto__: null,
|
|
751
|
+
create: create$c,
|
|
752
|
+
meta: meta$c
|
|
753
|
+
};
|
|
754
|
+
|
|
755
|
+
const meta$b = {
|
|
486
756
|
docs: {
|
|
487
757
|
description: 'Prefer virtual-dom constants over raw type, role, aria boolean, and tabIndex values'
|
|
488
758
|
},
|
|
489
759
|
messages: {
|
|
490
760
|
preferAriaBooleanConstant: 'Use an ARIA boolean constant instead of a raw string.',
|
|
761
|
+
preferEventListenerConstant: 'Use a named event listener constant instead of a raw numeric id.',
|
|
491
762
|
preferRoleConstant: 'Use `AriaRoles.*` instead of a raw role string.',
|
|
492
763
|
preferTabIndexConstant: 'Use `TabIndex.*` instead of a raw tabIndex number.',
|
|
493
764
|
preferTypeConstant: 'Use `VirtualDomElements.*` instead of a raw element type number.'
|
|
@@ -497,7 +768,7 @@ const meta$4 = {
|
|
|
497
768
|
const isAriaBooleanProperty = name => {
|
|
498
769
|
return /^aria[A-Z]/.test(name);
|
|
499
770
|
};
|
|
500
|
-
const create$
|
|
771
|
+
const create$b = context => {
|
|
501
772
|
return {
|
|
502
773
|
ObjectExpression(node) {
|
|
503
774
|
if (!isVirtualDomNode(node)) {
|
|
@@ -532,6 +803,13 @@ const create$4 = context => {
|
|
|
532
803
|
});
|
|
533
804
|
continue;
|
|
534
805
|
}
|
|
806
|
+
if (/^on[A-Z]/.test(name) && isNumericLiteral(property.value)) {
|
|
807
|
+
context.report({
|
|
808
|
+
messageId: 'preferEventListenerConstant',
|
|
809
|
+
node: property.value
|
|
810
|
+
});
|
|
811
|
+
continue;
|
|
812
|
+
}
|
|
535
813
|
if (isAriaBooleanProperty(name) && isStringLiteral(property.value) && (property.value.value === 'true' || property.value.value === 'false')) {
|
|
536
814
|
context.report({
|
|
537
815
|
messageId: 'preferAriaBooleanConstant',
|
|
@@ -545,11 +823,11 @@ const create$4 = context => {
|
|
|
545
823
|
|
|
546
824
|
const preferConstants = {
|
|
547
825
|
__proto__: null,
|
|
548
|
-
create: create$
|
|
549
|
-
meta: meta$
|
|
826
|
+
create: create$b,
|
|
827
|
+
meta: meta$b
|
|
550
828
|
};
|
|
551
829
|
|
|
552
|
-
const meta$
|
|
830
|
+
const meta$a = {
|
|
553
831
|
docs: {
|
|
554
832
|
description: 'Require Intl.DateTimeFormat instances to be created lazily'
|
|
555
833
|
},
|
|
@@ -564,7 +842,7 @@ const isFunctionNode = node => {
|
|
|
564
842
|
const isDateTimeFormat = node => {
|
|
565
843
|
return node.type === 'MemberExpression' && !node.computed && node.object.type === 'Identifier' && node.object.name === 'Intl' && node.property.type === 'Identifier' && node.property.name === 'DateTimeFormat';
|
|
566
844
|
};
|
|
567
|
-
const create$
|
|
845
|
+
const create$a = context => {
|
|
568
846
|
const isCreatedLazily = node => {
|
|
569
847
|
return context.sourceCode.getAncestors(node).some(isFunctionNode);
|
|
570
848
|
};
|
|
@@ -585,8 +863,8 @@ const create$3 = context => {
|
|
|
585
863
|
|
|
586
864
|
const preferLazyDateTimeFormat = {
|
|
587
865
|
__proto__: null,
|
|
588
|
-
create: create$
|
|
589
|
-
meta: meta$
|
|
866
|
+
create: create$a,
|
|
867
|
+
meta: meta$a
|
|
590
868
|
};
|
|
591
869
|
|
|
592
870
|
const isClassNameKey = node => {
|
|
@@ -634,7 +912,7 @@ const getParent = node => {
|
|
|
634
912
|
}
|
|
635
913
|
return undefined;
|
|
636
914
|
};
|
|
637
|
-
const meta$
|
|
915
|
+
const meta$9 = {
|
|
638
916
|
docs: {
|
|
639
917
|
description: 'Prefer mergeClassNames for composing virtual-dom className values'
|
|
640
918
|
},
|
|
@@ -643,7 +921,7 @@ const meta$2 = {
|
|
|
643
921
|
},
|
|
644
922
|
type: 'suggestion'
|
|
645
923
|
};
|
|
646
|
-
const create$
|
|
924
|
+
const create$9 = context => {
|
|
647
925
|
const reportNamespacedClassNameComposition = node => {
|
|
648
926
|
if (!isManualClassNameConcatenation(node) || !hasClassNamesReference(node)) {
|
|
649
927
|
return;
|
|
@@ -674,11 +952,11 @@ const create$2 = context => {
|
|
|
674
952
|
|
|
675
953
|
const preferMergeClassNames = {
|
|
676
954
|
__proto__: null,
|
|
677
|
-
create: create$
|
|
678
|
-
meta: meta$
|
|
955
|
+
create: create$9,
|
|
956
|
+
meta: meta$9
|
|
679
957
|
};
|
|
680
958
|
|
|
681
|
-
const meta$
|
|
959
|
+
const meta$8 = {
|
|
682
960
|
docs: {
|
|
683
961
|
description: 'Prefer destructuring state properties before use'
|
|
684
962
|
},
|
|
@@ -705,7 +983,7 @@ const isWriteExpression = node => {
|
|
|
705
983
|
}
|
|
706
984
|
return parent.type === 'UnaryExpression' && parent.operator === 'delete' && parent.argument === node;
|
|
707
985
|
};
|
|
708
|
-
const create$
|
|
986
|
+
const create$8 = context => {
|
|
709
987
|
return {
|
|
710
988
|
MemberExpression(node) {
|
|
711
989
|
if (node.computed) {
|
|
@@ -733,11 +1011,218 @@ const create$1 = context => {
|
|
|
733
1011
|
|
|
734
1012
|
const preferStateDestructuring = {
|
|
735
1013
|
__proto__: null,
|
|
736
|
-
create: create$
|
|
737
|
-
meta: meta$
|
|
1014
|
+
create: create$8,
|
|
1015
|
+
meta: meta$8
|
|
738
1016
|
};
|
|
739
1017
|
|
|
740
|
-
const meta = {
|
|
1018
|
+
const meta$7 = {
|
|
1019
|
+
docs: {
|
|
1020
|
+
description: 'Require event listener options for handlers with specific browser event behavior'
|
|
1021
|
+
},
|
|
1022
|
+
messages: {
|
|
1023
|
+
requirePreventDefault: '`{{name}}` event listeners must set `preventDefault` to `true`.'
|
|
1024
|
+
},
|
|
1025
|
+
type: 'problem'
|
|
1026
|
+
};
|
|
1027
|
+
const listenersRequiringPreventDefault = new Set(['handleDragOver', 'handleDrop']);
|
|
1028
|
+
const create$7 = context => {
|
|
1029
|
+
return {
|
|
1030
|
+
ObjectExpression(node) {
|
|
1031
|
+
if (!isObjectExpressionNode(node) || !getProperty(node, 'params')) {
|
|
1032
|
+
return;
|
|
1033
|
+
}
|
|
1034
|
+
const nameProperty = getProperty(node, 'name');
|
|
1035
|
+
if (!nameProperty || !isStringLiteral(nameProperty.value) || !listenersRequiringPreventDefault.has(nameProperty.value.value)) {
|
|
1036
|
+
return;
|
|
1037
|
+
}
|
|
1038
|
+
const preventDefaultProperty = getProperty(node, 'preventDefault');
|
|
1039
|
+
if (preventDefaultProperty && isLiteralNode(preventDefaultProperty.value) && preventDefaultProperty.value.value === true) {
|
|
1040
|
+
return;
|
|
1041
|
+
}
|
|
1042
|
+
context.report({
|
|
1043
|
+
data: {
|
|
1044
|
+
name: nameProperty.value.value
|
|
1045
|
+
},
|
|
1046
|
+
messageId: 'requirePreventDefault',
|
|
1047
|
+
node: preventDefaultProperty ? preventDefaultProperty.value : nameProperty
|
|
1048
|
+
});
|
|
1049
|
+
}
|
|
1050
|
+
};
|
|
1051
|
+
};
|
|
1052
|
+
|
|
1053
|
+
const requireEventListenerOptions = {
|
|
1054
|
+
__proto__: null,
|
|
1055
|
+
create: create$7,
|
|
1056
|
+
meta: meta$7
|
|
1057
|
+
};
|
|
1058
|
+
|
|
1059
|
+
const meta$6 = {
|
|
1060
|
+
docs: {
|
|
1061
|
+
description: 'Require alt text on virtual-dom image nodes'
|
|
1062
|
+
},
|
|
1063
|
+
messages: {
|
|
1064
|
+
requireImageAlt: 'Add an `alt` attribute to this virtual-dom image.'
|
|
1065
|
+
},
|
|
1066
|
+
type: 'problem'
|
|
1067
|
+
};
|
|
1068
|
+
const create$6 = context => {
|
|
1069
|
+
return {
|
|
1070
|
+
ObjectExpression(node) {
|
|
1071
|
+
if (!isVirtualDomNode(node)) {
|
|
1072
|
+
return;
|
|
1073
|
+
}
|
|
1074
|
+
const typeProperty = getProperty(node, 'type');
|
|
1075
|
+
if (!typeProperty || getVirtualDomElementName(typeProperty.value) !== 'Img' || getProperty(node, 'alt')) {
|
|
1076
|
+
return;
|
|
1077
|
+
}
|
|
1078
|
+
context.report({
|
|
1079
|
+
messageId: 'requireImageAlt',
|
|
1080
|
+
node
|
|
1081
|
+
});
|
|
1082
|
+
}
|
|
1083
|
+
};
|
|
1084
|
+
};
|
|
1085
|
+
|
|
1086
|
+
const requireImageAlt = {
|
|
1087
|
+
__proto__: null,
|
|
1088
|
+
create: create$6,
|
|
1089
|
+
meta: meta$6
|
|
1090
|
+
};
|
|
1091
|
+
|
|
1092
|
+
const meta$5 = {
|
|
1093
|
+
docs: {
|
|
1094
|
+
description: 'Require secure attributes on virtual-dom links'
|
|
1095
|
+
},
|
|
1096
|
+
messages: {
|
|
1097
|
+
secureLinkRel: 'Set `rel` to `noopener noreferrer` on virtual-dom links.',
|
|
1098
|
+
secureLinkTarget: 'Set `target` to `_blank` on virtual-dom links.'
|
|
1099
|
+
},
|
|
1100
|
+
type: 'problem'
|
|
1101
|
+
};
|
|
1102
|
+
const hasStringPropertyValue = (node, name, value) => {
|
|
1103
|
+
const property = getProperty(node, name);
|
|
1104
|
+
return Boolean(property && isStringLiteral(property.value) && property.value.value === value);
|
|
1105
|
+
};
|
|
1106
|
+
const create$5 = context => {
|
|
1107
|
+
return {
|
|
1108
|
+
ObjectExpression(node) {
|
|
1109
|
+
if (!isVirtualDomNode(node)) {
|
|
1110
|
+
return;
|
|
1111
|
+
}
|
|
1112
|
+
const typeProperty = getProperty(node, 'type');
|
|
1113
|
+
const hrefProperty = getProperty(node, 'href');
|
|
1114
|
+
if (!typeProperty || !hrefProperty || !isMemberExpressionWithProperty(typeProperty.value, 'A')) {
|
|
1115
|
+
return;
|
|
1116
|
+
}
|
|
1117
|
+
if (!hasStringPropertyValue(node, 'target', '_blank')) {
|
|
1118
|
+
context.report({
|
|
1119
|
+
messageId: 'secureLinkTarget',
|
|
1120
|
+
node
|
|
1121
|
+
});
|
|
1122
|
+
}
|
|
1123
|
+
if (!hasStringPropertyValue(node, 'rel', 'noopener noreferrer')) {
|
|
1124
|
+
context.report({
|
|
1125
|
+
messageId: 'secureLinkRel',
|
|
1126
|
+
node
|
|
1127
|
+
});
|
|
1128
|
+
}
|
|
1129
|
+
}
|
|
1130
|
+
};
|
|
1131
|
+
};
|
|
1132
|
+
|
|
1133
|
+
const secureLinks = {
|
|
1134
|
+
__proto__: null,
|
|
1135
|
+
create: create$5,
|
|
1136
|
+
meta: meta$5
|
|
1137
|
+
};
|
|
1138
|
+
|
|
1139
|
+
const validAriaProperties = new Set(['ariaActivedescendant', 'ariaAtomic', 'ariaAutoComplete', 'ariaBrailleLabel', 'ariaBrailleRoleDescription', 'ariaBusy', 'ariaChecked', 'ariaColCount', 'ariaColIndex', 'ariaColIndexText', 'ariaColSpan', 'ariaControls', 'ariaCurrent', 'ariaDescribedBy', 'ariaDescription', 'ariaDetails', 'ariaDisabled', 'ariaErrorMessage', 'ariaExpanded', 'ariaFlowTo', 'ariaHasPopup', 'ariaHidden', 'ariaInvalid', 'ariaKeyShortcuts', 'ariaLabel', 'ariaLabelledBy', 'ariaLevel', 'ariaLive', 'ariaModal', 'ariaMultiLine', 'ariaMultiSelectable', 'ariaOrientation', 'ariaOwns', 'ariaPlaceholder', 'ariaPosInSet', 'ariaPressed', 'ariaReadOnly', 'ariaRelevant', 'ariaRequired', 'ariaRoleDescription', 'ariaRowCount', 'ariaRowIndex', 'ariaRowIndexText', 'ariaRowSpan', 'ariaSelected', 'ariaSetSize', 'ariaSort', 'ariaValueMax', 'ariaValueMin', 'ariaValueNow', 'ariaValueText']);
|
|
1140
|
+
const meta$4 = {
|
|
1141
|
+
docs: {
|
|
1142
|
+
description: 'Validate virtual-dom ARIA property names'
|
|
1143
|
+
},
|
|
1144
|
+
messages: {
|
|
1145
|
+
validAriaProperty: '`{{name}}` is not a valid virtual-dom ARIA property.'
|
|
1146
|
+
},
|
|
1147
|
+
type: 'problem'
|
|
1148
|
+
};
|
|
1149
|
+
const create$4 = context => {
|
|
1150
|
+
return {
|
|
1151
|
+
ObjectExpression(node) {
|
|
1152
|
+
if (!isVirtualDomNode(node)) {
|
|
1153
|
+
return;
|
|
1154
|
+
}
|
|
1155
|
+
for (const property of node.properties) {
|
|
1156
|
+
if (!isPropertyNode(property)) {
|
|
1157
|
+
continue;
|
|
1158
|
+
}
|
|
1159
|
+
const name = getStaticPropertyName(property);
|
|
1160
|
+
if (!name?.startsWith('aria') || validAriaProperties.has(name)) {
|
|
1161
|
+
continue;
|
|
1162
|
+
}
|
|
1163
|
+
context.report({
|
|
1164
|
+
data: {
|
|
1165
|
+
name
|
|
1166
|
+
},
|
|
1167
|
+
messageId: 'validAriaProperty',
|
|
1168
|
+
node: property
|
|
1169
|
+
});
|
|
1170
|
+
}
|
|
1171
|
+
}
|
|
1172
|
+
};
|
|
1173
|
+
};
|
|
1174
|
+
|
|
1175
|
+
const validAriaProperties$1 = {
|
|
1176
|
+
__proto__: null,
|
|
1177
|
+
create: create$4,
|
|
1178
|
+
meta: meta$4
|
|
1179
|
+
};
|
|
1180
|
+
|
|
1181
|
+
const allowedValues = new Map([['ariaAtomic', new Set(['false', 'true'])], ['ariaAutoComplete', new Set(['both', 'inline', 'list', 'none'])], ['ariaBusy', new Set(['false', 'true'])], ['ariaChecked', new Set(['false', 'mixed', 'true'])], ['ariaCurrent', new Set(['date', 'false', 'location', 'page', 'step', 'time', 'true'])], ['ariaDisabled', new Set(['false', 'true'])], ['ariaExpanded', new Set(['false', 'true'])], ['ariaHasPopup', new Set(['dialog', 'false', 'grid', 'listbox', 'menu', 'tree', 'true'])], ['ariaHidden', new Set(['false', 'true'])], ['ariaInvalid', new Set(['false', 'grammar', 'spelling', 'true'])], ['ariaLive', new Set(['assertive', 'off', 'polite'])], ['ariaModal', new Set(['false', 'true'])], ['ariaMultiLine', new Set(['false', 'true'])], ['ariaMultiSelectable', new Set(['false', 'true'])], ['ariaOrientation', new Set(['horizontal', 'undefined', 'vertical'])], ['ariaPressed', new Set(['false', 'mixed', 'true'])], ['ariaReadOnly', new Set(['false', 'true'])], ['ariaRelevant', new Set(['additions', 'additions removals', 'additions text', 'all', 'removals', 'removals additions', 'removals text', 'text', 'text additions', 'text removals'])], ['ariaRequired', new Set(['false', 'true'])], ['ariaSelected', new Set(['false', 'true'])], ['ariaSort', new Set(['ascending', 'descending', 'none', 'other'])]]);
|
|
1182
|
+
const meta$3 = {
|
|
1183
|
+
docs: {
|
|
1184
|
+
description: 'Validate literal virtual-dom ARIA values'
|
|
1185
|
+
},
|
|
1186
|
+
messages: {
|
|
1187
|
+
validAriaValue: '`{{value}}` is not a valid value for `{{name}}`.'
|
|
1188
|
+
},
|
|
1189
|
+
type: 'problem'
|
|
1190
|
+
};
|
|
1191
|
+
const create$3 = context => {
|
|
1192
|
+
return {
|
|
1193
|
+
ObjectExpression(node) {
|
|
1194
|
+
if (!isVirtualDomNode(node)) {
|
|
1195
|
+
return;
|
|
1196
|
+
}
|
|
1197
|
+
for (const property of node.properties) {
|
|
1198
|
+
if (!isPropertyNode(property)) {
|
|
1199
|
+
continue;
|
|
1200
|
+
}
|
|
1201
|
+
const name = getStaticPropertyName(property);
|
|
1202
|
+
const values = name && allowedValues.get(name);
|
|
1203
|
+
if (!name || !values || !isStringLiteral(property.value) || values.has(property.value.value)) {
|
|
1204
|
+
continue;
|
|
1205
|
+
}
|
|
1206
|
+
context.report({
|
|
1207
|
+
data: {
|
|
1208
|
+
name,
|
|
1209
|
+
value: property.value.value
|
|
1210
|
+
},
|
|
1211
|
+
messageId: 'validAriaValue',
|
|
1212
|
+
node: property.value
|
|
1213
|
+
});
|
|
1214
|
+
}
|
|
1215
|
+
}
|
|
1216
|
+
};
|
|
1217
|
+
};
|
|
1218
|
+
|
|
1219
|
+
const validAriaValues = {
|
|
1220
|
+
__proto__: null,
|
|
1221
|
+
create: create$3,
|
|
1222
|
+
meta: meta$3
|
|
1223
|
+
};
|
|
1224
|
+
|
|
1225
|
+
const meta$2 = {
|
|
741
1226
|
docs: {
|
|
742
1227
|
description: 'Validate statically analyzable virtual-dom childCount values'
|
|
743
1228
|
},
|
|
@@ -812,7 +1297,7 @@ const hasImpossibleChildCount = (elements, index) => {
|
|
|
812
1297
|
}
|
|
813
1298
|
return false;
|
|
814
1299
|
};
|
|
815
|
-
const create = context => {
|
|
1300
|
+
const create$2 = context => {
|
|
816
1301
|
return {
|
|
817
1302
|
ArrayExpression(node) {
|
|
818
1303
|
if (!isArrayExpressionNode(node) || !node.elements.some(isVirtualDomNode) || !node.elements.every(isAnalyzableVirtualDomElement)) {
|
|
@@ -841,6 +1326,103 @@ const create = context => {
|
|
|
841
1326
|
};
|
|
842
1327
|
|
|
843
1328
|
const validChildCount = {
|
|
1329
|
+
__proto__: null,
|
|
1330
|
+
create: create$2,
|
|
1331
|
+
meta: meta$2
|
|
1332
|
+
};
|
|
1333
|
+
|
|
1334
|
+
const supportedEventProperties = new Set(['onBeforeInput', 'onBlur', 'onChange', 'onClick', 'onContextMenu', 'onDblClick', 'onDragEnd', 'onDragEnter', 'onDragLeave', 'onDragOver', 'onDragStart', 'onDrop', 'onFocus', 'onFocusIn', 'onFocusOut', 'onInput', 'onKeyDown', 'onKeyUp', 'onMouseDown', 'onMouseMove', 'onMouseOut', 'onMouseOver', 'onMouseUp', 'onPointerDown', 'onPointerMove', 'onPointerOut', 'onPointerOver', 'onScroll', 'onSelectionChange', 'onSubmit', 'onWheel']);
|
|
1335
|
+
const meta$1 = {
|
|
1336
|
+
docs: {
|
|
1337
|
+
description: 'Require virtual-dom event properties supported by the renderer'
|
|
1338
|
+
},
|
|
1339
|
+
messages: {
|
|
1340
|
+
validEventProperty: '`{{name}}` is not a supported virtual-dom event property.'
|
|
1341
|
+
},
|
|
1342
|
+
type: 'problem'
|
|
1343
|
+
};
|
|
1344
|
+
const create$1 = context => {
|
|
1345
|
+
return {
|
|
1346
|
+
ObjectExpression(node) {
|
|
1347
|
+
if (!isVirtualDomNode(node)) {
|
|
1348
|
+
return;
|
|
1349
|
+
}
|
|
1350
|
+
for (const property of node.properties) {
|
|
1351
|
+
if (!isPropertyNode(property)) {
|
|
1352
|
+
continue;
|
|
1353
|
+
}
|
|
1354
|
+
const name = getStaticPropertyName(property);
|
|
1355
|
+
if (!name?.startsWith('on') || supportedEventProperties.has(name)) {
|
|
1356
|
+
continue;
|
|
1357
|
+
}
|
|
1358
|
+
context.report({
|
|
1359
|
+
data: {
|
|
1360
|
+
name
|
|
1361
|
+
},
|
|
1362
|
+
messageId: 'validEventProperty',
|
|
1363
|
+
node: property
|
|
1364
|
+
});
|
|
1365
|
+
}
|
|
1366
|
+
}
|
|
1367
|
+
};
|
|
1368
|
+
};
|
|
1369
|
+
|
|
1370
|
+
const validEventProperties = {
|
|
1371
|
+
__proto__: null,
|
|
1372
|
+
create: create$1,
|
|
1373
|
+
meta: meta$1
|
|
1374
|
+
};
|
|
1375
|
+
|
|
1376
|
+
const voidElements = new Set(['Br', 'Col', 'Hr', 'Img', 'Input']);
|
|
1377
|
+
const meta = {
|
|
1378
|
+
docs: {
|
|
1379
|
+
description: 'Require canonical virtual-dom node shapes'
|
|
1380
|
+
},
|
|
1381
|
+
messages: {
|
|
1382
|
+
elementTextProperty: 'Use a `text(...)` child instead of a `text` property on an element node.',
|
|
1383
|
+
missingChildCount: 'Add an explicit `childCount` to this virtual-dom node.',
|
|
1384
|
+
voidElementChildren: '`VirtualDomElements.{{name}}` must have a `childCount` of 0.'
|
|
1385
|
+
},
|
|
1386
|
+
type: 'problem'
|
|
1387
|
+
};
|
|
1388
|
+
const create = context => {
|
|
1389
|
+
return {
|
|
1390
|
+
ObjectExpression(node) {
|
|
1391
|
+
if (!isObjectExpressionNode(node)) {
|
|
1392
|
+
return;
|
|
1393
|
+
}
|
|
1394
|
+
const typeProperty = getProperty(node, 'type');
|
|
1395
|
+
const elementName = typeProperty && getVirtualDomElementName(typeProperty.value);
|
|
1396
|
+
if (!typeProperty || !elementName) {
|
|
1397
|
+
return;
|
|
1398
|
+
}
|
|
1399
|
+
const childCountProperty = getProperty(node, 'childCount');
|
|
1400
|
+
if (!childCountProperty) {
|
|
1401
|
+
context.report({
|
|
1402
|
+
messageId: 'missingChildCount',
|
|
1403
|
+
node
|
|
1404
|
+
});
|
|
1405
|
+
} else if (voidElements.has(elementName) && getStaticNumberValue(childCountProperty.value) !== 0) {
|
|
1406
|
+
context.report({
|
|
1407
|
+
data: {
|
|
1408
|
+
name: elementName
|
|
1409
|
+
},
|
|
1410
|
+
messageId: 'voidElementChildren',
|
|
1411
|
+
node: childCountProperty
|
|
1412
|
+
});
|
|
1413
|
+
}
|
|
1414
|
+
const textProperty = getProperty(node, 'text');
|
|
1415
|
+
if (textProperty && elementName !== 'Text') {
|
|
1416
|
+
context.report({
|
|
1417
|
+
messageId: 'elementTextProperty',
|
|
1418
|
+
node: textProperty
|
|
1419
|
+
});
|
|
1420
|
+
}
|
|
1421
|
+
}
|
|
1422
|
+
};
|
|
1423
|
+
};
|
|
1424
|
+
|
|
1425
|
+
const validNodeShape = {
|
|
844
1426
|
__proto__: null,
|
|
845
1427
|
create,
|
|
846
1428
|
meta
|
|
@@ -853,19 +1435,32 @@ const plugin = {
|
|
|
853
1435
|
version: '0.0.1'
|
|
854
1436
|
},
|
|
855
1437
|
rules: {
|
|
1438
|
+
'accessible-control-name': accessibleControlName,
|
|
856
1439
|
'clickable-div-needs-role': clickableDivNeedsRole,
|
|
857
1440
|
'hoist-static-nodes': hoistStaticNodes,
|
|
1441
|
+
'no-conditional-spread': noConditionalSpread,
|
|
858
1442
|
'no-empty-aria': noEmptyAria,
|
|
859
1443
|
'no-empty-class-name': noEmptyClassName,
|
|
860
1444
|
'no-inline-event-handlers': noInlineEventHandlers,
|
|
861
1445
|
'no-inline-style': noInlineStyle,
|
|
1446
|
+
'no-nullish-attribute-values': noNullishAttributeValues,
|
|
862
1447
|
'no-object-attribute-values': noObjectAttributeValues,
|
|
1448
|
+
'no-positive-tab-index': noPositiveTabIndex,
|
|
863
1449
|
'no-raw-text-children': noRawTextChildren,
|
|
1450
|
+
'no-shared-event-listener-handlers': noSharedEventListenerHandlers,
|
|
1451
|
+
'prefer-class-name-constants': preferClassNameConstants,
|
|
864
1452
|
'prefer-constants': preferConstants,
|
|
865
1453
|
'prefer-lazy-date-time-format': preferLazyDateTimeFormat,
|
|
866
1454
|
'prefer-merge-class-names': preferMergeClassNames,
|
|
867
1455
|
'prefer-state-destructuring': preferStateDestructuring,
|
|
868
|
-
'
|
|
1456
|
+
'require-event-listener-options': requireEventListenerOptions,
|
|
1457
|
+
'require-image-alt': requireImageAlt,
|
|
1458
|
+
'secure-links': secureLinks,
|
|
1459
|
+
'valid-aria-properties': validAriaProperties$1,
|
|
1460
|
+
'valid-aria-values': validAriaValues,
|
|
1461
|
+
'valid-child-count': validChildCount,
|
|
1462
|
+
'valid-event-properties': validEventProperties,
|
|
1463
|
+
'valid-node-shape': validNodeShape
|
|
869
1464
|
}
|
|
870
1465
|
};
|
|
871
1466
|
const recommended = [{
|
|
@@ -876,16 +1471,20 @@ const recommended = [{
|
|
|
876
1471
|
rules: {
|
|
877
1472
|
'virtual-dom/clickable-div-needs-role': 'error',
|
|
878
1473
|
'virtual-dom/hoist-static-nodes': 'error',
|
|
1474
|
+
'virtual-dom/no-conditional-spread': 'error',
|
|
879
1475
|
'virtual-dom/no-empty-aria': 'error',
|
|
880
1476
|
'virtual-dom/no-empty-class-name': 'error',
|
|
881
1477
|
'virtual-dom/no-inline-event-handlers': 'error',
|
|
882
1478
|
'virtual-dom/no-inline-style': 'error',
|
|
883
1479
|
'virtual-dom/no-object-attribute-values': 'error',
|
|
884
1480
|
'virtual-dom/no-raw-text-children': 'error',
|
|
1481
|
+
'virtual-dom/no-shared-event-listener-handlers': 'error',
|
|
885
1482
|
'virtual-dom/prefer-constants': 'error',
|
|
886
1483
|
'virtual-dom/prefer-lazy-date-time-format': 'error',
|
|
887
1484
|
'virtual-dom/prefer-merge-class-names': 'error',
|
|
888
1485
|
'virtual-dom/prefer-state-destructuring': 'error',
|
|
1486
|
+
'virtual-dom/require-event-listener-options': 'error',
|
|
1487
|
+
'virtual-dom/secure-links': 'error',
|
|
889
1488
|
'virtual-dom/valid-child-count': 'error'
|
|
890
1489
|
}
|
|
891
1490
|
}, {
|
|
@@ -894,5 +1493,19 @@ const recommended = [{
|
|
|
894
1493
|
'virtual-dom/hoist-static-nodes': 'off'
|
|
895
1494
|
}
|
|
896
1495
|
}];
|
|
1496
|
+
const strict = [...recommended, {
|
|
1497
|
+
files: ['**/*.{js,mjs,cjs,ts,mts,cts}'],
|
|
1498
|
+
rules: {
|
|
1499
|
+
'virtual-dom/accessible-control-name': 'error',
|
|
1500
|
+
'virtual-dom/no-nullish-attribute-values': 'error',
|
|
1501
|
+
'virtual-dom/no-positive-tab-index': 'error',
|
|
1502
|
+
'virtual-dom/prefer-class-name-constants': 'error',
|
|
1503
|
+
'virtual-dom/require-image-alt': 'error',
|
|
1504
|
+
'virtual-dom/valid-aria-properties': 'error',
|
|
1505
|
+
'virtual-dom/valid-aria-values': 'error',
|
|
1506
|
+
'virtual-dom/valid-event-properties': 'error',
|
|
1507
|
+
'virtual-dom/valid-node-shape': 'error'
|
|
1508
|
+
}
|
|
1509
|
+
}];
|
|
897
1510
|
|
|
898
|
-
export { recommended as default };
|
|
1511
|
+
export { recommended as default, strict };
|