@caelo-cms/shared 0.10.57 → 0.10.59

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (64) hide show
  1. package/dist/ai-tools.d.ts +30 -0
  2. package/dist/ai-tools.d.ts.map +1 -1
  3. package/dist/ai-tools.js +26 -9
  4. package/dist/ai-tools.js.map +1 -1
  5. package/dist/bug-intake.d.ts +176 -0
  6. package/dist/bug-intake.d.ts.map +1 -0
  7. package/dist/bug-intake.js +200 -0
  8. package/dist/bug-intake.js.map +1 -0
  9. package/dist/content.js +7 -7
  10. package/dist/edit-markers.d.ts +49 -0
  11. package/dist/edit-markers.d.ts.map +1 -0
  12. package/dist/edit-markers.js +225 -0
  13. package/dist/edit-markers.js.map +1 -0
  14. package/dist/google-oauth.d.ts +22 -0
  15. package/dist/google-oauth.d.ts.map +1 -0
  16. package/dist/google-oauth.js +25 -0
  17. package/dist/google-oauth.js.map +1 -0
  18. package/dist/index.d.ts +4 -0
  19. package/dist/index.d.ts.map +1 -1
  20. package/dist/index.js +4 -0
  21. package/dist/index.js.map +1 -1
  22. package/dist/link-canonicalise.d.ts +109 -0
  23. package/dist/link-canonicalise.d.ts.map +1 -0
  24. package/dist/link-canonicalise.js +471 -0
  25. package/dist/link-canonicalise.js.map +1 -0
  26. package/dist/link-refs.d.ts +63 -8
  27. package/dist/link-refs.d.ts.map +1 -1
  28. package/dist/link-refs.js +80 -14
  29. package/dist/link-refs.js.map +1 -1
  30. package/dist/media.d.ts.map +1 -1
  31. package/dist/media.js +15 -0
  32. package/dist/media.js.map +1 -1
  33. package/dist/nested-module-render.d.ts +17 -0
  34. package/dist/nested-module-render.d.ts.map +1 -1
  35. package/dist/nested-module-render.js +45 -6
  36. package/dist/nested-module-render.js.map +1 -1
  37. package/dist/page-log.d.ts +1 -1
  38. package/dist/preview-compose.d.ts.map +1 -1
  39. package/dist/preview-compose.js +12 -2
  40. package/dist/preview-compose.js.map +1 -1
  41. package/dist/theme-normalize.d.ts.map +1 -1
  42. package/dist/theme-normalize.js +17 -2
  43. package/dist/theme-normalize.js.map +1 -1
  44. package/dist/version.d.ts +2 -2
  45. package/dist/version.js +1 -1
  46. package/package.json +1 -1
  47. package/src/ai-tools.ts +29 -11
  48. package/src/bug-intake.test.ts +154 -0
  49. package/src/bug-intake.ts +256 -0
  50. package/src/content.ts +7 -7
  51. package/src/edit-markers.test.ts +111 -0
  52. package/src/edit-markers.ts +244 -0
  53. package/src/google-oauth.ts +27 -0
  54. package/src/index.ts +4 -0
  55. package/src/link-canonicalise.test.ts +387 -0
  56. package/src/link-canonicalise.ts +598 -0
  57. package/src/link-refs.test.ts +206 -0
  58. package/src/link-refs.ts +119 -21
  59. package/src/media.ts +16 -0
  60. package/src/nested-module-render.ts +59 -4
  61. package/src/preview-compose.ts +11 -2
  62. package/src/theme-normalize-typography-subfields.test.ts +54 -0
  63. package/src/theme-normalize.ts +19 -2
  64. package/src/version.ts +1 -1
