@html-eslint/eslint-plugin 0.50.0 → 0.52.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.
Files changed (173) hide show
  1. package/lib/configs/recommended.js +8 -2
  2. package/lib/index.js +2 -6
  3. package/lib/languages/html-language.js +23 -15
  4. package/lib/languages/html-source-code.js +34 -26
  5. package/lib/languages/html-traversal-step.js +6 -10
  6. package/lib/rules/attrs-newline.js +9 -9
  7. package/lib/rules/class-spacing.js +148 -0
  8. package/lib/rules/element-newline.js +18 -21
  9. package/lib/rules/id-naming-convention.js +15 -12
  10. package/lib/rules/indent/indent-level.js +10 -17
  11. package/lib/rules/indent/indent.js +51 -56
  12. package/lib/rules/index.js +7 -1
  13. package/lib/rules/lowercase.js +11 -23
  14. package/lib/rules/max-element-depth.js +8 -10
  15. package/lib/rules/no-abstract-roles.js +8 -8
  16. package/lib/rules/no-accesskey-attrs.js +8 -8
  17. package/lib/rules/no-aria-hidden-body.js +2 -6
  18. package/lib/rules/no-aria-hidden-on-focusable.js +4 -5
  19. package/lib/rules/no-duplicate-attrs.js +12 -8
  20. package/lib/rules/no-duplicate-class.js +8 -14
  21. package/lib/rules/no-duplicate-id.js +9 -15
  22. package/lib/rules/no-duplicate-in-head.js +10 -17
  23. package/lib/rules/no-empty-headings.js +7 -8
  24. package/lib/rules/no-extra-spacing-attrs.js +13 -8
  25. package/lib/rules/no-extra-spacing-text.js +11 -14
  26. package/lib/rules/no-heading-inside-button.js +2 -6
  27. package/lib/rules/no-ineffective-attrs.js +14 -15
  28. package/lib/rules/no-inline-styles.js +2 -6
  29. package/lib/rules/no-invalid-entity.js +4 -8
  30. package/lib/rules/no-invalid-role.js +3 -10
  31. package/lib/rules/no-multiple-empty-lines.js +7 -7
  32. package/lib/rules/no-multiple-h1.js +4 -8
  33. package/lib/rules/no-nested-interactive.js +5 -9
  34. package/lib/rules/no-non-scalable-viewport.js +2 -6
  35. package/lib/rules/no-obsolete-attrs.js +83 -0
  36. package/lib/rules/no-obsolete-tags.js +2 -6
  37. package/lib/rules/no-positive-tabindex.js +8 -8
  38. package/lib/rules/no-restricted-attr-values.js +18 -21
  39. package/lib/rules/no-restricted-attrs.js +18 -22
  40. package/lib/rules/no-restricted-tags.js +17 -20
  41. package/lib/rules/no-script-style-type.js +7 -6
  42. package/lib/rules/no-skip-heading-levels.js +4 -8
  43. package/lib/rules/no-target-blank.js +3 -6
  44. package/lib/rules/no-trailing-spaces.js +7 -6
  45. package/lib/rules/no-whitespace-only-children.js +113 -0
  46. package/lib/rules/prefer-https.js +11 -14
  47. package/lib/rules/quotes.js +13 -16
  48. package/lib/rules/require-attrs.js +18 -17
  49. package/lib/rules/require-button-type.js +6 -5
  50. package/lib/rules/require-closing-tags.js +9 -12
  51. package/lib/rules/require-doctype.js +2 -6
  52. package/lib/rules/require-explicit-size.js +2 -5
  53. package/lib/rules/require-form-method.js +2 -6
  54. package/lib/rules/require-frame-title.js +2 -6
  55. package/lib/rules/require-img-alt.js +3 -6
  56. package/lib/rules/require-input-label.js +3 -5
  57. package/lib/rules/require-lang.js +2 -6
  58. package/lib/rules/require-li-container.js +2 -6
  59. package/lib/rules/require-meta-charset.js +6 -5
  60. package/lib/rules/require-meta-description.js +6 -5
  61. package/lib/rules/require-meta-viewport.js +6 -5
  62. package/lib/rules/require-open-graph-protocol.js +7 -8
  63. package/lib/rules/require-title.js +7 -5
  64. package/lib/rules/sort-attrs.js +13 -19
  65. package/lib/rules/use-baseline.js +8 -6
  66. package/lib/rules/utils/baseline.js +4 -6
  67. package/lib/rules/utils/naming.js +14 -7
  68. package/lib/rules/utils/node.js +63 -29
  69. package/lib/rules/utils/rule.js +1 -4
  70. package/lib/rules/utils/settings.js +9 -3
  71. package/lib/rules/utils/source-code.js +2 -6
  72. package/lib/rules/utils/template-literal.js +16 -7
  73. package/lib/rules/utils/visitors.js +4 -1
  74. package/lib/specs/index.js +5 -0
  75. package/lib/specs/obsolete-attrs.js +604 -0
  76. package/lib/types/ast.ts +5 -2
  77. package/package.json +6 -6
  78. package/types/configs/recommended.d.ts +2 -1
  79. package/types/configs/recommended.d.ts.map +1 -1
  80. package/types/index.d.ts +2 -6
  81. package/types/index.d.ts.map +1 -1
  82. package/types/languages/html-language.d.ts +12 -10
  83. package/types/languages/html-language.d.ts.map +1 -1
  84. package/types/languages/html-source-code.d.ts +13 -6
  85. package/types/languages/html-source-code.d.ts.map +1 -1
  86. package/types/languages/html-traversal-step.d.ts +5 -5
  87. package/types/languages/html-traversal-step.d.ts.map +1 -1
  88. package/types/rules/attrs-newline.d.ts +1 -1
  89. package/types/rules/attrs-newline.d.ts.map +1 -1
  90. package/types/rules/class-spacing.d.ts +4 -0
  91. package/types/rules/class-spacing.d.ts.map +1 -0
  92. package/types/rules/element-newline.d.ts +3 -3
  93. package/types/rules/element-newline.d.ts.map +1 -1
  94. package/types/rules/id-naming-convention.d.ts.map +1 -1
  95. package/types/rules/indent/indent-level.d.ts +10 -17
  96. package/types/rules/indent/indent-level.d.ts.map +1 -1
  97. package/types/rules/indent/indent.d.ts.map +1 -1
  98. package/types/rules/lowercase.d.ts.map +1 -1
  99. package/types/rules/max-element-depth.d.ts.map +1 -1
  100. package/types/rules/no-abstract-roles.d.ts.map +1 -1
  101. package/types/rules/no-accesskey-attrs.d.ts.map +1 -1
  102. package/types/rules/no-aria-hidden-body.d.ts.map +1 -1
  103. package/types/rules/no-aria-hidden-on-focusable.d.ts.map +1 -1
  104. package/types/rules/no-duplicate-attrs.d.ts.map +1 -1
  105. package/types/rules/no-duplicate-class.d.ts.map +1 -1
  106. package/types/rules/no-duplicate-id.d.ts.map +1 -1
  107. package/types/rules/no-duplicate-in-head.d.ts.map +1 -1
  108. package/types/rules/no-empty-headings.d.ts.map +1 -1
  109. package/types/rules/no-extra-spacing-attrs.d.ts.map +1 -1
  110. package/types/rules/no-extra-spacing-text.d.ts.map +1 -1
  111. package/types/rules/no-heading-inside-button.d.ts.map +1 -1
  112. package/types/rules/no-ineffective-attrs.d.ts.map +1 -1
  113. package/types/rules/no-inline-styles.d.ts.map +1 -1
  114. package/types/rules/no-invalid-entity.d.ts.map +1 -1
  115. package/types/rules/no-invalid-role.d.ts.map +1 -1
  116. package/types/rules/no-multiple-empty-lines.d.ts.map +1 -1
  117. package/types/rules/no-multiple-h1.d.ts.map +1 -1
  118. package/types/rules/no-nested-interactive.d.ts.map +1 -1
  119. package/types/rules/no-non-scalable-viewport.d.ts.map +1 -1
  120. package/types/rules/no-obsolete-attrs.d.ts +4 -0
  121. package/types/rules/no-obsolete-attrs.d.ts.map +1 -0
  122. package/types/rules/no-obsolete-tags.d.ts.map +1 -1
  123. package/types/rules/no-positive-tabindex.d.ts.map +1 -1
  124. package/types/rules/no-restricted-attr-values.d.ts.map +1 -1
  125. package/types/rules/no-restricted-attrs.d.ts.map +1 -1
  126. package/types/rules/no-restricted-tags.d.ts.map +1 -1
  127. package/types/rules/no-script-style-type.d.ts.map +1 -1
  128. package/types/rules/no-skip-heading-levels.d.ts.map +1 -1
  129. package/types/rules/no-target-blank.d.ts.map +1 -1
  130. package/types/rules/no-trailing-spaces.d.ts.map +1 -1
  131. package/types/rules/no-whitespace-only-children.d.ts +6 -0
  132. package/types/rules/no-whitespace-only-children.d.ts.map +1 -0
  133. package/types/rules/prefer-https.d.ts.map +1 -1
  134. package/types/rules/quotes.d.ts.map +1 -1
  135. package/types/rules/require-attrs.d.ts.map +1 -1
  136. package/types/rules/require-button-type.d.ts.map +1 -1
  137. package/types/rules/require-closing-tags.d.ts.map +1 -1
  138. package/types/rules/require-doctype.d.ts.map +1 -1
  139. package/types/rules/require-explicit-size.d.ts.map +1 -1
  140. package/types/rules/require-form-method.d.ts.map +1 -1
  141. package/types/rules/require-frame-title.d.ts.map +1 -1
  142. package/types/rules/require-img-alt.d.ts.map +1 -1
  143. package/types/rules/require-input-label.d.ts.map +1 -1
  144. package/types/rules/require-lang.d.ts.map +1 -1
  145. package/types/rules/require-li-container.d.ts.map +1 -1
  146. package/types/rules/require-meta-charset.d.ts.map +1 -1
  147. package/types/rules/require-meta-description.d.ts.map +1 -1
  148. package/types/rules/require-meta-viewport.d.ts.map +1 -1
  149. package/types/rules/require-open-graph-protocol.d.ts.map +1 -1
  150. package/types/rules/require-title.d.ts.map +1 -1
  151. package/types/rules/sort-attrs.d.ts.map +1 -1
  152. package/types/rules/use-baseline.d.ts.map +1 -1
  153. package/types/rules/utils/baseline.d.ts +1 -3
  154. package/types/rules/utils/baseline.d.ts.map +1 -1
  155. package/types/rules/utils/naming.d.ts +14 -7
  156. package/types/rules/utils/naming.d.ts.map +1 -1
  157. package/types/rules/utils/node.d.ts +11 -10
  158. package/types/rules/utils/node.d.ts.map +1 -1
  159. package/types/rules/utils/rule.d.ts +1 -4
  160. package/types/rules/utils/rule.d.ts.map +1 -1
  161. package/types/rules/utils/settings.d.ts +0 -1
  162. package/types/rules/utils/settings.d.ts.map +1 -1
  163. package/types/rules/utils/source-code.d.ts +2 -6
  164. package/types/rules/utils/source-code.d.ts.map +1 -1
  165. package/types/rules/utils/template-literal.d.ts +2 -1
  166. package/types/rules/utils/template-literal.d.ts.map +1 -1
  167. package/types/rules/utils/visitors.d.ts.map +1 -1
  168. package/types/specs/index.d.ts +3 -0
  169. package/types/specs/index.d.ts.map +1 -0
  170. package/types/specs/obsolete-attrs.d.ts +19 -0
  171. package/types/specs/obsolete-attrs.d.ts.map +1 -0
  172. package/types/types/ast.d.ts +5 -2
  173. package/types/types/ast.d.ts.map +1 -1
