@html-eslint/eslint-plugin 0.27.0 → 0.28.0-alpha.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.
@@ -1,10 +1,16 @@
1
1
  /**
2
2
  * @typedef { import("../types").RuleModule } RuleModule
3
+ * @typedef { import("../types").RuleListener } RuleListener
3
4
  */
4
5
 
5
6
  const { RULE_CATEGORY } = require("../constants");
6
7
  const { findAttr } = require("./utils/node");
7
-
8
+ const { parse } = require("@html-eslint/template-parser");
9
+ const {
10
+ shouldCheckTaggedTemplateExpression,
11
+ shouldCheckTemplateLiteral,
12
+ } = require("./utils/settings");
13
+ const { getSourceCode } = require("./utils/source-code");
8
14
  const MESSAGE_IDS = {
9
15
  INLINE_STYLE: "unexpectedInlineStyle",
10
16
  };
@@ -30,7 +36,10 @@ module.exports = {
30
36
  },
31
37
 
32
38
  create(context) {
33
- return {
39
+ /**
40
+ * @type {RuleListener}
41
+ */
42
+ const visitors = {
34
43
  Tag(node) {
35
44
  const styleAttr = findAttr(node, "style");
36
45
  if (styleAttr) {
@@ -41,5 +50,19 @@ module.exports = {
41
50
  }
42
51
  },
43
52
  };
53
+
54
+ return {
55
+ ...visitors,
56
+ TaggedTemplateExpression(node) {
57
+ if (shouldCheckTaggedTemplateExpression(node, context)) {
58
+ parse(node.quasi, getSourceCode(context), visitors);
59
+ }
60
+ },
61
+ TemplateLiteral(node) {
62
+ if (shouldCheckTemplateLiteral(node, context)) {
63
+ parse(node, getSourceCode(context), visitors);
64
+ }
65
+ },
66
+ };
44
67
  },
45
68
  };
@@ -0,0 +1,88 @@
1
+ /**
2
+ * @typedef {import("../../types").MaybeHTMLSettings} MaybeHTMLSettings
3
+ * @typedef {import("../../types").HTMLSettings} HTMLSettings
4
+ * @typedef {import("../../types").Context} Context
5
+ * @typedef {import("estree").TaggedTemplateExpression} TaggedTemplateExpression
6
+ * @typedef {import("estree").TemplateLiteral} TemplateLiteral
7
+ */
8
+
9
+ const { getSourceCode } = require("../utils/source-code");
10
+
11
+ const DEFAULT_SETTINGS = {
12
+ templateLiterals: {
13
+ tags: ["^html$"],
14
+ comments: ["^\\s*html\\s*$"],
15
+ },
16
+ };
17
+
18
+ /**
19
+ * @type {HTMLSettings | null}
20
+ */
21
+ let cachedSettings = null;
22
+
23
+ /**
24
+ * @param {{ html?: MaybeHTMLSettings }} settings
25
+ * @returns {HTMLSettings}
26
+ */
27
+ function getSettings(settings) {
28
+ const tags =
29
+ (settings &&
30
+ settings.html &&
31
+ settings.html.templateLiterals &&
32
+ settings.html.templateLiterals.tags) ||
33
+ DEFAULT_SETTINGS.templateLiterals.tags;
34
+
35
+ const comments =
36
+ (settings &&
37
+ settings.html &&
38
+ settings.html.templateLiterals &&
39
+ settings.html.templateLiterals.comments) ||
40
+ DEFAULT_SETTINGS.templateLiterals.comments;
41
+
42
+ if (cachedSettings) {
43
+ return cachedSettings;
44
+ }
45
+ cachedSettings = {
46
+ templateLiterals: {
47
+ tags: tags.map((tag) => new RegExp(tag, "u")),
48
+ comments: comments.map((comment) => new RegExp(comment, "u")),
49
+ },
50
+ };
51
+ return cachedSettings;
52
+ }
53
+
54
+ /**
55
+ * @param {TaggedTemplateExpression} node
56
+ * @param {Context} context
57
+ * @returns {boolean}
58
+ */
59
+ function shouldCheckTaggedTemplateExpression(node, context) {
60
+ const { templateLiterals } = getSettings(context.settings);
61
+ const tags = templateLiterals.tags;
62
+ const tagNode = node.tag;
63
+ return !!(
64
+ tagNode.type === "Identifier" && tags.some((tag) => tag.test(tagNode.name))
65
+ );
66
+ }
67
+
68
+ /**
69
+ *
70
+ * @param {TemplateLiteral} node
71
+ * @param {Context} context
72
+ * @returns {boolean}
73
+ */
74
+ function shouldCheckTemplateLiteral(node, context) {
75
+ const sourceCode = getSourceCode(context);
76
+ const { templateLiterals } = getSettings(context.settings);
77
+ const comments = sourceCode.getCommentsBefore(node);
78
+ const last = comments[comments.length - 1];
79
+ return !!(
80
+ last &&
81
+ templateLiterals.comments.some((comment) => comment.test(last.value))
82
+ );
83
+ }
84
+
85
+ module.exports = {
86
+ shouldCheckTemplateLiteral,
87
+ shouldCheckTaggedTemplateExpression,
88
+ };
@@ -0,0 +1,14 @@
1
+ /**
2
+ * @typedef {import("../../types").Context} Context
3
+ */
4
+
5
+ /**
6
+ * @param {Context} context
7
+ */
8
+ function getSourceCode(context) {
9
+ return context.sourceCode || context.getSourceCode();
10
+ }
11
+
12
+ module.exports = {
13
+ getSourceCode,
14
+ };
package/lib/types.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import ESTree from "estree";
1
+ import ESTree, { TaggedTemplateExpression, TemplateLiteral } from "estree";
2
2
  import ESLint from "eslint";
3
3
  import * as ESHtml from "es-html-parser";
4
4
 
@@ -200,12 +200,14 @@ interface RuleListener {
200
200
  CommentClose?: (node: CommentCloseNode) => void;
201
201
  CommentContent?: (node: CommentContentNode) => void;
202
202
  Doctype?: (node: DoctypeNode) => void;
203
- DoctypeOpen: (node: DoctypeOpenNode) => void;
203
+ DoctypeOpen?: (node: DoctypeOpenNode) => void;
204
204
  DoctypeClose?: (node: DoctypeCloseNode) => void;
205
205
  DoctypeAttribute?: (node: DoctypeAttributeNode) => void;
206
206
  DoctypeAttributeValue?: (node: DoctypeAttributeValueNode) => void;
207
207
  DoctypeAttributeWrapperStart?: (node: DoctypeAttributeWrapperStart) => void;
208
208
  DoctypeAttributeWrapperEnd?: (node: DoctypeAttributeWrapperEnd) => void;
209
+ TaggedTemplateExpression?: (node: TaggedTemplateExpression) => void;
210
+ TemplateLiteral?: (node: TemplateLiteral) => void;
209
211
  }
210
212
 
211
213
  export interface RuleModule extends ESLint.Rule.RuleModule {
@@ -258,7 +260,7 @@ type ReportDescriptorLocation = {
258
260
  column?: number;
259
261
  };
260
262
 
261
- interface Context extends Omit<ESLint.Rule.RuleContext, "report"> {
263
+ export interface Context extends Omit<ESLint.Rule.RuleContext, "report"> {
262
264
  report(descriptor: ReportDescriptor): void;
263
265
  }
264
266
 
@@ -275,3 +277,17 @@ export type ContentNode =
275
277
  | StyleTagNode
276
278
  | TagNode
277
279
  | TextNode;
280
+
281
+ export type MaybeHTMLSettings = {
282
+ templateLiterals?: {
283
+ tags?: string[];
284
+ comments?: string[];
285
+ };
286
+ };
287
+
288
+ export type HTMLSettings = {
289
+ templateLiterals: {
290
+ tags: RegExp[];
291
+ comments: RegExp[];
292
+ };
293
+ };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@html-eslint/eslint-plugin",
3
- "version": "0.27.0",
3
+ "version": "0.28.0-alpha.0",
4
4
  "description": "ESLint plugin for html",
5
5
  "author": "yeonjuan",
6
6
  "homepage": "https://github.com/yeonjuan/html-eslint#readme",
@@ -45,11 +45,13 @@
45
45
  "accessibility"
46
46
  ],
47
47
  "devDependencies": {
48
- "@html-eslint/parser": "^0.27.0",
49
- "@types/eslint": "^8.56.2",
48
+ "@html-eslint/parser": "^0.28.0-alpha.0",
49
+ "@html-eslint/template-parser": "^0.28.0-alpha.0",
50
+ "@types/eslint": "^9.6.1",
50
51
  "@types/estree": "^0.0.47",
51
52
  "es-html-parser": "^0.0.8",
53
+ "espree": "^10.3.0",
52
54
  "typescript": "^4.4.4"
53
55
  },
54
- "gitHead": "a7c09dfb3090bb779d6fe62fda814d4d7ca07d4a"
56
+ "gitHead": "4c4e3388a4d8541ade0201fb06690e46098ab9bf"
55
57
  }
@@ -1,4 +1,5 @@
1
1
  declare const _exports: RuleModule;
2
2
  export = _exports;
3
3
  export type RuleModule = import("../types").RuleModule;
4
+ export type RuleListener = import("../types").RuleListener;
4
5
  //# sourceMappingURL=no-inline-styles.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"no-inline-styles.d.ts","sourceRoot":"","sources":["../../lib/rules/no-inline-styles.js"],"names":[],"mappings":"wBAYU,UAAU;;yBAXN,OAAO,UAAU,EAAE,UAAU"}
1
+ {"version":3,"file":"no-inline-styles.d.ts","sourceRoot":"","sources":["../../lib/rules/no-inline-styles.js"],"names":[],"mappings":"wBAkBU,UAAU;;yBAjBN,OAAO,UAAU,EAAE,UAAU;2BAC7B,OAAO,UAAU,EAAE,YAAY"}
@@ -0,0 +1,19 @@
1
+ export type MaybeHTMLSettings = import("../../types").MaybeHTMLSettings;
2
+ export type HTMLSettings = import("../../types").HTMLSettings;
3
+ export type Context = import("../../types").Context;
4
+ export type TaggedTemplateExpression = import("estree").TaggedTemplateExpression;
5
+ export type TemplateLiteral = import("estree").TemplateLiteral;
6
+ /**
7
+ *
8
+ * @param {TemplateLiteral} node
9
+ * @param {Context} context
10
+ * @returns {boolean}
11
+ */
12
+ export function shouldCheckTemplateLiteral(node: TemplateLiteral, context: Context): boolean;
13
+ /**
14
+ * @param {TaggedTemplateExpression} node
15
+ * @param {Context} context
16
+ * @returns {boolean}
17
+ */
18
+ export function shouldCheckTaggedTemplateExpression(node: TaggedTemplateExpression, context: Context): boolean;
19
+ //# sourceMappingURL=settings.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"settings.d.ts","sourceRoot":"","sources":["../../../lib/rules/utils/settings.js"],"names":[],"mappings":"gCACa,OAAO,aAAa,EAAE,iBAAiB;2BACvC,OAAO,aAAa,EAAE,YAAY;sBAClC,OAAO,aAAa,EAAE,OAAO;uCAC7B,OAAO,QAAQ,EAAE,wBAAwB;8BACzC,OAAO,QAAQ,EAAE,eAAe;AA8D7C;;;;;GAKG;AACH,iDAJW,eAAe,WACf,OAAO,GACL,OAAO,CAWnB;AA7BD;;;;GAIG;AACH,0DAJW,wBAAwB,WACxB,OAAO,GACL,OAAO,CASnB"}
@@ -0,0 +1,9 @@
1
+ export type Context = import("../../types").Context;
2
+ /**
3
+ * @typedef {import("../../types").Context} Context
4
+ */
5
+ /**
6
+ * @param {Context} context
7
+ */
8
+ export function getSourceCode(context: Context): import("eslint").SourceCode;
9
+ //# sourceMappingURL=source-code.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"source-code.d.ts","sourceRoot":"","sources":["../../../lib/rules/utils/source-code.js"],"names":[],"mappings":"sBACa,OAAO,aAAa,EAAE,OAAO;AAD1C;;GAEG;AAEH;;GAEG;AACH,uCAFW,OAAO,+BAIjB"}