@@ -0,0 +1,471 @@
1
+ // SPDX-License-Identifier: MPL-2.0
2
+ /**
3
+ * Write-time canonicalisation of internal links (epic #724, rollout C):
4
+ * the pure core. Authors — operators and the AI — keep writing `/about`,
5
+ * `https://<own domain>/about#team` or `/_caelo/media/hero`; this turns
6
+ * every such link into its stored reference (`caelo:page/<id>#team`,
7
+ * `caelo:media/<id>`) so renaming or moving the target changes no stored
8
+ * link. External URLs, `mailto:`, `tel:`, fragments, template
9
+ * placeholders and non-page files stay literal.
10
+ *
11
+ * Where a link can live, and what is looked at:
12
+ *
13
+ * - a WHOLE value that is a URL: `url` / `link` / `image` fields, any
14
+ * field or object key named `href` / `src` / `url` / `link` or ending
15
+ * in `_href` / `_url` / `_link` / `_src` (`primary_cta_href`), the
16
+ * `href` of `link-list` items and structured-set items (any depth);
17
+ * - HTML anywhere (module HTML, rich text, any string value carrying
18
+ * markup): `href` (pages and media), `src` / `poster` / `srcset`
19
+ * (media only — a `src="/x"` that is not media is not a page link).
20
+ *
21
+ * A plain text value is never canonicalised as a whole: "/month" in a
22
+ * price label is text, not a link.
23
+ *
24
+ * Failure policy (CLAUDE.md §2, §11): an internal path that matches no
25
+ * page, a media URL that matches no asset and a reference whose target
26
+ * is gone are collected as {@link LinkCanonicaliseIssue}s; the write op
27
+ * turns them into one AI-actionable error. Two exceptions keep editing
28
+ * possible around content that predates this rule:
29
+ *
30
+ * - grandfathering: a literal that was ALREADY in the stored value
31
+ * (pre-#724 content, rollout E migrates it) is left as it is — an
32
+ * edit must not introduce a broken link, but it need not fix an
33
+ * unrelated old one. The reference-integrity check (rollout F)
34
+ * reports those.
35
+ * - report mode: imports keep unresolved literals and report them
36
+ * (maintainer decision 3 on #724) instead of failing the import.
37
+ * - pending: while a chat rebuilds a site import, a link to a page of
38
+ * that run not built yet is kept and listed in `run.pending`; the
39
+ * caller records it and the run's finalisation converts it (or
40
+ * reports it) once the run's pages exist.
41
+ */
42
+ import { findMalformedLinkRefs, formatLinkRef, LINK_REF_PART_PATTERNS, parseLinkRef, } from "./link-refs.js";
43
+ import { MEDIA_URL_PREFIX } from "./media.js";
44
+ /** Start a run. */
45
+ export function linkCanonicaliseRun(lookup, opts = {}) {
46
+ return {
47
+ lookup,
48
+ mode: opts.mode ?? "strict",
49
+ grandfathered: opts.grandfathered ?? new Set(),
50
+ issues: [],
51
+ pending: [],
52
+ };
53
+ }
54
+ // The reference grammar's own part patterns (link-refs.ts): a query,
55
+ // anchor or variant they accept always round-trips through
56
+ // `formatLinkRef`, and one they reject is an issue, never a throw (a
57
+ // thrown error would turn bad author input into a 500).
58
+ const QUERY_OK = LINK_REF_PART_PATTERNS.query;
59
+ const ANCHOR_OK = LINK_REF_PART_PATTERNS.anchor;
60
+ const VARIANT_RE = LINK_REF_PART_PATTERNS.variant;
61
+ const UUID_RE = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/;
62
+ const MEDIA_SEGMENT_RE = /^[a-z0-9][a-z0-9-]{0,63}$/;
63
+ // Text that starts like a reference. When the grammar rejects it, it is
64
+ // a broken reference, not some other URL (`malformed-link-ref`).
65
+ const REF_LIKE_RE = /^caelo:(?:page|media)\//;
66
+ // A last path segment with a file extension names a file, not a page —
67
+ // unless a page or an old-URL redirect answers it (`/about.html` an import
68
+ // redirected), which is checked first.
69
+ const FILE_EXT_RE = /\.[A-Za-z0-9]{1,8}$/;
70
+ // Files the static build itself serves at the site root; a link to one
71
+ // is a plain URL. Any other file path must come from the media library.
72
+ const SITE_SERVED_FILES = new Set(["/robots.txt", "/sitemap.xml"]);
73
+ /** Key / field names whose whole value is a URL. */
74
+ export function isLinkKeyName(name) {
75
+ const n = name.toLowerCase();
76
+ return (n === "href" ||
77
+ n === "src" ||
78
+ n === "url" ||
79
+ n === "link" ||
80
+ n.endsWith("_href") ||
81
+ n.endsWith("_url") ||
82
+ n.endsWith("_link") ||
83
+ n.endsWith("_src"));
84
+ }
85
+ /** Split `/a/b?q#h` into its parts (no URL parser: it must stay path-shaped). */
86
+ function splitPathTail(v) {
87
+ let rest = v;
88
+ let anchor = null;
89
+ const hash = rest.indexOf("#");
90
+ if (hash !== -1) {
91
+ anchor = rest.slice(hash + 1);
92
+ rest = rest.slice(0, hash);
93
+ }
94
+ let query = null;
95
+ const q = rest.indexOf("?");
96
+ if (q !== -1) {
97
+ query = rest.slice(q + 1);
98
+ rest = rest.slice(0, q);
99
+ }
100
+ return { path: rest, query: query === "" ? null : query, anchor: anchor === "" ? null : anchor };
101
+ }
102
+ /** `/a/b/` → `/a/b`; `/` stays `/`. Linear, no regex backtracking. */
103
+ export function normaliseLinkPath(path) {
104
+ let end = path.length;
105
+ while (end > 1 && path.charCodeAt(end - 1) === 47)
106
+ end -= 1;
107
+ return path.slice(0, end) || "/";
108
+ }
109
+ function issue(run, kind, value, where) {
110
+ run.issues.push({ kind, value, where });
111
+ }
112
+ /**
113
+ * Record every malformed reference in `text` (HTML or a plain value).
114
+ * The render flags exactly these (`link-ref-malformed`, via the shared
115
+ * `findMalformedLinkRefs`), so a write that would ship one is refused up
116
+ * front. A snippet already recorded at the same position (the
117
+ * whole-value check in {@link canonicaliseUrl} saw it first) is not
118
+ * reported twice.
119
+ */
120
+ function reportMalformedRefs(text, run, where) {
121
+ for (const raw of findMalformedLinkRefs(text)) {
122
+ if (run.grandfathered.has(raw))
123
+ continue;
124
+ const seen = run.issues.some((i) => i.kind === "malformed-link-ref" && i.where === where && i.value.startsWith(raw));
125
+ if (!seen)
126
+ issue(run, "malformed-link-ref", raw, where);
127
+ }
128
+ }
129
+ /**
130
+ * Canonicalise a `/_caelo/media/<slug>[/<variant>]` path, or null when it
131
+ * is not one.
132
+ *
133
+ * @param hasSuffix the link carries a `?query` or `#anchor`. A media
134
+ * reference cannot carry either (`caelo:media/<id>` has no suffix), so
135
+ * such a link is an `unsupported-link-form` issue instead of a
136
+ * reference that silently drops `#page=3`.
137
+ */
138
+ function canonicaliseMediaPath(path, raw, hasSuffix, run, where) {
139
+ if (!path.startsWith(`${MEDIA_URL_PREFIX}/`))
140
+ return null;
141
+ const segs = path.slice(MEDIA_URL_PREFIX.length + 1).split("/");
142
+ const first = segs[0] ?? "";
143
+ const variant = segs[1] ?? null;
144
+ if (segs.length > 2 || !MEDIA_SEGMENT_RE.test(first) || (variant && !VARIANT_RE.test(variant))) {
145
+ return null;
146
+ }
147
+ // Legacy `/_caelo/media/<uuid>/<variant>` names the asset by id.
148
+ const id = UUID_RE.test(first) && variant ? first : run.lookup.mediaIdForSlug(first);
149
+ if (id === null || !run.lookup.mediaExists(id)) {
150
+ if (!run.grandfathered.has(raw))
151
+ issue(run, "unknown-media", raw, where);
152
+ return raw;
153
+ }
154
+ if (hasSuffix) {
155
+ if (!run.grandfathered.has(raw))
156
+ issue(run, "unsupported-link-form", raw, where);
157
+ return raw;
158
+ }
159
+ // `orig` is the original, which a reference expresses as no variant.
160
+ return formatLinkRef({
161
+ kind: "media",
162
+ mediaId: id,
163
+ variant: variant === "orig" ? null : variant,
164
+ });
165
+ }
166
+ /**
167
+ * Canonicalise one URL value. Returns the stored form: a reference, or
168
+ * the value unchanged (external, non-page, or an issue was recorded).
169
+ *
170
+ * @param scope `pages+media` for link positions (`href`, link fields);
171
+ * `media` for image positions (`src`, `srcset`, `poster`).
172
+ */
173
+ export function canonicaliseUrl(value, run, where, scope = "pages+media") {
174
+ const v = value.trim();
175
+ if (v.length === 0 || v.includes("{{"))
176
+ return value;
177
+ const ref = parseLinkRef(v);
178
+ if (ref) {
179
+ if (!targetExists(ref, run.lookup) && !run.grandfathered.has(v)) {
180
+ issue(run, ref.kind === "page" ? "dangling-page-ref" : "dangling-media-ref", v, where);
181
+ }
182
+ return v;
183
+ }
184
+ // Starts like a reference but breaks the grammar (a truncated id,
185
+ // stray characters after it): passing it through would store a link
186
+ // no render resolves (CLAUDE.md §2).
187
+ if (REF_LIKE_RE.test(v)) {
188
+ if (!run.grandfathered.has(v))
189
+ issue(run, "malformed-link-ref", v, where);
190
+ return value;
191
+ }
192
+ let local;
193
+ if (/^https?:\/\//i.test(v)) {
194
+ let u;
195
+ try {
196
+ u = new URL(v);
197
+ }
198
+ catch {
199
+ return value;
200
+ }
201
+ if (!run.lookup.isOwnHost(u.host.toLowerCase()))
202
+ return value;
203
+ local = `${u.pathname}${u.search}${u.hash}`;
204
+ }
205
+ else if (v.startsWith("/") && !v.startsWith("//")) {
206
+ local = v;
207
+ }
208
+ else {
209
+ return value;
210
+ }
211
+ const { path, query, anchor } = splitPathTail(local);
212
+ const media = canonicaliseMediaPath(path, v, query !== null || anchor !== null, run, where);
213
+ if (media !== null)
214
+ return media;
215
+ if (scope === "media")
216
+ return value;
217
+ // Not a page: other reserved surfaces (`/_assets/…`, `/_caelo/fonts/…`)
218
+ // and the gateway (`/api/…`).
219
+ if (path.startsWith("/_") || path === "/api" || path.startsWith("/api/"))
220
+ return value;
221
+ const normalised = normaliseLinkPath(path);
222
+ const pageId = run.lookup.pageIdForPath(normalised);
223
+ if (pageId === null && run.lookup.isPendingPagePath?.(normalised)) {
224
+ // A page the import run will still build: kept as written and
225
+ // recorded by the caller; the run's finalisation converts it.
226
+ run.pending.push({ value: v, path: normalised, where });
227
+ return value;
228
+ }
229
+ if (pageId === null) {
230
+ const lastSegment = path.slice(path.lastIndexOf("/") + 1);
231
+ const isFile = FILE_EXT_RE.test(lastSegment);
232
+ if (isFile && SITE_SERVED_FILES.has(path))
233
+ return value;
234
+ if (!run.grandfathered.has(v))
235
+ issue(run, isFile ? "unknown-file" : "unknown-page-path", v, where);
236
+ return value;
237
+ }
238
+ if ((query !== null && !QUERY_OK.test(query)) || (anchor !== null && !ANCHOR_OK.test(anchor))) {
239
+ if (!run.grandfathered.has(v))
240
+ issue(run, "unsupported-link-form", v, where);
241
+ return value;
242
+ }
243
+ return formatLinkRef({ kind: "page", pageId, query, anchor });
244
+ }
245
+ function targetExists(ref, lookup) {
246
+ return ref.kind === "page" ? lookup.pageExists(ref.pageId) : lookup.mediaExists(ref.mediaId);
247
+ }
248
+ // Attribute scanner: `name="…"` / `name='…'` for the four link-bearing
249
+ // attributes. The value classes exclude their own quote, so each match
250
+ // is linear (no backtracking across attributes).
251
+ const ATTR_RE = /(\s(?:href|src|poster|srcset)\s*=\s*)(?:"([^"]*)"|'([^']*)')/gi;
252
+ /** Canonicalise the link-bearing attributes of an HTML fragment. */
253
+ export function canonicaliseHtmlLinks(html, run, where) {
254
+ if (!html.includes("=")) {
255
+ reportMalformedRefs(html, run, where);
256
+ return html;
257
+ }
258
+ // Attributes are only read inside a start tag, so escaped markup in a
259
+ // code sample (`&lt;a href="/x"&gt;` is text, not a link) is left alone.
260
+ let out = "";
261
+ let from = 0;
262
+ for (const [start, end] of startTags(html)) {
263
+ out += html.slice(from, start) + canonicaliseTagAttributes(html.slice(start, end), run, where);
264
+ from = end;
265
+ }
266
+ // Broken references anywhere the render looks (any attribute, a srcset
267
+ // entry), not only in the four attributes canonicalised above.
268
+ reportMalformedRefs(html, run, where);
269
+ return from === 0 ? html : out + html.slice(from);
270
+ }
271
+ /**
272
+ * `[start, end)` of every start tag (`<` + letter … `>`), quoted values
273
+ * allowed to contain `>`. One linear pass; an unterminated quote runs to
274
+ * the end of the input instead of being rescanned.
275
+ */
276
+ function* startTags(html) {
277
+ let i = html.indexOf("<");
278
+ while (i !== -1 && i < html.length - 1) {
279
+ const c = html.charCodeAt(i + 1);
280
+ const isLetter = (c >= 65 && c <= 90) || (c >= 97 && c <= 122);
281
+ if (!isLetter) {
282
+ i = html.indexOf("<", i + 1);
283
+ continue;
284
+ }
285
+ let j = i + 2;
286
+ let quote = 0;
287
+ while (j < html.length) {
288
+ const ch = html.charCodeAt(j);
289
+ if (quote !== 0) {
290
+ if (ch === quote)
291
+ quote = 0;
292
+ }
293
+ else if (ch === 34 || ch === 39) {
294
+ quote = ch;
295
+ }
296
+ else if (ch === 62) {
297
+ break;
298
+ }
299
+ j += 1;
300
+ }
301
+ const end = Math.min(j + 1, html.length);
302
+ yield [i, end];
303
+ i = html.indexOf("<", end);
304
+ }
305
+ }
306
+ function canonicaliseTagAttributes(tag, run, where) {
307
+ return tag.replace(ATTR_RE, (whole, prefix, dq, sq) => {
308
+ const quote = dq !== undefined ? '"' : "'";
309
+ const raw = (dq ?? sq);
310
+ const attr = prefix
311
+ .trim()
312
+ .replace(/\s*=\s*$/, "")
313
+ .toLowerCase();
314
+ let next;
315
+ if (attr === "href")
316
+ next = canonicaliseUrl(raw, run, where, "pages+media");
317
+ else if (attr === "srcset")
318
+ next = canonicaliseSrcset(raw, run, where);
319
+ else
320
+ next = canonicaliseUrl(raw, run, where, "media");
321
+ return next === raw ? whole : `${prefix}${quote}${next}${quote}`;
322
+ });
323
+ }
324
+ /** `url 400w, url 800w` — each candidate URL is a media position. */
325
+ function canonicaliseSrcset(srcset, run, where) {
326
+ return srcset
327
+ .split(",")
328
+ .map((entry) => {
329
+ const lead = entry.length - entry.trimStart().length;
330
+ const body = entry.slice(lead);
331
+ const sp = body.search(/\s/);
332
+ const url = sp === -1 ? body : body.slice(0, sp);
333
+ const rest = sp === -1 ? "" : body.slice(sp);
334
+ const next = canonicaliseUrl(url, run, where, "media");
335
+ return `${entry.slice(0, lead)}${next}${rest}`;
336
+ })
337
+ .join(",");
338
+ }
339
+ /**
340
+ * Canonicalise any JSON value: whole-value URLs where the key says so
341
+ * (`asUrl`), HTML attributes in every string, recursing through arrays
342
+ * and objects (object keys decide per {@link isLinkKeyName}).
343
+ */
344
+ export function canonicaliseJsonLinks(value, run, where, asUrl = false) {
345
+ if (typeof value === "string") {
346
+ if (asUrl)
347
+ return canonicaliseUrl(value, run, where);
348
+ if (value.includes("<"))
349
+ return canonicaliseHtmlLinks(value, run, where);
350
+ // A text value is never a link as a whole, but one that starts like a
351
+ // reference and breaks the grammar renders as a dead `caelo:` href
352
+ // wherever a module puts it in an attribute.
353
+ reportMalformedRefs(value, run, where);
354
+ return value;
355
+ }
356
+ if (Array.isArray(value)) {
357
+ let changed = false;
358
+ const next = value.map((v, i) => {
359
+ const r = canonicaliseJsonLinks(v, run, `${where}[${i}]`, asUrl);
360
+ if (r !== v)
361
+ changed = true;
362
+ return r;
363
+ });
364
+ return changed ? next : value;
365
+ }
366
+ if (value !== null && typeof value === "object") {
367
+ let changed = false;
368
+ const out = {};
369
+ for (const [k, v] of Object.entries(value)) {
370
+ const r = canonicaliseJsonLinks(v, run, `${where}.${k}`, isLinkKeyName(k));
371
+ if (r !== v)
372
+ changed = true;
373
+ out[k] = r;
374
+ }
375
+ return changed ? out : value;
376
+ }
377
+ return value;
378
+ }
379
+ /** Field kinds whose whole value is a URL. */
380
+ const URL_KINDS = new Set(["url", "link", "image"]);
381
+ /** Field kinds that hold nested-module refs, never links. */
382
+ const NESTED_KINDS = new Set(["module", "module-list"]);
383
+ function canonicaliseFieldValue(field, name, value, run, where) {
384
+ if (field && NESTED_KINDS.has(field.kind))
385
+ return value;
386
+ const asUrl = (field !== undefined && URL_KINDS.has(field.kind)) || isLinkKeyName(name);
387
+ return canonicaliseJsonLinks(value, run, where, asUrl);
388
+ }
389
+ /**
390
+ * Canonicalise a content instance's values against its module's fields.
391
+ * Values without a declared field are still scanned (key-name rule +
392
+ * HTML) — a stale value renders nowhere today but may again tomorrow.
393
+ */
394
+ export function canonicaliseContentValues(fields, values, run) {
395
+ const byName = new Map(fields.map((f) => [f.name, f]));
396
+ const out = {};
397
+ for (const [k, v] of Object.entries(values)) {
398
+ out[k] = canonicaliseFieldValue(byName.get(k), k, v, run, `values.${k}`);
399
+ }
400
+ return out;
401
+ }
402
+ /** Canonicalise every field's `default` (layout chrome content lives there). */
403
+ export function canonicaliseFieldDefaults(fields, run) {
404
+ return fields.map((f) => {
405
+ if (f.default === undefined || f.default === null)
406
+ return f;
407
+ const next = canonicaliseFieldValue(f, f.name, f.default, run, `fields.${f.name}.default`);
408
+ return next === f.default ? f : { ...f, default: next };
409
+ });
410
+ }
411
+ /**
412
+ * Every link literal inside a stored state (values, defaults, set items,
413
+ * module HTML) — the {@link LinkCanonicaliseRun.grandfathered} set of the
414
+ * next write. Collected with a lookup that knows nothing, so every
415
+ * candidate surfaces as an "issue" carrying its raw value.
416
+ */
417
+ export function collectLinkLiterals(state) {
418
+ const run = linkCanonicaliseRun(NOTHING_RESOLVES, { mode: "report" });
419
+ canonicaliseJsonLinks(state, run, "", false);
420
+ // Whole-value positions are only known with field context; strings
421
+ // that look like a link are therefore also taken verbatim.
422
+ const out = new Set(run.issues.map((i) => i.value));
423
+ collectStrings(state, out);
424
+ return out;
425
+ }
426
+ function collectStrings(value, out) {
427
+ if (typeof value === "string") {
428
+ const v = value.trim();
429
+ if (v.startsWith("/") || v.startsWith("caelo:") || /^https?:\/\//i.test(v))
430
+ out.add(v);
431
+ return;
432
+ }
433
+ if (Array.isArray(value))
434
+ for (const v of value)
435
+ collectStrings(v, out);
436
+ else if (value !== null && typeof value === "object") {
437
+ for (const v of Object.values(value))
438
+ collectStrings(v, out);
439
+ }
440
+ }
441
+ const NOTHING_RESOLVES = {
442
+ pageIdForPath: () => null,
443
+ mediaIdForSlug: () => null,
444
+ pageExists: () => false,
445
+ mediaExists: () => false,
446
+ isOwnHost: () => true,
447
+ };
448
+ const ISSUE_TEXT = {
449
+ "unknown-page-path": "is not the path of any page on this site",
450
+ "unknown-media": "names no image or file in the media library",
451
+ "dangling-page-ref": "links to a page that was deleted",
452
+ "dangling-media-ref": "links to an image or file that was deleted",
453
+ "unknown-file": "is a file path nothing on this site serves (files are served from the media library: upload it, then link its media URL from find_media)",
454
+ "unsupported-link-form": "has a query or #anchor a stored link cannot carry (page links allow plain query/anchor characters only; media links allow neither)",
455
+ "malformed-link-ref": "starts like an internal reference (caelo:page/ or caelo:media/) but is broken, e.g. a truncated id or extra characters after it; write the page's path (/about#team) or the media URL (/_caelo/media/<slug>) instead, never a caelo: reference",
456
+ };
457
+ /**
458
+ * One AI-actionable message for a refused write (CLAUDE.md §11): what is
459
+ * wrong with each link and the next step. Paths only — the author never
460
+ * sees reference ids except for a reference that is already broken.
461
+ */
462
+ export function describeLinkIssues(issues) {
463
+ const lines = issues.slice(0, 10).map((i) => `${i.where}: "${i.value}" ${ISSUE_TEXT[i.kind]}`);
464
+ const more = issues.length > 10 ? ` (and ${issues.length - 10} more)` : "";
465
+ return (`Internal link check failed — ${lines.join("; ")}${more}. ` +
466
+ "Internal links must point at an existing page or media asset. Next step: use the exact path " +
467
+ "of an existing page (list_pages shows every page's path) or an existing media URL (find_media); " +
468
+ "if the page does not exist yet, create it first (or leave the link out and add it once the page " +
469
+ "exists). For a link to another site, write the full https:// URL.");
470
+ }
471
+ //# sourceMappingURL=link-canonicalise.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"link-canonicalise.js","sourceRoot":"","sources":["../src/link-canonicalise.ts"],"names":[],"mappings":"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"}
@@ -31,6 +31,18 @@ export type LinkRef = PageLinkRef | MediaLinkRef;
31
31
  * grammar is left alone.
32
32
  */
33
33
  export declare const LINK_REF_MALFORMED = "link-ref-malformed";
34
+ /**
35
+ * Whole-string tests for the query, anchor and media-variant parts of a
36
+ * reference — built from the grammar's own sources, so a writer that
37
+ * validates author input with them (write-time canonicalisation, #724
38
+ * rollout C) accepts exactly what {@link formatLinkRef} accepts and a bad
39
+ * suffix is a validation issue, never a thrown error.
40
+ */
41
+ export declare const LINK_REF_PART_PATTERNS: Readonly<{
42
+ query: RegExp;
43
+ anchor: RegExp;
44
+ variant: RegExp;
45
+ }>;
34
46
  /**
35
47
  * Parse a string that IS exactly one reference (a whole field value).
36
48
  * Returns null for anything else — a path, an external URL, or a string
@@ -98,15 +110,28 @@ export type LinkResolution =
98
110
  /**
99
111
  * The target exists but is not published, so a deploy build will not
100
112
  * contain it. Rendered with its URL; the caller applies the
101
- * environment's policy ({@link linkIssueSeverity}).
113
+ * environment's policy ({@link linkIssueSeverity}). `pageId` is the
114
+ * page the URL points at — the referenced page, or its sibling in the
115
+ * rendering page's variant.
102
116
  */
103
117
  | {
104
118
  readonly status: "unpublished";
105
119
  readonly url: string;
120
+ readonly pageId: string;
106
121
  }
107
122
  /** No live target (never existed, deleted, another chat's branch). */
108
123
  | {
109
124
  readonly status: "missing";
125
+ }
126
+ /**
127
+ * The target exists, but has no sibling in the rendering page's
128
+ * variant (a German page linking to a page that has no German
129
+ * version). Not rendered — linking into another variant instead is
130
+ * exactly the silent fallback CLAUDE.md §2 forbids.
131
+ */
132
+ | {
133
+ readonly status: "no-variant";
134
+ readonly variant: string;
110
135
  };
111
136
  /**
112
137
  * Turns references into URLs for ONE rendering page. Synchronous: the
@@ -139,8 +164,17 @@ export declare const LINK_TARGET_MISSING = "link-target-missing";
139
164
  */
140
165
  export declare const LINK_RESOLVER_UNAVAILABLE = "link-resolver-unavailable";
141
166
  /**
142
- * True for every link failure marker: a missing target, a malformed
143
- * reference and a render without a resolver. The static generator's
167
+ * `missingSlots` marker for a page reference whose target has no sibling
168
+ * in the rendering page's variant:
169
+ * `link-variant-missing:page/<targetId>:<variant>` (variant = the
170
+ * rendering page's, e.g. a locale code). Blocks a deploy like a missing
171
+ * target.
172
+ */
173
+ export declare const LINK_VARIANT_MISSING = "link-variant-missing";
174
+ /**
175
+ * True for every link failure marker: a missing target, a target with
176
+ * no version in the rendering page's variant, a malformed reference and
177
+ * a render without a resolver. The static generator's
144
178
  * render gate and the nested-module echo filter both key on this, so a
145
179
  * new marker added here blocks a deploy everywhere at once.
146
180
  */
@@ -165,7 +199,9 @@ export declare function resolveLinkRefsInHtml(html: string, resolver: LinkResolv
165
199
  * cleanly (maintainer decision on #724): a missing target blocks
166
200
  * everywhere; an unpublished one is a warning at Stage and blocks
167
201
  * Publish live / promote. The editor preview shows drafts, so nothing
168
- * there is an issue beyond a missing target.
202
+ * there is an issue beyond a missing target. A target without a sibling
203
+ * in the rendering page's variant counts as missing: there is no page
204
+ * the link could go to.
169
205
  */
170
206
  export declare function linkIssueSeverity(env: LinkRenderEnv, status: LinkResolution["status"]): "block" | "warning" | null;
171
207
  /** A page as the link index needs it. */
@@ -185,6 +221,16 @@ export interface LinkIndexMedia {
185
221
  /** `media_assets.slug` — the URL the editor serves and the build rewrites. */
186
222
  readonly slug: string;
187
223
  }
224
+ /**
225
+ * One page's place in a plugin's page-variant partition (the
226
+ * `link-resolve` composition point): its `variant` (international-site:
227
+ * the locale code) and the `group` of pages that are versions of each
228
+ * other (null = the page has no versions besides itself).
229
+ */
230
+ export interface LinkPageVariant {
231
+ readonly variant: string;
232
+ readonly group: string | null;
233
+ }
188
234
  /** What a render-wide link index is built from. */
189
235
  export interface SiteLinkIndexInput {
190
236
  /** Every live (non-deleted) page visible to the render's scope, drafts included. */
@@ -198,6 +244,14 @@ export interface SiteLinkIndexInput {
198
244
  * internal link, and byte-identical with the canonical (#590).
199
245
  */
200
246
  readonly pageUrlStyle: PageUrlStyle;
247
+ /**
248
+ * The `link-resolve` composition point's answer: page id → its variant
249
+ * and variant group. Absent or empty = no plugin partitions the site,
250
+ * every page reference resolves to the referenced page. A page missing
251
+ * from a non-empty map is one no plugin has an opinion about: links
252
+ * FROM it resolve as referenced, and a link TO it is not remapped.
253
+ */
254
+ readonly pageVariants?: ReadonlyMap<string, LinkPageVariant>;
201
255
  }
202
256
  /**
203
257
  * The render-wide lookup tables, from which a per-page resolver is cut.
@@ -206,10 +260,11 @@ export interface SiteLinkIndexInput {
206
260
  export interface SiteLinkIndex {
207
261
  readonly env: LinkRenderEnv;
208
262
  /**
209
- * The resolver for rendering page `renderingPageId`. Today every page
210
- * gets the same answers; rollout D's `link-resolve` composition point
211
- * hooks in here to map a target onto the rendering page's locale.
212
- * Each call returns a fresh {@link RecordingLinkResolver}.
263
+ * The resolver for rendering page `renderingPageId`: page references
264
+ * resolve to the target's sibling in the rendering page's variant
265
+ * ({@link SiteLinkIndexInput.pageVariants}); null = a render outside
266
+ * any page, which maps nothing. Each call returns a fresh
267
+ * {@link RecordingLinkResolver}.
213
268
  */
214
269
  forPage(renderingPageId: string | null): RecordingLinkResolver;
215
270
  /** The page's public path (no style applied), or null when unknown. */
@@ -1 +1 @@
1
- {"version":3,"file":"link-refs.d.ts","sourceRoot":"","sources":["../src/link-refs.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"link-refs.d.ts","sourceRoot":"","sources":["../src/link-refs.ts"],"names":[],"mappings":"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"}