gurkencheck 0.0.4
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/LICENSE +13 -0
- package/README.md +327 -0
- package/dist/config-parser.d.ts +21 -0
- package/dist/config-parser.d.ts.map +1 -0
- package/dist/config-parser.js +171 -0
- package/dist/config-parser.js.map +1 -0
- package/dist/config-verifier.d.ts +4 -0
- package/dist/config-verifier.d.ts.map +1 -0
- package/dist/config-verifier.js +81 -0
- package/dist/config-verifier.js.map +1 -0
- package/dist/feature-finder.d.ts +18 -0
- package/dist/feature-finder.d.ts.map +1 -0
- package/dist/feature-finder.js +70 -0
- package/dist/feature-finder.js.map +1 -0
- package/dist/formatters/index.d.ts +23 -0
- package/dist/formatters/index.d.ts.map +1 -0
- package/dist/formatters/index.js +79 -0
- package/dist/formatters/index.js.map +1 -0
- package/dist/formatters/json.d.ts +31 -0
- package/dist/formatters/json.d.ts.map +1 -0
- package/dist/formatters/json.js +31 -0
- package/dist/formatters/json.js.map +1 -0
- package/dist/formatters/junit.d.ts +17 -0
- package/dist/formatters/junit.d.ts.map +1 -0
- package/dist/formatters/junit.js +61 -0
- package/dist/formatters/junit.js.map +1 -0
- package/dist/formatters/sarif.d.ts +6 -0
- package/dist/formatters/sarif.d.ts.map +1 -0
- package/dist/formatters/sarif.js +81 -0
- package/dist/formatters/sarif.js.map +1 -0
- package/dist/formatters/stylish.d.ts +9 -0
- package/dist/formatters/stylish.d.ts.map +1 -0
- package/dist/formatters/stylish.js +66 -0
- package/dist/formatters/stylish.js.map +1 -0
- package/dist/formatters/tap.d.ts +14 -0
- package/dist/formatters/tap.d.ts.map +1 -0
- package/dist/formatters/tap.js +45 -0
- package/dist/formatters/tap.js.map +1 -0
- package/dist/gherkin/dialects.d.ts +31 -0
- package/dist/gherkin/dialects.d.ts.map +1 -0
- package/dist/gherkin/dialects.js +40 -0
- package/dist/gherkin/dialects.js.map +1 -0
- package/dist/gherkin/keywords.d.ts +21 -0
- package/dist/gherkin/keywords.d.ts.map +1 -0
- package/dist/gherkin/keywords.js +53 -0
- package/dist/gherkin/keywords.js.map +1 -0
- package/dist/gherkin/parse.d.ts +32 -0
- package/dist/gherkin/parse.d.ts.map +1 -0
- package/dist/gherkin/parse.js +236 -0
- package/dist/gherkin/parse.js.map +1 -0
- package/dist/gherkin/traverse.d.ts +45 -0
- package/dist/gherkin/traverse.d.ts.map +1 -0
- package/dist/gherkin/traverse.js +89 -0
- package/dist/gherkin/traverse.js.map +1 -0
- package/dist/gherkin/variables.d.ts +26 -0
- package/dist/gherkin/variables.d.ts.map +1 -0
- package/dist/gherkin/variables.js +51 -0
- package/dist/gherkin/variables.js.map +1 -0
- package/dist/index.d.ts +39 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +31 -0
- package/dist/index.js.map +1 -0
- package/dist/linter.d.ts +23 -0
- package/dist/linter.d.ts.map +1 -0
- package/dist/linter.js +57 -0
- package/dist/linter.js.map +1 -0
- package/dist/logger.d.ts +16 -0
- package/dist/logger.d.ts.map +1 -0
- package/dist/logger.js +28 -0
- package/dist/logger.js.map +1 -0
- package/dist/main.d.ts +3 -0
- package/dist/main.d.ts.map +1 -0
- package/dist/main.js +144 -0
- package/dist/main.js.map +1 -0
- package/dist/presets.d.ts +19 -0
- package/dist/presets.d.ts.map +1 -0
- package/dist/presets.js +24 -0
- package/dist/presets.js.map +1 -0
- package/dist/rules/allowed-tags.d.ts +4 -0
- package/dist/rules/allowed-tags.d.ts.map +1 -0
- package/dist/rules/allowed-tags.js +34 -0
- package/dist/rules/allowed-tags.js.map +1 -0
- package/dist/rules/file-name.d.ts +4 -0
- package/dist/rules/file-name.d.ts.map +1 -0
- package/dist/rules/file-name.js +41 -0
- package/dist/rules/file-name.js.map +1 -0
- package/dist/rules/indentation.d.ts +4 -0
- package/dist/rules/indentation.d.ts.map +1 -0
- package/dist/rules/indentation.js +153 -0
- package/dist/rules/indentation.js.map +1 -0
- package/dist/rules/index.d.ts +13 -0
- package/dist/rules/index.d.ts.map +1 -0
- package/dist/rules/index.js +70 -0
- package/dist/rules/index.js.map +1 -0
- package/dist/rules/keywords-in-logical-order.d.ts +4 -0
- package/dist/rules/keywords-in-logical-order.d.ts.map +1 -0
- package/dist/rules/keywords-in-logical-order.js +37 -0
- package/dist/rules/keywords-in-logical-order.js.map +1 -0
- package/dist/rules/max-scenarios-per-file.d.ts +4 -0
- package/dist/rules/max-scenarios-per-file.d.ts.map +1 -0
- package/dist/rules/max-scenarios-per-file.js +42 -0
- package/dist/rules/max-scenarios-per-file.js.map +1 -0
- package/dist/rules/name-length.d.ts +4 -0
- package/dist/rules/name-length.d.ts.map +1 -0
- package/dist/rules/name-length.js +50 -0
- package/dist/rules/name-length.js.map +1 -0
- package/dist/rules/new-line-at-eof.d.ts +4 -0
- package/dist/rules/new-line-at-eof.d.ts.map +1 -0
- package/dist/rules/new-line-at-eof.js +30 -0
- package/dist/rules/new-line-at-eof.js.map +1 -0
- package/dist/rules/no-background-only-scenario.d.ts +4 -0
- package/dist/rules/no-background-only-scenario.d.ts.map +1 -0
- package/dist/rules/no-background-only-scenario.js +43 -0
- package/dist/rules/no-background-only-scenario.js.map +1 -0
- package/dist/rules/no-dupe-feature-names.d.ts +4 -0
- package/dist/rules/no-dupe-feature-names.d.ts.map +1 -0
- package/dist/rules/no-dupe-feature-names.js +25 -0
- package/dist/rules/no-dupe-feature-names.js.map +1 -0
- package/dist/rules/no-dupe-file-names.d.ts +4 -0
- package/dist/rules/no-dupe-file-names.d.ts.map +1 -0
- package/dist/rules/no-dupe-file-names.js +28 -0
- package/dist/rules/no-dupe-file-names.js.map +1 -0
- package/dist/rules/no-dupe-scenario-names.d.ts +4 -0
- package/dist/rules/no-dupe-scenario-names.d.ts.map +1 -0
- package/dist/rules/no-dupe-scenario-names.js +41 -0
- package/dist/rules/no-dupe-scenario-names.js.map +1 -0
- package/dist/rules/no-duplicate-tags.d.ts +4 -0
- package/dist/rules/no-duplicate-tags.d.ts.map +1 -0
- package/dist/rules/no-duplicate-tags.js +38 -0
- package/dist/rules/no-duplicate-tags.js.map +1 -0
- package/dist/rules/no-empty-background.d.ts +4 -0
- package/dist/rules/no-empty-background.d.ts.map +1 -0
- package/dist/rules/no-empty-background.js +24 -0
- package/dist/rules/no-empty-background.js.map +1 -0
- package/dist/rules/no-empty-file.d.ts +4 -0
- package/dist/rules/no-empty-file.d.ts.map +1 -0
- package/dist/rules/no-empty-file.js +12 -0
- package/dist/rules/no-empty-file.js.map +1 -0
- package/dist/rules/no-examples-in-scenarios.d.ts +4 -0
- package/dist/rules/no-examples-in-scenarios.d.ts.map +1 -0
- package/dist/rules/no-examples-in-scenarios.js +25 -0
- package/dist/rules/no-examples-in-scenarios.js.map +1 -0
- package/dist/rules/no-files-without-scenarios.d.ts +4 -0
- package/dist/rules/no-files-without-scenarios.d.ts.map +1 -0
- package/dist/rules/no-files-without-scenarios.js +18 -0
- package/dist/rules/no-files-without-scenarios.js.map +1 -0
- package/dist/rules/no-homogenous-tags.d.ts +4 -0
- package/dist/rules/no-homogenous-tags.d.ts.map +1 -0
- package/dist/rules/no-homogenous-tags.js +54 -0
- package/dist/rules/no-homogenous-tags.js.map +1 -0
- package/dist/rules/no-multiple-empty-lines.d.ts +4 -0
- package/dist/rules/no-multiple-empty-lines.d.ts.map +1 -0
- package/dist/rules/no-multiple-empty-lines.js +44 -0
- package/dist/rules/no-multiple-empty-lines.js.map +1 -0
- package/dist/rules/no-partially-commented-tag-lines.d.ts +4 -0
- package/dist/rules/no-partially-commented-tag-lines.d.ts.map +1 -0
- package/dist/rules/no-partially-commented-tag-lines.js +44 -0
- package/dist/rules/no-partially-commented-tag-lines.js.map +1 -0
- package/dist/rules/no-restricted-patterns.d.ts +4 -0
- package/dist/rules/no-restricted-patterns.d.ts.map +1 -0
- package/dist/rules/no-restricted-patterns.js +101 -0
- package/dist/rules/no-restricted-patterns.js.map +1 -0
- package/dist/rules/no-restricted-tags.d.ts +4 -0
- package/dist/rules/no-restricted-tags.d.ts.map +1 -0
- package/dist/rules/no-restricted-tags.js +35 -0
- package/dist/rules/no-restricted-tags.js.map +1 -0
- package/dist/rules/no-scenario-outlines-without-examples.d.ts +4 -0
- package/dist/rules/no-scenario-outlines-without-examples.d.ts.map +1 -0
- package/dist/rules/no-scenario-outlines-without-examples.js +29 -0
- package/dist/rules/no-scenario-outlines-without-examples.js.map +1 -0
- package/dist/rules/no-superfluous-tags.d.ts +4 -0
- package/dist/rules/no-superfluous-tags.d.ts.map +1 -0
- package/dist/rules/no-superfluous-tags.js +40 -0
- package/dist/rules/no-superfluous-tags.js.map +1 -0
- package/dist/rules/no-trailing-spaces.d.ts +4 -0
- package/dist/rules/no-trailing-spaces.d.ts.map +1 -0
- package/dist/rules/no-trailing-spaces.js +24 -0
- package/dist/rules/no-trailing-spaces.js.map +1 -0
- package/dist/rules/no-undeclared-variables.d.ts +4 -0
- package/dist/rules/no-undeclared-variables.d.ts.map +1 -0
- package/dist/rules/no-undeclared-variables.js +35 -0
- package/dist/rules/no-undeclared-variables.js.map +1 -0
- package/dist/rules/no-unnamed-features.d.ts +4 -0
- package/dist/rules/no-unnamed-features.d.ts.map +1 -0
- package/dist/rules/no-unnamed-features.js +19 -0
- package/dist/rules/no-unnamed-features.js.map +1 -0
- package/dist/rules/no-unnamed-scenarios.d.ts +4 -0
- package/dist/rules/no-unnamed-scenarios.d.ts.map +1 -0
- package/dist/rules/no-unnamed-scenarios.js +24 -0
- package/dist/rules/no-unnamed-scenarios.js.map +1 -0
- package/dist/rules/no-unused-variables.d.ts +4 -0
- package/dist/rules/no-unused-variables.d.ts.map +1 -0
- package/dist/rules/no-unused-variables.js +36 -0
- package/dist/rules/no-unused-variables.js.map +1 -0
- package/dist/rules/one-space-between-tags.d.ts +4 -0
- package/dist/rules/one-space-between-tags.d.ts.map +1 -0
- package/dist/rules/one-space-between-tags.js +36 -0
- package/dist/rules/one-space-between-tags.js.map +1 -0
- package/dist/rules/only-one-when.d.ts +4 -0
- package/dist/rules/only-one-when.d.ts.map +1 -0
- package/dist/rules/only-one-when.js +59 -0
- package/dist/rules/only-one-when.js.map +1 -0
- package/dist/rules/required-tags.d.ts +4 -0
- package/dist/rules/required-tags.d.ts.map +1 -0
- package/dist/rules/required-tags.js +36 -0
- package/dist/rules/required-tags.js.map +1 -0
- package/dist/rules/scenario-size.d.ts +4 -0
- package/dist/rules/scenario-size.d.ts.map +1 -0
- package/dist/rules/scenario-size.js +37 -0
- package/dist/rules/scenario-size.js.map +1 -0
- package/dist/rules/use-and.d.ts +4 -0
- package/dist/rules/use-and.d.ts.map +1 -0
- package/dist/rules/use-and.js +33 -0
- package/dist/rules/use-and.js.map +1 -0
- package/dist/rules.d.ts +24 -0
- package/dist/rules.d.ts.map +1 -0
- package/dist/rules.js +109 -0
- package/dist/rules.js.map +1 -0
- package/dist/suppressions.d.ts +33 -0
- package/dist/suppressions.d.ts.map +1 -0
- package/dist/suppressions.js +84 -0
- package/dist/suppressions.js.map +1 -0
- package/dist/types.d.ts +81 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +2 -0
- package/dist/types.js.map +1 -0
- package/dist/util/case.d.ts +21 -0
- package/dist/util/case.d.ts.map +1 -0
- package/dist/util/case.js +42 -0
- package/dist/util/case.js.map +1 -0
- package/dist/util/collections.d.ts +30 -0
- package/dist/util/collections.d.ts.map +1 -0
- package/dist/util/collections.js +87 -0
- package/dist/util/collections.js.map +1 -0
- package/dist/util/glob.d.ts +20 -0
- package/dist/util/glob.d.ts.map +1 -0
- package/dist/util/glob.js +203 -0
- package/dist/util/glob.js.map +1 -0
- package/dist/util/json.d.ts +14 -0
- package/dist/util/json.d.ts.map +1 -0
- package/dist/util/json.js +63 -0
- package/dist/util/json.js.map +1 -0
- package/dist/util/lines.d.ts +24 -0
- package/dist/util/lines.d.ts.map +1 -0
- package/dist/util/lines.js +45 -0
- package/dist/util/lines.js.map +1 -0
- package/dist/util/location.d.ts +15 -0
- package/dist/util/location.d.ts.map +1 -0
- package/dist/util/location.js +11 -0
- package/dist/util/location.js.map +1 -0
- package/dist/util/xml.d.ts +16 -0
- package/dist/util/xml.d.ts.map +1 -0
- package/dist/util/xml.js +36 -0
- package/dist/util/xml.js.map +1 -0
- package/dist/version.d.ts +3 -0
- package/dist/version.d.ts.map +1 -0
- package/dist/version.js +24 -0
- package/dist/version.js.map +1 -0
- package/package.json +61 -0
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A small glob implementation, replacing the `glob` package.
|
|
3
|
+
*
|
|
4
|
+
* Supports the subset of glob syntax that feature-file discovery needs:
|
|
5
|
+
* `*`, `?`, `**`, character classes (`[abc]`, `[!abc]`), brace alternatives
|
|
6
|
+
* (`{a,b}`) and backslash escapes.
|
|
7
|
+
*
|
|
8
|
+
* As with the `glob` package's defaults, `*` and `**` do not match entries
|
|
9
|
+
* whose name starts with a dot, and symlinked directories are not traversed.
|
|
10
|
+
*/
|
|
11
|
+
import fs from 'node:fs';
|
|
12
|
+
import path from 'node:path';
|
|
13
|
+
const REGEXP_SPECIAL_CHARACTERS = new Set('.+^$()|\\'.split(''));
|
|
14
|
+
/**
|
|
15
|
+
* Translates a glob pattern into an anchored regular expression matching
|
|
16
|
+
* slash-separated paths.
|
|
17
|
+
*/
|
|
18
|
+
export function globToRegExp(pattern) {
|
|
19
|
+
let source = '';
|
|
20
|
+
let braceDepth = 0;
|
|
21
|
+
let index = 0;
|
|
22
|
+
while (index < pattern.length) {
|
|
23
|
+
const character = pattern[index];
|
|
24
|
+
if (character === '*') {
|
|
25
|
+
const start = index;
|
|
26
|
+
while (pattern[index] === '*')
|
|
27
|
+
index++;
|
|
28
|
+
const isGlobstar = index - start >= 2;
|
|
29
|
+
const atSegmentStart = start === 0 || pattern[start - 1] === '/';
|
|
30
|
+
const atSegmentEnd = index === pattern.length || pattern[index] === '/';
|
|
31
|
+
if (isGlobstar && atSegmentStart && atSegmentEnd) {
|
|
32
|
+
if (pattern[index] === '/') {
|
|
33
|
+
// `**/` matches any number of leading path segments, including none.
|
|
34
|
+
source += '(?:[^/]*/)*';
|
|
35
|
+
index++;
|
|
36
|
+
}
|
|
37
|
+
else {
|
|
38
|
+
source += '.*';
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
else {
|
|
42
|
+
// A `*` anywhere else matches within a single path segment.
|
|
43
|
+
source += '[^/]*';
|
|
44
|
+
}
|
|
45
|
+
continue;
|
|
46
|
+
}
|
|
47
|
+
index++;
|
|
48
|
+
if (character === '?') {
|
|
49
|
+
source += '[^/]';
|
|
50
|
+
}
|
|
51
|
+
else if (character === '[') {
|
|
52
|
+
const closing = findClosingBracket(pattern, index);
|
|
53
|
+
if (closing === -1) {
|
|
54
|
+
source += '\\[';
|
|
55
|
+
}
|
|
56
|
+
else {
|
|
57
|
+
const negated = pattern[index] === '!' || pattern[index] === '^';
|
|
58
|
+
const body = pattern.slice(negated ? index + 1 : index, closing);
|
|
59
|
+
source += `[${negated ? '^' : ''}${body.replace(/\\/g, '\\\\')}]`;
|
|
60
|
+
index = closing + 1;
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
else if (character === '{') {
|
|
64
|
+
braceDepth++;
|
|
65
|
+
source += '(?:';
|
|
66
|
+
}
|
|
67
|
+
else if (character === '}' && braceDepth > 0) {
|
|
68
|
+
braceDepth--;
|
|
69
|
+
source += ')';
|
|
70
|
+
}
|
|
71
|
+
else if (character === ',' && braceDepth > 0) {
|
|
72
|
+
source += '|';
|
|
73
|
+
}
|
|
74
|
+
else if (character === '\\' && index < pattern.length) {
|
|
75
|
+
source += escapeLiteral(pattern[index]);
|
|
76
|
+
index++;
|
|
77
|
+
}
|
|
78
|
+
else {
|
|
79
|
+
source += escapeLiteral(character);
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
return new RegExp(`^${source}$`);
|
|
83
|
+
}
|
|
84
|
+
function escapeLiteral(character) {
|
|
85
|
+
return REGEXP_SPECIAL_CHARACTERS.has(character) ? `\\${character}` : character;
|
|
86
|
+
}
|
|
87
|
+
function findClosingBracket(pattern, from) {
|
|
88
|
+
for (let index = from + 1; index < pattern.length; index++) {
|
|
89
|
+
if (pattern[index] === ']')
|
|
90
|
+
return index;
|
|
91
|
+
}
|
|
92
|
+
return -1;
|
|
93
|
+
}
|
|
94
|
+
/** True when the segment contains glob syntax rather than a literal name. */
|
|
95
|
+
function isDynamic(segment) {
|
|
96
|
+
return /[*?[\]{}]/.test(segment);
|
|
97
|
+
}
|
|
98
|
+
/**
|
|
99
|
+
* The leading run of literal segments, used as the directory to start walking
|
|
100
|
+
* from so that `a/b/**` does not scan the whole tree.
|
|
101
|
+
*/
|
|
102
|
+
function staticPrefix(pattern) {
|
|
103
|
+
const segments = pattern.split('/');
|
|
104
|
+
const literal = [];
|
|
105
|
+
for (const segment of segments.slice(0, -1)) {
|
|
106
|
+
if (isDynamic(segment))
|
|
107
|
+
break;
|
|
108
|
+
literal.push(segment);
|
|
109
|
+
}
|
|
110
|
+
return literal.join('/');
|
|
111
|
+
}
|
|
112
|
+
function isHidden(name) {
|
|
113
|
+
return name.startsWith('.');
|
|
114
|
+
}
|
|
115
|
+
function walk(directory, onFile) {
|
|
116
|
+
let entries;
|
|
117
|
+
try {
|
|
118
|
+
entries = fs.readdirSync(directory, { withFileTypes: true });
|
|
119
|
+
}
|
|
120
|
+
catch {
|
|
121
|
+
// A missing or unreadable directory simply contributes no matches.
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
for (const entry of entries.sort((a, b) => (a.name < b.name ? -1 : a.name > b.name ? 1 : 0))) {
|
|
125
|
+
if (isHidden(entry.name)) {
|
|
126
|
+
continue;
|
|
127
|
+
}
|
|
128
|
+
const absolutePath = path.join(directory, entry.name);
|
|
129
|
+
if (entry.isDirectory()) {
|
|
130
|
+
walk(absolutePath, onFile);
|
|
131
|
+
}
|
|
132
|
+
else if (entry.isFile()) {
|
|
133
|
+
onFile(absolutePath);
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
/**
|
|
138
|
+
* True when the path, or any directory leading to it, matches one of the
|
|
139
|
+
* patterns.
|
|
140
|
+
*
|
|
141
|
+
* Testing the parent directories is what makes an entry like `build` or `o*e`
|
|
142
|
+
* skip the whole directory rather than only a file of that exact name. Without
|
|
143
|
+
* it an ignore file has to spell out `build/**` everywhere, which is not how
|
|
144
|
+
* .gitignore or .eslintignore behave.
|
|
145
|
+
*/
|
|
146
|
+
function isIgnored(relativePath, ignores) {
|
|
147
|
+
if (ignores.length === 0) {
|
|
148
|
+
return false;
|
|
149
|
+
}
|
|
150
|
+
const segments = relativePath.split('/');
|
|
151
|
+
for (let depth = 1; depth <= segments.length; depth++) {
|
|
152
|
+
const prefix = segments.slice(0, depth).join('/');
|
|
153
|
+
if (ignores.some((ignore) => ignore.test(prefix))) {
|
|
154
|
+
return true;
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
return false;
|
|
158
|
+
}
|
|
159
|
+
/**
|
|
160
|
+
* Returns the files matching `pattern`, as paths relative to `cwd` using
|
|
161
|
+
* forward slashes. Directories are never returned. Results are sorted.
|
|
162
|
+
*/
|
|
163
|
+
export function globSync(pattern, options = {}) {
|
|
164
|
+
const cwd = options.cwd ?? process.cwd();
|
|
165
|
+
const normalisedPattern = pattern.split(path.sep).join('/');
|
|
166
|
+
const matches = globToRegExp(normalisedPattern);
|
|
167
|
+
const ignores = (options.ignore ?? []).map((ignorePattern) => globToRegExp(ignorePattern.split(path.sep).join('/')));
|
|
168
|
+
const searchRoot = path.resolve(cwd, staticPrefix(normalisedPattern));
|
|
169
|
+
const found = [];
|
|
170
|
+
// An absolute pattern is matched against absolute paths: comparing it with
|
|
171
|
+
// a path relative to cwd can never match, and the search would come back
|
|
172
|
+
// empty rather than wrong, which reads as "nothing to report".
|
|
173
|
+
const absolutePattern = path.isAbsolute(normalisedPattern);
|
|
174
|
+
const consider = (absolutePath) => {
|
|
175
|
+
const relativePath = path.relative(cwd, absolutePath).split(path.sep).join('/');
|
|
176
|
+
const candidate = absolutePattern ? absolutePath.split(path.sep).join('/') : relativePath;
|
|
177
|
+
if (!matches.test(candidate))
|
|
178
|
+
return;
|
|
179
|
+
if (isIgnored(relativePath, ignores))
|
|
180
|
+
return;
|
|
181
|
+
found.push(relativePath);
|
|
182
|
+
};
|
|
183
|
+
const stats = statOrUndefined(searchRoot);
|
|
184
|
+
if (stats === undefined) {
|
|
185
|
+
return [];
|
|
186
|
+
}
|
|
187
|
+
if (stats.isFile()) {
|
|
188
|
+
consider(searchRoot);
|
|
189
|
+
}
|
|
190
|
+
else {
|
|
191
|
+
walk(searchRoot, consider);
|
|
192
|
+
}
|
|
193
|
+
return found.sort();
|
|
194
|
+
}
|
|
195
|
+
function statOrUndefined(target) {
|
|
196
|
+
try {
|
|
197
|
+
return fs.statSync(target);
|
|
198
|
+
}
|
|
199
|
+
catch {
|
|
200
|
+
return undefined;
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
//# sourceMappingURL=glob.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"glob.js","sourceRoot":"","sources":["../../src/util/glob.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* JSON with comments, replacing the `strip-json-comments` package.
|
|
3
|
+
*/
|
|
4
|
+
/**
|
|
5
|
+
* Blanks out `//` and comments from a JSON document, leaving
|
|
6
|
+
* everything else - including string contents and line breaks - untouched.
|
|
7
|
+
*
|
|
8
|
+
* Comments are replaced by spaces rather than removed so that the character
|
|
9
|
+
* offsets in any `JSON.parse` error still point at the right place.
|
|
10
|
+
*/
|
|
11
|
+
export declare function stripJsonComments(json: string): string;
|
|
12
|
+
/** Parses JSON that may contain comments. */
|
|
13
|
+
export declare function parseJsonWithComments(json: string): unknown;
|
|
14
|
+
//# sourceMappingURL=json.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"json.d.ts","sourceRoot":"","sources":["../../src/util/json.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH;;;;;;GAMG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAsDtD;AAED,6CAA6C;AAC7C,wBAAgB,qBAAqB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAE3D"}
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* JSON with comments, replacing the `strip-json-comments` package.
|
|
3
|
+
*/
|
|
4
|
+
/**
|
|
5
|
+
* Blanks out `//` and comments from a JSON document, leaving
|
|
6
|
+
* everything else - including string contents and line breaks - untouched.
|
|
7
|
+
*
|
|
8
|
+
* Comments are replaced by spaces rather than removed so that the character
|
|
9
|
+
* offsets in any `JSON.parse` error still point at the right place.
|
|
10
|
+
*/
|
|
11
|
+
export function stripJsonComments(json) {
|
|
12
|
+
let result = '';
|
|
13
|
+
let index = 0;
|
|
14
|
+
let inString = false;
|
|
15
|
+
while (index < json.length) {
|
|
16
|
+
const character = json[index];
|
|
17
|
+
const next = json[index + 1];
|
|
18
|
+
if (inString) {
|
|
19
|
+
result += character;
|
|
20
|
+
if (character === '\\' && index + 1 < json.length) {
|
|
21
|
+
result += json[index + 1];
|
|
22
|
+
index += 2;
|
|
23
|
+
continue;
|
|
24
|
+
}
|
|
25
|
+
if (character === '"') {
|
|
26
|
+
inString = false;
|
|
27
|
+
}
|
|
28
|
+
index++;
|
|
29
|
+
continue;
|
|
30
|
+
}
|
|
31
|
+
if (character === '"') {
|
|
32
|
+
inString = true;
|
|
33
|
+
result += character;
|
|
34
|
+
index++;
|
|
35
|
+
continue;
|
|
36
|
+
}
|
|
37
|
+
if (character === '/' && next === '/') {
|
|
38
|
+
while (index < json.length && json[index] !== '\n') {
|
|
39
|
+
result += ' ';
|
|
40
|
+
index++;
|
|
41
|
+
}
|
|
42
|
+
continue;
|
|
43
|
+
}
|
|
44
|
+
if (character === '/' && next === '*') {
|
|
45
|
+
const end = json.indexOf('*/', index + 2);
|
|
46
|
+
const stop = end === -1 ? json.length : end + 2;
|
|
47
|
+
while (index < stop) {
|
|
48
|
+
// Keep line breaks so reported line numbers stay accurate.
|
|
49
|
+
result += json[index] === '\n' ? '\n' : ' ';
|
|
50
|
+
index++;
|
|
51
|
+
}
|
|
52
|
+
continue;
|
|
53
|
+
}
|
|
54
|
+
result += character;
|
|
55
|
+
index++;
|
|
56
|
+
}
|
|
57
|
+
return result;
|
|
58
|
+
}
|
|
59
|
+
/** Parses JSON that may contain comments. */
|
|
60
|
+
export function parseJsonWithComments(json) {
|
|
61
|
+
return JSON.parse(stripJsonComments(json));
|
|
62
|
+
}
|
|
63
|
+
//# sourceMappingURL=json.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"json.js","sourceRoot":"","sources":["../../src/util/json.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH;;;;;;GAMG;AACH,MAAM,UAAU,iBAAiB,CAAC,IAAY;IAC5C,IAAI,MAAM,GAAG,EAAE,CAAC;IAChB,IAAI,KAAK,GAAG,CAAC,CAAC;IACd,IAAI,QAAQ,GAAG,KAAK,CAAC;IAErB,OAAO,KAAK,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC;QAC3B,MAAM,SAAS,GAAG,IAAI,CAAC,KAAK,CAAE,CAAC;QAC/B,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;QAE7B,IAAI,QAAQ,EAAE,CAAC;YACb,MAAM,IAAI,SAAS,CAAC;YACpB,IAAI,SAAS,KAAK,IAAI,IAAI,KAAK,GAAG,CAAC,GAAG,IAAI,CAAC,MAAM,EAAE,CAAC;gBAClD,MAAM,IAAI,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC;gBAC1B,KAAK,IAAI,CAAC,CAAC;gBACX,SAAS;YACX,CAAC;YACD,IAAI,SAAS,KAAK,GAAG,EAAE,CAAC;gBACtB,QAAQ,GAAG,KAAK,CAAC;YACnB,CAAC;YACD,KAAK,EAAE,CAAC;YACR,SAAS;QACX,CAAC;QAED,IAAI,SAAS,KAAK,GAAG,EAAE,CAAC;YACtB,QAAQ,GAAG,IAAI,CAAC;YAChB,MAAM,IAAI,SAAS,CAAC;YACpB,KAAK,EAAE,CAAC;YACR,SAAS;QACX,CAAC;QAED,IAAI,SAAS,KAAK,GAAG,IAAI,IAAI,KAAK,GAAG,EAAE,CAAC;YACtC,OAAO,KAAK,GAAG,IAAI,CAAC,MAAM,IAAI,IAAI,CAAC,KAAK,CAAC,KAAK,IAAI,EAAE,CAAC;gBACnD,MAAM,IAAI,GAAG,CAAC;gBACd,KAAK,EAAE,CAAC;YACV,CAAC;YACD,SAAS;QACX,CAAC;QAED,IAAI,SAAS,KAAK,GAAG,IAAI,IAAI,KAAK,GAAG,EAAE,CAAC;YACtC,MAAM,GAAG,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,EAAE,KAAK,GAAG,CAAC,CAAC,CAAC;YAC1C,MAAM,IAAI,GAAG,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC;YAChD,OAAO,KAAK,GAAG,IAAI,EAAE,CAAC;gBACpB,2DAA2D;gBAC3D,MAAM,IAAI,IAAI,CAAC,KAAK,CAAC,KAAK,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,GAAG,CAAC;gBAC5C,KAAK,EAAE,CAAC;YACV,CAAC;YACD,SAAS;QACX,CAAC;QAED,MAAM,IAAI,SAAS,CAAC;QACpB,KAAK,EAAE,CAAC;IACV,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,6CAA6C;AAC7C,MAAM,UAAU,qBAAqB,CAAC,IAAY;IAChD,OAAO,IAAI,CAAC,KAAK,CAAC,iBAAiB,CAAC,IAAI,CAAC,CAAC,CAAC;AAC7C,CAAC"}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Helpers for looking at a feature file as plain text.
|
|
3
|
+
*/
|
|
4
|
+
import type { FeatureFile } from '../types.ts';
|
|
5
|
+
/**
|
|
6
|
+
* The lines a person would see in their editor.
|
|
7
|
+
*
|
|
8
|
+
* Splitting on line breaks leaves a trailing empty entry when the file ends
|
|
9
|
+
* with one, which is how `new-line-at-eof` detects that newline. That entry is
|
|
10
|
+
* not a line of the file though, so any rule reporting a line number has to
|
|
11
|
+
* leave it out or it points past the end of the file.
|
|
12
|
+
*/
|
|
13
|
+
export declare function contentLines(file: FeatureFile): string[];
|
|
14
|
+
/**
|
|
15
|
+
* Marks which lines sit inside a doc string, delimiters included.
|
|
16
|
+
*
|
|
17
|
+
* Text inside a doc string is data belonging to the step, not part of the
|
|
18
|
+
* layout of the file, so rules about formatting have to leave it alone.
|
|
19
|
+
*
|
|
20
|
+
* This reads the raw lines rather than the parsed document so that it still
|
|
21
|
+
* works on a file the parser rejected.
|
|
22
|
+
*/
|
|
23
|
+
export declare function markDocStrings(lines: readonly string[]): boolean[];
|
|
24
|
+
//# sourceMappingURL=lines.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"lines.d.ts","sourceRoot":"","sources":["../../src/util/lines.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,OAAO,KAAK,EAAC,WAAW,EAAC,MAAM,aAAa,CAAC;AAE7C;;;;;;;GAOG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,WAAW,GAAG,MAAM,EAAE,CAGxD;AAKD;;;;;;;;GAQG;AACH,wBAAgB,cAAc,CAAC,KAAK,EAAE,SAAS,MAAM,EAAE,GAAG,OAAO,EAAE,CAwBlE"}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The lines a person would see in their editor.
|
|
3
|
+
*
|
|
4
|
+
* Splitting on line breaks leaves a trailing empty entry when the file ends
|
|
5
|
+
* with one, which is how `new-line-at-eof` detects that newline. That entry is
|
|
6
|
+
* not a line of the file though, so any rule reporting a line number has to
|
|
7
|
+
* leave it out or it points past the end of the file.
|
|
8
|
+
*/
|
|
9
|
+
export function contentLines(file) {
|
|
10
|
+
const { lines } = file;
|
|
11
|
+
return lines.at(-1) === '' ? lines.slice(0, -1) : [...lines];
|
|
12
|
+
}
|
|
13
|
+
/** The delimiters that open and close a doc string. */
|
|
14
|
+
const DOC_STRING_DELIMITERS = ['"""', '```'];
|
|
15
|
+
/**
|
|
16
|
+
* Marks which lines sit inside a doc string, delimiters included.
|
|
17
|
+
*
|
|
18
|
+
* Text inside a doc string is data belonging to the step, not part of the
|
|
19
|
+
* layout of the file, so rules about formatting have to leave it alone.
|
|
20
|
+
*
|
|
21
|
+
* This reads the raw lines rather than the parsed document so that it still
|
|
22
|
+
* works on a file the parser rejected.
|
|
23
|
+
*/
|
|
24
|
+
export function markDocStrings(lines) {
|
|
25
|
+
const inside = new Array(lines.length).fill(false);
|
|
26
|
+
let openDelimiter;
|
|
27
|
+
lines.forEach((line, index) => {
|
|
28
|
+
const trimmed = line.trim();
|
|
29
|
+
if (openDelimiter === undefined) {
|
|
30
|
+
// An opening delimiter may be followed by a content type, e.g. """json
|
|
31
|
+
const delimiter = DOC_STRING_DELIMITERS.find((candidate) => trimmed.startsWith(candidate));
|
|
32
|
+
if (delimiter !== undefined) {
|
|
33
|
+
openDelimiter = delimiter;
|
|
34
|
+
inside[index] = true;
|
|
35
|
+
}
|
|
36
|
+
return;
|
|
37
|
+
}
|
|
38
|
+
inside[index] = true;
|
|
39
|
+
if (trimmed.startsWith(openDelimiter)) {
|
|
40
|
+
openDelimiter = undefined;
|
|
41
|
+
}
|
|
42
|
+
});
|
|
43
|
+
return inside;
|
|
44
|
+
}
|
|
45
|
+
//# sourceMappingURL=lines.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"lines.js","sourceRoot":"","sources":["../../src/util/lines.ts"],"names":[],"mappings":"AAKA;;;;;;;GAOG;AACH,MAAM,UAAU,YAAY,CAAC,IAAiB;IAC5C,MAAM,EAAC,KAAK,EAAC,GAAG,IAAI,CAAC;IACrB,OAAO,KAAK,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,KAAK,CAAC,CAAC;AAC/D,CAAC;AAED,uDAAuD;AACvD,MAAM,qBAAqB,GAAG,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;AAE7C;;;;;;;;GAQG;AACH,MAAM,UAAU,cAAc,CAAC,KAAwB;IACrD,MAAM,MAAM,GAAG,IAAI,KAAK,CAAU,KAAK,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;IAC5D,IAAI,aAAiC,CAAC;IAEtC,KAAK,CAAC,OAAO,CAAC,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE;QAC5B,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,EAAE,CAAC;QAE5B,IAAI,aAAa,KAAK,SAAS,EAAE,CAAC;YAChC,uEAAuE;YACvE,MAAM,SAAS,GAAG,qBAAqB,CAAC,IAAI,CAAC,CAAC,SAAS,EAAE,EAAE,CAAC,OAAO,CAAC,UAAU,CAAC,SAAS,CAAC,CAAC,CAAC;YAC3F,IAAI,SAAS,KAAK,SAAS,EAAE,CAAC;gBAC5B,aAAa,GAAG,SAAS,CAAC;gBAC1B,MAAM,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC;YACvB,CAAC;YACD,OAAO;QACT,CAAC;QAED,MAAM,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC;QACrB,IAAI,OAAO,CAAC,UAAU,CAAC,aAAa,CAAC,EAAE,CAAC;YACtC,aAAa,GAAG,SAAS,CAAC;QAC5B,CAAC;IACH,CAAC,CAAC,CAAC;IAEH,OAAO,MAAM,CAAC;AAChB,CAAC"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Turning a parsed node's location into the position fields of a RuleError.
|
|
3
|
+
*/
|
|
4
|
+
import type { Location } from '@cucumber/messages';
|
|
5
|
+
/** The line and, when the parser recorded one, the column of a node. */
|
|
6
|
+
export declare function at(location: Location): {
|
|
7
|
+
line: number;
|
|
8
|
+
column?: number;
|
|
9
|
+
};
|
|
10
|
+
/** A position given as plain numbers, for rules working on raw text. */
|
|
11
|
+
export declare function atLineColumn(line: number, column?: number): {
|
|
12
|
+
line: number;
|
|
13
|
+
column?: number;
|
|
14
|
+
};
|
|
15
|
+
//# sourceMappingURL=location.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"location.d.ts","sourceRoot":"","sources":["../../src/util/location.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,OAAO,KAAK,EAAC,QAAQ,EAAC,MAAM,oBAAoB,CAAC;AAEjD,wEAAwE;AACxE,wBAAgB,EAAE,CAAC,QAAQ,EAAE,QAAQ,GAAG;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAC,CAItE;AAED,wEAAwE;AACxE,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAC,CAE3F"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
/** The line and, when the parser recorded one, the column of a node. */
|
|
2
|
+
export function at(location) {
|
|
3
|
+
return location.column === undefined
|
|
4
|
+
? { line: location.line }
|
|
5
|
+
: { line: location.line, column: location.column };
|
|
6
|
+
}
|
|
7
|
+
/** A position given as plain numbers, for rules working on raw text. */
|
|
8
|
+
export function atLineColumn(line, column) {
|
|
9
|
+
return column === undefined ? { line } : { line, column };
|
|
10
|
+
}
|
|
11
|
+
//# sourceMappingURL=location.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"location.js","sourceRoot":"","sources":["../../src/util/location.ts"],"names":[],"mappings":"AAKA,wEAAwE;AACxE,MAAM,UAAU,EAAE,CAAC,QAAkB;IACnC,OAAO,QAAQ,CAAC,MAAM,KAAK,SAAS;QAClC,CAAC,CAAC,EAAC,IAAI,EAAE,QAAQ,CAAC,IAAI,EAAC;QACvB,CAAC,CAAC,EAAC,IAAI,EAAE,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,CAAC,MAAM,EAAC,CAAC;AACrD,CAAC;AAED,wEAAwE;AACxE,MAAM,UAAU,YAAY,CAAC,IAAY,EAAE,MAAe;IACxD,OAAO,MAAM,KAAK,SAAS,CAAC,CAAC,CAAC,EAAC,IAAI,EAAC,CAAC,CAAC,CAAC,EAAC,IAAI,EAAE,MAAM,EAAC,CAAC;AACxD,CAAC"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Minimal XML writing, replacing the `xml-js` package.
|
|
3
|
+
*/
|
|
4
|
+
/** Escapes the five characters that may not appear literally in XML text. */
|
|
5
|
+
export declare function escapeXml(value: string): string;
|
|
6
|
+
/**
|
|
7
|
+
* Wraps text in a CDATA section, splitting it if it contains the `]]>`
|
|
8
|
+
* terminator, which cannot be escaped inside CDATA.
|
|
9
|
+
*/
|
|
10
|
+
export declare function cdata(value: string): string;
|
|
11
|
+
/** Renders `name="value"` pairs, skipping attributes with no value. */
|
|
12
|
+
export declare function attributes(pairs: Record<string, string | number | undefined>): string;
|
|
13
|
+
export declare const XML_DECLARATION = "<?xml version=\"1.0\" encoding=\"utf-8\"?>";
|
|
14
|
+
/** Indents each line of `content` by `depth` levels of four spaces. */
|
|
15
|
+
export declare function indent(content: string, depth: number): string;
|
|
16
|
+
//# sourceMappingURL=xml.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"xml.d.ts","sourceRoot":"","sources":["../../src/util/xml.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,6EAA6E;AAC7E,wBAAgB,SAAS,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAO/C;AAED;;;GAGG;AACH,wBAAgB,KAAK,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAE3C;AAED,uEAAuE;AACvE,wBAAgB,UAAU,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAAC,GAAG,MAAM,CAKrF;AAED,eAAO,MAAM,eAAe,+CAA2C,CAAC;AAExE,uEAAuE;AACvE,wBAAgB,MAAM,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,MAAM,CAM7D"}
|
package/dist/util/xml.js
ADDED
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Minimal XML writing, replacing the `xml-js` package.
|
|
3
|
+
*/
|
|
4
|
+
/** Escapes the five characters that may not appear literally in XML text. */
|
|
5
|
+
export function escapeXml(value) {
|
|
6
|
+
return value
|
|
7
|
+
.replace(/&/g, '&')
|
|
8
|
+
.replace(/</g, '<')
|
|
9
|
+
.replace(/>/g, '>')
|
|
10
|
+
.replace(/"/g, '"')
|
|
11
|
+
.replace(/'/g, ''');
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Wraps text in a CDATA section, splitting it if it contains the `]]>`
|
|
15
|
+
* terminator, which cannot be escaped inside CDATA.
|
|
16
|
+
*/
|
|
17
|
+
export function cdata(value) {
|
|
18
|
+
return `<![CDATA[${value.split(']]>').join(']]]]><![CDATA[>')}]]>`;
|
|
19
|
+
}
|
|
20
|
+
/** Renders `name="value"` pairs, skipping attributes with no value. */
|
|
21
|
+
export function attributes(pairs) {
|
|
22
|
+
return Object.entries(pairs)
|
|
23
|
+
.filter(([, value]) => value !== undefined)
|
|
24
|
+
.map(([name, value]) => ` ${name}="${escapeXml(String(value))}"`)
|
|
25
|
+
.join('');
|
|
26
|
+
}
|
|
27
|
+
export const XML_DECLARATION = '<?xml version="1.0" encoding="utf-8"?>';
|
|
28
|
+
/** Indents each line of `content` by `depth` levels of four spaces. */
|
|
29
|
+
export function indent(content, depth) {
|
|
30
|
+
const padding = ' '.repeat(depth);
|
|
31
|
+
return content
|
|
32
|
+
.split('\n')
|
|
33
|
+
.map((line) => (line === '' ? line : padding + line))
|
|
34
|
+
.join('\n');
|
|
35
|
+
}
|
|
36
|
+
//# sourceMappingURL=xml.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"xml.js","sourceRoot":"","sources":["../../src/util/xml.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,6EAA6E;AAC7E,MAAM,UAAU,SAAS,CAAC,KAAa;IACrC,OAAO,KAAK;SACT,OAAO,CAAC,IAAI,EAAE,OAAO,CAAC;SACtB,OAAO,CAAC,IAAI,EAAE,MAAM,CAAC;SACrB,OAAO,CAAC,IAAI,EAAE,MAAM,CAAC;SACrB,OAAO,CAAC,IAAI,EAAE,QAAQ,CAAC;SACvB,OAAO,CAAC,IAAI,EAAE,QAAQ,CAAC,CAAC;AAC7B,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,KAAK,CAAC,KAAa;IACjC,OAAO,YAAY,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,iBAAiB,CAAC,KAAK,CAAC;AACrE,CAAC;AAED,uEAAuE;AACvE,MAAM,UAAU,UAAU,CAAC,KAAkD;IAC3E,OAAO,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC;SACzB,MAAM,CAAC,CAAC,CAAC,EAAE,KAAK,CAAC,EAAE,EAAE,CAAC,KAAK,KAAK,SAAS,CAAC;SAC1C,GAAG,CAAC,CAAC,CAAC,IAAI,EAAE,KAAK,CAAC,EAAE,EAAE,CAAC,IAAI,IAAI,KAAK,SAAS,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,GAAG,CAAC;SAChE,IAAI,CAAC,EAAE,CAAC,CAAC;AACd,CAAC;AAED,MAAM,CAAC,MAAM,eAAe,GAAG,wCAAwC,CAAC;AAExE,uEAAuE;AACvE,MAAM,UAAU,MAAM,CAAC,OAAe,EAAE,KAAa;IACnD,MAAM,OAAO,GAAG,MAAM,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;IACrC,OAAO,OAAO;SACX,KAAK,CAAC,IAAI,CAAC;SACX,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC,IAAI,KAAK,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,OAAO,GAAG,IAAI,CAAC,CAAC;SACpD,IAAI,CAAC,IAAI,CAAC,CAAC;AAChB,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"version.d.ts","sourceRoot":"","sources":["../src/version.ts"],"names":[],"mappings":"AAWA,sEAAsE;AACtE,wBAAgB,OAAO,IAAI,MAAM,CAWhC"}
|
package/dist/version.js
ADDED
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The package version, read from package.json at run time.
|
|
3
|
+
*
|
|
4
|
+
* This file sits one directory below package.json both in the sources and in
|
|
5
|
+
* the compiled output, so the same relative path works either way.
|
|
6
|
+
*/
|
|
7
|
+
import fs from 'node:fs';
|
|
8
|
+
import path from 'node:path';
|
|
9
|
+
let cached;
|
|
10
|
+
/** The version from package.json, or `0.0.0` if it cannot be read. */
|
|
11
|
+
export function version() {
|
|
12
|
+
if (cached === undefined) {
|
|
13
|
+
try {
|
|
14
|
+
const packagePath = path.join(import.meta.dirname, '..', 'package.json');
|
|
15
|
+
const contents = JSON.parse(fs.readFileSync(packagePath, 'utf8'));
|
|
16
|
+
cached = contents.version ?? '0.0.0';
|
|
17
|
+
}
|
|
18
|
+
catch {
|
|
19
|
+
cached = '0.0.0';
|
|
20
|
+
}
|
|
21
|
+
}
|
|
22
|
+
return cached;
|
|
23
|
+
}
|
|
24
|
+
//# sourceMappingURL=version.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"version.js","sourceRoot":"","sources":["../src/version.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,EAAE,MAAM,SAAS,CAAC;AACzB,OAAO,IAAI,MAAM,WAAW,CAAC;AAE7B,IAAI,MAA0B,CAAC;AAE/B,sEAAsE;AACtE,MAAM,UAAU,OAAO;IACrB,IAAI,MAAM,KAAK,SAAS,EAAE,CAAC;QACzB,IAAI,CAAC;YACH,MAAM,WAAW,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,IAAI,CAAC,OAAO,EAAE,IAAI,EAAE,cAAc,CAAC,CAAC;YACzE,MAAM,QAAQ,GAAG,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC,YAAY,CAAC,WAAW,EAAE,MAAM,CAAC,CAAuB,CAAC;YACxF,MAAM,GAAG,QAAQ,CAAC,OAAO,IAAI,OAAO,CAAC;QACvC,CAAC;QAAC,MAAM,CAAC;YACP,MAAM,GAAG,OAAO,CAAC;QACnB,CAAC;IACH,CAAC;IACD,OAAO,MAAM,CAAC;AAChB,CAAC"}
|
package/package.json
ADDED
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "gurkencheck",
|
|
3
|
+
"version": "0.0.4",
|
|
4
|
+
"description": "A Gherkin linter/validator written in TypeScript, with no build step beyond tsc",
|
|
5
|
+
"keywords": [
|
|
6
|
+
"gherkin",
|
|
7
|
+
"cucumber",
|
|
8
|
+
"linter",
|
|
9
|
+
"lint",
|
|
10
|
+
"bdd",
|
|
11
|
+
"feature-files",
|
|
12
|
+
"typescript"
|
|
13
|
+
],
|
|
14
|
+
"license": "ISC",
|
|
15
|
+
"author": "Sebastian Schürmann",
|
|
16
|
+
"repository": {
|
|
17
|
+
"type": "git",
|
|
18
|
+
"url": "git+https://github.com/sebs/gurkencheck.git"
|
|
19
|
+
},
|
|
20
|
+
"homepage": "https://sebs.github.io/gurkencheck/",
|
|
21
|
+
"bugs": {
|
|
22
|
+
"url": "https://github.com/sebs/gurkencheck/issues"
|
|
23
|
+
},
|
|
24
|
+
"type": "module",
|
|
25
|
+
"main": "./dist/index.js",
|
|
26
|
+
"types": "./dist/index.d.ts",
|
|
27
|
+
"exports": {
|
|
28
|
+
".": {
|
|
29
|
+
"types": "./dist/index.d.ts",
|
|
30
|
+
"default": "./dist/index.js"
|
|
31
|
+
}
|
|
32
|
+
},
|
|
33
|
+
"bin": {
|
|
34
|
+
"gurkencheck": "./dist/main.js"
|
|
35
|
+
},
|
|
36
|
+
"files": [
|
|
37
|
+
"dist"
|
|
38
|
+
],
|
|
39
|
+
"engines": {
|
|
40
|
+
"node": ">=22.0.0"
|
|
41
|
+
},
|
|
42
|
+
"dependencies": {
|
|
43
|
+
"@cucumber/gherkin": "^42.0.1",
|
|
44
|
+
"@cucumber/messages": "^34.2.1"
|
|
45
|
+
},
|
|
46
|
+
"devDependencies": {
|
|
47
|
+
"@types/node": "^24.0.0",
|
|
48
|
+
"typescript": "^7.0.2"
|
|
49
|
+
},
|
|
50
|
+
"scripts": {
|
|
51
|
+
"build": "tsc -p tsconfig.build.json",
|
|
52
|
+
"typecheck": "tsc -p tsconfig.json --noEmit",
|
|
53
|
+
"test": "node --test \"test/**/*.test.ts\"",
|
|
54
|
+
"test:watch": "node --test --watch \"test/**/*.test.ts\"",
|
|
55
|
+
"coverage": "node --test --experimental-test-coverage \"test/**/*.test.ts\"",
|
|
56
|
+
"docs": "node site/build.ts",
|
|
57
|
+
"generate:rules": "node scripts/generate-rules.ts",
|
|
58
|
+
"demo": "node src/main.ts examples",
|
|
59
|
+
"prepare": "npm run build"
|
|
60
|
+
}
|
|
61
|
+
}
|