@tbela99/css-parser 0.7.1 → 0.9.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 (90) hide show
  1. package/.editorconfig +484 -0
  2. package/README.md +140 -84
  3. package/dist/index-umd-web.js +8461 -51655
  4. package/dist/index.cjs +8437 -51636
  5. package/dist/index.d.ts +220 -68
  6. package/dist/lib/ast/expand.js +46 -9
  7. package/dist/lib/ast/features/calc.js +76 -12
  8. package/dist/lib/ast/features/inlinecssvariables.js +6 -1
  9. package/dist/lib/ast/features/prefix.js +17 -9
  10. package/dist/lib/ast/features/shorthand.js +1 -0
  11. package/dist/lib/ast/math/expression.js +299 -11
  12. package/dist/lib/ast/math/math.js +7 -1
  13. package/dist/lib/ast/minify.js +30 -16
  14. package/dist/lib/ast/types.js +59 -49
  15. package/dist/lib/ast/walk.js +92 -18
  16. package/dist/lib/parser/declaration/list.js +1 -0
  17. package/dist/lib/parser/declaration/map.js +60 -52
  18. package/dist/lib/parser/declaration/set.js +1 -12
  19. package/dist/lib/parser/parse.js +371 -119
  20. package/dist/lib/parser/tokenize.js +31 -6
  21. package/dist/lib/parser/utils/declaration.js +2 -2
  22. package/dist/lib/parser/utils/type.js +6 -6
  23. package/dist/lib/renderer/color/a98rgb.js +1 -0
  24. package/dist/lib/renderer/color/color.js +1 -0
  25. package/dist/lib/renderer/color/colormix.js +1 -0
  26. package/dist/lib/renderer/color/hex.js +2 -1
  27. package/dist/lib/renderer/color/hsl.js +2 -1
  28. package/dist/lib/renderer/color/hwb.js +3 -2
  29. package/dist/lib/renderer/color/lab.js +2 -1
  30. package/dist/lib/renderer/color/lch.js +2 -1
  31. package/dist/lib/renderer/color/oklab.js +3 -2
  32. package/dist/lib/renderer/color/oklch.js +2 -1
  33. package/dist/lib/renderer/color/p3.js +2 -1
  34. package/dist/lib/renderer/color/prophotoRgb.js +56 -0
  35. package/dist/lib/renderer/color/prophotorgb.js +1 -1
  36. package/dist/lib/renderer/color/rec2020.js +1 -0
  37. package/dist/lib/renderer/color/relativecolor.js +52 -28
  38. package/dist/lib/renderer/color/rgb.js +2 -1
  39. package/dist/lib/renderer/color/srgb.js +3 -2
  40. package/dist/lib/renderer/color/utils/components.js +1 -0
  41. package/dist/lib/renderer/color/utils/constants.js +2 -1
  42. package/dist/lib/renderer/color/xyz.js +2 -1
  43. package/dist/lib/renderer/color/xyzd50.js +1 -0
  44. package/dist/lib/renderer/render.js +62 -12
  45. package/dist/lib/syntax/syntax.js +362 -4
  46. package/dist/lib/validation/at-rules/container.js +353 -0
  47. package/dist/lib/validation/at-rules/counter-style.js +78 -0
  48. package/dist/lib/validation/at-rules/custom-media.js +52 -0
  49. package/dist/lib/validation/at-rules/document.js +114 -0
  50. package/dist/lib/validation/at-rules/else.js +5 -0
  51. package/dist/lib/validation/at-rules/font-feature-values.js +52 -0
  52. package/dist/lib/validation/at-rules/import.js +199 -0
  53. package/dist/lib/validation/at-rules/keyframes.js +70 -0
  54. package/dist/lib/validation/at-rules/layer.js +30 -0
  55. package/dist/lib/validation/at-rules/media.js +254 -0
  56. package/dist/lib/validation/at-rules/namespace.js +85 -0
  57. package/dist/lib/validation/at-rules/page-margin-box.js +56 -0
  58. package/dist/lib/validation/at-rules/page.js +88 -0
  59. package/dist/lib/validation/at-rules/supports.js +262 -0
  60. package/dist/lib/validation/at-rules/when.js +178 -0
  61. package/dist/lib/validation/atrule.js +187 -0
  62. package/dist/lib/validation/config.js +35 -2
  63. package/dist/lib/validation/config.json.js +1683 -50905
  64. package/dist/lib/validation/declaration.js +102 -0
  65. package/dist/lib/validation/parser/parse.js +1137 -7
  66. package/dist/lib/validation/parser/types.js +28 -12
  67. package/dist/lib/validation/selector.js +26 -444
  68. package/dist/lib/validation/syntax.js +1475 -0
  69. package/dist/lib/validation/syntaxes/complex-selector-list.js +45 -0
  70. package/dist/lib/validation/syntaxes/complex-selector.js +53 -0
  71. package/dist/lib/validation/syntaxes/compound-selector.js +226 -0
  72. package/dist/lib/validation/syntaxes/family-name.js +91 -0
  73. package/dist/lib/validation/syntaxes/image.js +29 -0
  74. package/dist/lib/validation/syntaxes/keyframe-block-list.js +27 -0
  75. package/dist/lib/validation/syntaxes/keyframe-selector.js +137 -0
  76. package/dist/lib/validation/syntaxes/layer-name.js +67 -0
  77. package/dist/lib/validation/syntaxes/relative-selector-list.js +57 -0
  78. package/dist/lib/validation/syntaxes/relative-selector.js +36 -0
  79. package/dist/lib/validation/syntaxes/selector-list.js +5 -0
  80. package/dist/lib/validation/syntaxes/selector.js +5 -0
  81. package/dist/lib/validation/syntaxes/url.js +75 -0
  82. package/dist/lib/validation/utils/list.js +24 -0
  83. package/dist/lib/validation/utils/whitespace.js +22 -0
  84. package/dist/node/index.js +5 -5
  85. package/dist/web/index.js +5 -1
  86. package/dist/web/load.js +1 -0
  87. package/package.json +16 -14
  88. package/dist/lib/ast/utils/minifyfeature.js +0 -9
  89. package/dist/lib/iterable/weakset.js +0 -58
  90. package/dist/lib/parser/utils/syntax.js +0 -450
