@herb-tools/linter 0.8.7 → 0.8.8
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 +28 -2
- package/dist/herb-lint.js +5406 -15659
- package/dist/herb-lint.js.map +1 -1
- package/dist/index.cjs +381 -37
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +376 -39
- package/dist/index.js.map +1 -1
- package/dist/loader.cjs +1231 -7911
- package/dist/loader.cjs.map +1 -1
- package/dist/loader.js +1225 -7912
- package/dist/loader.js.map +1 -1
- package/dist/package.json +7 -7
- package/dist/src/cli/argument-parser.js +5 -2
- package/dist/src/cli/argument-parser.js.map +1 -1
- package/dist/src/cli/file-processor.js +1 -1
- package/dist/src/cli/file-processor.js.map +1 -1
- package/dist/src/cli.js +14 -8
- package/dist/src/cli.js.map +1 -1
- package/dist/src/custom-rule-loader.js +2 -2
- package/dist/src/custom-rule-loader.js.map +1 -1
- package/dist/src/linter.js +14 -1
- package/dist/src/linter.js.map +1 -1
- package/dist/src/rules/erb-strict-locals-comment-syntax.js +206 -0
- package/dist/src/rules/erb-strict-locals-comment-syntax.js.map +1 -0
- package/dist/src/rules/erb-strict-locals-required.js +38 -0
- package/dist/src/rules/erb-strict-locals-required.js.map +1 -0
- package/dist/src/rules/file-utils.js +21 -0
- package/dist/src/rules/file-utils.js.map +1 -0
- package/dist/src/rules/html-head-only-elements.js +2 -0
- package/dist/src/rules/html-head-only-elements.js.map +1 -1
- package/dist/src/rules/html-no-empty-headings.js +22 -36
- package/dist/src/rules/html-no-empty-headings.js.map +1 -1
- package/dist/src/rules/index.js +4 -0
- package/dist/src/rules/index.js.map +1 -1
- package/dist/src/rules/string-utils.js +72 -0
- package/dist/src/rules/string-utils.js.map +1 -0
- package/dist/src/rules.js +4 -0
- package/dist/src/rules.js.map +1 -1
- package/dist/src/types.js +6 -0
- package/dist/src/types.js.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/dist/types/cli/argument-parser.d.ts +1 -0
- package/dist/types/cli/file-processor.d.ts +1 -0
- package/dist/types/cli.d.ts +1 -1
- package/dist/types/linter.d.ts +5 -1
- package/dist/types/rules/erb-strict-locals-comment-syntax.d.ts +9 -0
- package/dist/types/rules/erb-strict-locals-required.d.ts +9 -0
- package/dist/types/rules/file-utils.d.ts +13 -0
- package/dist/types/rules/index.d.ts +4 -0
- package/dist/types/rules/string-utils.d.ts +15 -0
- package/dist/types/src/cli/argument-parser.d.ts +1 -0
- package/dist/types/src/cli/file-processor.d.ts +1 -0
- package/dist/types/src/cli.d.ts +1 -1
- package/dist/types/src/linter.d.ts +5 -1
- package/dist/types/src/rules/erb-strict-locals-comment-syntax.d.ts +9 -0
- package/dist/types/src/rules/erb-strict-locals-required.d.ts +9 -0
- package/dist/types/src/rules/file-utils.d.ts +13 -0
- package/dist/types/src/rules/index.d.ts +4 -0
- package/dist/types/src/rules/string-utils.d.ts +15 -0
- package/dist/types/src/types.d.ts +6 -0
- package/dist/types/types.d.ts +6 -0
- package/docs/rules/README.md +1 -0
- package/docs/rules/erb-strict-locals-comment-syntax.md +153 -0
- package/docs/rules/erb-strict-locals-required.md +107 -0
- package/package.json +7 -7
- package/src/cli/argument-parser.ts +6 -2
- package/src/cli/file-processor.ts +2 -1
- package/src/cli.ts +18 -8
- package/src/custom-rule-loader.ts +2 -2
- package/src/linter.ts +17 -1
- package/src/rules/erb-strict-locals-comment-syntax.ts +274 -0
- package/src/rules/erb-strict-locals-required.ts +52 -0
- package/src/rules/file-utils.ts +23 -0
- package/src/rules/html-head-only-elements.ts +1 -0
- package/src/rules/html-no-empty-headings.ts +21 -44
- package/src/rules/index.ts +4 -0
- package/src/rules/string-utils.ts +72 -0
- package/src/rules.ts +4 -0
- package/src/types.ts +6 -0
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { SourceRule } from "../types.js";
|
|
2
|
+
import { Location } from "@herb-tools/core";
|
|
3
|
+
import { BaseSourceRuleVisitor } from "./rule-utils.js";
|
|
4
|
+
import { isPartialFile } from "./file-utils.js";
|
|
5
|
+
function hasStrictLocals(source) {
|
|
6
|
+
return source.includes("<%# locals:") || source.includes("<%#locals:");
|
|
7
|
+
}
|
|
8
|
+
class ERBStrictLocalsRequiredVisitor extends BaseSourceRuleVisitor {
|
|
9
|
+
visitSource(source) {
|
|
10
|
+
const isPartial = isPartialFile(this.context.fileName);
|
|
11
|
+
if (isPartial !== true)
|
|
12
|
+
return;
|
|
13
|
+
if (hasStrictLocals(source))
|
|
14
|
+
return;
|
|
15
|
+
const firstLineLength = source.indexOf("\n") === -1 ? source.length : source.indexOf("\n");
|
|
16
|
+
const location = Location.from(1, 0, 1, firstLineLength);
|
|
17
|
+
this.addOffense("Partial is missing a strict locals declaration. Add `<%# locals: (...) %>` at the top of the file.", location);
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
export class ERBStrictLocalsRequiredRule extends SourceRule {
|
|
21
|
+
static unsafeAutocorrectable = true;
|
|
22
|
+
name = "erb-strict-locals-required";
|
|
23
|
+
get defaultConfig() {
|
|
24
|
+
return {
|
|
25
|
+
enabled: false,
|
|
26
|
+
severity: "error",
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
check(source, context) {
|
|
30
|
+
const visitor = new ERBStrictLocalsRequiredVisitor(this.name, context);
|
|
31
|
+
visitor.visit(source);
|
|
32
|
+
return visitor.offenses;
|
|
33
|
+
}
|
|
34
|
+
autofix(_offense, source, _context) {
|
|
35
|
+
return `<%# locals: () %>\n\n${source}`;
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
//# sourceMappingURL=erb-strict-locals-required.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"erb-strict-locals-required.js","sourceRoot":"","sources":["../../../src/rules/erb-strict-locals-required.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAA;AACxC,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAA;AAC3C,OAAO,EAAE,qBAAqB,EAAE,MAAM,iBAAiB,CAAA;AAEvD,OAAO,EAAE,aAAa,EAAE,MAAM,iBAAiB,CAAA;AAI/C,SAAS,eAAe,CAAC,MAAc;IACrC,OAAO,MAAM,CAAC,QAAQ,CAAC,aAAa,CAAC,IAAI,MAAM,CAAC,QAAQ,CAAC,YAAY,CAAC,CAAA;AACxE,CAAC;AAED,MAAM,8BAA+B,SAAQ,qBAAqB;IACtD,WAAW,CAAC,MAAc;QAClC,MAAM,SAAS,GAAG,aAAa,CAAC,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAA;QAEtD,IAAI,SAAS,KAAK,IAAI;YAAE,OAAM;QAC9B,IAAI,eAAe,CAAC,MAAM,CAAC;YAAE,OAAM;QAEnC,MAAM,eAAe,GAAG,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,CAAA;QAC1F,MAAM,QAAQ,GAAG,QAAQ,CAAC,IAAI,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,eAAe,CAAC,CAAA;QAExD,IAAI,CAAC,UAAU,CACb,oGAAoG,EACpG,QAAQ,CACT,CAAA;IACH,CAAC;CACF;AAED,MAAM,OAAO,2BAA4B,SAAQ,UAAU;IACzD,MAAM,CAAC,qBAAqB,GAAG,IAAI,CAAA;IACnC,IAAI,GAAG,4BAA4B,CAAA;IAEnC,IAAI,aAAa;QACf,OAAO;YACL,OAAO,EAAE,KAAK;YACd,QAAQ,EAAE,OAAO;SAClB,CAAA;IACH,CAAC;IAED,KAAK,CAAC,MAAc,EAAE,OAA8B;QAClD,MAAM,OAAO,GAAG,IAAI,8BAA8B,CAAC,IAAI,CAAC,IAAI,EAAE,OAAO,CAAC,CAAA;QAEtE,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,CAAA;QAErB,OAAO,OAAO,CAAC,QAAQ,CAAA;IACzB,CAAC;IAED,OAAO,CAAC,QAAqB,EAAE,MAAc,EAAE,QAA+B;QAC5E,OAAO,wBAAwB,MAAM,EAAE,CAAA;IACzC,CAAC"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* File path and naming utilities for linter rules
|
|
3
|
+
*/
|
|
4
|
+
/**
|
|
5
|
+
* Extracts the basename (filename) from a file path
|
|
6
|
+
* Works with both forward slashes and backslashes
|
|
7
|
+
*/
|
|
8
|
+
export function getBasename(filePath) {
|
|
9
|
+
const lastSlash = Math.max(filePath.lastIndexOf("/"), filePath.lastIndexOf("\\"));
|
|
10
|
+
return lastSlash === -1 ? filePath : filePath.slice(lastSlash + 1);
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* Checks if a file is a Rails partial (filename starts with `_`)
|
|
14
|
+
* Returns null if fileName is undefined (unknown context)
|
|
15
|
+
*/
|
|
16
|
+
export function isPartialFile(fileName) {
|
|
17
|
+
if (!fileName)
|
|
18
|
+
return null;
|
|
19
|
+
return getBasename(fileName).startsWith("_");
|
|
20
|
+
}
|
|
21
|
+
//# sourceMappingURL=file-utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"file-utils.js","sourceRoot":"","sources":["../../../src/rules/file-utils.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH;;;GAGG;AACH,MAAM,UAAU,WAAW,CAAC,QAAgB;IAC1C,MAAM,SAAS,GAAG,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,WAAW,CAAC,GAAG,CAAC,EAAE,QAAQ,CAAC,WAAW,CAAC,IAAI,CAAC,CAAC,CAAA;IAEjF,OAAO,SAAS,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,SAAS,GAAG,CAAC,CAAC,CAAA;AACpE,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,aAAa,CAAC,QAA4B;IACxD,IAAI,CAAC,QAAQ;QAAE,OAAO,IAAI,CAAA;IAE1B,OAAO,WAAW,CAAC,QAAQ,CAAC,CAAC,UAAU,CAAC,GAAG,CAAC,CAAA;AAC9C,CAAC"}
|
|
@@ -20,6 +20,8 @@ class HeadOnlyElementsVisitor extends BaseRuleVisitor {
|
|
|
20
20
|
return;
|
|
21
21
|
if (tagName === "title" && this.insideSVG)
|
|
22
22
|
return;
|
|
23
|
+
if (tagName === "style" && this.insideSVG)
|
|
24
|
+
return;
|
|
23
25
|
if (tagName === "meta" && this.hasItempropAttribute(node))
|
|
24
26
|
return;
|
|
25
27
|
this.addOffense(`Element \`<${tagName}>\` must be placed inside the \`<head>\` tag.`, node.location);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"html-head-only-elements.js","sourceRoot":"","sources":["../../../src/rules/html-head-only-elements.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAA;AACrC,OAAO,EAAE,eAAe,EAAE,UAAU,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,cAAc,CAAA;AAKvF,MAAM,uBAAwB,SAAQ,eAAe;IAC3C,YAAY,GAAa,EAAE,CAAA;IAEnC,oBAAoB,CAAC,IAAqB;QACxC,MAAM,OAAO,GAAG,UAAU,CAAC,IAAI,CAAC,EAAE,WAAW,EAAE,CAAA;QAC/C,IAAI,CAAC,OAAO;YAAE,OAAM;QAEpB,IAAI,CAAC,oBAAoB,CAAC,IAAI,EAAE,OAAO,CAAC,CAAA;QAExC,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,OAAO,CAAC,CAAA;QAC/B,IAAI,CAAC,eAAe,CAAC,IAAI,CAAC,CAAA;QAC1B,IAAI,CAAC,YAAY,CAAC,GAAG,EAAE,CAAA;IACzB,CAAC;IAEO,oBAAoB,CAAC,IAAqB,EAAE,OAAe;QACjE,IAAI,IAAI,CAAC,UAAU;YAAE,OAAM;QAC3B,IAAI,CAAC,IAAI,CAAC,UAAU;YAAE,OAAM;QAC5B,IAAI,CAAC,aAAa,CAAC,OAAO,CAAC;YAAE,OAAM;QACnC,IAAI,OAAO,KAAK,OAAO,IAAI,IAAI,CAAC,SAAS;YAAE,OAAM;QACjD,IAAI,OAAO,KAAK,MAAM,IAAI,IAAI,CAAC,oBAAoB,CAAC,IAAI,CAAC;YAAE,OAAM;QAEjE,IAAI,CAAC,UAAU,CACb,cAAc,OAAO,+CAA+C,EACpE,IAAI,CAAC,QAAQ,CACd,CAAA;IACH,CAAC;IAEO,oBAAoB,CAAC,IAAqB;QAChD,OAAO,YAAY,CAAC,IAAI,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAA;IAChD,CAAC;IAED,IAAY,UAAU;QACpB,OAAO,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAA;IAC3C,CAAC;IAED,IAAY,UAAU;QACpB,OAAO,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAA;IAC3C,CAAC;IAED,IAAY,SAAS;QACnB,OAAO,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAA;IAC1C,CAAC;CACF;AAED,MAAM,OAAO,wBAAyB,SAAQ,UAAU;IACtD,MAAM,CAAC,eAAe,GAAG,KAAK,CAAA;IAC9B,IAAI,GAAG,yBAAyB,CAAA;IAEhC,IAAI,aAAa;QACf,OAAO;YACL,OAAO,EAAE,IAAI;YACb,QAAQ,EAAE,OAAO;YACjB,OAAO,EAAE,CAAC,UAAU,EAAE,cAAc,CAAC;SACtC,CAAA;IACH,CAAC;IAED,KAAK,CAAC,MAAmB,EAAE,OAA8B;QACvD,MAAM,OAAO,GAAG,IAAI,uBAAuB,CAAC,IAAI,CAAC,IAAI,EAAE,OAAO,CAAC,CAAA;QAE/D,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,KAAK,CAAC,CAAA;QAE3B,OAAO,OAAO,CAAC,QAAQ,CAAA;IACzB,CAAC"}
|
|
1
|
+
{"version":3,"file":"html-head-only-elements.js","sourceRoot":"","sources":["../../../src/rules/html-head-only-elements.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAA;AACrC,OAAO,EAAE,eAAe,EAAE,UAAU,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,cAAc,CAAA;AAKvF,MAAM,uBAAwB,SAAQ,eAAe;IAC3C,YAAY,GAAa,EAAE,CAAA;IAEnC,oBAAoB,CAAC,IAAqB;QACxC,MAAM,OAAO,GAAG,UAAU,CAAC,IAAI,CAAC,EAAE,WAAW,EAAE,CAAA;QAC/C,IAAI,CAAC,OAAO;YAAE,OAAM;QAEpB,IAAI,CAAC,oBAAoB,CAAC,IAAI,EAAE,OAAO,CAAC,CAAA;QAExC,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,OAAO,CAAC,CAAA;QAC/B,IAAI,CAAC,eAAe,CAAC,IAAI,CAAC,CAAA;QAC1B,IAAI,CAAC,YAAY,CAAC,GAAG,EAAE,CAAA;IACzB,CAAC;IAEO,oBAAoB,CAAC,IAAqB,EAAE,OAAe;QACjE,IAAI,IAAI,CAAC,UAAU;YAAE,OAAM;QAC3B,IAAI,CAAC,IAAI,CAAC,UAAU;YAAE,OAAM;QAC5B,IAAI,CAAC,aAAa,CAAC,OAAO,CAAC;YAAE,OAAM;QACnC,IAAI,OAAO,KAAK,OAAO,IAAI,IAAI,CAAC,SAAS;YAAE,OAAM;QACjD,IAAI,OAAO,KAAK,OAAO,IAAI,IAAI,CAAC,SAAS;YAAE,OAAM;QACjD,IAAI,OAAO,KAAK,MAAM,IAAI,IAAI,CAAC,oBAAoB,CAAC,IAAI,CAAC;YAAE,OAAM;QAEjE,IAAI,CAAC,UAAU,CACb,cAAc,OAAO,+CAA+C,EACpE,IAAI,CAAC,QAAQ,CACd,CAAA;IACH,CAAC;IAEO,oBAAoB,CAAC,IAAqB;QAChD,OAAO,YAAY,CAAC,IAAI,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAA;IAChD,CAAC;IAED,IAAY,UAAU;QACpB,OAAO,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAA;IAC3C,CAAC;IAED,IAAY,UAAU;QACpB,OAAO,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAA;IAC3C,CAAC;IAED,IAAY,SAAS;QACnB,OAAO,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAA;IAC1C,CAAC;CACF;AAED,MAAM,OAAO,wBAAyB,SAAQ,UAAU;IACtD,MAAM,CAAC,eAAe,GAAG,KAAK,CAAA;IAC9B,IAAI,GAAG,yBAAyB,CAAA;IAEhC,IAAI,aAAa;QACf,OAAO;YACL,OAAO,EAAE,IAAI;YACb,QAAQ,EAAE,OAAO;YACjB,OAAO,EAAE,CAAC,UAAU,EAAE,cAAc,CAAC;SACtC,CAAA;IACH,CAAC;IAED,KAAK,CAAC,MAAmB,EAAE,OAA8B;QACvD,MAAM,OAAO,GAAG,IAAI,uBAAuB,CAAC,IAAI,CAAC,IAAI,EAAE,OAAO,CAAC,CAAA;QAE/D,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,KAAK,CAAC,CAAA;QAE3B,OAAO,OAAO,CAAC,QAAQ,CAAA;IACzB,CAAC"}
|
|
@@ -1,21 +1,24 @@
|
|
|
1
1
|
import { BaseRuleVisitor, getTagName, getAttributes, findAttributeByName, getAttributeValue, HEADING_TAGS } from "./rule-utils.js";
|
|
2
|
+
import { isHTMLOpenTagNode, isLiteralNode, isHTMLTextNode, isHTMLElementNode } from "@herb-tools/core";
|
|
2
3
|
import { ParserRule } from "../types.js";
|
|
3
4
|
class NoEmptyHeadingsVisitor extends BaseRuleVisitor {
|
|
4
5
|
visitHTMLElementNode(node) {
|
|
6
|
+
const tagName = getTagName(node.open_tag)?.toLowerCase();
|
|
7
|
+
if (tagName === "template")
|
|
8
|
+
return;
|
|
5
9
|
this.checkHeadingElement(node);
|
|
6
10
|
super.visitHTMLElementNode(node);
|
|
7
11
|
}
|
|
8
12
|
checkHeadingElement(node) {
|
|
9
|
-
if (!node.open_tag
|
|
13
|
+
if (!node.open_tag)
|
|
10
14
|
return;
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
const tagName = getTagName(
|
|
14
|
-
if (!tagName)
|
|
15
|
+
if (!isHTMLOpenTagNode(node.open_tag))
|
|
16
|
+
return;
|
|
17
|
+
const tagName = getTagName(node.open_tag);
|
|
18
|
+
if (!tagName)
|
|
15
19
|
return;
|
|
16
|
-
}
|
|
17
20
|
const isStandardHeading = HEADING_TAGS.has(tagName);
|
|
18
|
-
const isAriaHeading = this.hasHeadingRole(
|
|
21
|
+
const isAriaHeading = this.hasHeadingRole(node.open_tag);
|
|
19
22
|
if (!isStandardHeading && !isAriaHeading) {
|
|
20
23
|
return;
|
|
21
24
|
}
|
|
@@ -32,23 +35,14 @@ class NoEmptyHeadingsVisitor extends BaseRuleVisitor {
|
|
|
32
35
|
}
|
|
33
36
|
let hasAccessibleContent = false;
|
|
34
37
|
for (const child of node.body) {
|
|
35
|
-
if (child
|
|
36
|
-
|
|
37
|
-
if (literalNode.content.trim().length > 0) {
|
|
38
|
+
if (isLiteralNode(child) || isHTMLTextNode(child)) {
|
|
39
|
+
if (child.content.trim().length > 0) {
|
|
38
40
|
hasAccessibleContent = true;
|
|
39
41
|
break;
|
|
40
42
|
}
|
|
41
43
|
}
|
|
42
|
-
else if (child
|
|
43
|
-
|
|
44
|
-
if (textNode.content.trim().length > 0) {
|
|
45
|
-
hasAccessibleContent = true;
|
|
46
|
-
break;
|
|
47
|
-
}
|
|
48
|
-
}
|
|
49
|
-
else if (child.type === "AST_HTML_ELEMENT_NODE") {
|
|
50
|
-
const elementNode = child;
|
|
51
|
-
if (this.isElementAccessible(elementNode)) {
|
|
44
|
+
else if (isHTMLElementNode(child)) {
|
|
45
|
+
if (this.isElementAccessible(child)) {
|
|
52
46
|
hasAccessibleContent = true;
|
|
53
47
|
break;
|
|
54
48
|
}
|
|
@@ -70,11 +64,11 @@ class NoEmptyHeadingsVisitor extends BaseRuleVisitor {
|
|
|
70
64
|
return roleValue === "heading";
|
|
71
65
|
}
|
|
72
66
|
isElementAccessible(node) {
|
|
73
|
-
if (!node.open_tag
|
|
67
|
+
if (!node.open_tag)
|
|
74
68
|
return true;
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
const attributes = getAttributes(
|
|
69
|
+
if (!isHTMLOpenTagNode(node.open_tag))
|
|
70
|
+
return true;
|
|
71
|
+
const attributes = getAttributes(node.open_tag);
|
|
78
72
|
const ariaHiddenAttribute = findAttributeByName(attributes, "aria-hidden");
|
|
79
73
|
if (ariaHiddenAttribute) {
|
|
80
74
|
const ariaHiddenValue = getAttributeValue(ariaHiddenAttribute);
|
|
@@ -86,21 +80,13 @@ class NoEmptyHeadingsVisitor extends BaseRuleVisitor {
|
|
|
86
80
|
return false;
|
|
87
81
|
}
|
|
88
82
|
for (const child of node.body) {
|
|
89
|
-
if (child
|
|
90
|
-
|
|
91
|
-
if (literalNode.content.trim().length > 0) {
|
|
92
|
-
return true;
|
|
93
|
-
}
|
|
94
|
-
}
|
|
95
|
-
else if (child.type === "AST_HTML_TEXT_NODE") {
|
|
96
|
-
const textNode = child;
|
|
97
|
-
if (textNode.content.trim().length > 0) {
|
|
83
|
+
if (isLiteralNode(child) || isHTMLTextNode(child)) {
|
|
84
|
+
if (child.content.trim().length > 0) {
|
|
98
85
|
return true;
|
|
99
86
|
}
|
|
100
87
|
}
|
|
101
|
-
else if (child
|
|
102
|
-
|
|
103
|
-
if (this.isElementAccessible(elementNode)) {
|
|
88
|
+
else if (isHTMLElementNode(child)) {
|
|
89
|
+
if (this.isElementAccessible(child)) {
|
|
104
90
|
return true;
|
|
105
91
|
}
|
|
106
92
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"html-no-empty-headings.js","sourceRoot":"","sources":["../../../src/rules/html-no-empty-headings.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,UAAU,EAAE,aAAa,EAAE,mBAAmB,EAAE,iBAAiB,EAAE,YAAY,EAAE,MAAM,iBAAiB,CAAA;
|
|
1
|
+
{"version":3,"file":"html-no-empty-headings.js","sourceRoot":"","sources":["../../../src/rules/html-no-empty-headings.ts"],"names":[],"mappings":"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"}
|
package/dist/src/rules/index.js
CHANGED
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
export * from "./rule-utils.js";
|
|
2
|
+
export * from "./file-utils.js";
|
|
3
|
+
export * from "./string-utils.js";
|
|
2
4
|
export * from "./herb-disable-comment-base.js";
|
|
3
5
|
export * from "./erb-comment-syntax.js";
|
|
4
6
|
export * from "./erb-no-case-node-children.js";
|
|
@@ -11,6 +13,8 @@ export * from "./erb-prefer-image-tag-helper.js";
|
|
|
11
13
|
export * from "./erb-require-trailing-newline.js";
|
|
12
14
|
export * from "./erb-require-whitespace-inside-tags.js";
|
|
13
15
|
export * from "./erb-right-trim.js";
|
|
16
|
+
export * from "./erb-strict-locals-comment-syntax.js";
|
|
17
|
+
export * from "./erb-strict-locals-required.js";
|
|
14
18
|
export * from "./herb-disable-comment-valid-rule-name.js";
|
|
15
19
|
export * from "./herb-disable-comment-no-redundant-all.js";
|
|
16
20
|
export * from "./herb-disable-comment-no-duplicate-rules.js";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/rules/index.ts"],"names":[],"mappings":"AAAA,cAAc,iBAAiB,CAAA;AAC/B,cAAc,gCAAgC,CAAA;AAE9C,cAAc,yBAAyB,CAAA;AACvC,cAAc,gCAAgC,CAAA;AAC9C,cAAc,wBAAwB,CAAA;AACtC,cAAc,2BAA2B,CAAA;AACzC,cAAc,0CAA0C,CAAA;AACxD,cAAc,iCAAiC,CAAA;AAC/C,cAAc,0CAA0C,CAAA;AACxD,cAAc,kCAAkC,CAAA;AAChD,cAAc,mCAAmC,CAAA;AACjD,cAAc,yCAAyC,CAAA;AACvD,cAAc,qBAAqB,CAAA;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/rules/index.ts"],"names":[],"mappings":"AAAA,cAAc,iBAAiB,CAAA;AAC/B,cAAc,iBAAiB,CAAA;AAC/B,cAAc,mBAAmB,CAAA;AACjC,cAAc,gCAAgC,CAAA;AAE9C,cAAc,yBAAyB,CAAA;AACvC,cAAc,gCAAgC,CAAA;AAC9C,cAAc,wBAAwB,CAAA;AACtC,cAAc,2BAA2B,CAAA;AACzC,cAAc,0CAA0C,CAAA;AACxD,cAAc,iCAAiC,CAAA;AAC/C,cAAc,0CAA0C,CAAA;AACxD,cAAc,kCAAkC,CAAA;AAChD,cAAc,mCAAmC,CAAA;AACjD,cAAc,yCAAyC,CAAA;AACvD,cAAc,qBAAqB,CAAA;AACnC,cAAc,uCAAuC,CAAA;AACrD,cAAc,iCAAiC,CAAA;AAE/C,cAAc,2CAA2C,CAAA;AACzD,cAAc,4CAA4C,CAAA;AAC1D,cAAc,8CAA8C,CAAA;AAC5D,cAAc,yCAAyC,CAAA;AACvD,cAAc,qCAAqC,CAAA;AACnD,cAAc,uCAAuC,CAAA;AAErD,cAAc,+BAA+B,CAAA;AAC7C,cAAc,wCAAwC,CAAA;AACtD,cAAc,oCAAoC,CAAA;AAClD,cAAc,4CAA4C,CAAA;AAC1D,cAAc,mCAAmC,CAAA;AACjD,cAAc,mCAAmC,CAAA;AACjD,cAAc,oCAAoC,CAAA;AAClD,cAAc,2CAA2C,CAAA;AACzD,cAAc,iDAAiD,CAAA;AAC/D,cAAc,8BAA8B,CAAA;AAC5C,cAAc,uCAAuC,CAAA;AACrD,cAAc,8BAA8B,CAAA;AAC5C,cAAc,4BAA4B,CAAA;AAC1C,cAAc,2BAA2B,CAAA;AACzC,cAAc,sCAAsC,CAAA;AACpD,cAAc,gCAAgC,CAAA;AAC9C,cAAc,uCAAuC,CAAA;AACrD,cAAc,kCAAkC,CAAA;AAChD,cAAc,mCAAmC,CAAA;AACjD,cAAc,4BAA4B,CAAA;AAC1C,cAAc,mCAAmC,CAAA;AACjD,cAAc,+BAA+B,CAAA;AAC7C,cAAc,6BAA6B,CAAA;AAC3C,cAAc,2BAA2B,CAAA;AACzC,cAAc,iCAAiC,CAAA;AAC/C,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,8BAA8B,CAAA;AAC5C,cAAc,6CAA6C,CAAA;AAC3D,cAAc,8BAA8B,CAAA;AAE5C,cAAc,kCAAkC,CAAA"}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Checks if parentheses in a string are balanced
|
|
3
|
+
* Returns false if there are more closing parens than opening at any point
|
|
4
|
+
*/
|
|
5
|
+
export function hasBalancedParentheses(content) {
|
|
6
|
+
let depth = 0;
|
|
7
|
+
for (const char of content) {
|
|
8
|
+
if (char === "(")
|
|
9
|
+
depth++;
|
|
10
|
+
if (char === ")")
|
|
11
|
+
depth--;
|
|
12
|
+
if (depth < 0)
|
|
13
|
+
return false;
|
|
14
|
+
}
|
|
15
|
+
return depth === 0;
|
|
16
|
+
}
|
|
17
|
+
/**
|
|
18
|
+
* Splits a string by commas at the top level only
|
|
19
|
+
* Respects nested parentheses, brackets, braces, and strings
|
|
20
|
+
*
|
|
21
|
+
* @example
|
|
22
|
+
* splitByTopLevelComma("a, b, c") // ["a", " b", " c"]
|
|
23
|
+
* splitByTopLevelComma("a, (b, c), d") // ["a", " (b, c)", " d"]
|
|
24
|
+
* splitByTopLevelComma('a, "b, c", d') // ["a", ' "b, c"', " d"]
|
|
25
|
+
*/
|
|
26
|
+
export function splitByTopLevelComma(str) {
|
|
27
|
+
const result = [];
|
|
28
|
+
let current = "";
|
|
29
|
+
let parenDepth = 0;
|
|
30
|
+
let bracketDepth = 0;
|
|
31
|
+
let braceDepth = 0;
|
|
32
|
+
let inString = false;
|
|
33
|
+
let stringChar = "";
|
|
34
|
+
for (let i = 0; i < str.length; i++) {
|
|
35
|
+
const char = str[i];
|
|
36
|
+
const previousChar = i > 0 ? str[i - 1] : "";
|
|
37
|
+
if ((char === '"' || char === "'") && previousChar !== "\\") {
|
|
38
|
+
if (!inString) {
|
|
39
|
+
inString = true;
|
|
40
|
+
stringChar = char;
|
|
41
|
+
}
|
|
42
|
+
else if (char === stringChar) {
|
|
43
|
+
inString = false;
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
if (!inString) {
|
|
47
|
+
if (char === "(")
|
|
48
|
+
parenDepth++;
|
|
49
|
+
if (char === ")")
|
|
50
|
+
parenDepth--;
|
|
51
|
+
if (char === "[")
|
|
52
|
+
bracketDepth++;
|
|
53
|
+
if (char === "]")
|
|
54
|
+
bracketDepth--;
|
|
55
|
+
if (char === "{")
|
|
56
|
+
braceDepth++;
|
|
57
|
+
if (char === "}")
|
|
58
|
+
braceDepth--;
|
|
59
|
+
if (char === "," && parenDepth === 0 && bracketDepth === 0 && braceDepth === 0) {
|
|
60
|
+
result.push(current);
|
|
61
|
+
current = "";
|
|
62
|
+
continue;
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
current += char;
|
|
66
|
+
}
|
|
67
|
+
if (current) {
|
|
68
|
+
result.push(current);
|
|
69
|
+
}
|
|
70
|
+
return result;
|
|
71
|
+
}
|
|
72
|
+
//# sourceMappingURL=string-utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"string-utils.js","sourceRoot":"","sources":["../../../src/rules/string-utils.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,MAAM,UAAU,sBAAsB,CAAC,OAAe;IACpD,IAAI,KAAK,GAAG,CAAC,CAAA;IAEb,KAAK,MAAM,IAAI,IAAI,OAAO,EAAE,CAAC;QAC3B,IAAI,IAAI,KAAK,GAAG;YAAE,KAAK,EAAE,CAAA;QACzB,IAAI,IAAI,KAAK,GAAG;YAAE,KAAK,EAAE,CAAA;QACzB,IAAI,KAAK,GAAG,CAAC;YAAE,OAAO,KAAK,CAAA;IAC7B,CAAC;IAED,OAAO,KAAK,KAAK,CAAC,CAAA;AACpB,CAAC;AAED;;;;;;;;GAQG;AACH,MAAM,UAAU,oBAAoB,CAAC,GAAW;IAC9C,MAAM,MAAM,GAAa,EAAE,CAAA;IAE3B,IAAI,OAAO,GAAG,EAAE,CAAA;IAChB,IAAI,UAAU,GAAG,CAAC,CAAA;IAClB,IAAI,YAAY,GAAG,CAAC,CAAA;IACpB,IAAI,UAAU,GAAG,CAAC,CAAA;IAClB,IAAI,QAAQ,GAAG,KAAK,CAAA;IACpB,IAAI,UAAU,GAAG,EAAE,CAAA;IAEnB,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,GAAG,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;QACpC,MAAM,IAAI,GAAG,GAAG,CAAC,CAAC,CAAC,CAAA;QACnB,MAAM,YAAY,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAA;QAE5C,IAAI,CAAC,IAAI,KAAK,GAAG,IAAI,IAAI,KAAK,GAAG,CAAC,IAAI,YAAY,KAAK,IAAI,EAAE,CAAC;YAC5D,IAAI,CAAC,QAAQ,EAAE,CAAC;gBACd,QAAQ,GAAG,IAAI,CAAA;gBACf,UAAU,GAAG,IAAI,CAAA;YACnB,CAAC;iBAAM,IAAI,IAAI,KAAK,UAAU,EAAE,CAAC;gBAC/B,QAAQ,GAAG,KAAK,CAAA;YAClB,CAAC;QACH,CAAC;QAED,IAAI,CAAC,QAAQ,EAAE,CAAC;YACd,IAAI,IAAI,KAAK,GAAG;gBAAE,UAAU,EAAE,CAAA;YAC9B,IAAI,IAAI,KAAK,GAAG;gBAAE,UAAU,EAAE,CAAA;YAC9B,IAAI,IAAI,KAAK,GAAG;gBAAE,YAAY,EAAE,CAAA;YAChC,IAAI,IAAI,KAAK,GAAG;gBAAE,YAAY,EAAE,CAAA;YAChC,IAAI,IAAI,KAAK,GAAG;gBAAE,UAAU,EAAE,CAAA;YAC9B,IAAI,IAAI,KAAK,GAAG;gBAAE,UAAU,EAAE,CAAA;YAE9B,IAAI,IAAI,KAAK,GAAG,IAAI,UAAU,KAAK,CAAC,IAAI,YAAY,KAAK,CAAC,IAAI,UAAU,KAAK,CAAC,EAAE,CAAC;gBAC/E,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,CAAA;gBACpB,OAAO,GAAG,EAAE,CAAA;gBACZ,SAAQ;YACV,CAAC;QACH,CAAC;QAED,OAAO,IAAI,IAAI,CAAA;IACjB,CAAC;IAED,IAAI,OAAO,EAAE,CAAC;QACZ,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,CAAA;IACtB,CAAC;IAED,OAAO,MAAM,CAAA;AACf,CAAC"}
|
package/dist/src/rules.js
CHANGED
|
@@ -9,6 +9,8 @@ import { ERBPreferImageTagHelperRule } from "./rules/erb-prefer-image-tag-helper
|
|
|
9
9
|
import { ERBRequireTrailingNewlineRule } from "./rules/erb-require-trailing-newline.js";
|
|
10
10
|
import { ERBRequireWhitespaceRule } from "./rules/erb-require-whitespace-inside-tags.js";
|
|
11
11
|
import { ERBRightTrimRule } from "./rules/erb-right-trim.js";
|
|
12
|
+
import { ERBStrictLocalsCommentSyntaxRule } from "./rules/erb-strict-locals-comment-syntax.js";
|
|
13
|
+
import { ERBStrictLocalsRequiredRule } from "./rules/erb-strict-locals-required.js";
|
|
12
14
|
import { HerbDisableCommentValidRuleNameRule } from "./rules/herb-disable-comment-valid-rule-name.js";
|
|
13
15
|
import { HerbDisableCommentNoRedundantAllRule } from "./rules/herb-disable-comment-no-redundant-all.js";
|
|
14
16
|
import { HerbDisableCommentNoDuplicateRulesRule } from "./rules/herb-disable-comment-no-duplicate-rules.js";
|
|
@@ -60,6 +62,8 @@ export const rules = [
|
|
|
60
62
|
ERBRequireTrailingNewlineRule,
|
|
61
63
|
ERBRequireWhitespaceRule,
|
|
62
64
|
ERBRightTrimRule,
|
|
65
|
+
ERBStrictLocalsCommentSyntaxRule,
|
|
66
|
+
ERBStrictLocalsRequiredRule,
|
|
63
67
|
HerbDisableCommentValidRuleNameRule,
|
|
64
68
|
HerbDisableCommentNoRedundantAllRule,
|
|
65
69
|
HerbDisableCommentNoDuplicateRulesRule,
|
package/dist/src/rules.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"rules.js","sourceRoot":"","sources":["../../src/rules.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,gBAAgB,EAAE,MAAM,+BAA+B,CAAC;AACjE,OAAO,EAAE,yBAAyB,EAAE,MAAM,sCAAsC,CAAA;AAChF,OAAO,EAAE,kBAAkB,EAAE,MAAM,8BAA8B,CAAA;AACjE,OAAO,EAAE,qBAAqB,EAAE,MAAM,iCAAiC,CAAA;AACvE,OAAO,EAAE,wBAAwB,EAAE,MAAM,gDAAgD,CAAA;AACzF,OAAO,EAAE,0BAA0B,EAAE,MAAM,uCAAuC,CAAA;AAClF,OAAO,EAAE,iCAAiC,EAAE,MAAM,gDAAgD,CAAA;AAClG,OAAO,EAAE,2BAA2B,EAAE,MAAM,wCAAwC,CAAA;AACpF,OAAO,EAAE,6BAA6B,EAAE,MAAM,yCAAyC,CAAA;AACvF,OAAO,EAAE,wBAAwB,EAAE,MAAM,+CAA+C,CAAA;AACxF,OAAO,EAAE,gBAAgB,EAAE,MAAM,2BAA2B,CAAA;
|
|
1
|
+
{"version":3,"file":"rules.js","sourceRoot":"","sources":["../../src/rules.ts"],"names":[],"mappings":"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"}
|
package/dist/src/types.js
CHANGED
|
@@ -14,6 +14,8 @@ export class ParserRule {
|
|
|
14
14
|
static type = "parser";
|
|
15
15
|
/** Indicates whether this rule supports autofix. Defaults to false. */
|
|
16
16
|
static autocorrectable = false;
|
|
17
|
+
/** Indicates whether this rule supports unsafe autofix (requires --fix-unsafely). Defaults to false. */
|
|
18
|
+
static unsafeAutocorrectable = false;
|
|
17
19
|
get defaultConfig() {
|
|
18
20
|
return DEFAULT_RULE_CONFIG;
|
|
19
21
|
}
|
|
@@ -25,6 +27,8 @@ export class LexerRule {
|
|
|
25
27
|
static type = "lexer";
|
|
26
28
|
/** Indicates whether this rule supports autofix. Defaults to false. */
|
|
27
29
|
static autocorrectable = false;
|
|
30
|
+
/** Indicates whether this rule supports unsafe autofix (requires --fix-unsafely). Defaults to false. */
|
|
31
|
+
static unsafeAutocorrectable = false;
|
|
28
32
|
get defaultConfig() {
|
|
29
33
|
return DEFAULT_RULE_CONFIG;
|
|
30
34
|
}
|
|
@@ -42,6 +46,8 @@ export class SourceRule {
|
|
|
42
46
|
static type = "source";
|
|
43
47
|
/** Indicates whether this rule supports autofix. Defaults to false. */
|
|
44
48
|
static autocorrectable = false;
|
|
49
|
+
/** Indicates whether this rule supports unsafe autofix (requires --fix-unsafely). Defaults to false. */
|
|
50
|
+
static unsafeAutocorrectable = false;
|
|
45
51
|
get defaultConfig() {
|
|
46
52
|
return DEFAULT_RULE_CONFIG;
|
|
47
53
|
}
|
package/dist/src/types.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/types.ts"],"names":[],"mappings":"AAsEA;;;GAGG;AACH,MAAM,CAAC,MAAM,mBAAmB,GAAmB;IACjD,OAAO,EAAE,IAAI;IACb,QAAQ,EAAE,OAAO;IACjB,OAAO,EAAE,EAAE;CACZ,CAAA;AAED;;GAEG;AACH,MAAM,OAAgB,UAAU;IAC9B,MAAM,CAAC,IAAI,GAAG,QAAiB,CAAA;IAC/B,uEAAuE;IACvE,MAAM,CAAC,eAAe,GAAG,KAAK,CAAA;
|
|
1
|
+
{"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/types.ts"],"names":[],"mappings":"AAsEA;;;GAGG;AACH,MAAM,CAAC,MAAM,mBAAmB,GAAmB;IACjD,OAAO,EAAE,IAAI;IACb,QAAQ,EAAE,OAAO;IACjB,OAAO,EAAE,EAAE;CACZ,CAAA;AAED;;GAEG;AACH,MAAM,OAAgB,UAAU;IAC9B,MAAM,CAAC,IAAI,GAAG,QAAiB,CAAA;IAC/B,uEAAuE;IACvE,MAAM,CAAC,eAAe,GAAG,KAAK,CAAA;IAC9B,wGAAwG;IACxG,MAAM,CAAC,qBAAqB,GAAG,KAAK,CAAA;IAGpC,IAAI,aAAa;QACf,OAAO,mBAAmB,CAAA;IAC5B,CAAC;;AAuBH;;GAEG;AACH,MAAM,OAAgB,SAAS;IAC7B,MAAM,CAAC,IAAI,GAAG,OAAgB,CAAA;IAC9B,uEAAuE;IACvE,MAAM,CAAC,eAAe,GAAG,KAAK,CAAA;IAC9B,wGAAwG;IACxG,MAAM,CAAC,qBAAqB,GAAG,KAAK,CAAA;IAGpC,IAAI,aAAa;QACf,OAAO,mBAAmB,CAAA;IAC5B,CAAC;;AAuCH;;GAEG;AACH,MAAM,CAAC,MAAM,oBAAoB,GAAgB;IAC/C,QAAQ,EAAE,SAAS;IACnB,cAAc,EAAE,SAAS;IACzB,qBAAqB,EAAE,SAAS;IAChC,qBAAqB,EAAE,SAAS;CACxB,CAAA;AAEV,MAAM,OAAgB,UAAU;IAC9B,MAAM,CAAC,IAAI,GAAG,QAAiB,CAAA;IAC/B,uEAAuE;IACvE,MAAM,CAAC,eAAe,GAAG,KAAK,CAAA;IAC9B,wGAAwG;IACxG,MAAM,CAAC,qBAAqB,GAAG,KAAK,CAAA;IAGpC,IAAI,aAAa;QACf,OAAO,mBAAmB,CAAA;IAC5B,CAAC"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"root":["../src/cli.ts","../src/custom-rule-loader.ts","../src/herb-disable-comment-utils.ts","../src/herb-lint.ts","../src/index.ts","../src/linter-ignore.ts","../src/linter.ts","../src/loader.ts","../src/rules.ts","../src/types.ts","../src/cli/argument-parser.ts","../src/cli/file-processor.ts","../src/cli/index.ts","../src/cli/output-manager.ts","../src/cli/summary-reporter.ts","../src/cli/formatters/base-formatter.ts","../src/cli/formatters/detailed-formatter.ts","../src/cli/formatters/github-actions-formatter.ts","../src/cli/formatters/index.ts","../src/cli/formatters/json-formatter.ts","../src/cli/formatters/simple-formatter.ts","../src/rules/erb-comment-syntax.ts","../src/rules/erb-no-case-node-children.ts","../src/rules/erb-no-empty-tags.ts","../src/rules/erb-no-extra-newline.ts","../src/rules/erb-no-extra-whitespace-inside-tags.ts","../src/rules/erb-no-output-control-flow.ts","../src/rules/erb-no-silent-tag-in-attribute-name.ts","../src/rules/erb-prefer-image-tag-helper.ts","../src/rules/erb-require-trailing-newline.ts","../src/rules/erb-require-whitespace-inside-tags.ts","../src/rules/erb-right-trim.ts","../src/rules/herb-disable-comment-base.ts","../src/rules/herb-disable-comment-malformed.ts","../src/rules/herb-disable-comment-missing-rules.ts","../src/rules/herb-disable-comment-no-duplicate-rules.ts","../src/rules/herb-disable-comment-no-redundant-all.ts","../src/rules/herb-disable-comment-unnecessary.ts","../src/rules/herb-disable-comment-valid-rule-name.ts","../src/rules/html-anchor-require-href.ts","../src/rules/html-aria-attribute-must-be-valid.ts","../src/rules/html-aria-label-is-well-formatted.ts","../src/rules/html-aria-level-must-be-valid.ts","../src/rules/html-aria-role-heading-requires-level.ts","../src/rules/html-aria-role-must-be-valid.ts","../src/rules/html-attribute-double-quotes.ts","../src/rules/html-attribute-equals-spacing.ts","../src/rules/html-attribute-values-require-quotes.ts","../src/rules/html-avoid-both-disabled-and-aria-disabled.ts","../src/rules/html-body-only-elements.ts","../src/rules/html-boolean-attributes-no-value.ts","../src/rules/html-head-only-elements.ts","../src/rules/html-iframe-has-title.ts","../src/rules/html-img-require-alt.ts","../src/rules/html-input-require-autocomplete.ts","../src/rules/html-navigation-has-label.ts","../src/rules/html-no-aria-hidden-on-focusable.ts","../src/rules/html-no-block-inside-inline.ts","../src/rules/html-no-duplicate-attributes.ts","../src/rules/html-no-duplicate-ids.ts","../src/rules/html-no-duplicate-meta-names.ts","../src/rules/html-no-empty-attributes.ts","../src/rules/html-no-empty-headings.ts","../src/rules/html-no-nested-links.ts","../src/rules/html-no-positive-tab-index.ts","../src/rules/html-no-self-closing.ts","../src/rules/html-no-space-in-tag.ts","../src/rules/html-no-title-attribute.ts","../src/rules/html-no-underscores-in-attribute-names.ts","../src/rules/html-tag-name-lowercase.ts","../src/rules/index.ts","../src/rules/parser-no-errors.ts","../src/rules/rule-utils.ts","../src/rules/svg-tag-name-capitalization.ts"],"version":"5.9.3"}
|
|
1
|
+
{"root":["../src/cli.ts","../src/custom-rule-loader.ts","../src/herb-disable-comment-utils.ts","../src/herb-lint.ts","../src/index.ts","../src/linter-ignore.ts","../src/linter.ts","../src/loader.ts","../src/rules.ts","../src/types.ts","../src/cli/argument-parser.ts","../src/cli/file-processor.ts","../src/cli/index.ts","../src/cli/output-manager.ts","../src/cli/summary-reporter.ts","../src/cli/formatters/base-formatter.ts","../src/cli/formatters/detailed-formatter.ts","../src/cli/formatters/github-actions-formatter.ts","../src/cli/formatters/index.ts","../src/cli/formatters/json-formatter.ts","../src/cli/formatters/simple-formatter.ts","../src/rules/erb-comment-syntax.ts","../src/rules/erb-no-case-node-children.ts","../src/rules/erb-no-empty-tags.ts","../src/rules/erb-no-extra-newline.ts","../src/rules/erb-no-extra-whitespace-inside-tags.ts","../src/rules/erb-no-output-control-flow.ts","../src/rules/erb-no-silent-tag-in-attribute-name.ts","../src/rules/erb-prefer-image-tag-helper.ts","../src/rules/erb-require-trailing-newline.ts","../src/rules/erb-require-whitespace-inside-tags.ts","../src/rules/erb-right-trim.ts","../src/rules/erb-strict-locals-comment-syntax.ts","../src/rules/erb-strict-locals-required.ts","../src/rules/file-utils.ts","../src/rules/herb-disable-comment-base.ts","../src/rules/herb-disable-comment-malformed.ts","../src/rules/herb-disable-comment-missing-rules.ts","../src/rules/herb-disable-comment-no-duplicate-rules.ts","../src/rules/herb-disable-comment-no-redundant-all.ts","../src/rules/herb-disable-comment-unnecessary.ts","../src/rules/herb-disable-comment-valid-rule-name.ts","../src/rules/html-anchor-require-href.ts","../src/rules/html-aria-attribute-must-be-valid.ts","../src/rules/html-aria-label-is-well-formatted.ts","../src/rules/html-aria-level-must-be-valid.ts","../src/rules/html-aria-role-heading-requires-level.ts","../src/rules/html-aria-role-must-be-valid.ts","../src/rules/html-attribute-double-quotes.ts","../src/rules/html-attribute-equals-spacing.ts","../src/rules/html-attribute-values-require-quotes.ts","../src/rules/html-avoid-both-disabled-and-aria-disabled.ts","../src/rules/html-body-only-elements.ts","../src/rules/html-boolean-attributes-no-value.ts","../src/rules/html-head-only-elements.ts","../src/rules/html-iframe-has-title.ts","../src/rules/html-img-require-alt.ts","../src/rules/html-input-require-autocomplete.ts","../src/rules/html-navigation-has-label.ts","../src/rules/html-no-aria-hidden-on-focusable.ts","../src/rules/html-no-block-inside-inline.ts","../src/rules/html-no-duplicate-attributes.ts","../src/rules/html-no-duplicate-ids.ts","../src/rules/html-no-duplicate-meta-names.ts","../src/rules/html-no-empty-attributes.ts","../src/rules/html-no-empty-headings.ts","../src/rules/html-no-nested-links.ts","../src/rules/html-no-positive-tab-index.ts","../src/rules/html-no-self-closing.ts","../src/rules/html-no-space-in-tag.ts","../src/rules/html-no-title-attribute.ts","../src/rules/html-no-underscores-in-attribute-names.ts","../src/rules/html-tag-name-lowercase.ts","../src/rules/index.ts","../src/rules/parser-no-errors.ts","../src/rules/rule-utils.ts","../src/rules/string-utils.ts","../src/rules/svg-tag-name-capitalization.ts"],"version":"5.9.3"}
|
package/dist/types/cli.d.ts
CHANGED
|
@@ -17,7 +17,7 @@ export declare class CLI {
|
|
|
17
17
|
showTiming: boolean;
|
|
18
18
|
}): void;
|
|
19
19
|
protected determineProjectPath(patterns: string[]): void;
|
|
20
|
-
protected adjustPattern(pattern: string | undefined,
|
|
20
|
+
protected adjustPattern(pattern: string | undefined, configGlobPatterns: string[]): string;
|
|
21
21
|
protected resolvePatternToFiles(pattern: string, config: Config, force: boolean): Promise<{
|
|
22
22
|
files: string[];
|
|
23
23
|
explicitFile: string | undefined;
|
package/dist/types/linter.d.ts
CHANGED
|
@@ -123,7 +123,11 @@ export declare class Linter {
|
|
|
123
123
|
* @param source - The source code to fix
|
|
124
124
|
* @param context - Optional context for linting (e.g., fileName)
|
|
125
125
|
* @param offensesToFix - Optional array of specific offenses to fix. If not provided, all fixable offenses will be fixed.
|
|
126
|
+
* @param options - Options for autofix behavior
|
|
127
|
+
* @param options.includeUnsafe - If true, also apply unsafe fixes (rules with unsafeAutocorrectable = true)
|
|
126
128
|
* @returns AutofixResult containing the corrected source and lists of fixed/unfixed offenses
|
|
127
129
|
*/
|
|
128
|
-
autofix(source: string, context?: Partial<LintContext>, offensesToFix?: LintOffense[]
|
|
130
|
+
autofix(source: string, context?: Partial<LintContext>, offensesToFix?: LintOffense[], options?: {
|
|
131
|
+
includeUnsafe?: boolean;
|
|
132
|
+
}): AutofixResult;
|
|
129
133
|
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { ParserRule } from "../types.js";
|
|
2
|
+
import type { UnboundLintOffense, LintContext, FullRuleConfig } from "../types.js";
|
|
3
|
+
import type { ParseResult } from "@herb-tools/core";
|
|
4
|
+
export declare const STRICT_LOCALS_PATTERN: RegExp;
|
|
5
|
+
export declare class ERBStrictLocalsCommentSyntaxRule extends ParserRule {
|
|
6
|
+
name: string;
|
|
7
|
+
get defaultConfig(): FullRuleConfig;
|
|
8
|
+
check(result: ParseResult, context?: Partial<LintContext>): UnboundLintOffense[];
|
|
9
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { SourceRule } from "../types.js";
|
|
2
|
+
import type { UnboundLintOffense, LintOffense, LintContext, FullRuleConfig } from "../types.js";
|
|
3
|
+
export declare class ERBStrictLocalsRequiredRule extends SourceRule {
|
|
4
|
+
static unsafeAutocorrectable: boolean;
|
|
5
|
+
name: string;
|
|
6
|
+
get defaultConfig(): FullRuleConfig;
|
|
7
|
+
check(source: string, context?: Partial<LintContext>): UnboundLintOffense[];
|
|
8
|
+
autofix(_offense: LintOffense, source: string, _context?: Partial<LintContext>): string | null;
|
|
9
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* File path and naming utilities for linter rules
|
|
3
|
+
*/
|
|
4
|
+
/**
|
|
5
|
+
* Extracts the basename (filename) from a file path
|
|
6
|
+
* Works with both forward slashes and backslashes
|
|
7
|
+
*/
|
|
8
|
+
export declare function getBasename(filePath: string): string;
|
|
9
|
+
/**
|
|
10
|
+
* Checks if a file is a Rails partial (filename starts with `_`)
|
|
11
|
+
* Returns null if fileName is undefined (unknown context)
|
|
12
|
+
*/
|
|
13
|
+
export declare function isPartialFile(fileName: string | undefined): boolean | null;
|
|
@@ -1,4 +1,6 @@
|
|
|
1
1
|
export * from "./rule-utils.js";
|
|
2
|
+
export * from "./file-utils.js";
|
|
3
|
+
export * from "./string-utils.js";
|
|
2
4
|
export * from "./herb-disable-comment-base.js";
|
|
3
5
|
export * from "./erb-comment-syntax.js";
|
|
4
6
|
export * from "./erb-no-case-node-children.js";
|
|
@@ -11,6 +13,8 @@ export * from "./erb-prefer-image-tag-helper.js";
|
|
|
11
13
|
export * from "./erb-require-trailing-newline.js";
|
|
12
14
|
export * from "./erb-require-whitespace-inside-tags.js";
|
|
13
15
|
export * from "./erb-right-trim.js";
|
|
16
|
+
export * from "./erb-strict-locals-comment-syntax.js";
|
|
17
|
+
export * from "./erb-strict-locals-required.js";
|
|
14
18
|
export * from "./herb-disable-comment-valid-rule-name.js";
|
|
15
19
|
export * from "./herb-disable-comment-no-redundant-all.js";
|
|
16
20
|
export * from "./herb-disable-comment-no-duplicate-rules.js";
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Checks if parentheses in a string are balanced
|
|
3
|
+
* Returns false if there are more closing parens than opening at any point
|
|
4
|
+
*/
|
|
5
|
+
export declare function hasBalancedParentheses(content: string): boolean;
|
|
6
|
+
/**
|
|
7
|
+
* Splits a string by commas at the top level only
|
|
8
|
+
* Respects nested parentheses, brackets, braces, and strings
|
|
9
|
+
*
|
|
10
|
+
* @example
|
|
11
|
+
* splitByTopLevelComma("a, b, c") // ["a", " b", " c"]
|
|
12
|
+
* splitByTopLevelComma("a, (b, c), d") // ["a", " (b, c)", " d"]
|
|
13
|
+
* splitByTopLevelComma('a, "b, c", d') // ["a", ' "b, c"', " d"]
|
|
14
|
+
*/
|
|
15
|
+
export declare function splitByTopLevelComma(str: string): string[];
|
package/dist/types/src/cli.d.ts
CHANGED
|
@@ -17,7 +17,7 @@ export declare class CLI {
|
|
|
17
17
|
showTiming: boolean;
|
|
18
18
|
}): void;
|
|
19
19
|
protected determineProjectPath(patterns: string[]): void;
|
|
20
|
-
protected adjustPattern(pattern: string | undefined,
|
|
20
|
+
protected adjustPattern(pattern: string | undefined, configGlobPatterns: string[]): string;
|
|
21
21
|
protected resolvePatternToFiles(pattern: string, config: Config, force: boolean): Promise<{
|
|
22
22
|
files: string[];
|
|
23
23
|
explicitFile: string | undefined;
|
|
@@ -123,7 +123,11 @@ export declare class Linter {
|
|
|
123
123
|
* @param source - The source code to fix
|
|
124
124
|
* @param context - Optional context for linting (e.g., fileName)
|
|
125
125
|
* @param offensesToFix - Optional array of specific offenses to fix. If not provided, all fixable offenses will be fixed.
|
|
126
|
+
* @param options - Options for autofix behavior
|
|
127
|
+
* @param options.includeUnsafe - If true, also apply unsafe fixes (rules with unsafeAutocorrectable = true)
|
|
126
128
|
* @returns AutofixResult containing the corrected source and lists of fixed/unfixed offenses
|
|
127
129
|
*/
|
|
128
|
-
autofix(source: string, context?: Partial<LintContext>, offensesToFix?: LintOffense[]
|
|
130
|
+
autofix(source: string, context?: Partial<LintContext>, offensesToFix?: LintOffense[], options?: {
|
|
131
|
+
includeUnsafe?: boolean;
|
|
132
|
+
}): AutofixResult;
|
|
129
133
|
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { ParserRule } from "../types.js";
|
|
2
|
+
import type { UnboundLintOffense, LintContext, FullRuleConfig } from "../types.js";
|
|
3
|
+
import type { ParseResult } from "@herb-tools/core";
|
|
4
|
+
export declare const STRICT_LOCALS_PATTERN: RegExp;
|
|
5
|
+
export declare class ERBStrictLocalsCommentSyntaxRule extends ParserRule {
|
|
6
|
+
name: string;
|
|
7
|
+
get defaultConfig(): FullRuleConfig;
|
|
8
|
+
check(result: ParseResult, context?: Partial<LintContext>): UnboundLintOffense[];
|
|
9
|
+
}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { SourceRule } from "../types.js";
|
|
2
|
+
import type { UnboundLintOffense, LintOffense, LintContext, FullRuleConfig } from "../types.js";
|
|
3
|
+
export declare class ERBStrictLocalsRequiredRule extends SourceRule {
|
|
4
|
+
static unsafeAutocorrectable: boolean;
|
|
5
|
+
name: string;
|
|
6
|
+
get defaultConfig(): FullRuleConfig;
|
|
7
|
+
check(source: string, context?: Partial<LintContext>): UnboundLintOffense[];
|
|
8
|
+
autofix(_offense: LintOffense, source: string, _context?: Partial<LintContext>): string | null;
|
|
9
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* File path and naming utilities for linter rules
|
|
3
|
+
*/
|
|
4
|
+
/**
|
|
5
|
+
* Extracts the basename (filename) from a file path
|
|
6
|
+
* Works with both forward slashes and backslashes
|
|
7
|
+
*/
|
|
8
|
+
export declare function getBasename(filePath: string): string;
|
|
9
|
+
/**
|
|
10
|
+
* Checks if a file is a Rails partial (filename starts with `_`)
|
|
11
|
+
* Returns null if fileName is undefined (unknown context)
|
|
12
|
+
*/
|
|
13
|
+
export declare function isPartialFile(fileName: string | undefined): boolean | null;
|