@caretcms/caretize 0.1.0 → 0.1.2
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 +41 -5
- package/dist/bind-collection.js +1 -1
- package/dist/bind-collection.js.map +1 -1
- package/dist/bind-route.d.ts.map +1 -1
- package/dist/bind-route.js +9 -4
- package/dist/bind-route.js.map +1 -1
- package/dist/cli-args.d.ts +16 -1
- package/dist/cli-args.d.ts.map +1 -1
- package/dist/cli-args.js +39 -3
- package/dist/cli-args.js.map +1 -1
- package/dist/cli.js +390 -27
- package/dist/cli.js.map +1 -1
- package/dist/detect.d.ts +17 -1
- package/dist/detect.d.ts.map +1 -1
- package/dist/detect.js +61 -22
- package/dist/detect.js.map +1 -1
- package/dist/diff.d.ts +20 -0
- package/dist/diff.d.ts.map +1 -0
- package/dist/diff.js +75 -0
- package/dist/diff.js.map +1 -0
- package/dist/discover.d.ts.map +1 -1
- package/dist/discover.js +8 -2
- package/dist/discover.js.map +1 -1
- package/dist/escalation.d.ts +47 -0
- package/dist/escalation.d.ts.map +1 -0
- package/dist/escalation.js +112 -0
- package/dist/escalation.js.map +1 -0
- package/dist/frontmatter.d.ts +41 -4
- package/dist/frontmatter.d.ts.map +1 -1
- package/dist/frontmatter.js +122 -12
- package/dist/frontmatter.js.map +1 -1
- package/dist/import-wrap.d.ts +30 -0
- package/dist/import-wrap.d.ts.map +1 -1
- package/dist/import-wrap.js +101 -7
- package/dist/import-wrap.js.map +1 -1
- package/dist/init.d.ts +70 -0
- package/dist/init.d.ts.map +1 -0
- package/dist/init.js +198 -0
- package/dist/init.js.map +1 -0
- package/dist/keys.d.ts +55 -0
- package/dist/keys.d.ts.map +1 -0
- package/dist/keys.js +84 -0
- package/dist/keys.js.map +1 -0
- package/dist/output.d.ts +63 -10
- package/dist/output.d.ts.map +1 -1
- package/dist/output.js +190 -22
- package/dist/output.js.map +1 -1
- package/dist/plan.d.ts +7 -0
- package/dist/plan.d.ts.map +1 -1
- package/dist/plan.js +17 -4
- package/dist/plan.js.map +1 -1
- package/dist/preflight.d.ts +2 -0
- package/dist/preflight.d.ts.map +1 -1
- package/dist/preflight.js +18 -3
- package/dist/preflight.js.map +1 -1
- package/dist/run.js +6 -4
- package/dist/run.js.map +1 -1
- package/dist/select-policy.d.ts +38 -0
- package/dist/select-policy.d.ts.map +1 -0
- package/dist/select-policy.js +44 -0
- package/dist/select-policy.js.map +1 -0
- package/dist/tiers.d.ts +42 -0
- package/dist/tiers.d.ts.map +1 -0
- package/dist/tiers.js +67 -0
- package/dist/tiers.js.map +1 -0
- package/dist/wrap.d.ts +9 -4
- package/dist/wrap.d.ts.map +1 -1
- package/dist/wrap.js +3 -2
- package/dist/wrap.js.map +1 -1
- package/package.json +2 -2
package/dist/init.js
ADDED
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Pure helpers for `caretize init` — the one command that wires CaretCMS into an
|
|
3
|
+
* Astro project so tagging actually makes content editable (the gap preflight
|
|
4
|
+
* only *warns* about today). Kept process-free and side-effect-free so the
|
|
5
|
+
* load-bearing logic — editing an existing astro.config, scaffolding .env — is
|
|
6
|
+
* unit-testable; cli.ts owns the readline I/O, the npm install, and disk writes.
|
|
7
|
+
*
|
|
8
|
+
* Config editing mirrors caretize's write contract: every edit is a PURE
|
|
9
|
+
* INSERTION of the original bytes (verified by a subsequence check), so an edit
|
|
10
|
+
* can add to a config but never delete or reorder what's there. When the config
|
|
11
|
+
* shape isn't one we can touch confidently, planConfigWiring returns ok:false
|
|
12
|
+
* and the caller falls back to printing a snippet to paste — never a silent
|
|
13
|
+
* corruption.
|
|
14
|
+
*/
|
|
15
|
+
/** True when every character of `needle` appears in `haystack` in order. The
|
|
16
|
+
* proof that an edit only inserted: no original character was dropped/moved. */
|
|
17
|
+
function isSubsequence(needle, haystack) {
|
|
18
|
+
let i = 0;
|
|
19
|
+
for (let j = 0; j < haystack.length && i < needle.length; j++) {
|
|
20
|
+
if (haystack[j] === needle[i])
|
|
21
|
+
i++;
|
|
22
|
+
}
|
|
23
|
+
return i === needle.length;
|
|
24
|
+
}
|
|
25
|
+
const CARET_IMPORT = `import caret from '@caretcms/core';`;
|
|
26
|
+
const NODE_IMPORT = `import node from '@astrojs/node';`;
|
|
27
|
+
function caretCall(needs) {
|
|
28
|
+
return needs.staticDelivery ? `caret({ delivery: "static" })` : "caret()";
|
|
29
|
+
}
|
|
30
|
+
/** A complete, minimal embedded-mode config — written verbatim when a project
|
|
31
|
+
* has no astro.config at all, and shown as the paste-me snippet when an
|
|
32
|
+
* existing config is too complex to edit safely. */
|
|
33
|
+
export function freshConfig(mode = "static") {
|
|
34
|
+
if (mode === "server") {
|
|
35
|
+
return (`import { defineConfig } from 'astro/config';\n` +
|
|
36
|
+
`import node from '@astrojs/node';\n` +
|
|
37
|
+
`import caret from '@caretcms/core';\n` +
|
|
38
|
+
`\n` +
|
|
39
|
+
`export default defineConfig({\n` +
|
|
40
|
+
` output: 'server',\n` +
|
|
41
|
+
` adapter: node({ mode: 'standalone' }),\n` +
|
|
42
|
+
` integrations: [caret()],\n` +
|
|
43
|
+
`});\n`);
|
|
44
|
+
}
|
|
45
|
+
return (`import { defineConfig } from 'astro/config';\n` +
|
|
46
|
+
`import caret from '@caretcms/core';\n` +
|
|
47
|
+
`\n` +
|
|
48
|
+
`export default defineConfig({\n` +
|
|
49
|
+
` integrations: [caret({ delivery: "static" })],\n` +
|
|
50
|
+
`});\n`);
|
|
51
|
+
}
|
|
52
|
+
/** Index of the `{` that opens the config object — defineConfig({…}) preferred,
|
|
53
|
+
* bare `export default {…}` accepted. null when neither shape is present. */
|
|
54
|
+
export function findConfigObjectBrace(source) {
|
|
55
|
+
const m = source.match(/defineConfig\s*\(\s*\{/);
|
|
56
|
+
if (m && m.index !== undefined)
|
|
57
|
+
return m.index + m[0].length - 1;
|
|
58
|
+
const m2 = source.match(/export\s+default\s*\{/);
|
|
59
|
+
if (m2 && m2.index !== undefined)
|
|
60
|
+
return m2.index + m2[0].length - 1;
|
|
61
|
+
return null;
|
|
62
|
+
}
|
|
63
|
+
/** Offset just past the last top-level `import …` line (0 when there are none),
|
|
64
|
+
* so new imports land after the existing import block. */
|
|
65
|
+
function lastImportEnd(source) {
|
|
66
|
+
const re = /^import[^\n]*\n/gm;
|
|
67
|
+
let last = null;
|
|
68
|
+
for (let m = re.exec(source); m; m = re.exec(source))
|
|
69
|
+
last = m;
|
|
70
|
+
return last ? last.index + last[0].length : 0;
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Plan the edits that wire caret() / the adapter / output into an EXISTING
|
|
74
|
+
* config. Returns the edited text plus what was inserted vs. what needs manual
|
|
75
|
+
* attention. All edits are pure insertions; the result is subsequence-verified
|
|
76
|
+
* against the source, and any failure (unrecognized shape, verification miss)
|
|
77
|
+
* yields ok:false so the caller prints a snippet instead.
|
|
78
|
+
*/
|
|
79
|
+
export function planConfigWiring(source, needs) {
|
|
80
|
+
const inserted = [];
|
|
81
|
+
const manual = [];
|
|
82
|
+
const braceIdx = findConfigObjectBrace(source);
|
|
83
|
+
if (braceIdx === null)
|
|
84
|
+
return { output: source, inserted, manual, ok: false };
|
|
85
|
+
const edits = [];
|
|
86
|
+
// Imports — only those not already present, inserted after the import block.
|
|
87
|
+
const importsToAdd = [];
|
|
88
|
+
if (needs.caret && !/from\s+['"]@caretcms\/core['"]/.test(source))
|
|
89
|
+
importsToAdd.push(CARET_IMPORT);
|
|
90
|
+
if (needs.adapter && !/from\s+['"]@astrojs\/node['"]/.test(source))
|
|
91
|
+
importsToAdd.push(NODE_IMPORT);
|
|
92
|
+
if (importsToAdd.length) {
|
|
93
|
+
edits.push({ index: lastImportEnd(source), text: importsToAdd.join("\n") + "\n" });
|
|
94
|
+
inserted.push(...importsToAdd);
|
|
95
|
+
}
|
|
96
|
+
// New object properties — combined into one block at the config brace so they
|
|
97
|
+
// land in a stable, readable order regardless of insertion bookkeeping.
|
|
98
|
+
const newProps = [];
|
|
99
|
+
if (needs.output) {
|
|
100
|
+
if (/\boutput\s*:/.test(source)) {
|
|
101
|
+
// Changing an existing value would be a replacement, not an insertion —
|
|
102
|
+
// outside the safety contract, so hand it back to the user.
|
|
103
|
+
manual.push(`set output to 'server' (config already declares an output)`);
|
|
104
|
+
}
|
|
105
|
+
else {
|
|
106
|
+
newProps.push(`output: 'server',`);
|
|
107
|
+
inserted.push(`output: 'server'`);
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
if (needs.adapter) {
|
|
111
|
+
newProps.push(`adapter: node({ mode: 'standalone' }),`);
|
|
112
|
+
inserted.push(`adapter: node({ mode: 'standalone' })`);
|
|
113
|
+
}
|
|
114
|
+
if (needs.caret) {
|
|
115
|
+
const intMatch = source.match(/integrations\s*:\s*\[/);
|
|
116
|
+
const call = caretCall(needs);
|
|
117
|
+
if (intMatch && intMatch.index !== undefined) {
|
|
118
|
+
if (/\bcaret\s*\(/.test(source)) {
|
|
119
|
+
// Defensive: caller gates on !caretWired, but never double-insert.
|
|
120
|
+
}
|
|
121
|
+
else {
|
|
122
|
+
const at = intMatch.index + intMatch[0].length;
|
|
123
|
+
// No trailing comma when the array is empty (`[]`) — only when there's
|
|
124
|
+
// an existing entry to precede.
|
|
125
|
+
const empty = source.slice(at).trimStart().startsWith("]");
|
|
126
|
+
edits.push({ index: at, text: empty ? call : `${call}, ` });
|
|
127
|
+
inserted.push(empty ? `integrations: [${call}]` : `integrations: [${call}, …]`);
|
|
128
|
+
}
|
|
129
|
+
}
|
|
130
|
+
else {
|
|
131
|
+
newProps.push(`integrations: [${call}],`);
|
|
132
|
+
inserted.push(`integrations: [${call}]`);
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
else if (needs.staticDelivery && !/delivery\s*:/.test(source)) {
|
|
136
|
+
const emptyCall = source.match(/\bcaret\s*\(\s*\)/);
|
|
137
|
+
if (emptyCall && emptyCall.index !== undefined) {
|
|
138
|
+
const at = emptyCall.index + emptyCall[0].lastIndexOf(")");
|
|
139
|
+
edits.push({ index: at, text: `{ delivery: "static" }` });
|
|
140
|
+
inserted.push(`caret({ delivery: "static" })`);
|
|
141
|
+
}
|
|
142
|
+
else {
|
|
143
|
+
const objectCall = source.match(/\bcaret\s*\(\s*\{/);
|
|
144
|
+
if (objectCall && objectCall.index !== undefined) {
|
|
145
|
+
const at = objectCall.index + objectCall[0].length;
|
|
146
|
+
edits.push({ index: at, text: ` delivery: "static",` });
|
|
147
|
+
inserted.push(`delivery: "static"`);
|
|
148
|
+
}
|
|
149
|
+
else {
|
|
150
|
+
manual.push(`enable static delivery with caret({ delivery: "static" })`);
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
if (newProps.length) {
|
|
155
|
+
edits.push({ index: braceIdx + 1, text: `\n ` + newProps.join(`\n `) });
|
|
156
|
+
}
|
|
157
|
+
// Apply highest-offset-first so earlier edits don't shift later indices.
|
|
158
|
+
edits.sort((a, b) => b.index - a.index);
|
|
159
|
+
let output = source;
|
|
160
|
+
for (const e of edits)
|
|
161
|
+
output = output.slice(0, e.index) + e.text + output.slice(e.index);
|
|
162
|
+
// Safety gate: prove it's a pure insertion. If somehow it isn't, refuse.
|
|
163
|
+
if (output !== source && !isSubsequence(source, output)) {
|
|
164
|
+
return { output: source, inserted: [], manual, ok: false };
|
|
165
|
+
}
|
|
166
|
+
return { output, inserted, manual, ok: true };
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Plan additions to a project's .env. Generates nothing itself — the caller
|
|
170
|
+
* passes a freshly-generated `secret` (mirrors backup.ts injecting its
|
|
171
|
+
* timestamp), keeping this deterministic and testable. Existing keys (commented
|
|
172
|
+
* or not) are never touched, so re-running init is idempotent.
|
|
173
|
+
*
|
|
174
|
+
* CARET_SESSION_SECRET is a machine secret → generated outright. The edit
|
|
175
|
+
* password is left as a COMMENTED placeholder so dev keeps printing a temp
|
|
176
|
+
* password (an empty value would suppress that), while still reminding the user
|
|
177
|
+
* to set one before deploying.
|
|
178
|
+
*/
|
|
179
|
+
export function renderEnvAdditions(existing, secret) {
|
|
180
|
+
const has = (k) => new RegExp(`^\\s*#?\\s*${k}\\s*=`, "m").test(existing);
|
|
181
|
+
const lines = [];
|
|
182
|
+
const added = [];
|
|
183
|
+
if (!has("CARET_SESSION_SECRET")) {
|
|
184
|
+
lines.push(`CARET_SESSION_SECRET=${secret}`);
|
|
185
|
+
added.push("CARET_SESSION_SECRET (generated)");
|
|
186
|
+
}
|
|
187
|
+
if (!has("CARET_EDIT_PASSWORD")) {
|
|
188
|
+
lines.push(`# Set before deploying — until then dev prints a temp password:`);
|
|
189
|
+
lines.push(`# CARET_EDIT_PASSWORD=choose-a-strong-password`);
|
|
190
|
+
added.push("CARET_EDIT_PASSWORD (placeholder)");
|
|
191
|
+
}
|
|
192
|
+
if (lines.length === 0)
|
|
193
|
+
return { append: "", added };
|
|
194
|
+
const sep = existing && !existing.endsWith("\n") ? "\n" : "";
|
|
195
|
+
const header = existing.trim() ? "\n# CaretCMS\n" : "# CaretCMS\n";
|
|
196
|
+
return { append: sep + header + lines.join("\n") + "\n", added };
|
|
197
|
+
}
|
|
198
|
+
//# sourceMappingURL=init.js.map
|
package/dist/init.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"init.js","sourceRoot":"","sources":["../src/init.ts"],"names":[],"mappings":"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"}
|
package/dist/keys.d.ts
ADDED
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Cross-tier storage-key registry.
|
|
3
|
+
*
|
|
4
|
+
* Every tier derives `collection::id::field` keys independently — the tag pass
|
|
5
|
+
* from element content, wraps/hoists from variable/prop names — and each one
|
|
6
|
+
* only dedupes against itself plus the file's existing `data-caret` attributes.
|
|
7
|
+
* Without a shared registry one run can mint the SAME key twice with two
|
|
8
|
+
* different value shapes (a tag's string vs a wrap's array), and `editable()`
|
|
9
|
+
* keys from a prior run are invisible to the tag pass entirely.
|
|
10
|
+
*
|
|
11
|
+
* The CLI threads one registry per file: existing keys are pre-claimed, tags
|
|
12
|
+
* claim first (their names are content-derived and surfaced in the review),
|
|
13
|
+
* then wraps, then hoists. A later claim that collides takes a `_2`/`_3` field
|
|
14
|
+
* suffix — still within the runtime's field grammar. Bind-tier keys are
|
|
15
|
+
* per-row template literals into a *collection's* entries (a different
|
|
16
|
+
* namespace from the page scope), so they stay outside the registry.
|
|
17
|
+
*/
|
|
18
|
+
/**
|
|
19
|
+
* Keys already present in a file's source: every static `data-caret` value
|
|
20
|
+
* (full triples as-is; scoped shorthands resolved when the file's scope is
|
|
21
|
+
* known) plus every `editable()` key.
|
|
22
|
+
*/
|
|
23
|
+
export declare function collectExistingKeys(source: string, scope?: {
|
|
24
|
+
collection: string;
|
|
25
|
+
id: string;
|
|
26
|
+
}): Set<string>;
|
|
27
|
+
/** `key` if free, else the first `key_2`, `key_3`, … not in `used`. */
|
|
28
|
+
export declare function deconflictKey(key: string, used: ReadonlySet<string>): string;
|
|
29
|
+
/**
|
|
30
|
+
* Apply the registry to one file's planned changes, in claim order: existing
|
|
31
|
+
* keys (pre-claimed from `source`), tags, wraps, hoist props. Mutates the
|
|
32
|
+
* colliding entries in place — including the tag's attribute text and the
|
|
33
|
+
* hoist prop's precomputed `constInsert`, which bake the key in.
|
|
34
|
+
*/
|
|
35
|
+
export declare function applyKeyRegistry(source: string, scope: {
|
|
36
|
+
collection: string;
|
|
37
|
+
id: string;
|
|
38
|
+
} | undefined, tags: Array<{
|
|
39
|
+
field: string;
|
|
40
|
+
binding: string;
|
|
41
|
+
attribute: string;
|
|
42
|
+
candidate: {
|
|
43
|
+
rich?: boolean;
|
|
44
|
+
};
|
|
45
|
+
}>, wraps: Array<{
|
|
46
|
+
key: string;
|
|
47
|
+
}>, hoists: Array<{
|
|
48
|
+
props: Array<{
|
|
49
|
+
key: string;
|
|
50
|
+
constName: string;
|
|
51
|
+
literalValue: string;
|
|
52
|
+
constInsert: string;
|
|
53
|
+
}>;
|
|
54
|
+
}>): void;
|
|
55
|
+
//# sourceMappingURL=keys.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"keys.d.ts","sourceRoot":"","sources":["../src/keys.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAQH;;;;GAIG;AACH,wBAAgB,mBAAmB,CACjC,MAAM,EAAE,MAAM,EACd,KAAK,CAAC,EAAE;IAAE,UAAU,EAAE,MAAM,CAAC;IAAC,EAAE,EAAE,MAAM,CAAA;CAAE,GACzC,GAAG,CAAC,MAAM,CAAC,CASb;AAED,uEAAuE;AACvE,wBAAgB,aAAa,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE,WAAW,CAAC,MAAM,CAAC,GAAG,MAAM,CAM5E;AAED;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAC9B,MAAM,EAAE,MAAM,EACd,KAAK,EAAE;IAAE,UAAU,EAAE,MAAM,CAAC;IAAC,EAAE,EAAE,MAAM,CAAA;CAAE,GAAG,SAAS,EACrD,IAAI,EAAE,KAAK,CAAC;IACV,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE;QAAE,IAAI,CAAC,EAAE,OAAO,CAAA;KAAE,CAAC;CAC/B,CAAC,EACF,KAAK,EAAE,KAAK,CAAC;IAAE,GAAG,EAAE,MAAM,CAAA;CAAE,CAAC,EAC7B,MAAM,EAAE,KAAK,CAAC;IACZ,KAAK,EAAE,KAAK,CAAC;QAAE,GAAG,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAC;QAAC,YAAY,EAAE,MAAM,CAAC;QAAC,WAAW,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;CAC7F,CAAC,GACD,IAAI,CA2BN"}
|
package/dist/keys.js
ADDED
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Cross-tier storage-key registry.
|
|
3
|
+
*
|
|
4
|
+
* Every tier derives `collection::id::field` keys independently — the tag pass
|
|
5
|
+
* from element content, wraps/hoists from variable/prop names — and each one
|
|
6
|
+
* only dedupes against itself plus the file's existing `data-caret` attributes.
|
|
7
|
+
* Without a shared registry one run can mint the SAME key twice with two
|
|
8
|
+
* different value shapes (a tag's string vs a wrap's array), and `editable()`
|
|
9
|
+
* keys from a prior run are invisible to the tag pass entirely.
|
|
10
|
+
*
|
|
11
|
+
* The CLI threads one registry per file: existing keys are pre-claimed, tags
|
|
12
|
+
* claim first (their names are content-derived and surfaced in the review),
|
|
13
|
+
* then wraps, then hoists. A later claim that collides takes a `_2`/`_3` field
|
|
14
|
+
* suffix — still within the runtime's field grammar. Bind-tier keys are
|
|
15
|
+
* per-row template literals into a *collection's* entries (a different
|
|
16
|
+
* namespace from the page scope), so they stay outside the registry.
|
|
17
|
+
*/
|
|
18
|
+
/** `editable("collection::id::field", …)` calls in the frontmatter. */
|
|
19
|
+
const EDITABLE_KEY_RE = /\beditable\(\s*["'`]([^"'`]+)["'`]/g;
|
|
20
|
+
/** Static `data-caret="…"` attribute values anywhere in the source. */
|
|
21
|
+
const DATA_CARET_ATTR_RE = /\bdata-caret\s*=\s*"([^"]+)"/g;
|
|
22
|
+
/**
|
|
23
|
+
* Keys already present in a file's source: every static `data-caret` value
|
|
24
|
+
* (full triples as-is; scoped shorthands resolved when the file's scope is
|
|
25
|
+
* known) plus every `editable()` key.
|
|
26
|
+
*/
|
|
27
|
+
export function collectExistingKeys(source, scope) {
|
|
28
|
+
const keys = new Set();
|
|
29
|
+
for (const m of source.matchAll(DATA_CARET_ATTR_RE)) {
|
|
30
|
+
const value = m[1];
|
|
31
|
+
if (value.includes("::"))
|
|
32
|
+
keys.add(value);
|
|
33
|
+
else if (scope)
|
|
34
|
+
keys.add(`${scope.collection}::${scope.id}::${value}`);
|
|
35
|
+
}
|
|
36
|
+
for (const m of source.matchAll(EDITABLE_KEY_RE))
|
|
37
|
+
keys.add(m[1]);
|
|
38
|
+
return keys;
|
|
39
|
+
}
|
|
40
|
+
/** `key` if free, else the first `key_2`, `key_3`, … not in `used`. */
|
|
41
|
+
export function deconflictKey(key, used) {
|
|
42
|
+
if (!used.has(key))
|
|
43
|
+
return key;
|
|
44
|
+
for (let n = 2;; n++) {
|
|
45
|
+
const candidate = `${key}_${n}`;
|
|
46
|
+
if (!used.has(candidate))
|
|
47
|
+
return candidate;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Apply the registry to one file's planned changes, in claim order: existing
|
|
52
|
+
* keys (pre-claimed from `source`), tags, wraps, hoist props. Mutates the
|
|
53
|
+
* colliding entries in place — including the tag's attribute text and the
|
|
54
|
+
* hoist prop's precomputed `constInsert`, which bake the key in.
|
|
55
|
+
*/
|
|
56
|
+
export function applyKeyRegistry(source, scope, tags, wraps, hoists) {
|
|
57
|
+
const used = collectExistingKeys(source, scope);
|
|
58
|
+
for (const t of tags) {
|
|
59
|
+
const free = deconflictKey(t.binding, used);
|
|
60
|
+
if (free !== t.binding) {
|
|
61
|
+
t.field = free.slice(free.lastIndexOf("::") + 2);
|
|
62
|
+
t.binding = free;
|
|
63
|
+
t.attribute = t.candidate.rich
|
|
64
|
+
? `data-caret="${free}" data-caret-rich`
|
|
65
|
+
: `data-caret="${free}"`;
|
|
66
|
+
}
|
|
67
|
+
used.add(t.binding);
|
|
68
|
+
}
|
|
69
|
+
for (const w of wraps) {
|
|
70
|
+
w.key = deconflictKey(w.key, used);
|
|
71
|
+
used.add(w.key);
|
|
72
|
+
}
|
|
73
|
+
for (const h of hoists) {
|
|
74
|
+
for (const p of h.props) {
|
|
75
|
+
const free = deconflictKey(p.key, used);
|
|
76
|
+
if (free !== p.key) {
|
|
77
|
+
p.key = free;
|
|
78
|
+
p.constInsert = `\nconst ${p.constName} = await editable(${JSON.stringify(free)}, ${JSON.stringify(p.literalValue)});`;
|
|
79
|
+
}
|
|
80
|
+
used.add(p.key);
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
//# sourceMappingURL=keys.js.map
|
package/dist/keys.js.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"keys.js","sourceRoot":"","sources":["../src/keys.ts"],"names":[],"mappings":"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"}
|
package/dist/output.d.ts
CHANGED
|
@@ -7,24 +7,77 @@ import type { FilePlan, PlannedTag } from "./plan.js";
|
|
|
7
7
|
import type { WrapTarget } from "./wrap.js";
|
|
8
8
|
import type { PropHoistTarget } from "./prop-hoist.js";
|
|
9
9
|
import type { CollectionBindTarget } from "./bind-collection.js";
|
|
10
|
+
import type { Preflight } from "./preflight.js";
|
|
11
|
+
import { type TierId } from "./tiers.js";
|
|
10
12
|
type BindsByFile = Map<string, CollectionBindTarget[]>;
|
|
11
13
|
/** One-line description of a tag candidate, e.g. `<h1> "Hello"` or `<img> src="…"`. */
|
|
12
14
|
export declare function tagLine(t: PlannedTag): string;
|
|
13
|
-
/** The post-scan tally line.
|
|
14
|
-
|
|
15
|
+
/** The post-scan tally line. When the project is already partly tagged
|
|
16
|
+
* (`priorTagged` > 0) this is a RE-RUN: frame candidates as "new" and note how
|
|
17
|
+
* many spots are already editable, so re-running reads as incremental progress
|
|
18
|
+
* rather than a cold scan. */
|
|
19
|
+
export declare function formatScanSummary(fileCount: number, plans: FilePlan[], wrapsByFile: Map<string, WrapTarget[]>, hoistsByFile: Map<string, PropHoistTarget[]>, bindsByFile?: BindsByFile, priorTagged?: number): string;
|
|
15
20
|
/** The full `--dry-run` plan dump, ending with the "nothing written" footer. */
|
|
16
21
|
export declare function formatPlan(plans: FilePlan[], wrapsByFile: Map<string, WrapTarget[]>, hoistsByFile: Map<string, PropHoistTarget[]>, bindsByFile?: BindsByFile): string;
|
|
17
22
|
/** The closing summary block after a commit. */
|
|
18
23
|
export declare function formatSummary(files: number, changes: number, wrapped: number, hoisted: number, flagged: number, hadBackups: boolean, bound?: number): string;
|
|
19
24
|
/**
|
|
20
|
-
* The
|
|
21
|
-
*
|
|
22
|
-
*
|
|
23
|
-
*
|
|
25
|
+
* The single most-important "what now?" line, tailored to where the project
|
|
26
|
+
* actually is in CaretCMS setup. Tagging succeeds even when nothing is editable
|
|
27
|
+
* yet (core not installed / not wired / wrong output mode), so a generic
|
|
28
|
+
* "click to edit" footer is misleading — point at the ONE next step instead.
|
|
24
29
|
*/
|
|
25
|
-
export declare function
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
30
|
+
export declare function formatNextStep(pf: Preflight): string;
|
|
31
|
+
/**
|
|
32
|
+
* The grouped "I can also make these editable" offer shown after the default
|
|
33
|
+
* review (interactive mode). Lists only tiers with a non-zero count, in TIERS
|
|
34
|
+
* order, each tagged with its risk note (so the identity-guessing binders are
|
|
35
|
+
* labeled before consent). Returns "" when there's nothing to offer.
|
|
36
|
+
*
|
|
37
|
+
* The prompt question itself (`[Y/n/customize]`) is asked by cli.ts via readline;
|
|
38
|
+
* this renders only the menu body so it stays pure + testable.
|
|
39
|
+
*/
|
|
40
|
+
export declare function formatEscalationOffer(counts: Partial<Record<TierId, number>>): string;
|
|
41
|
+
/**
|
|
42
|
+
* The `--diff` preview: the actual before→after for every file that would change,
|
|
43
|
+
* as hunks (changed lines + context). Makes the codemod tangible — "show me
|
|
44
|
+
* exactly what you'd insert" — and pairs with the backup/--restore safety net.
|
|
45
|
+
* Files that failed verification are surfaced via `formatFailures` separately.
|
|
46
|
+
*/
|
|
47
|
+
export declare function formatDiff(prepared: ReadonlyArray<{
|
|
48
|
+
relPath: string;
|
|
49
|
+
source: string;
|
|
50
|
+
output: string;
|
|
51
|
+
tagCount: number;
|
|
52
|
+
ok: boolean;
|
|
53
|
+
}>): string;
|
|
54
|
+
/** Files whose prepared output failed verification — shown in --dry-run too,
|
|
55
|
+
* so the user learns BEFORE the real run aborts on them. */
|
|
56
|
+
export declare function formatFailures(prepared: ReadonlyArray<{
|
|
57
|
+
relPath: string;
|
|
58
|
+
ok: boolean;
|
|
59
|
+
reason?: string;
|
|
60
|
+
}>): string;
|
|
61
|
+
/** Which opt-in tiers are already ON — a hint is only offered while its tier is off. */
|
|
62
|
+
export interface HintOpts {
|
|
63
|
+
rich?: boolean;
|
|
64
|
+
richClass?: boolean;
|
|
65
|
+
collections?: boolean;
|
|
66
|
+
routes?: boolean;
|
|
67
|
+
lowconf?: boolean;
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* The "what's left + how to get it" summary — so skipped coverage reads as one
|
|
71
|
+
* unmissable checklist line, not four scattered re-run incantations. Every
|
|
72
|
+
* remaining opt-in tier that's still OFF is rolled into a single line that
|
|
73
|
+
* points at `--all` (the one flag), with the individual flags noted once.
|
|
74
|
+
*
|
|
75
|
+
* The styled-class case is kept separate: it isn't unlocked by a tier flag (the
|
|
76
|
+
* sanitizer strips the class regardless) — it needs a CSS move or
|
|
77
|
+
* caret({ allowedClasses }), so it carries its own guidance.
|
|
78
|
+
*
|
|
79
|
+
* Returns "" when there's nothing to say.
|
|
80
|
+
*/
|
|
81
|
+
export declare function formatHints(plans: FilePlan[], opts?: HintOpts): string;
|
|
29
82
|
export {};
|
|
30
83
|
//# sourceMappingURL=output.d.ts.map
|
package/dist/output.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"output.d.ts","sourceRoot":"","sources":["../src/output.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,QAAQ,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AACtD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AAC5C,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iBAAiB,CAAC;AACvD,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,sBAAsB,CAAC;
|
|
1
|
+
{"version":3,"file":"output.d.ts","sourceRoot":"","sources":["../src/output.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,QAAQ,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AACtD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,WAAW,CAAC;AAC5C,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,iBAAiB,CAAC;AACvD,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,sBAAsB,CAAC;AACjE,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAEhD,OAAO,EAAS,KAAK,MAAM,EAAE,MAAM,YAAY,CAAC;AAGhD,KAAK,WAAW,GAAG,GAAG,CAAC,MAAM,EAAE,oBAAoB,EAAE,CAAC,CAAC;AAEvD,uFAAuF;AACvF,wBAAgB,OAAO,CAAC,CAAC,EAAE,UAAU,GAAG,MAAM,CAK7C;AAED;;;+BAG+B;AAC/B,wBAAgB,iBAAiB,CAC/B,SAAS,EAAE,MAAM,EACjB,KAAK,EAAE,QAAQ,EAAE,EACjB,WAAW,EAAE,GAAG,CAAC,MAAM,EAAE,UAAU,EAAE,CAAC,EACtC,YAAY,EAAE,GAAG,CAAC,MAAM,EAAE,eAAe,EAAE,CAAC,EAC5C,WAAW,GAAE,WAAuB,EACpC,WAAW,SAAI,GACd,MAAM,CAWR;AAED,gFAAgF;AAChF,wBAAgB,UAAU,CACxB,KAAK,EAAE,QAAQ,EAAE,EACjB,WAAW,EAAE,GAAG,CAAC,MAAM,EAAE,UAAU,EAAE,CAAC,EACtC,YAAY,EAAE,GAAG,CAAC,MAAM,EAAE,eAAe,EAAE,CAAC,EAC5C,WAAW,GAAE,WAAuB,GACnC,MAAM,CA4BR;AAED,gDAAgD;AAChD,wBAAgB,aAAa,CAC3B,KAAK,EAAE,MAAM,EACb,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,EACf,UAAU,EAAE,OAAO,EACnB,KAAK,SAAI,GACR,MAAM,CAUR;AAED;;;;;GAKG;AACH,wBAAgB,cAAc,CAAC,EAAE,EAAE,SAAS,GAAG,MAAM,CAwBpD;AAED;;;;;;;;GAQG;AACH,wBAAgB,qBAAqB,CAAC,MAAM,EAAE,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,GAAG,MAAM,CAUrF;AAED;;;;;GAKG;AACH,wBAAgB,UAAU,CACxB,QAAQ,EAAE,aAAa,CAAC;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAC;IAAC,EAAE,EAAE,OAAO,CAAA;CAAE,CAAC,GAC1G,MAAM,CAQR;AAED;6DAC6D;AAC7D,wBAAgB,cAAc,CAC5B,QAAQ,EAAE,aAAa,CAAC;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,EAAE,EAAE,OAAO,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,GACzE,MAAM,CAQR;AAED,wFAAwF;AACxF,MAAM,WAAW,QAAQ;IACvB,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAoCD;;;;;;;;;;;GAWG;AACH,wBAAgB,WAAW,CAAC,KAAK,EAAE,QAAQ,EAAE,EAAE,IAAI,GAAE,QAAa,GAAG,MAAM,CAoE1E"}
|