@@ -0,0 +1,45 @@
1
+ import { ValidationLevel } from '../../ast/types.js';
2
+ import '../../ast/minify.js';
3
+ import '../../ast/walk.js';
4
+ import '../../parser/parse.js';
5
+ import '../../renderer/color/utils/constants.js';
6
+ import '../../renderer/sourcemap/lib/encode.js';
7
+ import '../../parser/utils/config.js';
8
+ import { validateSelector } from './selector.js';
9
+ import { consumeWhitespace } from '../utils/whitespace.js';
10
+ import { splitTokenList } from '../utils/list.js';
11
+
12
+ function validateComplexSelectorList(tokens, root, options) {
13
+ tokens = tokens.slice();
14
+ consumeWhitespace(tokens);
15
+ if (tokens.length == 0) {
16
+ return {
17
+ valid: ValidationLevel.Drop,
18
+ matches: [],
19
+ // @ts-ignore
20
+ node: root,
21
+ syntax: null,
22
+ error: 'expecting complex selector list',
23
+ tokens
24
+ };
25
+ }
26
+ let result = null;
27
+ for (const t of splitTokenList(tokens)) {
28
+ result = validateSelector(t, root, options);
29
+ if (result.valid == ValidationLevel.Drop) {
30
+ return result;
31
+ }
32
+ }
33
+ // @ts-ignore
34
+ return result ?? {
35
+ valid: ValidationLevel.Drop,
36
+ matches: [],
37
+ // @ts-ignore
38
+ node: root,
39
+ syntax: null,
40
+ error: 'expecting complex selector list',
41
+ tokens
42
+ };
43
+ }
44
+
45
+ export { validateComplexSelectorList };
@@ -0,0 +1,53 @@
1
+ import { consumeWhitespace } from '../utils/whitespace.js';
2
+ import { splitTokenList } from '../utils/list.js';
3
+ import { EnumToken, ValidationLevel } from '../../ast/types.js';
4
+ import '../../ast/minify.js';
5
+ import '../../ast/walk.js';
6
+ import '../../parser/parse.js';
7
+ import '../../renderer/color/utils/constants.js';
8
+ import '../../renderer/sourcemap/lib/encode.js';
9
+ import '../../parser/utils/config.js';
10
+ import { validateCompoundSelector } from './compound-selector.js';
11
+
12
+ const combinatorsTokens = [EnumToken.ChildCombinatorTokenType, EnumToken.ColumnCombinatorTokenType,
13
+ // EnumToken.DescendantCombinatorTokenType,
14
+ EnumToken.NextSiblingCombinatorTokenType, EnumToken.SubsequentSiblingCombinatorTokenType];
15
+ // <compound-selector> [ <combinator>? <compound-selector> ]*
16
+ function validateComplexSelector(tokens, root, options) {
17
+ // [ <type-selector>? <subclass-selector>* [ <pseudo-element-selector> <pseudo-class-selector>* ]* ]!
18
+ tokens = tokens.slice();
19
+ consumeWhitespace(tokens);
20
+ if (tokens.length == 0) {
21
+ return {
22
+ valid: ValidationLevel.Drop,
23
+ matches: [],
24
+ // @ts-ignore
25
+ node: root,
26
+ syntax: null,
27
+ error: 'expected selector',
28
+ tokens
29
+ };
30
+ }
31
+ // const config = getSyntaxConfig();
32
+ //
33
+ // let match: number = 0;
34
+ let result = null;
35
+ // const combinators: EnumToken[] = combinatorsTokens.filter((t: EnumToken) => t != EnumToken.DescendantCombinatorTokenType);
36
+ for (const t of splitTokenList(tokens, combinatorsTokens)) {
37
+ result = validateCompoundSelector(t, root, options);
38
+ if (result.valid == ValidationLevel.Drop) {
39
+ return result;
40
+ }
41
+ }
42
+ // @ts-ignore
43
+ return result ?? {
44
+ valid: ValidationLevel.Drop,
45
+ matches: [],
46
+ node: root,
47
+ syntax: null,
48
+ error: 'expecting compound-selector',
49
+ tokens
50
+ };
51
+ }
52
+
53
+ export { combinatorsTokens, validateComplexSelector };
@@ -0,0 +1,226 @@
1
+ import { ValidationLevel, EnumToken } from '../../ast/types.js';
2
+ import '../../ast/minify.js';
3
+ import '../../ast/walk.js';
4
+ import '../../parser/parse.js';
5
+ import { mozExtensions, webkitExtensions } from '../../syntax/syntax.js';
6
+ import '../../parser/utils/config.js';
7
+ import '../../renderer/color/utils/constants.js';
8
+ import '../../renderer/sourcemap/lib/encode.js';
9
+ import { consumeWhitespace } from '../utils/whitespace.js';
10
+ import { getSyntaxConfig } from '../config.js';
11
+
12
+ function validateCompoundSelector(tokens, root, options) {
13
+ if (tokens.length == 0) {
14
+ // @ts-ignore
15
+ return {
16
+ valid: ValidationLevel.Drop,
17
+ matches: [],
18
+ // @ts-ignore
19
+ node: root,
20
+ // @ts-ignore
21
+ syntax: null,
22
+ error: 'expected selector',
23
+ tokens
24
+ };
25
+ }
26
+ tokens = tokens.slice();
27
+ consumeWhitespace(tokens);
28
+ const config = getSyntaxConfig();
29
+ let match = 0;
30
+ let length = tokens.length;
31
+ while (tokens.length > 0) {
32
+ while (tokens.length > 0 && tokens[0].typ == EnumToken.NestingSelectorTokenType) {
33
+ if (!options?.nestedSelector) {
34
+ // @ts-ignore
35
+ return {
36
+ valid: ValidationLevel.Drop,
37
+ matches: [],
38
+ // @ts-ignore
39
+ node: tokens[0],
40
+ syntax: null,
41
+ error: 'nested selector not allowed',
42
+ tokens
43
+ };
44
+ }
45
+ match++;
46
+ tokens.shift();
47
+ consumeWhitespace(tokens);
48
+ }
49
+ // <type-selector>
50
+ while (tokens.length > 0 &&
51
+ [
52
+ EnumToken.IdenTokenType,
53
+ EnumToken.NameSpaceAttributeTokenType,
54
+ EnumToken.ClassSelectorTokenType,
55
+ EnumToken.HashTokenType,
56
+ EnumToken.UniversalSelectorTokenType
57
+ ].includes(tokens[0].typ)) {
58
+ match++;
59
+ tokens.shift();
60
+ consumeWhitespace(tokens);
61
+ }
62
+ while (tokens.length > 0 && tokens[0].typ == EnumToken.PseudoClassFuncTokenType) {
63
+ if (!mozExtensions.has(tokens[0].val + '()') &&
64
+ !webkitExtensions.has(tokens[0].val + '()') &&
65
+ !((tokens[0].val + '()') in config.selectors)) {
66
+ if (!options?.lenient || /^(:?)-webkit-/.test(tokens[0].val)) {
67
+ // @ts-ignore
68
+ return {
69
+ valid: ValidationLevel.Drop,
70
+ matches: [],
71
+ // @ts-ignore
72
+ node: tokens[0],
73
+ syntax: null,
74
+ error: 'unknown pseudo-class: ' + tokens[0].val + '()',
75
+ tokens
76
+ };
77
+ }
78
+ }
79
+ match++;
80
+ tokens.shift();
81
+ consumeWhitespace(tokens);
82
+ }
83
+ while (tokens.length > 0 && tokens[0].typ == EnumToken.PseudoClassTokenType) {
84
+ const isPseudoElement = tokens[0].val.startsWith('::');
85
+ if (
86
+ // https://developer.mozilla.org/en-US/docs/Web/CSS/WebKit_Extensions#pseudo-elements
87
+ !(isPseudoElement && tokens[0].val.startsWith('::-webkit-')) &&
88
+ !mozExtensions.has(tokens[0].val) &&
89
+ !webkitExtensions.has(tokens[0].val) &&
90
+ !(tokens[0].val in config.selectors) &&
91
+ !(!isPseudoElement &&
92
+ (':' + tokens[0].val) in config.selectors)) {
93
+ if (!options?.lenient || /^(:?)-webkit-/.test(tokens[0].val)) {
94
+ // @ts-ignore
95
+ return {
96
+ valid: ValidationLevel.Drop,
97
+ matches: [],
98
+ // @ts-ignore
99
+ node: tokens[0],
100
+ syntax: null,
101
+ error: 'unknown pseudo-class: ' + tokens[0].val,
102
+ tokens
103
+ };
104
+ }
105
+ }
106
+ match++;
107
+ tokens.shift();
108
+ consumeWhitespace(tokens);
109
+ }
110
+ while (tokens.length > 0 && tokens[0].typ == EnumToken.AttrTokenType) {
111
+ const children = tokens[0].chi.slice();
112
+ consumeWhitespace(children);
113
+ if (children.length == 0) {
114
+ // @ts-ignore
115
+ return {
116
+ valid: ValidationLevel.Drop,
117
+ matches: [],
118
+ node: tokens[0],
119
+ syntax: null,
120
+ error: 'invalid attribute selector',
121
+ tokens
122
+ };
123
+ }
124
+ if (![
125
+ EnumToken.IdenTokenType,
126
+ EnumToken.NameSpaceAttributeTokenType,
127
+ EnumToken.MatchExpressionTokenType
128
+ ].includes(children[0].typ)) {
129
+ // @ts-ignore
130
+ return {
131
+ valid: ValidationLevel.Drop,
132
+ matches: [],
133
+ node: tokens[0],
134
+ syntax: null,
135
+ error: 'invalid attribute selector',
136
+ tokens
137
+ };
138
+ }
139
+ if (children[0].typ == EnumToken.MatchExpressionTokenType) {
140
+ if (children.length != 1) {
141
+ return {
142
+ valid: ValidationLevel.Drop,
143
+ matches: [],
144
+ node: tokens[0],
145
+ syntax: null,
146
+ error: 'invalid <attribute-selector>',
147
+ tokens
148
+ };
149
+ }
150
+ if (![
151
+ EnumToken.IdenTokenType,
152
+ EnumToken.NameSpaceAttributeTokenType
153
+ ].includes(children[0].l.typ) ||
154
+ ![
155
+ EnumToken.EqualMatchTokenType, EnumToken.DashMatchTokenType,
156
+ EnumToken.StartMatchTokenType, EnumToken.ContainMatchTokenType,
157
+ EnumToken.EndMatchTokenType, EnumToken.IncludeMatchTokenType
158
+ ].includes(children[0].op.typ) ||
159
+ ![
160
+ EnumToken.StringTokenType,
161
+ EnumToken.IdenTokenType
162
+ ].includes(children[0].r.typ)) {
163
+ // @ts-ignore
164
+ return {
165
+ valid: ValidationLevel.Drop,
166
+ matches: [],
167
+ node: tokens[0],
168
+ syntax: null,
169
+ error: 'invalid attribute selector',
170
+ tokens
171
+ };
172
+ }
173
+ if (children[0].attr != null && !['i', 's'].includes(children[0].attr)) {
174
+ // @ts-ignore
175
+ return {
176
+ valid: ValidationLevel.Drop,
177
+ matches: [],
178
+ node: tokens[0],
179
+ syntax: null,
180
+ error: 'invalid attribute selector',
181
+ tokens
182
+ };
183
+ }
184
+ }
185
+ match++;
186
+ tokens.shift();
187
+ consumeWhitespace(tokens);
188
+ }
189
+ if (length == tokens.length) {
190
+ return {
191
+ valid: ValidationLevel.Drop,
192
+ matches: [],
193
+ // @ts-ignore
194
+ node: tokens[0],
195
+ // @ts-ignore
196
+ syntax: null,
197
+ error: 'expected compound selector',
198
+ tokens
199
+ };
200
+ }
201
+ length = tokens.length;
202
+ }
203
+ return match == 0 ? {
204
+ valid: ValidationLevel.Drop,
205
+ matches: [],
206
+ // @ts-ignore
207
+ node: root,
208
+ // @ts-ignore
209
+ syntax: null,
210
+ error: 'expected compound selector',
211
+ tokens
212
+ } :
213
+ // @ts-ignore
214
+ {
215
+ valid: ValidationLevel.Valid,
216
+ matches: [],
217
+ // @ts-ignore
218
+ node: root,
219
+ // @ts-ignore
220
+ syntax: null,
221
+ error: null,
222
+ tokens
223
+ };
224
+ }
225
+
226
+ export { validateCompoundSelector };
@@ -0,0 +1,91 @@
1
+ import { ValidationLevel, EnumToken } from '../../ast/types.js';
2
+ import '../../ast/minify.js';
3
+ import '../../ast/walk.js';
4
+ import '../../parser/parse.js';
5
+ import '../../renderer/color/utils/constants.js';
6
+ import '../../renderer/sourcemap/lib/encode.js';
7
+ import '../../parser/utils/config.js';
8
+ import { consumeWhitespace } from '../utils/whitespace.js';
9
+
10
+ function validateFamilyName(tokens, atRule) {
11
+ let node;
12
+ tokens = tokens.slice();
13
+ consumeWhitespace(tokens);
14
+ if (tokens.length == 0) {
15
+ // @ts-ignore
16
+ return {
17
+ valid: ValidationLevel.Drop,
18
+ matches: [],
19
+ node: atRule,
20
+ syntax: null,
21
+ error: 'expected at-rule prelude',
22
+ tokens
23
+ };
24
+ }
25
+ if (tokens[0].typ == EnumToken.CommaTokenType) {
26
+ // @ts-ignore
27
+ return {
28
+ valid: ValidationLevel.Drop,
29
+ matches: [],
30
+ node: tokens[0],
31
+ syntax: null,
32
+ error: 'unexpected token',
33
+ tokens
34
+ };
35
+ }
36
+ while (tokens.length > 0) {
37
+ // @ts-ignore
38
+ if (tokens[0].typ == EnumToken.CommaTokenType) {
39
+ node = tokens.shift();
40
+ consumeWhitespace(tokens);
41
+ if (tokens.length == 0) {
42
+ // @ts-ignore
43
+ return {
44
+ valid: ValidationLevel.Drop,
45
+ matches: [],
46
+ node,
47
+ syntax: null,
48
+ error: 'unexpected token',
49
+ tokens
50
+ };
51
+ }
52
+ }
53
+ node = tokens[0];
54
+ if (![EnumToken.IdenTokenType, EnumToken.StringTokenType].includes(node.typ)) {
55
+ // @ts-ignore
56
+ return {
57
+ valid: ValidationLevel.Drop,
58
+ matches: [],
59
+ node,
60
+ syntax: null,
61
+ error: 'unexpected token',
62
+ tokens
63
+ };
64
+ }
65
+ tokens.shift();
66
+ consumeWhitespace(tokens);
67
+ // @ts-ignore
68
+ if (tokens.length > 0 && node.typ == EnumToken.BadStringTokenType && tokens[0].typ != EnumToken.CommaTokenType) {
69
+ // @ts-ignore
70
+ return {
71
+ valid: ValidationLevel.Drop,
72
+ matches: [],
73
+ node: tokens[0],
74
+ syntax: null,
75
+ error: 'expected comma token',
76
+ tokens
77
+ };
78
+ }
79
+ }
80
+ // @ts-ignore
81
+ return {
82
+ valid: ValidationLevel.Valid,
83
+ matches: [],
84
+ node: null,
85
+ syntax: null,
86
+ error: '',
87
+ tokens
88
+ };
89
+ }
90
+
91
+ export { validateFamilyName };
@@ -0,0 +1,29 @@
1
+ import { EnumToken, ValidationLevel } from '../../ast/types.js';
2
+ import '../../ast/minify.js';
3
+ import '../../ast/walk.js';
4
+ import '../../parser/parse.js';
5
+ import '../../renderer/color/utils/constants.js';
6
+ import '../../renderer/sourcemap/lib/encode.js';
7
+ import '../../parser/utils/config.js';
8
+ import { validateSyntax } from '../syntax.js';
9
+ import { getParsedSyntax } from '../config.js';
10
+ import { validateURL } from './url.js';
11
+
12
+ function validateImage(token) {
13
+ if (token.typ == EnumToken.UrlFunctionTokenType) {
14
+ return validateURL(token);
15
+ }
16
+ if (token.typ == EnumToken.ImageFunctionTokenType) {
17
+ return validateSyntax(getParsedSyntax("syntaxes" /* ValidationSyntaxGroupEnum.Syntaxes */, token.val + '()'), token.chi);
18
+ }
19
+ return {
20
+ valid: ValidationLevel.Drop,
21
+ matches: [],
22
+ node: token,
23
+ syntax: 'image()',
24
+ error: 'expected <image> or <url>',
25
+ tokens: []
26
+ };
27
+ }
28
+
29
+ export { validateImage };
@@ -0,0 +1,27 @@
1
+ import { EnumToken, ValidationLevel } from '../../ast/types.js';
2
+ import '../../ast/minify.js';
3
+ import '../../ast/walk.js';
4
+ import '../../parser/parse.js';
5
+ import '../../renderer/color/utils/constants.js';
6
+ import '../../renderer/sourcemap/lib/encode.js';
7
+ import '../../parser/utils/config.js';
8
+ import { validateKeyframeSelector } from './keyframe-selector.js';
9
+
10
+ function validateKeyframeBlockList(tokens, atRule, options) {
11
+ let i = 0;
12
+ let j = 0;
13
+ let result = null;
14
+ while (i + 1 < tokens.length) {
15
+ if (tokens[++i].typ == EnumToken.CommaTokenType) {
16
+ result = validateKeyframeSelector(tokens.slice(j, i), atRule);
17
+ if (result.valid == ValidationLevel.Drop) {
18
+ return result;
19
+ }
20
+ j = i + 1;
21
+ i = j;
22
+ }
23
+ }
24
+ return validateKeyframeSelector(i == j ? tokens.slice(i) : tokens.slice(j, i + 1), atRule);
25
+ }
26
+
27
+ export { validateKeyframeBlockList };
@@ -0,0 +1,137 @@
1
+ import { consumeWhitespace } from '../utils/whitespace.js';
2
+ import { ValidationLevel, EnumToken } from '../../ast/types.js';
3
+ import '../../ast/minify.js';
4
+ import '../../ast/walk.js';
5
+ import '../../parser/parse.js';
6
+ import '../../renderer/color/utils/constants.js';
7
+ import '../../renderer/sourcemap/lib/encode.js';
8
+ import '../../parser/utils/config.js';
9
+
10
+ function validateKeyframeSelector(tokens, atRule, options) {
11
+ consumeWhitespace(tokens);
12
+ if (tokens.length == 0) {
13
+ // @ts-ignore
14
+ return {
15
+ valid: ValidationLevel.Drop,
16
+ matches: [],
17
+ node: atRule,
18
+ syntax: null,
19
+ error: 'expected keyframe selector',
20
+ tokens
21
+ };
22
+ }
23
+ if (tokens[0].typ == EnumToken.PercentageTokenType) {
24
+ tokens.shift();
25
+ consumeWhitespace(tokens);
26
+ if (tokens.length == 0) {
27
+ // @ts-ignore
28
+ return {
29
+ valid: ValidationLevel.Valid,
30
+ matches: [],
31
+ node: atRule,
32
+ syntax: null,
33
+ error: '',
34
+ tokens
35
+ };
36
+ }
37
+ // @ts-ignore
38
+ return {
39
+ valid: ValidationLevel.Drop,
40
+ matches: [],
41
+ node: tokens[0],
42
+ syntax: null,
43
+ error: 'unexpected token',
44
+ tokens
45
+ };
46
+ }
47
+ if (tokens[0].typ != EnumToken.IdenTokenType) {
48
+ // @ts-ignore
49
+ return {
50
+ valid: ValidationLevel.Drop,
51
+ matches: [],
52
+ node: tokens[0],
53
+ // @ts-ignore
54
+ syntax: null,
55
+ error: 'expected keyframe selector',
56
+ tokens
57
+ };
58
+ }
59
+ if (['from', 'to'].includes(tokens[0].val)) {
60
+ tokens.shift();
61
+ consumeWhitespace(tokens);
62
+ if (tokens.length > 0) {
63
+ // @ts-ignore
64
+ return {
65
+ valid: ValidationLevel.Drop,
66
+ matches: [],
67
+ node: tokens[0],
68
+ syntax: null,
69
+ error: 'unexpected token',
70
+ tokens
71
+ };
72
+ }
73
+ // @ts-ignore
74
+ return {
75
+ valid: ValidationLevel.Valid,
76
+ matches: [],
77
+ node: null,
78
+ // @ts-ignore
79
+ syntax: null,
80
+ error: '',
81
+ tokens
82
+ };
83
+ }
84
+ if (!['cover', 'contain', 'entry', 'exit', 'entry-crossing', 'exit-crossing'].includes(tokens[0].val)) {
85
+ // @ts-ignore
86
+ return {
87
+ valid: ValidationLevel.Drop,
88
+ matches: [],
89
+ node: tokens[0],
90
+ // @ts-ignore
91
+ syntax: null,
92
+ error: 'unexpected token',
93
+ tokens
94
+ };
95
+ }
96
+ tokens.shift();
97
+ consumeWhitespace(tokens);
98
+ // @ts-ignore
99
+ if (tokens.length == 0 || tokens[0].typ != EnumToken.PercentageTokenType) {
100
+ // @ts-ignore
101
+ return {
102
+ valid: ValidationLevel.Drop,
103
+ matches: [],
104
+ node: tokens[0],
105
+ // @ts-ignore
106
+ syntax: null,
107
+ error: 'expecting percentage token',
108
+ tokens
109
+ };
110
+ }
111
+ tokens.shift();
112
+ consumeWhitespace(tokens);
113
+ if (tokens.length > 0) {
114
+ // @ts-ignore
115
+ return {
116
+ valid: ValidationLevel.Drop,
117
+ matches: [],
118
+ node: tokens[0],
119
+ // @ts-ignore
120
+ syntax: null,
121
+ error: 'unexpected token',
122
+ tokens
123
+ };
124
+ }
125
+ // @ts-ignore
126
+ return {
127
+ valid: ValidationLevel.Valid,
128
+ matches: [],
129
+ node: null,
130
+ // @ts-ignore
131
+ syntax: null,
132
+ error: '',
133
+ tokens
134
+ };
135
+ }
136
+
137
+ export { validateKeyframeSelector };
@@ -0,0 +1,67 @@
1
+ import { EnumToken, ValidationLevel } from '../../ast/types.js';
2
+ import '../../ast/minify.js';
3
+ import '../../ast/walk.js';
4
+ import '../../parser/parse.js';
5
+ import '../../renderer/color/utils/constants.js';
6
+ import '../../renderer/sourcemap/lib/encode.js';
7
+ import '../../parser/utils/config.js';
8
+
9
+ function validateLayerName(tokens) {
10
+ const slice = tokens.reduce((acc, curr) => {
11
+ if (curr.typ == EnumToken.CommaTokenType) {
12
+ acc.push([]);
13
+ }
14
+ else if (curr.typ != EnumToken.CommentTokenType) {
15
+ acc[acc.length - 1].push(curr);
16
+ }
17
+ return acc;
18
+ }, [[]]).slice(1);
19
+ for (let i = 0; i < slice.length; i++) {
20
+ if (slice[i].length == 0) {
21
+ // @ts-ignore
22
+ return {
23
+ valid: ValidationLevel.Drop,
24
+ matches: tokens,
25
+ node: null,
26
+ syntax: null,
27
+ error: 'Invalid ident',
28
+ tokens
29
+ };
30
+ }
31
+ if (slice[i][0].typ != EnumToken.IdenTokenType) {
32
+ // @ts-ignore
33
+ return {
34
+ valid: ValidationLevel.Drop,
35
+ matches: tokens,
36
+ node: slice[i][0],
37
+ syntax: 'ident',
38
+ error: 'expecting ident',
39
+ tokens
40
+ };
41
+ }
42
+ for (let j = 1; j < slice[i].length; j++) {
43
+ if (slice[i][j].typ != EnumToken.ClassSelectorTokenType) {
44
+ // @ts-ignore
45
+ return {
46
+ valid: ValidationLevel.Drop,
47
+ matches: tokens,
48
+ node: slice[i][j],
49
+ syntax: 'layer-name',
50
+ error: 'expecting class selector',
51
+ tokens
52
+ };
53
+ }
54
+ }
55
+ }
56
+ // @ts-ignore
57
+ return {
58
+ valid: ValidationLevel.Valid,
59
+ matches: tokens,
60
+ node: null,
61
+ syntax: null,
62
+ error: '',
63
+ tokens
64
+ };
65
+ }
66
+
67
+ export { validateLayerName };