@@ -1,20 +1,38 @@
1
1
  /**
2
- * @import {AnyNode, Tag, TemplateText, TemplateLiteral, OpenTemplate, CloseTemplate, ScriptTag, StyleTag, Text} from "@html-eslint/types";
3
- * @import {Line, RuleListener, Context, RuleModule} from "../../types";
4
- * @import {AST} from "eslint";
5
- *
2
+ * @import {
3
+ * AnyNode,
4
+ * CloseTemplate,
5
+ * OpenTemplate,
6
+ * ScriptTag,
7
+ * StyleTag,
8
+ * Tag,
9
+ * TemplateLiteral,
10
+ * TemplateText,
11
+ * Text
12
+ * } from "@html-eslint/types"
13
+ * @import {AST} from "eslint"
14
+ * @import {
15
+ * Context,
16
+ * Line,
17
+ * RuleListener,
18
+ * RuleModule
19
+ * } from "../../types"
6
20
  * @typedef {AnyNode | Line} AnyNodeOrLine
21
+ *
7
22
  * @typedef {Object} IndentType
8
23
  * @property {"tab"} TAB
9
24
  * @property {"space"} SPACE
25
+ *
10
26
  * @typedef {Object} MessageId
11
27
  * @property {"wrongIndent"} WRONG_INDENT
28
+ *
12
29
  * @typedef {Object} IndentOptionInfo
13
30
  * @property {IndentType["TAB"] | IndentType["SPACE"]} indentType
14
31
  * @property {number} indentSize
15
32
  * @property {string} indentChar
16
33
  *
17
34
  * @typedef {"tab" | number} Option1
35
+ *
18
36
  * @typedef {Object} Option2
19
37
  * @property {number} [Option2.Attribute]
20
38
  * @property {Record<string, number>} [Option2.tagChildrenIndent]
@@ -29,7 +47,6 @@ const {
29
47
  splitToLineNodes,
30
48
  isLine,
31
49
  isTag,
32
- hasTemplate,
33
50
  isScript,
34
51
  isStyle,
35
52
  isText,
@@ -54,9 +71,7 @@ const INDENT_TYPES = {
54
71
 
55
72
  const IGNORING_NODES = ["pre", "xmp"];
56
73
 
57
- /**
58
- * @type {RuleModule<[Option1, Option2]>}
59
- */
74
+ /** @type {RuleModule<[Option1, Option2]>} */
60
75
  module.exports = {
61
76
  meta: {
62
77
  type: "code",
@@ -127,7 +142,7 @@ module.exports = {
127
142
 
128
143
  /**
129
144
  * @param {Tag | ScriptTag | StyleTag | Text} node
130
- * @return {number}
145
+ * @returns {number}
131
146
  */
132
147
  function getTagIncreasingLevel(node) {
133
148
  if (
@@ -149,7 +164,7 @@ module.exports = {
149
164
 
150
165
  /**
151
166
  * @param {AnyNode} node
152
- * @return {number}
167
+ * @returns {number}
153
168
  */
154
169
  function getIncreasingLevel(node) {
155
170
  if (isLine(node)) {
@@ -189,7 +204,6 @@ module.exports = {
189
204
  }
190
205
 
191
206
  /**
192
- *
193
207
  * @param {TemplateLiteral} node
194
208
  * @returns {number}
195
209
  */
@@ -222,7 +236,11 @@ module.exports = {
222
236
  let parentIgnoringChildCount = 0;
223
237
 
224
238
  /**
225
- * @param {AnyNode | Line | TemplateText | OpenTemplate | CloseTemplate} node
239
+ * @param {AnyNode
240
+ * | Line
241
+ * | TemplateText
242
+ * | OpenTemplate
243
+ * | CloseTemplate} node
226
244
  * @returns {string}
227
245
  */
228
246
  function getActualIndent(node) {
@@ -237,9 +255,7 @@ module.exports = {
237
255
  return line.slice(0, column);
238
256
  }
239
257
 
240
- /**
241
- * @returns {string}
242
- */
258
+ /** @returns {string} */
243
259
  function getExpectedIndent() {
244
260
  let base = "";
245
261
  if (indentType === "space") {
@@ -284,7 +300,11 @@ module.exports = {
284
300
  }
285
301
 
286
302
  /**
287
- * @param {AnyNode | Line | TemplateText | OpenTemplate | CloseTemplate} node
303
+ * @param {AnyNode
304
+ * | Line
305
+ * | TemplateText
306
+ * | OpenTemplate
307
+ * | CloseTemplate} node
288
308
  */
289
309
  function checkIndent(node) {
290
310
  if (parentIgnoringChildCount > 0) {
@@ -309,9 +329,7 @@ module.exports = {
309
329
  }
310
330
  }
311
331
 
312
- /**
313
- * @type {RuleListener}
314
- */
332
+ /** @type {RuleListener} */
315
333
  const commentVisitor = {
316
334
  Comment(node) {
317
335
  indentLevel.indent(node);
@@ -319,22 +337,13 @@ module.exports = {
319
337
  CommentOpen: checkIndent,
320
338
  CommentContent(node) {
321
339
  indentLevel.indent(node);
322
- if (hasTemplate(node)) {
323
- node.parts.forEach((part) => {
324
- if (part.type !== NODE_TYPES.Part) {
325
- if (part.open) {
326
- checkIndent(part.open);
327
- }
328
- if (part.close) {
329
- checkIndent(part.close);
330
- }
331
- }
332
- });
333
- }
334
-
335
340
  const lineNodes = splitToLineNodes(node);
336
341
  lineNodes.forEach((lineNode) => {
337
- if (lineNode.hasTemplate) {
342
+ if (
343
+ lineNode.isOverlapTemplate &&
344
+ !lineNode.hasCloseTemplate &&
345
+ !lineNode.hasOpenTemplate
346
+ ) {
338
347
  return;
339
348
  }
340
349
  if (lineNode.value.trim().length) {
@@ -351,9 +360,7 @@ module.exports = {
351
360
  },
352
361
  };
353
362
 
354
- /**
355
- * @type {RuleListener}
356
- */
363
+ /** @type {RuleListener} */
357
364
  const visitor = {
358
365
  Tag(node) {
359
366
  if (IGNORING_NODES.includes(node.name)) {
@@ -401,23 +408,13 @@ module.exports = {
401
408
  },
402
409
  Text(node) {
403
410
  indentLevel.indent(node);
404
- if (hasTemplate(node)) {
405
- node.parts.forEach((part) => {
406
- if (part.type !== NODE_TYPES.Part) {
407
- if (part.open) {
408
- checkIndent(part.open);
409
- }
410
- if (part.close) {
411
- checkIndent(part.close);
412
- }
413
- }
414
- });
415
- }
416
-
417
411
  const lineNodes = splitToLineNodes(node);
418
-
419
412
  lineNodes.forEach((lineNode) => {
420
- if (lineNode.hasTemplate) {
413
+ if (
414
+ lineNode.isOverlapTemplate &&
415
+ !lineNode.hasCloseTemplate &&
416
+ !lineNode.hasOpenTemplate
417
+ ) {
421
418
  return;
422
419
  }
423
420
  if (lineNode.value.trim().length) {
@@ -464,7 +461,7 @@ module.exports = {
464
461
  /**
465
462
  * @param {AnyNodeOrLine | TemplateText | OpenTemplate | CloseTemplate} node
466
463
  * @param {string} actualIndent
467
- * @return {{range: AST.Range; loc: AST.SourceLocation}}
464
+ * @returns {{ range: AST.Range; loc: AST.SourceLocation }}
468
465
  */
469
466
  function getIndentNodeToReport(node, actualIndent) {
470
467
  let rangeStart = node.range[0];
@@ -498,13 +495,11 @@ function countLeftPadding(str) {
498
495
 
499
496
  /**
500
497
  * @param {Context<any[]>} context
501
- * @return {IndentOptionInfo}
498
+ * @returns {IndentOptionInfo}
502
499
  */
503
500
  function getIndentOptionInfo(context) {
504
501
  const options = context.options;
505
- /**
506
- * @type {IndentType['SPACE'] | IndentType['TAB']}
507
- */
502
+ /** @type {IndentType["SPACE"] | IndentType["TAB"]} */
508
503
  let indentType = INDENT_TYPES.SPACE;
509
504
  let indentSize = 4;
510
505
  if (options.length) {
@@ -53,6 +53,9 @@ const noInvalidEntity = require("./no-invalid-entity");
53
53
  const noDuplicateInHead = require("./no-duplicate-in-head");
54
54
  const noIneffectiveAttrs = require("./no-ineffective-attrs");
55
55
  const noRestrictedTags = require("./no-restricted-tags");
56
+ const noWhitespaceOnlyChildren = require("./no-whitespace-only-children");
57
+ const noObsoleteAttrs = require("./no-obsolete-attrs");
58
+ const classSpacing = require("./class-spacing");
56
59
  // import new rule here ↑
57
60
  // DO NOT REMOVE THIS COMMENT
58
61
 
@@ -112,11 +115,14 @@ const rules = {
112
115
  "no-duplicate-in-head": noDuplicateInHead,
113
116
  "no-ineffective-attrs": noIneffectiveAttrs,
114
117
  "no-restricted-tags": noRestrictedTags,
118
+ "no-whitespace-only-children": noWhitespaceOnlyChildren,
119
+ "no-obsolete-attrs": noObsoleteAttrs,
120
+ "class-spacing": classSpacing,
115
121
  // export new rule here ↑
116
122
  // DO NOT REMOVE THIS COMMENT
117
123
  };
118
124
 
119
125
  module.exports =
120
- /** @type {Record<string, import('@eslint/core').RuleDefinition>} */ (
126
+ /** @type {Record<string, import("@eslint/core").RuleDefinition>} */ (
121
127
  /** @type {unknown} */ (rules)
122
128
  );
@@ -1,11 +1,11 @@
1
1
  /**
2
2
  * @import {
3
- * Tag,
4
- * StyleTag,
5
- * ScriptTag,
6
3
  * Doctype,
7
- * } from "@html-eslint/types";
8
- * @import {RuleModule} from "../types";
4
+ * ScriptTag,
5
+ * StyleTag,
6
+ * Tag
7
+ * } from "@html-eslint/types"
8
+ * @import {RuleModule} from "../types"
9
9
  */
10
10
 
11
11
  const { RULE_CATEGORY } = require("../constants");
@@ -18,9 +18,7 @@ const MESSAGE_IDS = {
18
18
  UNEXPECTED: "unexpected",
19
19
  };
20
20
 
21
- /**
22
- * @type {RuleModule<[]>}
23
- */
21
+ /** @type {RuleModule<[]>} */
24
22
  module.exports = {
25
23
  meta: {
26
24
  type: "suggestion",
@@ -41,14 +39,10 @@ module.exports = {
41
39
 
42
40
  create(context) {
43
41
  const allowedAttrKeySet = new Set(SVG_CAMEL_CASE_ATTRIBUTES);
44
- /**
45
- * @type {Tag[]}
46
- */
42
+ /** @type {Tag[]} */
47
43
  const svgStack = [];
48
44
 
49
- /**
50
- * @param {Tag} node
51
- */
45
+ /** @param {Tag} node */
52
46
  function enterSvg(node) {
53
47
  svgStack.push(node);
54
48
  }
@@ -65,18 +59,14 @@ module.exports = {
65
59
  return !!svgStack.length && allowedAttrKeySet.has(key);
66
60
  }
67
61
 
68
- /**
69
- * @param {Tag | StyleTag | ScriptTag} node
70
- */
62
+ /** @param {Tag | StyleTag | ScriptTag} node */
71
63
  function nameOf(node) {
72
64
  if (isScript(node)) return "script";
73
65
  if (isStyle(node)) return "style";
74
66
  return node.name;
75
67
  }
76
68
 
77
- /**
78
- * @param {Tag | StyleTag | ScriptTag} node
79
- */
69
+ /** @param {Tag | StyleTag | ScriptTag} node */
80
70
  function check(node) {
81
71
  const raw = node.openStart.value.slice(1);
82
72
  const name = nameOf(node);
@@ -133,9 +123,7 @@ module.exports = {
133
123
  }
134
124
  }
135
125
 
136
- /**
137
- * @param {Doctype} doctype
138
- */
126
+ /** @param {Doctype} doctype */
139
127
  function checkDoctype(doctype) {
140
128
  if (doctype.open.value !== doctype.open.value.toLowerCase()) {
141
129
  context.report({
@@ -1,7 +1,10 @@
1
1
  /**
2
- * @import {Tag, StyleTag, ScriptTag} from "@html-eslint/types";
3
- * @import {RuleModule} from "../types";
4
- *
2
+ * @import {
3
+ * ScriptTag,
4
+ * StyleTag,
5
+ * Tag
6
+ * } from "@html-eslint/types"
7
+ * @import {RuleModule} from "../types"
5
8
  * @typedef {Object} Option
6
9
  * @property {number} [Option.max]
7
10
  */
@@ -14,9 +17,7 @@ const MESSAGE_IDS = {
14
17
  MAX_DEPTH_EXCEEDED: "maxDepthExceeded",
15
18
  };
16
19
 
17
- /**
18
- * @type {RuleModule<[Option]>}
19
- */
20
+ /** @type {RuleModule<[Option]>} */
20
21
  module.exports = {
21
22
  meta: {
22
23
  type: "code",
@@ -63,10 +64,7 @@ module.exports = {
63
64
  depth = 0;
64
65
  }
65
66
 
66
- /**
67
- *
68
- * @param {Tag | ScriptTag | StyleTag} node
69
- */
67
+ /** @param {Tag | ScriptTag | StyleTag} node */
70
68
  function increaseDepth(node) {
71
69
  depth++;
72
70
  if (depth > maxDepth) {
@@ -1,6 +1,10 @@
1
1
  /**
2
- * @import {Tag, StyleTag, ScriptTag} from "@html-eslint/types";
3
- * @import {RuleModule} from "../types";
2
+ * @import {
3
+ * ScriptTag,
4
+ * StyleTag,
5
+ * Tag
6
+ * } from "@html-eslint/types"
7
+ * @import {RuleModule} from "../types"
4
8
  */
5
9
 
6
10
  const { RULE_CATEGORY } = require("../constants");
@@ -27,9 +31,7 @@ const ABSTRACT_ROLE_SET = new Set([
27
31
  "window",
28
32
  ]);
29
33
 
30
- /**
31
- * @type {RuleModule<[]>}
32
- */
34
+ /** @type {RuleModule<[]>} */
33
35
  module.exports = {
34
36
  meta: {
35
37
  type: "code",
@@ -49,9 +51,7 @@ module.exports = {
49
51
  },
50
52
 
51
53
  create(context) {
52
- /**
53
- * @param {Tag | ScriptTag | StyleTag} node
54
- */
54
+ /** @param {Tag | ScriptTag | StyleTag} node */
55
55
  function check(node) {
56
56
  const roleAttr = findAttr(node, "role");
57
57
  if (
@@ -1,6 +1,10 @@
1
1
  /**
2
- * @import {Tag, StyleTag, ScriptTag} from "@html-eslint/types";
3
- * @import {RuleModule} from "../types";
2
+ * @import {
3
+ * ScriptTag,
4
+ * StyleTag,
5
+ * Tag
6
+ * } from "@html-eslint/types"
7
+ * @import {RuleModule} from "../types"
4
8
  */
5
9
 
6
10
  const { RULE_CATEGORY } = require("../constants");
@@ -12,9 +16,7 @@ const MESSAGE_IDS = {
12
16
  UNEXPECTED: "unexpected",
13
17
  };
14
18
 
15
- /**
16
- * @type {RuleModule<[]>}
17
- */
19
+ /** @type {RuleModule<[]>} */
18
20
  module.exports = {
19
21
  meta: {
20
22
  type: "code",
@@ -34,9 +36,7 @@ module.exports = {
34
36
  },
35
37
 
36
38
  create(context) {
37
- /**
38
- * @param {Tag | ScriptTag | StyleTag} node
39
- */
39
+ /** @param {Tag | ScriptTag | StyleTag} node */
40
40
  function check(node) {
41
41
  const accessKeyAttr = findAttr(node, "accesskey");
42
42
  if (accessKeyAttr) {
@@ -1,6 +1,4 @@
1
- /**
2
- * @import {RuleModule} from "../types";
3
- */
1
+ /** @import {RuleModule} from "../types" */
4
2
 
5
3
  const { RULE_CATEGORY } = require("../constants");
6
4
  const { findAttr } = require("./utils/node");
@@ -11,9 +9,7 @@ const MESSAGE_IDS = {
11
9
  UNEXPECTED: "unexpected",
12
10
  };
13
11
 
14
- /**
15
- * @type {RuleModule<[]>}
16
- */
12
+ /** @type {RuleModule<[]>} */
17
13
  module.exports = {
18
14
  meta: {
19
15
  type: "code",
@@ -1,6 +1,6 @@
1
1
  /**
2
- * @import {Tag} from "@html-eslint/types";
3
- * @import {RuleModule} from "../types";
2
+ * @import {Tag} from "@html-eslint/types"
3
+ * @import {RuleModule} from "../types"
4
4
  */
5
5
 
6
6
  const { RULE_CATEGORY } = require("../constants");
@@ -27,9 +27,7 @@ const FOCUSABLE_ELEMENTS = new Set([
27
27
  "summary",
28
28
  ]);
29
29
 
30
- /**
31
- * @type {RuleModule<[]>}
32
- */
30
+ /** @type {RuleModule<[]>} */
33
31
  module.exports = {
34
32
  meta: {
35
33
  type: "code",
@@ -52,6 +50,7 @@ module.exports = {
52
50
  create(context) {
53
51
  /**
54
52
  * Checks if an element is focusable
53
+ *
55
54
  * @param {Tag} node
56
55
  * @returns {boolean}
57
56
  */
@@ -1,6 +1,14 @@
1
1
  /**
2
- * @import {Tag, StyleTag, ScriptTag, Attribute} from "@html-eslint/types";
3
- * @import {RuleModule, SuggestionReportDescriptor} from "../types";
2
+ * @import {
3
+ * Attribute,
4
+ * ScriptTag,
5
+ * StyleTag,
6
+ * Tag
7
+ * } from "@html-eslint/types"
8
+ * @import {
9
+ * RuleModule,
10
+ * SuggestionReportDescriptor
11
+ * } from "../types"
4
12
  */
5
13
 
6
14
  const { RULE_CATEGORY } = require("../constants");
@@ -13,9 +21,7 @@ const MESSAGE_IDS = {
13
21
  REMOVE_ATTR: "removeAttr",
14
22
  };
15
23
 
16
- /**
17
- * @type {RuleModule<[]>}
18
- */
24
+ /** @type {RuleModule<[]>} */
19
25
  module.exports = {
20
26
  meta: {
21
27
  type: "code",
@@ -55,9 +61,7 @@ module.exports = {
55
61
  ];
56
62
  }
57
63
 
58
- /**
59
- * @param {Tag | StyleTag | ScriptTag} node
60
- */
64
+ /** @param {Tag | StyleTag | ScriptTag} node */
61
65
  function check(node) {
62
66
  if (Array.isArray(node.attributes)) {
63
67
  const attrsSet = new Set();
@@ -1,10 +1,10 @@
1
1
  /**
2
- * @import {AttributeValue} from "@html-eslint/types";
3
- * @import {RuleModule} from "../types";
2
+ * @import {AttributeValue} from "@html-eslint/types"
3
+ * @import {RuleModule} from "../types"
4
4
  * @typedef {Object} ClassInfo
5
5
  * @property {string} name
6
- * @property {import("@html-eslint/types").AnyNode['loc']} loc
7
- * @property {import("@html-eslint/types").AnyNode['range']} range
6
+ * @property {import("@html-eslint/types").AnyNode["loc"]} loc
7
+ * @property {import("@html-eslint/types").AnyNode["range"]} range
8
8
  */
9
9
 
10
10
  const { NODE_TYPES } = require("@html-eslint/parser");
@@ -16,9 +16,7 @@ const MESSAGE_IDS = {
16
16
  DUPLICATE_CLASS: "duplicateClass",
17
17
  };
18
18
 
19
- /**
20
- * @type {RuleModule<[]>}
21
- */
19
+ /** @type {RuleModule<[]>} */
22
20
  module.exports = {
23
21
  meta: {
24
22
  type: "code",
@@ -38,17 +36,13 @@ module.exports = {
38
36
  create(context) {
39
37
  /**
40
38
  * @param {AttributeValue} value
41
- * @returns {{value: string, pos: number}[]}
39
+ * @returns {{ value: string; pos: number }[]}
42
40
  */
43
41
  function splitClassAndSpaces(value) {
44
- /**
45
- * @type {{value: string, pos: number}[]}
46
- */
42
+ /** @type {{ value: string; pos: number }[]} */
47
43
  const result = [];
48
44
  const regex = /(\s+|\S+)/g;
49
- /**
50
- * @type {RegExpExecArray | null}
51
- */
45
+ /** @type {RegExpExecArray | null} */
52
46
  let match = null;
53
47
 
54
48
  while ((match = regex.exec(value.value)) !== null) {
@@ -1,6 +1,9 @@
1
1
  /**
2
- * @import {Tag, AttributeValue} from "@html-eslint/types";
3
- * @import {RuleModule} from "../types";
2
+ * @import {
3
+ * AttributeValue,
4
+ * Tag
5
+ * } from "@html-eslint/types"
6
+ * @import {RuleModule} from "../types"
4
7
  */
5
8
 
6
9
  const { parseTemplateLiteral } = require("./utils/template-literal");
@@ -17,9 +20,7 @@ const MESSAGE_IDS = {
17
20
  DUPLICATE_ID: "duplicateId",
18
21
  };
19
22
 
20
- /**
21
- * @type {RuleModule<[]>}
22
- */
23
+ /** @type {RuleModule<[]>} */
23
24
  module.exports = {
24
25
  meta: {
25
26
  type: "code",
@@ -40,13 +41,9 @@ module.exports = {
40
41
 
41
42
  create(context) {
42
43
  const htmlIdAttrsMap = new Map();
43
- /**
44
- * @param {Map<string, AttributeValue[]>} map
45
- */
44
+ /** @param {Map<string, AttributeValue[]>} map */
46
45
  function createTagVisitor(map) {
47
- /**
48
- * @param {Tag} node
49
- */
46
+ /** @param {Tag} node */
50
47
  return function (node) {
51
48
  if (!node.attributes || node.attributes.length <= 0) {
52
49
  return;
@@ -64,10 +61,7 @@ module.exports = {
64
61
  };
65
62
  }
66
63
 
67
- /**
68
- *
69
- * @param {Map<string, AttributeValue[]>} map
70
- */
64
+ /** @param {Map<string, AttributeValue[]>} map */
71
65
  function report(map) {
72
66
  map.forEach((attrs) => {
73
67
  if (Array.isArray(attrs) && attrs.length > 1) {
@@ -1,6 +1,6 @@
1
1
  /**
2
- * @import {Tag} from "@html-eslint/types";
3
- * @import {RuleModule} from "../types";
2
+ * @import {Tag} from "@html-eslint/types"
3
+ * @import {RuleModule} from "../types"
4
4
  */
5
5
 
6
6
  const { parseTemplateLiteral } = require("./utils/template-literal");
@@ -18,8 +18,9 @@ const MESSAGE_IDS = {
18
18
  };
19
19
 
20
20
  /**
21
- * Returns a formatted string representing a tag's key detail.
22
- * E.g., meta[charset=UTF-8], meta[name=viewport], link[rel=canonical]
21
+ * Returns a formatted string representing a tag's key detail. E.g.,
22
+ * meta[charset=UTF-8], meta[name=viewport], link[rel=canonical]
23
+ *
23
24
  * @param {Tag} node
24
25
  * @returns {string | null}
25
26
  */
@@ -58,9 +59,7 @@ function getTrackingKey(node) {
58
59
  return null;
59
60
  }
60
61
 
61
- /**
62
- * @type {RuleModule<[]>}
63
- */
62
+ /** @type {RuleModule<[]>} */
64
63
  module.exports = {
65
64
  meta: {
66
65
  type: "code",
@@ -83,13 +82,11 @@ module.exports = {
83
82
 
84
83
  /**
85
84
  * @param {Map<string, Tag[]>} map
86
- * @param {{count: number}|null} headCountRef
85
+ * @param {{ count: number } | null} headCountRef
87
86
  */
88
87
  function createTagVisitor(map, headCountRef = null) {
89
88
  return {
90
- /**
91
- * @param {Tag} node
92
- */
89
+ /** @param {Tag} node */
93
90
  Tag(node) {
94
91
  const tagName = node.name.toLowerCase();
95
92
 
@@ -119,9 +116,7 @@ module.exports = {
119
116
  }
120
117
  },
121
118
 
122
- /**
123
- * @param {Tag} node
124
- */
119
+ /** @param {Tag} node */
125
120
  "Tag:exit"(node) {
126
121
  const tagName = node.name.toLowerCase();
127
122
  if (tagName === "head") {
@@ -135,9 +130,7 @@ module.exports = {
135
130
  };
136
131
  }
137
132
 
138
- /**
139
- * @param {Map<string, Tag[]>} map
140
- */
133
+ /** @param {Map<string, Tag[]>} map */
141
134
  function report(map) {
142
135
  map.forEach((tags, tagKey) => {
143
136
  if (Array.isArray(tags) && tags.length > 1) {