@hyperframes/lint 0.8.141 → 0.8.143
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/browser.js +37 -17
- package/dist/browser.js.map +1 -1
- package/dist/index.js +37 -17
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
package/dist/browser.js
CHANGED
|
@@ -108,10 +108,7 @@ function hasUnquotedLessThan(attrs) {
|
|
|
108
108
|
return false;
|
|
109
109
|
}
|
|
110
110
|
function readAttr(tagSource, attr) {
|
|
111
|
-
|
|
112
|
-
const escaped = attr.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
113
|
-
const match = tagSource.match(new RegExp(`(?<![\\w-])${escaped}\\s*=\\s*["']([^"']+)["']`, "i"));
|
|
114
|
-
return match?.[1] || null;
|
|
111
|
+
return readAttributeValue(tagSource, attr, false) || null;
|
|
115
112
|
}
|
|
116
113
|
function hasAttrName(tagSource, attr) {
|
|
117
114
|
return readDecodedAttr(tagSource, attr) !== null;
|
|
@@ -134,15 +131,18 @@ function mediaWindowsOverlap(a, b) {
|
|
|
134
131
|
return a.start < b.end && b.start < a.end;
|
|
135
132
|
}
|
|
136
133
|
function readDecodedAttr(tagSource, attr) {
|
|
134
|
+
return readAttributeValue(tagSource, attr, true);
|
|
135
|
+
}
|
|
136
|
+
function readAttributeValue(tagSource, attr, decodeEntities) {
|
|
137
137
|
if (!tagSource) return null;
|
|
138
138
|
let value = null;
|
|
139
139
|
const parser = new Parser(
|
|
140
140
|
{
|
|
141
|
-
onattribute(name,
|
|
142
|
-
if (value === null && name.toLowerCase() === attr.toLowerCase()) value =
|
|
141
|
+
onattribute(name, attributeValue) {
|
|
142
|
+
if (value === null && name.toLowerCase() === attr.toLowerCase()) value = attributeValue;
|
|
143
143
|
}
|
|
144
144
|
},
|
|
145
|
-
{ decodeEntities
|
|
145
|
+
{ decodeEntities, lowerCaseAttributeNames: false, lowerCaseTags: true }
|
|
146
146
|
);
|
|
147
147
|
parser.end(tagSource);
|
|
148
148
|
return value;
|
|
@@ -745,6 +745,12 @@ import {
|
|
|
745
745
|
HTML_BODY_CSS_HEIGHT_FIRST_RE,
|
|
746
746
|
VIEWPORT_META_SIZE_RE
|
|
747
747
|
} from "@hyperframes/parsers/composition";
|
|
748
|
+
var SCRIPT_SYNTAX_EXEMPT_TYPES = /* @__PURE__ */ new Set([
|
|
749
|
+
"application/json",
|
|
750
|
+
"application/hyperframes-slideshow+json",
|
|
751
|
+
"importmap",
|
|
752
|
+
"module"
|
|
753
|
+
]);
|
|
748
754
|
function repeatedDescendantId(selector) {
|
|
749
755
|
let repeated = null;
|
|
750
756
|
const requiredPseudoIds = (pseudo) => {
|
|
@@ -1363,10 +1369,8 @@ var coreRules = [
|
|
|
1363
1369
|
({ scripts, locate }) => {
|
|
1364
1370
|
const findings = [];
|
|
1365
1371
|
for (const script of scripts) {
|
|
1366
|
-
const
|
|
1367
|
-
if (
|
|
1368
|
-
attrs
|
|
1369
|
-
))
|
|
1372
|
+
const type = readDecodedAttr(script.raw, "type")?.trim().toLowerCase() ?? "";
|
|
1373
|
+
if (readDecodedAttr(script.raw, "src") !== null || SCRIPT_SYNTAX_EXEMPT_TYPES.has(type))
|
|
1370
1374
|
continue;
|
|
1371
1375
|
const syntaxError = getInlineScriptSyntaxError(script.content);
|
|
1372
1376
|
if (!syntaxError) continue;
|
|
@@ -1783,6 +1787,7 @@ function findImperativeMediaControlFindings(ctx) {
|
|
|
1783
1787
|
};
|
|
1784
1788
|
if (mediaTags.length === 0 || ctx.scripts.length === 0) return findings;
|
|
1785
1789
|
for (const script of ctx.scripts) {
|
|
1790
|
+
const code = stripJsCode(script.content);
|
|
1786
1791
|
const mediaVars = /* @__PURE__ */ new Map();
|
|
1787
1792
|
const assignmentPatterns = [
|
|
1788
1793
|
{
|
|
@@ -1799,6 +1804,7 @@ function findImperativeMediaControlFindings(ctx) {
|
|
|
1799
1804
|
for (const { pattern, variableIndex, targetIndex } of assignmentPatterns) {
|
|
1800
1805
|
let match;
|
|
1801
1806
|
while ((match = pattern.exec(script.content)) !== null) {
|
|
1807
|
+
if (code[match.index] !== script.content[match.index]) continue;
|
|
1802
1808
|
const variableName = match[variableIndex];
|
|
1803
1809
|
const target = match[targetIndex];
|
|
1804
1810
|
if (!variableName || !target) continue;
|
|
@@ -1809,12 +1815,12 @@ function findImperativeMediaControlFindings(ctx) {
|
|
|
1809
1815
|
}
|
|
1810
1816
|
const directIdPatterns = [
|
|
1811
1817
|
{
|
|
1812
|
-
pattern: /\b(?:document|window\.document)\.getElementById\(\s*["']([^"']+)["']\s*\)
|
|
1818
|
+
pattern: /\b(?:document|window\.document)\.getElementById\(\s*["']([^"']+)["']\s*\)\s*(?:\?\.|\.)\s*play\s*(?:\?\.\s*)?\(/g,
|
|
1813
1819
|
kind: "play()",
|
|
1814
1820
|
targetIndex: 1
|
|
1815
1821
|
},
|
|
1816
1822
|
{
|
|
1817
|
-
pattern: /\b(?:document|window\.document)\.getElementById\(\s*["']([^"']+)["']\s*\)
|
|
1823
|
+
pattern: /\b(?:document|window\.document)\.getElementById\(\s*["']([^"']+)["']\s*\)\s*(?:\?\.|\.)\s*pause\s*(?:\?\.\s*)?\(/g,
|
|
1818
1824
|
kind: "pause()",
|
|
1819
1825
|
targetIndex: 1
|
|
1820
1826
|
},
|
|
@@ -1829,12 +1835,12 @@ function findImperativeMediaControlFindings(ctx) {
|
|
|
1829
1835
|
targetIndex: 1
|
|
1830
1836
|
},
|
|
1831
1837
|
{
|
|
1832
|
-
pattern: /\b(?:document|window\.document)\.querySelector\(\s*(["'])([\s\S]*?)\1\s*\)
|
|
1838
|
+
pattern: /\b(?:document|window\.document)\.querySelector\(\s*(["'])([\s\S]*?)\1\s*\)\s*(?:\?\.|\.)\s*play\s*(?:\?\.\s*)?\(/g,
|
|
1833
1839
|
kind: "play()",
|
|
1834
1840
|
targetIndex: 2
|
|
1835
1841
|
},
|
|
1836
1842
|
{
|
|
1837
|
-
pattern: /\b(?:document|window\.document)\.querySelector\(\s*(["'])([\s\S]*?)\1\s*\)
|
|
1843
|
+
pattern: /\b(?:document|window\.document)\.querySelector\(\s*(["'])([\s\S]*?)\1\s*\)\s*(?:\?\.|\.)\s*pause\s*(?:\?\.\s*)?\(/g,
|
|
1838
1844
|
kind: "pause()",
|
|
1839
1845
|
targetIndex: 2
|
|
1840
1846
|
},
|
|
@@ -1852,6 +1858,7 @@ function findImperativeMediaControlFindings(ctx) {
|
|
|
1852
1858
|
for (const { pattern, kind, targetIndex } of directIdPatterns) {
|
|
1853
1859
|
let match;
|
|
1854
1860
|
while ((match = pattern.exec(script.content)) !== null) {
|
|
1861
|
+
if (code[match.index] !== script.content[match.index]) continue;
|
|
1855
1862
|
const target = match[targetIndex];
|
|
1856
1863
|
if (!target) continue;
|
|
1857
1864
|
const elementId = mediaIndex.ids.has(target) ? target : selectorTargetsManagedMedia(target, mediaIndex) ? void 0 : null;
|
|
@@ -1869,8 +1876,20 @@ function findImperativeMediaControlFindings(ctx) {
|
|
|
1869
1876
|
for (const [variableName, elementId] of mediaVars) {
|
|
1870
1877
|
const escapedVar = escapeRegExp(variableName);
|
|
1871
1878
|
const variablePatterns = [
|
|
1872
|
-
{
|
|
1873
|
-
|
|
1879
|
+
{
|
|
1880
|
+
pattern: new RegExp(
|
|
1881
|
+
`\\b${escapedVar}\\s*(?:\\?\\.|\\.)\\s*play\\s*(?:\\?\\.\\s*)?\\(`,
|
|
1882
|
+
"g"
|
|
1883
|
+
),
|
|
1884
|
+
kind: "play()"
|
|
1885
|
+
},
|
|
1886
|
+
{
|
|
1887
|
+
pattern: new RegExp(
|
|
1888
|
+
`\\b${escapedVar}\\s*(?:\\?\\.|\\.)\\s*pause\\s*(?:\\?\\.\\s*)?\\(`,
|
|
1889
|
+
"g"
|
|
1890
|
+
),
|
|
1891
|
+
kind: "pause()"
|
|
1892
|
+
},
|
|
1874
1893
|
{ pattern: new RegExp(`\\b${escapedVar}\\.currentTime\\s*=`, "g"), kind: "currentTime" },
|
|
1875
1894
|
{
|
|
1876
1895
|
pattern: new RegExp(`\\b${escapedVar}\\.muted\\s*=`, "g"),
|
|
@@ -1880,6 +1899,7 @@ function findImperativeMediaControlFindings(ctx) {
|
|
|
1880
1899
|
for (const { pattern, kind } of variablePatterns) {
|
|
1881
1900
|
let match;
|
|
1882
1901
|
while ((match = pattern.exec(script.content)) !== null) {
|
|
1902
|
+
if (code[match.index] !== script.content[match.index]) continue;
|
|
1883
1903
|
findings.push({
|
|
1884
1904
|
code: "imperative_media_control",
|
|
1885
1905
|
severity: "error",
|