@markup-carve/carve-lsp 0.1.2 → 0.1.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/README.md +61 -14
- package/dist/analyze.d.ts +15 -1
- package/dist/analyze.js +214 -16
- package/dist/analyze.js.map +1 -1
- package/dist/analyze.test.js +29 -1
- package/dist/analyze.test.js.map +1 -1
- package/dist/captions.d.ts +49 -0
- package/dist/captions.js +124 -0
- package/dist/captions.js.map +1 -0
- package/dist/codelens.js +12 -0
- package/dist/codelens.js.map +1 -1
- package/dist/codelens.test.js +5 -0
- package/dist/codelens.test.js.map +1 -1
- package/dist/colon-fence-kinds.test.d.ts +1 -0
- package/dist/colon-fence-kinds.test.js +128 -0
- package/dist/colon-fence-kinds.test.js.map +1 -0
- package/dist/colon-fences.d.ts +24 -0
- package/dist/colon-fences.js +174 -0
- package/dist/colon-fences.js.map +1 -0
- package/dist/colon-fences.test.d.ts +1 -0
- package/dist/colon-fences.test.js +23 -0
- package/dist/colon-fences.test.js.map +1 -0
- package/dist/completion.d.ts +6 -2
- package/dist/completion.js +84 -8
- package/dist/completion.js.map +1 -1
- package/dist/completion.test.js +7 -0
- package/dist/completion.test.js.map +1 -1
- package/dist/composite-figure-crossref.test.d.ts +1 -0
- package/dist/composite-figure-crossref.test.js +265 -0
- package/dist/composite-figure-crossref.test.js.map +1 -0
- package/dist/composite-figure.test.d.ts +1 -0
- package/dist/composite-figure.test.js +76 -0
- package/dist/composite-figure.test.js.map +1 -0
- package/dist/definition.d.ts +4 -2
- package/dist/definition.js +28 -5
- package/dist/definition.js.map +1 -1
- package/dist/dependencies.d.ts +15 -0
- package/dist/dependencies.js +59 -0
- package/dist/dependencies.js.map +1 -0
- package/dist/diagnostic-scheduler.d.ts +58 -0
- package/dist/diagnostic-scheduler.js +70 -0
- package/dist/diagnostic-scheduler.js.map +1 -0
- package/dist/diagnostic-scheduler.test.d.ts +1 -0
- package/dist/diagnostic-scheduler.test.js +75 -0
- package/dist/diagnostic-scheduler.test.js.map +1 -0
- package/dist/document-highlights.d.ts +2 -0
- package/dist/document-highlights.js +21 -0
- package/dist/document-highlights.js.map +1 -0
- package/dist/document-highlights.test.d.ts +1 -0
- package/dist/document-highlights.test.js +13 -0
- package/dist/document-highlights.test.js.map +1 -0
- package/dist/document-links.d.ts +3 -0
- package/dist/document-links.js +36 -0
- package/dist/document-links.js.map +1 -0
- package/dist/document-links.test.d.ts +1 -0
- package/dist/document-links.test.js +12 -0
- package/dist/document-links.test.js.map +1 -0
- package/dist/folding.d.ts +1 -0
- package/dist/folding.js +36 -1
- package/dist/folding.js.map +1 -1
- package/dist/folding.test.js +6 -1
- package/dist/folding.test.js.map +1 -1
- package/dist/format-corpus.test.d.ts +1 -0
- package/dist/format-corpus.test.js +16 -0
- package/dist/format-corpus.test.js.map +1 -0
- package/dist/format.d.ts +3 -0
- package/dist/format.js +38 -74
- package/dist/format.js.map +1 -1
- package/dist/format.test.js +27 -32
- package/dist/format.test.js.map +1 -1
- package/dist/hover.js +78 -19
- package/dist/hover.js.map +1 -1
- package/dist/include-cache.d.ts +26 -0
- package/dist/include-cache.js +74 -0
- package/dist/include-cache.js.map +1 -0
- package/dist/include-completion.d.ts +3 -0
- package/dist/include-completion.js +68 -0
- package/dist/include-completion.js.map +1 -0
- package/dist/include-completion.test.d.ts +1 -0
- package/dist/include-completion.test.js +15 -0
- package/dist/include-completion.test.js.map +1 -0
- package/dist/include-definition-denial.test.d.ts +1 -0
- package/dist/include-definition-denial.test.js +86 -0
- package/dist/include-definition-denial.test.js.map +1 -0
- package/dist/include-definition.d.ts +3 -0
- package/dist/include-definition.js +37 -0
- package/dist/include-definition.js.map +1 -0
- package/dist/include-features.test.d.ts +1 -0
- package/dist/include-features.test.js +133 -0
- package/dist/include-features.test.js.map +1 -0
- package/dist/include-path.d.ts +6 -0
- package/dist/include-path.js +31 -2
- package/dist/include-path.js.map +1 -1
- package/dist/include-settings.d.ts +2 -0
- package/dist/include-settings.js +1 -0
- package/dist/include-settings.js.map +1 -1
- package/dist/includes.d.ts +8 -0
- package/dist/includes.js +28 -7
- package/dist/includes.js.map +1 -1
- package/dist/inlay-hints.d.ts +3 -0
- package/dist/inlay-hints.js +43 -0
- package/dist/inlay-hints.js.map +1 -0
- package/dist/inlay-hints.test.d.ts +1 -0
- package/dist/inlay-hints.test.js +10 -0
- package/dist/inlay-hints.test.js.map +1 -0
- package/dist/lint-actions.d.ts +3 -0
- package/dist/lint-actions.js +90 -0
- package/dist/lint-actions.js.map +1 -0
- package/dist/lint-actions.test.d.ts +1 -0
- package/dist/lint-actions.test.js +31 -0
- package/dist/lint-actions.test.js.map +1 -0
- package/dist/no-git-dependencies.test.d.ts +1 -0
- package/dist/no-git-dependencies.test.js +243 -0
- package/dist/no-git-dependencies.test.js.map +1 -0
- package/dist/packaging.test.d.ts +1 -0
- package/dist/packaging.test.js +69 -0
- package/dist/packaging.test.js.map +1 -0
- package/dist/references.d.ts +2 -0
- package/dist/references.js +113 -21
- package/dist/references.js.map +1 -1
- package/dist/selection.d.ts +2 -0
- package/dist/selection.js +36 -0
- package/dist/selection.js.map +1 -0
- package/dist/selection.test.d.ts +1 -0
- package/dist/selection.test.js +10 -0
- package/dist/selection.test.js.map +1 -0
- package/dist/semantic.d.ts +5 -3
- package/dist/semantic.js +45 -4
- package/dist/semantic.js.map +1 -1
- package/dist/semantic.test.js +11 -0
- package/dist/semantic.test.js.map +1 -1
- package/dist/server-capabilities.test.d.ts +1 -0
- package/dist/server-capabilities.test.js +84 -0
- package/dist/server-capabilities.test.js.map +1 -0
- package/dist/server.js +353 -24
- package/dist/server.js.map +1 -1
- package/dist/settings.d.ts +11 -0
- package/dist/settings.js +50 -0
- package/dist/settings.js.map +1 -0
- package/dist/settings.test.d.ts +1 -0
- package/dist/settings.test.js +22 -0
- package/dist/settings.test.js.map +1 -0
- package/dist/spec-0-1-4-constructs.test.d.ts +1 -0
- package/dist/spec-0-1-4-constructs.test.js +101 -0
- package/dist/spec-0-1-4-constructs.test.js.map +1 -0
- package/dist/table-diagnostics.d.ts +3 -0
- package/dist/table-diagnostics.js +60 -0
- package/dist/table-diagnostics.js.map +1 -0
- package/dist/table-diagnostics.test.d.ts +1 -0
- package/dist/table-diagnostics.test.js +12 -0
- package/dist/table-diagnostics.test.js.map +1 -0
- package/dist/versioned-cache.d.ts +8 -0
- package/dist/versioned-cache.js +17 -0
- package/dist/versioned-cache.js.map +1 -0
- package/dist/versioned-cache.test.d.ts +1 -0
- package/dist/versioned-cache.test.js +13 -0
- package/dist/versioned-cache.test.js.map +1 -0
- package/dist/workspace-graph.d.ts +25 -0
- package/dist/workspace-graph.js +94 -0
- package/dist/workspace-graph.js.map +1 -0
- package/dist/workspace-graph.test.d.ts +1 -0
- package/dist/workspace-graph.test.js +31 -0
- package/dist/workspace-graph.test.js.map +1 -0
- package/dist/workspace-index.d.ts +40 -0
- package/dist/workspace-index.js +254 -0
- package/dist/workspace-index.js.map +1 -0
- package/dist/workspace-index.test.d.ts +1 -0
- package/dist/workspace-index.test.js +65 -0
- package/dist/workspace-index.test.js.map +1 -0
- package/dist/workspace-loader.d.ts +11 -0
- package/dist/workspace-loader.js +50 -0
- package/dist/workspace-loader.js.map +1 -0
- package/dist/workspace-loader.test.d.ts +1 -0
- package/dist/workspace-loader.test.js +19 -0
- package/dist/workspace-loader.test.js.map +1 -0
- package/package.json +4 -3
package/dist/includes.js
CHANGED
|
@@ -59,9 +59,22 @@ function warn(state, rule, message, at, file, detail) {
|
|
|
59
59
|
* encounter fixes the order, and a later successful read upgrades an entry
|
|
60
60
|
* first seen unresolved.
|
|
61
61
|
*/
|
|
62
|
-
function note(state, id, resolved) {
|
|
63
|
-
|
|
64
|
-
|
|
62
|
+
function note(state, id, resolved, watch) {
|
|
63
|
+
// A canonical/watchable path is the dependency identity when available.
|
|
64
|
+
// Two nested files can both name `missing.crv`; keying those by the raw
|
|
65
|
+
// spelling would collapse distinct future files into one watcher.
|
|
66
|
+
const key = watch ?? id;
|
|
67
|
+
const previous = state.dependencies.get(key);
|
|
68
|
+
if (!previous || resolved) {
|
|
69
|
+
state.dependencies.set(key, {
|
|
70
|
+
id,
|
|
71
|
+
resolved,
|
|
72
|
+
...(watch === undefined ? {} : { watch }),
|
|
73
|
+
});
|
|
74
|
+
}
|
|
75
|
+
else if (previous.watch === undefined && watch !== undefined) {
|
|
76
|
+
previous.watch = watch;
|
|
77
|
+
}
|
|
65
78
|
}
|
|
66
79
|
function visit(state, text, file, stack, depth, anchor) {
|
|
67
80
|
const directives = findDirectives(text, (part, start, end) => {
|
|
@@ -103,11 +116,11 @@ function visit(state, text, file, stack, depth, anchor) {
|
|
|
103
116
|
continue;
|
|
104
117
|
}
|
|
105
118
|
if (!resolved.ok) {
|
|
106
|
-
note(state, resolved.id, false);
|
|
119
|
+
note(state, resolved.id, false, resolved.watch);
|
|
107
120
|
warn(state, 'include-unresolved', `Include "${directive.path}" could not be resolved.`, at, file, resolved.denial);
|
|
108
121
|
continue;
|
|
109
122
|
}
|
|
110
|
-
note(state, resolved.id, true);
|
|
123
|
+
note(state, resolved.id, true, resolved.watch);
|
|
111
124
|
if (stack.includes(resolved.id)) {
|
|
112
125
|
warn(state, 'include-cycle', `Include cycle detected for "${directive.path}".`, at, file);
|
|
113
126
|
continue;
|
|
@@ -121,6 +134,12 @@ function visit(state, text, file, stack, depth, anchor) {
|
|
|
121
134
|
warn(state, 'include-budget', `Include byte budget exceeded by "${directive.path}".`, at, file);
|
|
122
135
|
continue;
|
|
123
136
|
}
|
|
137
|
+
if (!state.documents.has(resolved.id)) {
|
|
138
|
+
state.documents.set(resolved.id, {
|
|
139
|
+
source: resolved.source,
|
|
140
|
+
...(resolved.version === undefined ? {} : { version: resolved.version }),
|
|
141
|
+
});
|
|
142
|
+
}
|
|
124
143
|
visit(state, resolved.source, resolved.id, [...stack, resolved.id], depth + 1, at);
|
|
125
144
|
}
|
|
126
145
|
}
|
|
@@ -135,7 +154,7 @@ function visit(state, text, file, stack, depth, anchor) {
|
|
|
135
154
|
*/
|
|
136
155
|
export function resolveIncludes(source, options = {}) {
|
|
137
156
|
if (!options.resolver)
|
|
138
|
-
return { warnings: [], dependencies: [], bytes: 0 };
|
|
157
|
+
return { warnings: [], dependencies: [], bytes: 0, documents: [] };
|
|
139
158
|
const normalized = source.replace(/\r\n?/g, '\n');
|
|
140
159
|
const state = {
|
|
141
160
|
resolver: options.resolver,
|
|
@@ -145,14 +164,16 @@ export function resolveIncludes(source, options = {}) {
|
|
|
145
164
|
usedBytes: 0,
|
|
146
165
|
warnings: [],
|
|
147
166
|
dependencies: new Map(),
|
|
167
|
+
documents: new Map(),
|
|
148
168
|
lineStarts: lineStarts(normalized),
|
|
149
169
|
};
|
|
150
170
|
const rootStack = options.sourcePath !== undefined ? [options.sourcePath] : [];
|
|
151
171
|
visit(state, normalized, options.sourcePath, rootStack, 0, null);
|
|
152
172
|
return {
|
|
153
173
|
warnings: state.warnings,
|
|
154
|
-
dependencies: [...state.dependencies
|
|
174
|
+
dependencies: [...state.dependencies.values()],
|
|
155
175
|
bytes: state.usedBytes,
|
|
176
|
+
documents: [...state.documents].map(([id, child]) => ({ id, ...child })),
|
|
156
177
|
};
|
|
157
178
|
}
|
|
158
179
|
//# sourceMappingURL=includes.js.map
|
package/dist/includes.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"includes.js","sourceRoot":"","sources":["../src/includes.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;GAkBG;AACH,OAAO,EAAE,cAAc,EAAE,MAAM,wBAAwB,CAAA;
|
|
1
|
+
{"version":3,"file":"includes.js","sourceRoot":"","sources":["../src/includes.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import { InlayHintKind } from 'vscode-languageserver/node.js';
|
|
2
|
+
import { parse, resolve } from '@markup-carve/carve';
|
|
3
|
+
/** Quiet, author-value hints. Clients can disable the provider globally. */
|
|
4
|
+
export function inlayHints(source, requested) {
|
|
5
|
+
const hints = [];
|
|
6
|
+
try {
|
|
7
|
+
const doc = resolve(parse(source, { positions: true }));
|
|
8
|
+
walk(doc.children, (node) => {
|
|
9
|
+
if (node.type !== 'heading' || !node.pos || !node.attrs?.id)
|
|
10
|
+
return;
|
|
11
|
+
const line = node.pos.startLine - 1;
|
|
12
|
+
if (requested && (line < requested.start.line || line > requested.end.line))
|
|
13
|
+
return;
|
|
14
|
+
const lines = source.replace(/\r\n?/g, '\n').split('\n');
|
|
15
|
+
const text = lines[line] ?? '';
|
|
16
|
+
// An authored id is already visible; the useful hint is the generated one.
|
|
17
|
+
if (text.includes(`{#${node.attrs.id}`) || (lines[line - 1] ?? '').includes(`#${node.attrs.id}`))
|
|
18
|
+
return;
|
|
19
|
+
hints.push({
|
|
20
|
+
position: { line, character: text.length },
|
|
21
|
+
label: ` #${node.attrs.id}`,
|
|
22
|
+
kind: InlayHintKind.Type,
|
|
23
|
+
paddingLeft: true,
|
|
24
|
+
tooltip: 'Generated heading id',
|
|
25
|
+
});
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
catch {
|
|
29
|
+
return [];
|
|
30
|
+
}
|
|
31
|
+
return hints;
|
|
32
|
+
}
|
|
33
|
+
function walk(nodes, visit) {
|
|
34
|
+
for (const node of nodes) {
|
|
35
|
+
visit(node);
|
|
36
|
+
if ('children' in node && Array.isArray(node.children))
|
|
37
|
+
walk(node.children.filter(isBlock), visit);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
function isBlock(value) {
|
|
41
|
+
return Boolean(value && typeof value === 'object' && 'type' in value);
|
|
42
|
+
}
|
|
43
|
+
//# sourceMappingURL=inlay-hints.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"inlay-hints.js","sourceRoot":"","sources":["../src/inlay-hints.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAA8B,MAAM,+BAA+B,CAAA;AACzF,OAAO,EAAE,KAAK,EAAE,OAAO,EAAkB,MAAM,qBAAqB,CAAA;AAEpE,4EAA4E;AAC5E,MAAM,UAAU,UAAU,CAAC,MAAc,EAAE,SAAiB;IAC1D,MAAM,KAAK,GAAgB,EAAE,CAAA;IAC7B,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,OAAO,CAAC,KAAK,CAAC,MAAM,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC,CAAA;QACvD,IAAI,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC,IAAI,EAAE,EAAE;YAC1B,IAAI,IAAI,CAAC,IAAI,KAAK,SAAS,IAAI,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE,EAAE;gBAAE,OAAM;YACnE,MAAM,IAAI,GAAG,IAAI,CAAC,GAAG,CAAC,SAAS,GAAG,CAAC,CAAA;YACnC,IAAI,SAAS,IAAI,CAAC,IAAI,GAAG,SAAS,CAAC,KAAK,CAAC,IAAI,IAAI,IAAI,GAAG,SAAS,CAAC,GAAG,CAAC,IAAI,CAAC;gBAAE,OAAM;YACnF,MAAM,KAAK,GAAG,MAAM,CAAC,OAAO,CAAC,QAAQ,EAAE,IAAI,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAA;YACxD,MAAM,IAAI,GAAG,KAAK,CAAC,IAAI,CAAC,IAAI,EAAE,CAAA;YAC9B,2EAA2E;YAC3E,IAAI,IAAI,CAAC,QAAQ,CAAC,KAAK,IAAI,CAAC,KAAK,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,QAAQ,CAAC,IAAI,IAAI,CAAC,KAAK,CAAC,EAAE,EAAE,CAAC;gBAAE,OAAM;YACxG,KAAK,CAAC,IAAI,CAAC;gBACT,QAAQ,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,IAAI,CAAC,MAAM,EAAE;gBAC1C,KAAK,EAAE,MAAM,IAAI,CAAC,KAAK,CAAC,EAAE,EAAE;gBAC5B,IAAI,EAAE,aAAa,CAAC,IAAI;gBACxB,WAAW,EAAE,IAAI;gBACjB,OAAO,EAAE,sBAAsB;aAChC,CAAC,CAAA;QACJ,CAAC,CAAC,CAAA;IACJ,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,CAAA;IACX,CAAC;IACD,OAAO,KAAK,CAAA;AACd,CAAC;AAED,SAAS,IAAI,CAAC,KAAkB,EAAE,KAAgC;IAChE,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,KAAK,CAAC,IAAI,CAAC,CAAA;QACX,IAAI,UAAU,IAAI,IAAI,IAAI,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,QAAQ,CAAC;YAAE,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,MAAM,CAAC,OAAO,CAAC,EAAE,KAAK,CAAC,CAAA;IACpG,CAAC;AACH,CAAC;AAED,SAAS,OAAO,CAAC,KAAc;IAC7B,OAAO,OAAO,CAAC,KAAK,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,MAAM,IAAI,KAAK,CAAC,CAAA;AACvE,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import test from 'node:test';
|
|
2
|
+
import assert from 'node:assert/strict';
|
|
3
|
+
import { inlayHints } from './inlay-hints.js';
|
|
4
|
+
test('shows generated heading ids and omits authored ids', () => {
|
|
5
|
+
const generated = inlayHints('# Hello world\n');
|
|
6
|
+
assert.equal(generated.length, 1);
|
|
7
|
+
assert.match(String(generated[0].label).toLocaleLowerCase(), /hello-world/);
|
|
8
|
+
assert.equal(inlayHints('{#custom}\n# Hello world\n').length, 0);
|
|
9
|
+
});
|
|
10
|
+
//# sourceMappingURL=inlay-hints.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"inlay-hints.test.js","sourceRoot":"","sources":["../src/inlay-hints.test.ts"],"names":[],"mappings":"AAAA,OAAO,IAAI,MAAM,WAAW,CAAA;AAC5B,OAAO,MAAM,MAAM,oBAAoB,CAAA;AACvC,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAA;AAE7C,IAAI,CAAC,oDAAoD,EAAE,GAAG,EAAE;IAC9D,MAAM,SAAS,GAAG,UAAU,CAAC,iBAAiB,CAAC,CAAA;IAC/C,MAAM,CAAC,KAAK,CAAC,SAAS,CAAC,MAAM,EAAE,CAAC,CAAC,CAAA;IACjC,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,CAAE,CAAC,KAAK,CAAC,CAAC,iBAAiB,EAAE,EAAE,aAAa,CAAC,CAAA;IAC5E,MAAM,CAAC,KAAK,CAAC,UAAU,CAAC,4BAA4B,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,CAAA;AAClE,CAAC,CAAC,CAAA"}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import { CodeActionKind } from 'vscode-languageserver/node.js';
|
|
2
|
+
/** Safe, local rewrites for diagnostics emitted by lintCarve. */
|
|
3
|
+
export function lintCodeActions(uri, source, diagnostics) {
|
|
4
|
+
const lines = source.replace(/\r\n?/g, '\n').split('\n');
|
|
5
|
+
const actions = [];
|
|
6
|
+
for (const diagnostic of diagnostics) {
|
|
7
|
+
const code = String(diagnostic.code ?? '');
|
|
8
|
+
const line = lines[diagnostic.range.start.line] ?? '';
|
|
9
|
+
let edit = null;
|
|
10
|
+
let title = '';
|
|
11
|
+
if (code === 'raw-block-syntax') {
|
|
12
|
+
const match = /^(\s*`{3,})raw(?: +([^\s]+))?/.exec(line);
|
|
13
|
+
if (match) {
|
|
14
|
+
const replacement = `${match[1]}=${match[2] ?? 'html'}`;
|
|
15
|
+
edit = replace(diagnostic.range.start.line, match[0].length, replacement);
|
|
16
|
+
title = 'Convert to a Carve raw fence';
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
else if (code === 'blockquote-marker-without-space') {
|
|
20
|
+
const marker = /^\s*>/.exec(line);
|
|
21
|
+
if (marker) {
|
|
22
|
+
const character = marker[0].length;
|
|
23
|
+
edit = { range: point(diagnostic.range.start.line, character), newText: ' ' };
|
|
24
|
+
title = 'Insert the block-quote separator';
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
else if (code === 'table-alignment-run-padding') {
|
|
28
|
+
const marker = /\|=?[<>~^v]{1,2}(?=\S)/.exec(line);
|
|
29
|
+
if (marker) {
|
|
30
|
+
const character = marker.index + marker[0].length;
|
|
31
|
+
edit = { range: point(diagnostic.range.start.line, character), newText: ' ' };
|
|
32
|
+
title = 'Terminate the table alignment run with a space';
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
else if (code === 'unresolved-footnote') {
|
|
36
|
+
const match = /\[\^([^\]]+)\]/.exec(line.slice(diagnostic.range.start.character)) ?? /\[\^([^\]]+)\]/.exec(line);
|
|
37
|
+
if (match) {
|
|
38
|
+
edit = append(source, `\n[^${match[1]}]: `);
|
|
39
|
+
title = `Create footnote definition “${match[1]}”`;
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
else if (code === 'unresolved-reference-link') {
|
|
43
|
+
const match = /\]\[([^\]]+)\]/.exec(line.slice(diagnostic.range.start.character)) ?? /\]\[([^\]]+)\]/.exec(line);
|
|
44
|
+
if (match && match[1]) {
|
|
45
|
+
edit = append(source, `\n[${match[1]}]: `);
|
|
46
|
+
title = `Create link definition “${match[1]}”`;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
else if (code === 'colon-fence-length-mismatch') {
|
|
50
|
+
const authored = /^\s*(:{3,})/.exec(line);
|
|
51
|
+
const expected = Number(diagnostic.data?.expectedWidth);
|
|
52
|
+
if (authored && Number.isInteger(expected) && expected >= 3) {
|
|
53
|
+
const start = line.indexOf(authored[1]);
|
|
54
|
+
const range = { start: { line: diagnostic.range.start.line, character: start }, end: { line: diagnostic.range.start.line, character: start + authored[1].length } };
|
|
55
|
+
actions.push({
|
|
56
|
+
title: `Resize to ${expected} colons and close the container`, kind: CodeActionKind.QuickFix,
|
|
57
|
+
diagnostics: [diagnostic], isPreferred: true,
|
|
58
|
+
edit: { changes: { [uri]: [{ range, newText: ':'.repeat(expected) }] } },
|
|
59
|
+
});
|
|
60
|
+
actions.push({
|
|
61
|
+
title: 'Preserve the colon run as literal text', kind: CodeActionKind.QuickFix,
|
|
62
|
+
diagnostics: [diagnostic], isPreferred: false,
|
|
63
|
+
edit: { changes: { [uri]: [{ range: point(diagnostic.range.start.line, start), newText: '\\' }] } },
|
|
64
|
+
});
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
if (!edit)
|
|
68
|
+
continue;
|
|
69
|
+
actions.push({
|
|
70
|
+
title,
|
|
71
|
+
kind: CodeActionKind.QuickFix,
|
|
72
|
+
diagnostics: [diagnostic],
|
|
73
|
+
isPreferred: true,
|
|
74
|
+
edit: { changes: { [uri]: [edit] } },
|
|
75
|
+
});
|
|
76
|
+
}
|
|
77
|
+
return actions;
|
|
78
|
+
}
|
|
79
|
+
function append(source, newText) {
|
|
80
|
+
const lines = source.replace(/\r\n?/g, '\n').split('\n');
|
|
81
|
+
const line = Math.max(0, lines.length - 1);
|
|
82
|
+
return { range: point(line, lines[line]?.length ?? 0), newText };
|
|
83
|
+
}
|
|
84
|
+
function point(line, character) {
|
|
85
|
+
return { start: { line, character }, end: { line, character } };
|
|
86
|
+
}
|
|
87
|
+
function replace(line, end, newText) {
|
|
88
|
+
return { range: { start: { line, character: 0 }, end: { line, character: end } }, newText };
|
|
89
|
+
}
|
|
90
|
+
//# sourceMappingURL=lint-actions.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"lint-actions.js","sourceRoot":"","sources":["../src/lint-actions.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import test from 'node:test';
|
|
2
|
+
import assert from 'node:assert/strict';
|
|
3
|
+
import { lintCodeActions } from './lint-actions.js';
|
|
4
|
+
const diagnostic = (code) => ({
|
|
5
|
+
code,
|
|
6
|
+
message: code,
|
|
7
|
+
range: { start: { line: 0, character: 0 }, end: { line: 0, character: 1 } },
|
|
8
|
+
});
|
|
9
|
+
test('offers safe lint quick fixes', () => {
|
|
10
|
+
const raw = lintCodeActions('file:///a.crv', '```raw html\n', [diagnostic('raw-block-syntax')]);
|
|
11
|
+
assert.equal(raw[0]?.edit?.changes?.['file:///a.crv']?.[0]?.newText, '```=html');
|
|
12
|
+
const quote = lintCodeActions('file:///a.crv', '>text\n', [diagnostic('blockquote-marker-without-space')]);
|
|
13
|
+
assert.equal(quote[0]?.edit?.changes?.['file:///a.crv']?.[0]?.newText, ' ');
|
|
14
|
+
});
|
|
15
|
+
test('creates missing footnote and link-reference definitions', () => {
|
|
16
|
+
const footnote = lintCodeActions('file:///a.crv', 'See [^n].\n', [diagnostic('unresolved-footnote')]);
|
|
17
|
+
assert.match(footnote[0]?.edit?.changes?.['file:///a.crv']?.[0]?.newText ?? '', /\[\^n\]:/);
|
|
18
|
+
const link = lintCodeActions('file:///a.crv', 'See [x][r].\n', [diagnostic('unresolved-reference-link')]);
|
|
19
|
+
assert.match(link[0]?.edit?.changes?.['file:///a.crv']?.[0]?.newText ?? '', /\[r\]:/);
|
|
20
|
+
});
|
|
21
|
+
test('offers both explicit intentions for a near colon closer', () => {
|
|
22
|
+
const near = { ...diagnostic('colon-fence-length-mismatch'), data: { expectedWidth: 4 } };
|
|
23
|
+
const actions = lintCodeActions('file:///a.crv', ':::\n', [near]);
|
|
24
|
+
assert.deepEqual(actions.map((action) => action.title), [
|
|
25
|
+
'Resize to 4 colons and close the container',
|
|
26
|
+
'Preserve the colon run as literal text',
|
|
27
|
+
]);
|
|
28
|
+
assert.equal(actions[0]?.edit?.changes?.['file:///a.crv']?.[0]?.newText, '::::');
|
|
29
|
+
assert.equal(actions[1]?.edit?.changes?.['file:///a.crv']?.[0]?.newText, '\\');
|
|
30
|
+
});
|
|
31
|
+
//# sourceMappingURL=lint-actions.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"lint-actions.test.js","sourceRoot":"","sources":["../src/lint-actions.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,243 @@
|
|
|
1
|
+
import assert from 'node:assert/strict';
|
|
2
|
+
import { spawnSync } from 'node:child_process';
|
|
3
|
+
import { mkdtempSync, readFileSync, rmSync, writeFileSync } from 'node:fs';
|
|
4
|
+
import { tmpdir } from 'node:os';
|
|
5
|
+
import { join } from 'node:path';
|
|
6
|
+
import test, { after } from 'node:test';
|
|
7
|
+
import { fileURLToPath } from 'node:url';
|
|
8
|
+
/**
|
|
9
|
+
* The publish-time guard must detect a git dependency by what a spec IS NOT.
|
|
10
|
+
*
|
|
11
|
+
* WHY THIS FILE EXISTS. `ci.yml` already runs `tools/no-git-dependencies.mjs` on
|
|
12
|
+
* every pull request - but only against the manifest committed here, which is
|
|
13
|
+
* clean. So that step passes with the guard's logic in ANY state: delete the
|
|
14
|
+
* whole rule and it still exits zero, because there is nothing in this manifest
|
|
15
|
+
* for it to find. Running the script against a MUTATED manifest is what makes
|
|
16
|
+
* the logic load-bearing rather than the manifest.
|
|
17
|
+
*
|
|
18
|
+
* WHY THE GUARD WAS WIDENED. The rule was already an inversion, but the "not"
|
|
19
|
+
* was still spelled as a list of protocols plus a slash test, and both miss
|
|
20
|
+
* npm's scp-style URL: it carries no protocol, and when the repository sits at
|
|
21
|
+
* the root of its host it carries no slash either. That is the third hole in
|
|
22
|
+
* this guard family in this org - `git+https://` in pandoc-carve, `github:`
|
|
23
|
+
* here, then the bare `owner/repo#ref` shorthand - and each earlier fix added
|
|
24
|
+
* the next spelling to the list, which is why there was a next one (#123).
|
|
25
|
+
* markup-carve/carve-grammars#299 replaced the tail of the list with a catch-all
|
|
26
|
+
* over the characters no registry range can contain; this is that shape.
|
|
27
|
+
*
|
|
28
|
+
* Both directions are asserted. A rejection has to exit non-zero AND name the
|
|
29
|
+
* field, quote the spec and give a reason; an acceptance has to exit zero. So a
|
|
30
|
+
* guard stuck at always-pass and a guard stuck at always-fail each fail here,
|
|
31
|
+
* which is the property the CI step alone does not have.
|
|
32
|
+
*
|
|
33
|
+
* The `npm:` alias row is the near miss that keeps the rule from collapsing into
|
|
34
|
+
* "reject anything with a slash or an at-sign". An alias resolves from the
|
|
35
|
+
* registry, so rejecting it would be an over-broad fix that breaks a manifest
|
|
36
|
+
* that is fine - and an over-rejecting guard gets switched off by whoever hits
|
|
37
|
+
* it, which is worse than the hole.
|
|
38
|
+
*/
|
|
39
|
+
const root = fileURLToPath(new URL('..', import.meta.url));
|
|
40
|
+
const guard = join(root, 'tools', 'no-git-dependencies.mjs');
|
|
41
|
+
const manifestPath = join(root, 'package.json');
|
|
42
|
+
const baseline = JSON.parse(readFileSync(manifestPath, 'utf8'));
|
|
43
|
+
const scratch = mkdtempSync(join(tmpdir(), 'carve-lsp-guard-'));
|
|
44
|
+
after(() => rmSync(scratch, { recursive: true, force: true }));
|
|
45
|
+
/** Run the REAL script against a manifest written to a scratch file. */
|
|
46
|
+
const runGuard = (manifest) => {
|
|
47
|
+
const path = join(scratch, 'package.json');
|
|
48
|
+
writeFileSync(path, JSON.stringify(manifest, null, 2), 'utf8');
|
|
49
|
+
const run = spawnSync(process.execPath, [guard, path], { encoding: 'utf8' });
|
|
50
|
+
assert.equal(run.error, undefined, `spawning the guard failed: ${run.error}`);
|
|
51
|
+
assert.notEqual(run.status, null, 'the guard was killed by a signal rather than exiting');
|
|
52
|
+
return { status: run.status, out: `${run.stdout}${run.stderr}` };
|
|
53
|
+
};
|
|
54
|
+
const ENGINE = '@markup-carve/carve';
|
|
55
|
+
const withDep = (spec) => ({
|
|
56
|
+
...baseline,
|
|
57
|
+
dependencies: { ...baseline.dependencies, [ENGINE]: spec },
|
|
58
|
+
});
|
|
59
|
+
/**
|
|
60
|
+
* Each row: what the spec is, the manifest carrying it, and whether a consumer's
|
|
61
|
+
* npm could install it from the registry alone. Cross-checked while writing
|
|
62
|
+
* against `npm-package-arg`, the module npm itself classifies a spec with -
|
|
63
|
+
* every `reject` row is one npa either calls `git` or refuses to classify at
|
|
64
|
+
* all, and every `accept` row is one it calls version, range, tag or alias.
|
|
65
|
+
*/
|
|
66
|
+
const MATRIX = [
|
|
67
|
+
['a github: pin', withDep('github:markup-carve/carve-js#61f824d'), 'reject'],
|
|
68
|
+
[
|
|
69
|
+
'a git+https:// pin',
|
|
70
|
+
withDep('git+https://github.com/markup-carve/carve-js.git#61f824d'),
|
|
71
|
+
'reject',
|
|
72
|
+
],
|
|
73
|
+
[
|
|
74
|
+
'a bare owner/repo#sha shorthand',
|
|
75
|
+
withDep('markup-carve/carve-js#61f824d5d5724bfaa26dd07dc5c159249a66c977'),
|
|
76
|
+
'reject',
|
|
77
|
+
],
|
|
78
|
+
[
|
|
79
|
+
'a git spec in optionalDependencies',
|
|
80
|
+
{ ...baseline, optionalDependencies: { 'some-tool': 'github:markup-carve/some-tool#abc123' } },
|
|
81
|
+
'reject',
|
|
82
|
+
],
|
|
83
|
+
// The two rows this ticket is about. The first still carries a slash, so the
|
|
84
|
+
// previous version caught it by accident; the second does not, and was
|
|
85
|
+
// accepted.
|
|
86
|
+
['an scp-style git URL', withDep('git@github.com:markup-carve/carve-js.git'), 'reject'],
|
|
87
|
+
['an scp-style git URL with no slash', withDep('git@example.com:repo.git'), 'reject'],
|
|
88
|
+
// Caught by the catch-all rather than by a pattern named for them, which is
|
|
89
|
+
// the point of the catch-all: neither was anticipated and both leaked before.
|
|
90
|
+
['a workspace: protocol spec', withDep('workspace:*'), 'reject'],
|
|
91
|
+
['a catalog: protocol spec', withDep('catalog:default'), 'reject'],
|
|
92
|
+
['an exact version', withDep('0.1.4'), 'accept'],
|
|
93
|
+
['a caret range', withDep('^0.1.4'), 'accept'],
|
|
94
|
+
['a dist-tag', withDep('latest'), 'accept'],
|
|
95
|
+
['a compound range', withDep('>=0.1.4 <0.2.0'), 'accept'],
|
|
96
|
+
['a prerelease version', withDep('0.2.0-beta.1'), 'accept'],
|
|
97
|
+
['an npm: alias', withDep('npm:@markup-carve/carve@^0.1.4'), 'accept'],
|
|
98
|
+
/*
|
|
99
|
+
* ALIAS TARGETS (#126, markup-carve/carve-grammars#302). `npm:` used to
|
|
100
|
+
* return early and clean - an unconditional ALLOW on a prefix, which is the
|
|
101
|
+
* same denylist mistake as the URL-prefix list this file replaced, pointing
|
|
102
|
+
* the other way: it never asked what the alias pointed AT.
|
|
103
|
+
* `npm-package-arg` refuses every reject row here.
|
|
104
|
+
*
|
|
105
|
+
* BOTH DIRECTIONS, and the accept rows are the load-bearing half. The way a
|
|
106
|
+
* fix for this goes wrong is over-rejection - the rule collapsing into
|
|
107
|
+
* "reject anything with a slash or an at-sign" - and an over-rejecting guard
|
|
108
|
+
* is worse than the hole, because the next person who hits it switches the
|
|
109
|
+
* guard off.
|
|
110
|
+
*/
|
|
111
|
+
['an npm: alias to a plain package', withDep('npm:some-pkg'), 'accept'],
|
|
112
|
+
['an npm: alias to a range', withDep('npm:some-pkg@^1.0.0'), 'accept'],
|
|
113
|
+
['an npm: alias to a scoped package', withDep('npm:@scope/pkg@^1.0.0'), 'accept'],
|
|
114
|
+
['an npm: alias to a dist-tag', withDep('npm:some-pkg@latest'), 'accept'],
|
|
115
|
+
// `npm:foo@` is npm's `*`, the same alias as `npm:foo`.
|
|
116
|
+
['an npm: alias with an empty target', withDep('npm:some-pkg@'), 'accept'],
|
|
117
|
+
// No separating `@` at all, so there is no target to recurse into - the
|
|
118
|
+
// whole remainder is the alias's NAME, and that is what has to be refused.
|
|
119
|
+
['an npm: alias whose name is a git URL', withDep('npm:git+https://x/y'), 'reject'],
|
|
120
|
+
['an npm: alias whose name is a github: spec', withDep('npm:github:owner/repo'), 'reject'],
|
|
121
|
+
['an npm: alias whose name is a shorthand', withDep('npm:owner/repo'), 'reject'],
|
|
122
|
+
// With a target, which recurses back through the same rule.
|
|
123
|
+
['an npm: alias targeting github:', withDep('npm:foo@github:owner/repo'), 'reject'],
|
|
124
|
+
['an npm: alias targeting git+https://', withDep('npm:foo@git+https://x/y.git'), 'reject'],
|
|
125
|
+
['an npm: alias targeting a shorthand', withDep('npm:foo@owner/repo'), 'reject'],
|
|
126
|
+
['an npm: alias targeting file:', withDep('npm:foo@file:../x'), 'reject'],
|
|
127
|
+
['an npm: alias targeting workspace:', withDep('npm:foo@workspace:*'), 'reject'],
|
|
128
|
+
['an npm: alias with no name at all', withDep('npm:'), 'reject'],
|
|
129
|
+
['a nested npm: alias', withDep('npm:foo@npm:bar@1'), 'reject'],
|
|
130
|
+
/*
|
|
131
|
+
* PUNCTUATION npm REFUSES, found by `codex review` on #126 one layer under
|
|
132
|
+
* the alias hole it was reviewing. npm rejects a package name or a dist-tag
|
|
133
|
+
* carrying "any characters that encodeURIComponent encodes" - its own words -
|
|
134
|
+
* and the guard accepted all of these.
|
|
135
|
+
*
|
|
136
|
+
* The accept rows below it are why this is two character rules and not one. A
|
|
137
|
+
* semver RANGE is not held to the tag rule: `^1.0.0` and `1.0.0 || 2.0.0`
|
|
138
|
+
* carry characters encodeURIComponent encodes, and rejecting those would be
|
|
139
|
+
* the over-reach this guard is written to avoid. So does `my!tag`, which is a
|
|
140
|
+
* perfectly valid dist-tag and looks like nonsense.
|
|
141
|
+
*/
|
|
142
|
+
['an alias name with a fragment', withDep('npm:foo#bar'), 'reject'],
|
|
143
|
+
['an alias name with a query', withDep('npm:foo?bar'), 'reject'],
|
|
144
|
+
['an alias name with a percent', withDep('npm:foo%bar'), 'reject'],
|
|
145
|
+
['an alias scope with a fragment', withDep('npm:@scope#bar/pkg'), 'reject'],
|
|
146
|
+
['an alias targeting a bad tag', withDep('npm:foo@#bad'), 'reject'],
|
|
147
|
+
['a bare spec with a fragment', withDep('#bad'), 'reject'],
|
|
148
|
+
['a bare spec with braces', withDep('{x}'), 'reject'],
|
|
149
|
+
['a bare spec with a comma', withDep('a,b'), 'reject'],
|
|
150
|
+
['a dist-tag that only looks odd', withDep('my!tag'), 'accept'],
|
|
151
|
+
['a dist-tag with parentheses', withDep('a(b)'), 'accept'],
|
|
152
|
+
['a version with build metadata', withDep('1.0.0+build.1'), 'accept'],
|
|
153
|
+
['an alias to a tilde-led name', withDep('npm:~foo'), 'accept'],
|
|
154
|
+
// A range's whitespace need not be a space, which is why the class above
|
|
155
|
+
// admits all of it. Also found by `codex review`, and the reason the guard is
|
|
156
|
+
// knowingly lenient on one spelling - see the whitespace note in the script.
|
|
157
|
+
['a range separated by a tab', withDep('>=1\t<2'), 'accept'],
|
|
158
|
+
['a range broken across lines', withDep('1.0.0\n|| 2.0.0'), 'accept'],
|
|
159
|
+
// A scope with no package. Also `codex review`, and the third thing it found
|
|
160
|
+
// under this one change: every PATTERN written for an alias name grew a
|
|
161
|
+
// fallback branch that let something through, which is why the shipped rule
|
|
162
|
+
// counts `/`-separated pieces instead of matching a shape.
|
|
163
|
+
['a scope with no package', withDep('npm:@foo'), 'reject'],
|
|
164
|
+
['a scope with no package and a target', withDep('npm:@foo@1'), 'reject'],
|
|
165
|
+
['a scoped name with a third segment', withDep('npm:@scope/pkg/extra'), 'reject'],
|
|
166
|
+
// npm's leading `.`/`_` rule is on the WHOLE name, so it never reaches a
|
|
167
|
+
// scope - the fourth thing `codex review` found here, and the second
|
|
168
|
+
// over-rejection. All three of the accept rows were rejected by the version
|
|
169
|
+
// that applied the rule per segment.
|
|
170
|
+
['an alias to an underscored scope', withDep('npm:@_scope/pkg'), 'accept'],
|
|
171
|
+
['an alias to an underscored package in a scope', withDep('npm:@scope/_pkg'), 'accept'],
|
|
172
|
+
['an alias to a dotted scope', withDep('npm:@.scope/pkg'), 'accept'],
|
|
173
|
+
['an alias to a dotted package in a scope', withDep('npm:@scope/.pkg'), 'reject'],
|
|
174
|
+
['an alias to an underscored bare name', withDep('npm:_pkg'), 'reject'],
|
|
175
|
+
// npm reads the alias prefix case-insensitively, and a case-sensitive test
|
|
176
|
+
// sent `NPM:foo` down to the catch-all where its `:` got it rejected. The
|
|
177
|
+
// fifth thing `codex review` found, and the third over-rejection - it only
|
|
178
|
+
// became visible once there was something past the prefix worth reaching.
|
|
179
|
+
['an upper-case alias prefix', withDep('NPM:some-pkg'), 'accept'],
|
|
180
|
+
['a mixed-case alias prefix', withDep('Npm:some-pkg@^1.0.0'), 'accept'],
|
|
181
|
+
['a nested alias in upper case', withDep('npm:foo@NPM:bar'), 'reject'],
|
|
182
|
+
// A target carrying leading whitespace, which slipped past the nested-alias
|
|
183
|
+
// test and was then trimmed and read as a good alias one frame down. The
|
|
184
|
+
// sixth and last thing `codex review` found on this change.
|
|
185
|
+
['a nested alias behind a space', withDep('npm:foo@ npm:bar'), 'reject'],
|
|
186
|
+
['a git target behind a space', withDep('npm:foo@ github:o/r'), 'reject'],
|
|
187
|
+
['a range behind a space', withDep('npm:foo@ ^1.0.0'), 'accept'],
|
|
188
|
+
// A leading dot is a local path to npm, whatever follows it - `.`, `..`,
|
|
189
|
+
// `./x` and `.x` are all directories, and none reaches the registry.
|
|
190
|
+
['a bare dot', withDep('.'), 'reject'],
|
|
191
|
+
['a parent directory', withDep('..'), 'reject'],
|
|
192
|
+
['a relative path', withDep('./local'), 'reject'],
|
|
193
|
+
['a dot-led tag lookalike', withDep('.x'), 'reject'],
|
|
194
|
+
['an alias targeting a directory', withDep('npm:foo@.'), 'reject'],
|
|
195
|
+
// The near miss on that rule: a dot INSIDE a tag is ordinary.
|
|
196
|
+
['a tag ending in a dot', withDep('x.'), 'accept'],
|
|
197
|
+
];
|
|
198
|
+
for (const [label, manifest, verdict] of MATRIX) {
|
|
199
|
+
test(`${verdict}s ${label}`, () => {
|
|
200
|
+
const { status, out } = runGuard(manifest);
|
|
201
|
+
if (verdict === 'accept') {
|
|
202
|
+
assert.equal(status, 0, `the guard rejected ${label}, which installs fine:\n${out}`);
|
|
203
|
+
return;
|
|
204
|
+
}
|
|
205
|
+
assert.notEqual(status, 0, `the guard passed ${label}, which needs git at install time`);
|
|
206
|
+
// A non-zero exit alone would also come from a crash, so the report has to
|
|
207
|
+
// name what it found.
|
|
208
|
+
const optional = (manifest.optionalDependencies ?? {});
|
|
209
|
+
const [field, spec] = Object.keys(optional).length
|
|
210
|
+
? ['optionalDependencies', Object.values(optional)[0]]
|
|
211
|
+
: ['dependencies', manifest.dependencies[ENGINE]];
|
|
212
|
+
assert.ok(out.includes(field), `the report does not name the field it found it in:\n${out}`);
|
|
213
|
+
assert.ok(out.includes(spec), `the report does not quote the offending spec:\n${out}`);
|
|
214
|
+
assert.match(out, /registry/i, `the report does not say why:\n${out}`);
|
|
215
|
+
});
|
|
216
|
+
}
|
|
217
|
+
test("accepts this repo's own manifest", () => {
|
|
218
|
+
// The engine is declared as the exact registry version the v0.1.4 draft is
|
|
219
|
+
// cut from. This row is what keeps that publishable: a widening of the rule
|
|
220
|
+
// that also rejected the committed manifest would block the release.
|
|
221
|
+
const run = spawnSync(process.execPath, [guard, manifestPath], { encoding: 'utf8' });
|
|
222
|
+
assert.equal(run.status, 0, `the guard rejects the manifest that is committed here:\n${run.stdout}${run.stderr}`);
|
|
223
|
+
});
|
|
224
|
+
test('devDependencies are left alone', () => {
|
|
225
|
+
// A contributor's git devDependency costs a consumer nothing, and rejecting it
|
|
226
|
+
// would be the same over-reach the npm: alias row guards against.
|
|
227
|
+
const { status } = runGuard({
|
|
228
|
+
...baseline,
|
|
229
|
+
devDependencies: { ...baseline.devDependencies, something: 'github:someone/something#abc' },
|
|
230
|
+
});
|
|
231
|
+
assert.equal(status, 0, 'a git devDependency was rejected; only installed fields are in scope');
|
|
232
|
+
});
|
|
233
|
+
test('both workflows run this script and not their own copy of the rule', () => {
|
|
234
|
+
// The guard is worth nothing if a workflow still carries an inline prefix list
|
|
235
|
+
// beside it, so both halves are pinned for each: the call is there, and no
|
|
236
|
+
// workflow greps the manifest for a spelling of its own.
|
|
237
|
+
for (const workflow of ['ci.yml', 'release.yml']) {
|
|
238
|
+
const text = readFileSync(join(root, '.github', 'workflows', workflow), 'utf8');
|
|
239
|
+
assert.ok(text.includes('node tools/no-git-dependencies.mjs'), `${workflow} does not call tools/no-git-dependencies.mjs`);
|
|
240
|
+
assert.doesNotMatch(text, /github:\|git|\^\(github\|git/, `${workflow} still carries a prefix-list filter beside the script`);
|
|
241
|
+
}
|
|
242
|
+
});
|
|
243
|
+
//# sourceMappingURL=no-git-dependencies.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"no-git-dependencies.test.js","sourceRoot":"","sources":["../src/no-git-dependencies.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|