@xtrable-ltd/nanoesis 0.1.23 → 0.1.25

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 (30) hide show
  1. package/dist/adapter-azure-blob.d.ts +13 -6
  2. package/dist/adapter-azure-blob.js +21 -9
  3. package/dist/{chunk-WHK3SBV7.js → chunk-H6ZHZWDJ.js} +29 -12
  4. package/dist/{chunk-SHGYQTZ7.js → chunk-TEIQFPNO.js} +6 -2
  5. package/dist/editor-api.js +2 -2
  6. package/dist/index.d.ts +57 -6
  7. package/dist/index.js +7 -1
  8. package/dist/mcp.js +3 -3
  9. package/editor/assets/{MigrationsPane-hBGg21Ij.js → MigrationsPane-B0x1iqiv.js} +1 -1
  10. package/editor/assets/{TemplatesPane-BzZB6Kts.js → TemplatesPane-CIpyieRF.js} +7 -7
  11. package/editor/assets/{cssMode-Ds5VxRKY.js → cssMode-DhaV27rt.js} +1 -1
  12. package/editor/assets/{freemarker2-Gw8CKJiZ.js → freemarker2-DokFNyj0.js} +1 -1
  13. package/editor/assets/{handlebars-DVp1g4p2.js → handlebars-Dw9FmLS4.js} +1 -1
  14. package/editor/assets/{html-kkPnNaEo.js → html-CMqaP5wp.js} +1 -1
  15. package/editor/assets/{htmlMode-BiG4uwoG.js → htmlMode-CDxfYToP.js} +1 -1
  16. package/editor/assets/index-BOZboKLR.css +7 -0
  17. package/editor/assets/{index-DxbHJHyK.js → index-oaWmlNac.js} +63 -63
  18. package/editor/assets/{javascript-BC4Bf5K5.js → javascript-B4MO-q5P.js} +1 -1
  19. package/editor/assets/{jsonMode-lLRUZoYu.js → jsonMode-DavXHLfw.js} +1 -1
  20. package/editor/assets/{liquid-BPzeih2Z.js → liquid-1A6xvXiH.js} +1 -1
  21. package/editor/assets/{mdx-BxKzBYDE.js → mdx-CdGqZmKc.js} +1 -1
  22. package/editor/assets/{python-DvM64iSM.js → python-xlLpeYr9.js} +1 -1
  23. package/editor/assets/{razor-CG83wwEb.js → razor-DYPAhJKR.js} +1 -1
  24. package/editor/assets/{tsMode-D3JNQ8by.js → tsMode-DSEeCQ6X.js} +1 -1
  25. package/editor/assets/{typescript-zv70Ruos.js → typescript-CgJRoqTj.js} +1 -1
  26. package/editor/assets/{xml-CBgqXGl5.js → xml-BnuD7ypQ.js} +1 -1
  27. package/editor/assets/{yaml-Bg6knfUf.js → yaml-BzsAd7-q.js} +1 -1
  28. package/editor/index.html +2 -2
  29. package/package.json +1 -1
  30. package/editor/assets/index-C9dl_3yI.css +0 -7
@@ -20,8 +20,12 @@ interface BlobContainer {
20
20
  list(prefix: string): Promise<readonly string[]>;
21
21
  /** A blob's bytes, or null if it does not exist. */
22
22
  read(name: string): Promise<Uint8Array | null>;
23
- /** Create or overwrite a blob with the given bytes and content type. */
24
- write(name: string, data: Uint8Array, contentType: string): Promise<void>;
23
+ /**
24
+ * Create or overwrite a blob with the given bytes and content type. `cacheControl`, when
25
+ * given, is stored as the blob's `Cache-Control` so a static-website read serves the right
26
+ * freshness (DESIGN §11); omitted for the editor's working blobs.
27
+ */
28
+ write(name: string, data: Uint8Array, contentType: string, cacheControl?: string): Promise<void>;
25
29
  /** Delete a blob; a missing blob is a no-op (idempotent). */
26
30
  remove(name: string): Promise<void>;
27
31
  }
@@ -31,13 +35,16 @@ interface BlobContainer {
31
35
  */
32
36
  declare class InMemoryBlobContainer implements BlobContainer {
33
37
  private readonly blobs;
38
+ private readonly cacheControls;
34
39
  constructor(seed?: Readonly<Record<string, Uint8Array | string>>);
35
40
  list(prefix: string): Promise<readonly string[]>;
36
41
  read(name: string): Promise<Uint8Array | null>;
37
- write(name: string, data: Uint8Array, contentType?: string): Promise<void>;
42
+ write(name: string, data: Uint8Array, contentType?: string, cacheControl?: string): Promise<void>;
38
43
  remove(name: string): Promise<void>;
39
44
  /** Test helper: the current blob names. */
40
45
  get names(): readonly string[];
46
+ /** Test helper: the `Cache-Control` a blob was written with, if any. */
47
+ cacheControlOf(name: string): string | undefined;
41
48
  }
42
49
 
43
50
  /**
@@ -56,7 +63,7 @@ declare class AzureBlobContainer implements BlobContainer {
56
63
  ensureContainer(): Promise<void>;
57
64
  list(prefix: string): Promise<readonly string[]>;
58
65
  read(name: string): Promise<Uint8Array | null>;
59
- write(name: string, data: Uint8Array, contentType: string): Promise<void>;
66
+ write(name: string, data: Uint8Array, contentType: string, cacheControl?: string): Promise<void>;
60
67
  remove(name: string): Promise<void>;
61
68
  }
62
69
 
@@ -71,7 +78,7 @@ declare class BlobContainerStore implements BlobStore {
71
78
  private readonly container;
72
79
  constructor(container: BlobContainer);
73
80
  get(key: string): Promise<Uint8Array | undefined>;
74
- put(key: string, bytes: Uint8Array): Promise<void>;
81
+ put(key: string, bytes: Uint8Array, cacheControl?: string): Promise<void>;
75
82
  delete(key: string): Promise<void>;
76
83
  }
77
84
 
@@ -87,7 +94,7 @@ declare class BlobArtifactSink implements ArtifactSink {
87
94
  private readonly container;
88
95
  constructor(container: BlobContainer);
89
96
  wipe(): Promise<void>;
90
- write(path: string, contents: string | Uint8Array): Promise<void>;
97
+ write(path: string, contents: string | Uint8Array, cacheControl?: string): Promise<void>;
91
98
  }
92
99
 
93
100
  /**
@@ -1,10 +1,11 @@
1
1
  import {
2
2
  contentTypeFor
3
- } from "./chunk-WHK3SBV7.js";
3
+ } from "./chunk-H6ZHZWDJ.js";
4
4
 
5
5
  // ../../adapters/azure-blob/src/container.ts
6
6
  var InMemoryBlobContainer = class {
7
7
  blobs = /* @__PURE__ */ new Map();
8
+ cacheControls = /* @__PURE__ */ new Map();
8
9
  constructor(seed = {}) {
9
10
  for (const [name, value] of Object.entries(seed)) {
10
11
  this.blobs.set(name, typeof value === "string" ? new TextEncoder().encode(value) : value);
@@ -20,9 +21,10 @@ var InMemoryBlobContainer = class {
20
21
  async read(name) {
21
22
  return this.blobs.get(name) ?? null;
22
23
  }
23
- async write(name, data, contentType) {
24
+ async write(name, data, contentType, cacheControl) {
24
25
  void contentType;
25
26
  this.blobs.set(name, data);
27
+ if (cacheControl !== void 0) this.cacheControls.set(name, cacheControl);
26
28
  }
27
29
  async remove(name) {
28
30
  this.blobs.delete(name);
@@ -31,6 +33,10 @@ var InMemoryBlobContainer = class {
31
33
  get names() {
32
34
  return [...this.blobs.keys()].sort();
33
35
  }
36
+ /** Test helper: the `Cache-Control` a blob was written with, if any. */
37
+ cacheControlOf(name) {
38
+ return this.cacheControls.get(name);
39
+ }
34
40
  };
35
41
 
36
42
  // ../../adapters/azure-blob/src/azure-container.ts
@@ -68,9 +74,12 @@ var AzureBlobContainer = class _AzureBlobContainer {
68
74
  throw error;
69
75
  }
70
76
  }
71
- async write(name, data, contentType) {
77
+ async write(name, data, contentType, cacheControl) {
72
78
  await this.client.getBlockBlobClient(name).uploadData(Buffer.from(data), {
73
- blobHTTPHeaders: { blobContentType: contentType }
79
+ blobHTTPHeaders: {
80
+ blobContentType: contentType,
81
+ ...cacheControl !== void 0 && { blobCacheControl: cacheControl }
82
+ }
74
83
  });
75
84
  }
76
85
  async remove(name) {
@@ -92,9 +101,9 @@ var BlobContainerStore = class {
92
101
  async get(key) {
93
102
  return await this.container.read(normalizeBlobName(key)) ?? void 0;
94
103
  }
95
- async put(key, bytes) {
104
+ async put(key, bytes, cacheControl) {
96
105
  const name = normalizeBlobName(key);
97
- await this.container.write(name, bytes, contentTypeFor(name));
106
+ await this.container.write(name, bytes, contentTypeFor(name), cacheControl);
98
107
  }
99
108
  async delete(key) {
100
109
  await this.container.remove(normalizeBlobName(key));
@@ -112,10 +121,10 @@ var BlobArtifactSink = class {
112
121
  await this.container.remove(name);
113
122
  }
114
123
  }
115
- async write(path, contents) {
124
+ async write(path, contents, cacheControl) {
116
125
  const name = normalizeBlobName(path);
117
126
  const data = typeof contents === "string" ? new TextEncoder().encode(contents) : contents;
118
- await this.container.write(name, data, contentTypeFor(name));
127
+ await this.container.write(name, data, contentTypeFor(name), cacheControl);
119
128
  }
120
129
  };
121
130
 
@@ -124,7 +133,10 @@ function azureStorage(container) {
124
133
  const store = new BlobContainerStore(container);
125
134
  return {
126
135
  get: (key) => store.get(key),
127
- put: (key, bytes) => store.put(key, bytes),
136
+ // Forward `cacheControl` (DESIGN §11): this is the published-site sink `createEditor`
137
+ // actually wires (`asSink(azureStorage(website))`), so dropping the arg here silently
138
+ // strips the publish Cache-Control before it reaches the blob.
139
+ put: (key, bytes, cacheControl) => store.put(key, bytes, cacheControl),
128
140
  delete: (key) => store.delete(key),
129
141
  wipe: async () => {
130
142
  for (const name of await container.list("")) await container.remove(name);
@@ -1554,6 +1554,13 @@ function renderAuthors(value, directory) {
1554
1554
  return joinAuthors(names);
1555
1555
  }
1556
1556
 
1557
+ // ../engine/src/publish/cache-control.ts
1558
+ var CACHE_REVALIDATE = "no-cache";
1559
+ var CACHE_IMMUTABLE = "public, max-age=31536000, immutable";
1560
+ function cacheControlFor(artifact) {
1561
+ return artifact.cacheControl ?? CACHE_REVALIDATE;
1562
+ }
1563
+
1557
1564
  // ../engine/src/media/media.ts
1558
1565
  var DEFAULT_WIDTHS = [400, 800, 1200, 1600];
1559
1566
  var MIME = {
@@ -1591,7 +1598,7 @@ async function processImage(input, assetPath, encoder) {
1591
1598
  const artifacts = [];
1592
1599
  const urlOf = (variant) => {
1593
1600
  const path = `${base}.${hash}-${variant.width}.${extOf(variant.format)}`;
1594
- artifacts.push({ path, contents: variant.bytes });
1601
+ artifacts.push({ path, contents: variant.bytes, cacheControl: CACHE_IMMUTABLE });
1595
1602
  return `/${path}`;
1596
1603
  };
1597
1604
  const byFormat = /* @__PURE__ */ new Map();
@@ -2786,11 +2793,11 @@ async function validateSite(source) {
2786
2793
  deriveFields(snapshotHtml, components),
2787
2794
  deriveFields(currentHtml, components)
2788
2795
  );
2789
- const destructive = new Set(
2790
- delta.typeChanged.filter((change) => change.destructive).map((change) => change.name)
2796
+ const renderDrift = new Set(
2797
+ delta.typeChanged.filter((change) => change.destructive && valueKindOf(change.from) !== valueKindOf(change.to)).map((change) => change.name)
2791
2798
  );
2792
- driftFieldsCache.set(templateName, destructive);
2793
- return destructive;
2799
+ driftFieldsCache.set(templateName, renderDrift);
2800
+ return renderDrift;
2794
2801
  };
2795
2802
  const snapshotNameCache = /* @__PURE__ */ new Map();
2796
2803
  const highestSnapshotName = async (baseName) => {
@@ -2874,7 +2881,7 @@ async function validateSite(source) {
2874
2881
  add(
2875
2882
  "warning",
2876
2883
  "content.type-drift",
2877
- `"${node.path}" has field${affected.length === 1 ? "" : "s"} whose type changed destructively in template "${templateName}": ${affected.map((f) => `"${f}"`).join(", ")}. The value will render under the new type (commonly HTML escaped as text). Open the Migrations workspace to migrate.`,
2884
+ `"${node.path}" has field${affected.length === 1 ? "" : "s"} whose stored value now renders under a different kind in template "${templateName}": ${affected.map((f) => `"${f}"`).join(", ")}. The value carries over but may look different (e.g. rich text shown as escaped text). Re-edit the field, or revert the template's type change if it wasn't intended.`,
2878
2885
  node.path
2879
2886
  );
2880
2887
  }
@@ -3093,14 +3100,14 @@ async function publishSite(source, sink, options = {}) {
3093
3100
  hashByPath.set(artifact.path, contentHash(asBytes(artifact.contents)));
3094
3101
  const hashFor = (path) => hashByPath.get(path);
3095
3102
  const stamped = artifacts.map(
3096
- (artifact) => typeof artifact.contents === "string" && artifact.path.endsWith(".html") ? { path: artifact.path, contents: cacheBustAssets(artifact.contents, hashFor) } : artifact
3103
+ (artifact) => typeof artifact.contents === "string" && artifact.path.endsWith(".html") ? { ...artifact, contents: cacheBustAssets(artifact.contents, hashFor) } : artifact
3097
3104
  );
3098
3105
  const byPath = /* @__PURE__ */ new Map();
3099
- for (const artifact of [...stamped, ...passthrough]) byPath.set(artifact.path, artifact.contents);
3106
+ for (const artifact of [...stamped, ...passthrough]) byPath.set(artifact.path, artifact);
3100
3107
  await mapWithConcurrency(
3101
- [...byPath],
3108
+ [...byPath.values()],
3102
3109
  writeConcurrency,
3103
- ([path, contents]) => sink.write(path, contents)
3110
+ (artifact) => sink.write(artifact.path, artifact.contents, cacheControlFor(artifact))
3104
3111
  );
3105
3112
  await purge.purgeAll();
3106
3113
  return { ok: true, validation, written: [...byPath.keys()].sort(), summary };
@@ -3155,13 +3162,20 @@ function normalizePath2(path) {
3155
3162
  }
3156
3163
  var InMemoryArtifactSink = class {
3157
3164
  store = /* @__PURE__ */ new Map();
3158
- async write(path, contents) {
3159
- this.store.set(normalizePath2(path), contents);
3165
+ cacheControls = /* @__PURE__ */ new Map();
3166
+ async write(path, contents, cacheControl) {
3167
+ const key = normalizePath2(path);
3168
+ this.store.set(key, contents);
3169
+ if (cacheControl !== void 0) this.cacheControls.set(key, cacheControl);
3160
3170
  }
3161
3171
  /** The artifacts written so far, path→contents, for assertions in tests. */
3162
3172
  get written() {
3163
3173
  return this.store;
3164
3174
  }
3175
+ /** The `Cache-Control` an artifact was written with, for assertions in tests. */
3176
+ cacheControlOf(path) {
3177
+ return this.cacheControls.get(normalizePath2(path));
3178
+ }
3165
3179
  };
3166
3180
 
3167
3181
  // ../engine/src/identity.ts
@@ -3393,6 +3407,9 @@ export {
3393
3407
  toAuthorRefs,
3394
3408
  joinAuthors,
3395
3409
  renderAuthors,
3410
+ CACHE_REVALIDATE,
3411
+ CACHE_IMMUTABLE,
3412
+ cacheControlFor,
3396
3413
  contentHash,
3397
3414
  processImage,
3398
3415
  buildPictureMarkup,
@@ -17,7 +17,7 @@ import {
17
17
  renderReferenceMarkdown,
18
18
  validateSite,
19
19
  workingStoreRoundTripDiagnostic
20
- } from "./chunk-WHK3SBV7.js";
20
+ } from "./chunk-H6ZHZWDJ.js";
21
21
 
22
22
  // ../editor-api/src/scaffold.ts
23
23
  var HOME_HTML = `<!doctype html>
@@ -911,7 +911,11 @@ async function anyPublishedContentItem(store, dir = "content") {
911
911
  function asSink(storage) {
912
912
  const encoder = new TextEncoder();
913
913
  return {
914
- write: (path, contents) => storage.put(path, typeof contents === "string" ? encoder.encode(contents) : contents)
914
+ write: (path, contents, cacheControl) => storage.put(
915
+ path,
916
+ typeof contents === "string" ? encoder.encode(contents) : contents,
917
+ cacheControl
918
+ )
915
919
  };
916
920
  }
917
921
  function createEditor(config) {
@@ -21,8 +21,8 @@ import {
21
21
  serveEditorAsset,
22
22
  templateSnapshotIntegrityDiagnostic,
23
23
  templateSuffixConflictDiagnostic
24
- } from "./chunk-SHGYQTZ7.js";
25
- import "./chunk-WHK3SBV7.js";
24
+ } from "./chunk-TEIQFPNO.js";
25
+ import "./chunk-H6ZHZWDJ.js";
26
26
  export {
27
27
  FileBrandingStore,
28
28
  InMemoryBrandingStore,
package/dist/index.d.ts CHANGED
@@ -149,8 +149,12 @@ declare function parseSortFile(raw: unknown): SortFile;
149
149
  interface BlobStore {
150
150
  /** The bytes stored at `key`, or `undefined` if nothing is stored there. */
151
151
  get(key: string): Promise<Uint8Array | undefined>;
152
- /** Create or overwrite `key` with `bytes`. */
153
- put(key: string, bytes: Uint8Array): Promise<void>;
152
+ /**
153
+ * Create or overwrite `key` with `bytes`. `cacheControl` is an optional `Cache-Control`
154
+ * value the publish sink passes for a served-website store to persist (DESIGN §11); the
155
+ * editor's working store omits it, and a store with no header model ignores it.
156
+ */
157
+ put(key: string, bytes: Uint8Array, cacheControl?: string): Promise<void>;
154
158
  /** Remove `key`. Deleting an absent key is a no-op (idempotent). */
155
159
  delete(key: string): Promise<void>;
156
160
  }
@@ -310,6 +314,12 @@ interface Artifact {
310
314
  /** Output path relative to the published root, e.g. "blog/first/index.html". */
311
315
  readonly path: string;
312
316
  readonly contents: string | Uint8Array;
317
+ /**
318
+ * The `Cache-Control` policy for this artifact (DESIGN §11; see
319
+ * {@link cacheControlFor}). Absent means revalidate-every-load; a fingerprinted
320
+ * (content-hashed) asset sets it to immutable. Only the publish sink reads it.
321
+ */
322
+ readonly cacheControl?: string;
313
323
  }
314
324
  /**
315
325
  * Compile a whole site to artifacts (DESIGN §15 step 9, compile phase). Walks the
@@ -1291,8 +1301,13 @@ declare const noopPurgeService: PurgeService;
1291
1301
  * Paths are POSIX-style and relative to the published root (e.g. "blog/first/index.html").
1292
1302
  */
1293
1303
  interface ArtifactSink {
1294
- /** Write one artifact, creating any intermediate structure the backing store needs. */
1295
- write(path: string, contents: string | Uint8Array): Promise<void>;
1304
+ /**
1305
+ * Write one artifact, creating any intermediate structure the backing store needs.
1306
+ * `cacheControl` is the artifact's `Cache-Control` policy (DESIGN §11): a store that
1307
+ * serves HTTP (the blob sink) persists it; one with no header model (the filesystem
1308
+ * sink) ignores it. Optional so non-publish callers (e.g. a port probe) can omit it.
1309
+ */
1310
+ write(path: string, contents: string | Uint8Array, cacheControl?: string): Promise<void>;
1296
1311
  }
1297
1312
  /**
1298
1313
  * An in-memory {@link ArtifactSink} backed by a flat path→contents map. This is the
@@ -1301,9 +1316,12 @@ interface ArtifactSink {
1301
1316
  */
1302
1317
  declare class InMemoryArtifactSink implements ArtifactSink {
1303
1318
  private readonly store;
1304
- write(path: string, contents: string | Uint8Array): Promise<void>;
1319
+ private readonly cacheControls;
1320
+ write(path: string, contents: string | Uint8Array, cacheControl?: string): Promise<void>;
1305
1321
  /** The artifacts written so far, path→contents, for assertions in tests. */
1306
1322
  get written(): ReadonlyMap<string, string | Uint8Array>;
1323
+ /** The `Cache-Control` an artifact was written with, for assertions in tests. */
1324
+ cacheControlOf(path: string): string | undefined;
1307
1325
  }
1308
1326
 
1309
1327
  interface PublishOptions extends CompileSiteOptions {
@@ -1365,6 +1383,39 @@ interface PublishResult {
1365
1383
  */
1366
1384
  declare function publishSite(source: ContentSource, sink: ArtifactSink, options?: PublishOptions): Promise<PublishResult>;
1367
1385
 
1386
+ /**
1387
+ * Cache-Control policy for published artifacts (DESIGN §11; see
1388
+ * docs/cache-busting-and-browser-cache.md). The published site is served from a static
1389
+ * store ($web / a folder behind a CDN) that sets no freshness directive of its own, so
1390
+ * without an explicit header browsers fall back to *heuristic* caching (RFC 9111 §4.2.2)
1391
+ * and keep serving a stale copy until a hard refresh. A CDN purge can't fix that, it
1392
+ * clears the edge, not a visitor's browser. So publish stamps each artifact with the
1393
+ * policy for its class, and the storage port persists it (the Azure adapter as the blob's
1394
+ * `cacheControl`; the filesystem adapter has no header model and ignores it).
1395
+ *
1396
+ * Two classes today:
1397
+ * - **Revalidate** (HTML and every non-fingerprinted file): `no-cache` means "always
1398
+ * check with the origin before reuse". The store serves strong `ETag`/`Last-Modified`,
1399
+ * so this is a cheap `304` when nothing changed and the new bytes the instant something
1400
+ * does, no stale window, no hard refresh.
1401
+ * - **Immutable** (content-hashed asset filenames): cache hard and forever. Safe only
1402
+ * because the filename encodes the content hash, so changed bytes mean a new URL. Today
1403
+ * that's the responsive image variants the media pipeline emits (`hero.<hash>-800.webp`);
1404
+ * stable-named assets (`styles.css`) stay on revalidate until they're content-hashed too.
1405
+ */
1406
+ /** Revalidate every load: the default for HTML and any non-fingerprinted artifact. */
1407
+ declare const CACHE_REVALIDATE = "no-cache";
1408
+ /** Cache hard and forever: only for content-hashed (fingerprinted) asset filenames. */
1409
+ declare const CACHE_IMMUTABLE = "public, max-age=31536000, immutable";
1410
+ /**
1411
+ * The Cache-Control value for an artifact: its own policy if it declared one (a
1412
+ * fingerprinted asset opts into {@link CACHE_IMMUTABLE}), else {@link CACHE_REVALIDATE}.
1413
+ * Revalidate is the safe default, never serve a non-hashed file as immutable.
1414
+ */
1415
+ declare function cacheControlFor(artifact: {
1416
+ readonly cacheControl?: string;
1417
+ }): string;
1418
+
1368
1419
  /**
1369
1420
  * The identity port (DESIGN §11). The engine has *no auth logic*, auth is purely an
1370
1421
  * HTTP-layer concern that lives in the host, but the port type lives here alongside
@@ -1714,4 +1765,4 @@ declare function createDiagnosticRegistry(): DiagnosticRegistry;
1714
1765
 
1715
1766
  declare const workingStoreRoundTripDiagnostic: Diagnostic;
1716
1767
 
1717
- export { type Artifact, type ArtifactSink, type AuthEndpoints, type AuthResult, type AuthorDirectory, type AuthorEntry, type AuthorOption, type AuthorRef, type AuthoringReference, type BlobStore, type BoundItem, type ChangePasswordRequest, type ChangePasswordSuccess, type CollectionConfig, type CollectionQuery, type CompileInput, type CompilePageOptions, type CompileSiteOptions, type CompiledPage, type ComponentMap, type ContentIndex, type ContentItem, ContentParseError, type ContentSource, type CreateTokenSuccess, type CreateUserRequest, DEFAULT_DIRS, DOCUMENT_SHELL, type DerivedField, type DiagnoseDeps, type Severity as DiagnoseSeverity, type Source as DiagnoseSource, type Diagnostic$1 as Diagnostic, type Diagnostic as DiagnosticCheck, type DiagnosticRegistry, type DirEntry, type DirNode, type EncodeRequest, type EncodedImage, type EncodedVariant, type EntryKind, FIELD_TYPES, type FieldPrimitive, type FieldRecord, type FieldType, type FieldTypeDef, type FieldValue, type Finding, type IdentityProvider, type ImageEncoder, type ImageFormat, type ImageInfo, InMemoryArtifactSink, InMemoryBlobStore, InMemoryContentSource, IndexedStore, type ItemNode, type LengthConstraints, type LoginRequest, type LoginSuccess, type MediaResolver, type MigrationResolution, type PageEntry, type PendingMigrationItem, type PendingMigrations, type PreBuildHook, type Principal, type PublishOptions, type PublishResult, type PublishSummary, type PurgeService, RESERVED_PREFIX, type ReconcileResult, type RedirectRule, type ReferenceContext, type ReferenceEntry, type ReferenceSection, type RefreshSuccess, type RenameResult, type Repair, type RepairArgs, type ResetPasswordRequest, type ResolveContext, type Role, type RssOptions, type SchemaDelta, type SchemaFieldRef, type Scope, type Severity$1 as Severity, type SiteConfig, type SortFile, type StampDecision, type StampRecord, type Storage, type TemplateAnalysis, type TemplateKind, type TokenContext, type TokenRef, type TreeNode, type TypeChange, type UpdateUserRequest, type UserAdminEndpoints, type UserSummary, type ValidationResult, type ValueKind, type WorkingStore, analyzeTemplate, applyMigration, baseTemplateName, bestFitSnapshot, buildAuthoringReference, buildContentIndex, buildPictureMarkup, buildRedirects, buildResolveContext, buildRss, buildSitemap, canEdit, compilePage, compileSite, compileTemplate, computeSchemaDelta, contentHash, contentTypeFor, createDiagnosticRegistry, deriveFields, detectStamp, emptyIndex, escapeHtmlAttribute, escapeHtmlText, escapeJsonStringContent, findTokens, hasRole, humanize, inferControl, isDestructiveTypeChange, isFieldType, isReservedVersionedPath, isVersionedTemplateName, joinAuthors, loadComponentScripts, loadComponentStyles, loadComponents, loadContentTree, loadDocumentShell, loadIndex, loadRedirects, loadSiteConfig, loadTemplate, nextVersionNumber, noopPurgeService, outputPathForItem, parseContentItem, parseRedirects, parseSortFile, pendingMigrations, processImage, publishSite, reconcileIndex, renderAuthors, renderReferenceMarkdown, sanitizeUrl, saveIndex, slugify, snapshotName, textContent, toAuthorRefs, urlForItem, validateSite, valueKindOf, versionNumber, wholeValueToken, workingStoreRoundTripDiagnostic };
1768
+ export { type Artifact, type ArtifactSink, type AuthEndpoints, type AuthResult, type AuthorDirectory, type AuthorEntry, type AuthorOption, type AuthorRef, type AuthoringReference, type BlobStore, type BoundItem, CACHE_IMMUTABLE, CACHE_REVALIDATE, type ChangePasswordRequest, type ChangePasswordSuccess, type CollectionConfig, type CollectionQuery, type CompileInput, type CompilePageOptions, type CompileSiteOptions, type CompiledPage, type ComponentMap, type ContentIndex, type ContentItem, ContentParseError, type ContentSource, type CreateTokenSuccess, type CreateUserRequest, DEFAULT_DIRS, DOCUMENT_SHELL, type DerivedField, type DiagnoseDeps, type Severity as DiagnoseSeverity, type Source as DiagnoseSource, type Diagnostic$1 as Diagnostic, type Diagnostic as DiagnosticCheck, type DiagnosticRegistry, type DirEntry, type DirNode, type EncodeRequest, type EncodedImage, type EncodedVariant, type EntryKind, FIELD_TYPES, type FieldPrimitive, type FieldRecord, type FieldType, type FieldTypeDef, type FieldValue, type Finding, type IdentityProvider, type ImageEncoder, type ImageFormat, type ImageInfo, InMemoryArtifactSink, InMemoryBlobStore, InMemoryContentSource, IndexedStore, type ItemNode, type LengthConstraints, type LoginRequest, type LoginSuccess, type MediaResolver, type MigrationResolution, type PageEntry, type PendingMigrationItem, type PendingMigrations, type PreBuildHook, type Principal, type PublishOptions, type PublishResult, type PublishSummary, type PurgeService, RESERVED_PREFIX, type ReconcileResult, type RedirectRule, type ReferenceContext, type ReferenceEntry, type ReferenceSection, type RefreshSuccess, type RenameResult, type Repair, type RepairArgs, type ResetPasswordRequest, type ResolveContext, type Role, type RssOptions, type SchemaDelta, type SchemaFieldRef, type Scope, type Severity$1 as Severity, type SiteConfig, type SortFile, type StampDecision, type StampRecord, type Storage, type TemplateAnalysis, type TemplateKind, type TokenContext, type TokenRef, type TreeNode, type TypeChange, type UpdateUserRequest, type UserAdminEndpoints, type UserSummary, type ValidationResult, type ValueKind, type WorkingStore, analyzeTemplate, applyMigration, baseTemplateName, bestFitSnapshot, buildAuthoringReference, buildContentIndex, buildPictureMarkup, buildRedirects, buildResolveContext, buildRss, buildSitemap, cacheControlFor, canEdit, compilePage, compileSite, compileTemplate, computeSchemaDelta, contentHash, contentTypeFor, createDiagnosticRegistry, deriveFields, detectStamp, emptyIndex, escapeHtmlAttribute, escapeHtmlText, escapeJsonStringContent, findTokens, hasRole, humanize, inferControl, isDestructiveTypeChange, isFieldType, isReservedVersionedPath, isVersionedTemplateName, joinAuthors, loadComponentScripts, loadComponentStyles, loadComponents, loadContentTree, loadDocumentShell, loadIndex, loadRedirects, loadSiteConfig, loadTemplate, nextVersionNumber, noopPurgeService, outputPathForItem, parseContentItem, parseRedirects, parseSortFile, pendingMigrations, processImage, publishSite, reconcileIndex, renderAuthors, renderReferenceMarkdown, sanitizeUrl, saveIndex, slugify, snapshotName, textContent, toAuthorRefs, urlForItem, validateSite, valueKindOf, versionNumber, wholeValueToken, workingStoreRoundTripDiagnostic };
package/dist/index.js CHANGED
@@ -1,4 +1,6 @@
1
1
  import {
2
+ CACHE_IMMUTABLE,
3
+ CACHE_REVALIDATE,
2
4
  ContentParseError,
3
5
  DEFAULT_DIRS,
4
6
  DOCUMENT_SHELL,
@@ -19,6 +21,7 @@ import {
19
21
  buildResolveContext,
20
22
  buildRss,
21
23
  buildSitemap,
24
+ cacheControlFor,
22
25
  canEdit,
23
26
  compilePage,
24
27
  compileSite,
@@ -75,8 +78,10 @@ import {
75
78
  versionNumber,
76
79
  wholeValueToken,
77
80
  workingStoreRoundTripDiagnostic
78
- } from "./chunk-WHK3SBV7.js";
81
+ } from "./chunk-H6ZHZWDJ.js";
79
82
  export {
83
+ CACHE_IMMUTABLE,
84
+ CACHE_REVALIDATE,
80
85
  ContentParseError,
81
86
  DEFAULT_DIRS,
82
87
  DOCUMENT_SHELL,
@@ -97,6 +102,7 @@ export {
97
102
  buildResolveContext,
98
103
  buildRss,
99
104
  buildSitemap,
105
+ cacheControlFor,
100
106
  canEdit,
101
107
  compilePage,
102
108
  compileSite,
package/dist/mcp.js CHANGED
@@ -3,8 +3,8 @@ import {
3
3
  MCP_TOOLS,
4
4
  callMcpTool,
5
5
  readMcpResource
6
- } from "./chunk-SHGYQTZ7.js";
7
- import "./chunk-WHK3SBV7.js";
6
+ } from "./chunk-TEIQFPNO.js";
7
+ import "./chunk-H6ZHZWDJ.js";
8
8
 
9
9
  // ../../hosts/host-mcp/src/http.ts
10
10
  import { WebStandardStreamableHTTPServerTransport } from "@modelcontextprotocol/sdk/server/webStandardStreamableHttp.js";
@@ -56,7 +56,7 @@ function createMcpServer(deps, identity) {
56
56
  }
57
57
 
58
58
  // ../../hosts/host-mcp/src/http.ts
59
- var DEFAULT_VERSION = true ? "0.1.23" : "0.0.0-workspace";
59
+ var DEFAULT_VERSION = true ? "0.1.25" : "0.0.0-workspace";
60
60
  async function handleMcpRequest(deps, request, opts) {
61
61
  const server = createMcpServer(deps, {
62
62
  name: opts?.name ?? "nanoesis",
@@ -1,4 +1,4 @@
1
- import{af as Ie,aD as F,ad as Te,a7 as g,T as w,Q as e,f as n,a8 as Qe,o as a,N as H,aE as h,w as O,az as o,O as _,ar as v,p as Ue,G as X,v as Ve,g as He,aK as Xe,ax as c,aF as A,at as Y,au as _e,U as Ye,aq as Ze,a9 as ea}from"./index-DxbHJHyK.js";var aa=_('<p class="placeholder svelte-1lpfi31">Loading preview…</p>'),ta=_('<p class="error svelte-1lpfi31" role="alert"> </p>'),la=_("<option> </option>"),sa=_('<select class="svelte-1lpfi31"></select>'),ra=_('<li class="orphan svelte-1lpfi31"><div class="orphan-head svelte-1lpfi31"><code class="orphan-name svelte-1lpfi31"> </code> <span class="orphan-value svelte-1lpfi31"> </span></div> <div class="orphan-actions svelte-1lpfi31" role="radiogroup"><label class="svelte-1lpfi31"><input type="radio" value="drop"/> Drop</label> <label class="svelte-1lpfi31"><input type="radio" value="keep"/> Keep (unrendered)</label> <label class="svelte-1lpfi31"><input type="radio" value="rename"/> Rename to</label> <!></div></li>'),ia=_(`<section class="resolutions svelte-1lpfi31" aria-label="Orphan field resolutions"><h3 class="svelte-1lpfi31">Orphan fields</h3> <p class="hint svelte-1lpfi31">These fields exist in this item's JSON but the current template doesn't render them.
1
+ import{af as Ie,aD as F,ad as Te,a7 as g,T as w,Q as e,f as n,a8 as Qe,o as a,N as H,aE as h,w as O,az as o,O as _,ar as v,p as Ue,G as X,v as Ve,g as He,aK as Xe,ax as c,aF as A,at as Y,au as _e,U as Ye,aq as Ze,a9 as ea}from"./index-oaWmlNac.js";var aa=_('<p class="placeholder svelte-1lpfi31">Loading preview…</p>'),ta=_('<p class="error svelte-1lpfi31" role="alert"> </p>'),la=_("<option> </option>"),sa=_('<select class="svelte-1lpfi31"></select>'),ra=_('<li class="orphan svelte-1lpfi31"><div class="orphan-head svelte-1lpfi31"><code class="orphan-name svelte-1lpfi31"> </code> <span class="orphan-value svelte-1lpfi31"> </span></div> <div class="orphan-actions svelte-1lpfi31" role="radiogroup"><label class="svelte-1lpfi31"><input type="radio" value="drop"/> Drop</label> <label class="svelte-1lpfi31"><input type="radio" value="keep"/> Keep (unrendered)</label> <label class="svelte-1lpfi31"><input type="radio" value="rename"/> Rename to</label> <!></div></li>'),ia=_(`<section class="resolutions svelte-1lpfi31" aria-label="Orphan field resolutions"><h3 class="svelte-1lpfi31">Orphan fields</h3> <p class="hint svelte-1lpfi31">These fields exist in this item's JSON but the current template doesn't render them.
2
2
  Pick what to do with each.</p> <ul class="orphans svelte-1lpfi31"></ul></section>`),na=_('<p class="error svelte-1lpfi31" role="alert"> </p>'),oa=_('<div class="diff svelte-1lpfi31"><section class="pane svelte-1lpfi31" aria-label="Previous version (left)"><header class="pane-head svelte-1lpfi31"><!></header> <pre class="source svelte-1lpfi31"> </pre></section> <section class="pane svelte-1lpfi31" aria-label="Current template (right)"><header class="pane-head svelte-1lpfi31"> </header> <pre class="source svelte-1lpfi31"> </pre></section></div> <!> <!> <div class="commit-bar svelte-1lpfi31"><button type="button" class="primary svelte-1lpfi31"> </button></div>',1),va=_('<header class="detail-head svelte-1lpfi31"><button type="button" class="back svelte-1lpfi31">← Back</button> <h2 class="svelte-1lpfi31"> </h2></header> <!>',1),pa=_('<p class="error svelte-1lpfi31" role="alert"> </p>'),ca=_('<p class="placeholder svelte-1lpfi31">Loading…</p>'),fa=_(`<div class="empty svelte-1lpfi31"><h3 class="svelte-1lpfi31">All caught up</h3> <p>Every content item's fields match its bound template. Migrations show up here when a
3
3
  destructive template edit (or a manual hand-edit) leaves an item with orphan fields.</p></div>`),da=_('<li class="item"><button class="item-row svelte-1lpfi31" type="button"><span class="item-path svelte-1lpfi31"><code> </code></span> <span class="item-summary svelte-1lpfi31"><!> <!> <!></span> <span class="open-icon svelte-1lpfi31">→</span></button></li>'),ua=_('<section class="group svelte-1lpfi31"><h3 class="group-title svelte-1lpfi31"><code class="svelte-1lpfi31"> </code> <span class="count svelte-1lpfi31"> </span></h3> <ul class="items svelte-1lpfi31"></ul></section>'),ma=_('<header class="list-head svelte-1lpfi31"><h2>Migrations</h2> <button type="button" class="svelte-1lpfi31"> </button></header> <!>',1),_a=_('<div class="migrations svelte-1lpfi31"><!> <!></div>');function ga(Ee,Le){Ie(Le,!0);let j=F(null),d=F(null),Z=F(!1),R=F(null),r=F(Te({})),he=F(Te({})),D=F(!1),J=F(null);g.ensureLoaded();async function Re(s){v(j,s,!0),v(r,{},!0),v(he,{},!0),v(d,null),v(R,null),v(Z,!0);try{v(d,await ea(s),!0);const f={};for(const l of e(d).orphans){const u=Se(l.name,e(d).currentTemplateFields);f[l.name]=u?{rename:u}:"keep"}v(r,f,!0)}catch(f){v(R,f instanceof Error?f.message:String(f),!0)}finally{v(Z,!1)}}function ge(){v(j,null),v(d,null),v(R,null)}function Se(s,f){const l=s.toLowerCase();for(const u of f)if(u.toLowerCase().startsWith(l)||u.toLowerCase().endsWith(l))return u;return null}async function Ce(){if(!(e(j)===null||e(d)===null)){v(D,!0),v(J,null);try{const s={drop:Object.entries(e(r)).filter(([,l])=>l==="drop").map(([l])=>l),keep:Object.entries(e(r)).filter(([,l])=>l==="keep").map(([l])=>l),rename:Object.fromEntries(Object.entries(e(r)).filter(([,l])=>typeof l=="object"&&l!==null&&"rename"in l).map(([l,u])=>[l,u.rename])),fill:{...e(he)}},f=await He(e(j),s);g.refresh().catch(()=>{}),ge()}catch(s){v(J,s instanceof Error?s.message:String(s),!0)}finally{v(D,!1)}}}function Pe(s){return typeof s=="string"?s:JSON.stringify(s)}const qe=Xe(()=>g.list===null?[]:Object.entries(g.list.byTemplate).map(([s,f])=>({template:s,items:[...f].sort((l,u)=>l.path.localeCompare(u.path))})));var be=_a(),xe=a(be);{var Be=s=>{var f=va(),l=H(f),u=a(l),ee=o(u,2),ae=a(ee),te=o(l,2);{var le=i=>{var m=aa();n(i,m)},se=i=>{var m=ta(),k=a(m);h(()=>c(k,e(R))),n(i,m)},re=i=>{var m=oa(),k=H(m),E=a(k),M=a(E),K=a(M);{var W=p=>{var x=A();h(()=>c(x,`Before — ${e(d).left.template??""}`)),n(p,x)},$=p=>{var x=A("Before — no snapshot available");n(p,x)};w(K,p=>{e(d).left?p(W):p($,-1)})}var ie=o(M,2),ne=a(ie),oe=o(E,2),z=a(oe),S=a(z),b=o(z,2),G=a(b),C=o(k,2);{var I=p=>{var x=ia(),P=o(a(x),4);X(P,21,()=>e(d).orphans,q=>q.name,(q,t)=>{var y=ra(),U=a(y),ye=a(U),Je=a(ye),Ke=o(ye,2),We=a(Ke),we=o(U,2),ke=a(we),fe=a(ke),Fe=o(ke,2),de=a(Fe),Oe=o(Fe,2),ue=a(Oe),$e=o(Oe,2);{var ze=B=>{var T=sa();X(T,20,()=>e(d).currentTemplateFields,N=>N,(N,me)=>{var V=la(),Ge=a(V),Me={};h(()=>{c(Ge,me),Me!==(Me=me)&&(V.value=(V.__value=me)??"")}),n(N,V)});var je;Ye(T),h(()=>{je!==(je=e(r)[e(t).name].rename)&&(T.value=(T.__value=e(r)[e(t).name].rename)??"",Ze(T,e(r)[e(t).name].rename))}),O("change",T,N=>v(r,{...e(r),[e(t).name]:{rename:N.currentTarget.value}},!0)),n(B,T)};w($e,B=>{typeof e(r)[e(t).name]=="object"&&e(r)[e(t).name]!==null&&"rename"in e(r)[e(t).name]&&B(ze)})}h(B=>{c(Je,e(t).name),c(We,B),Y(we,"aria-label",`Resolution for ${e(t).name}`),Y(fe,"name",`d-${e(t).name}`),_e(fe,e(r)[e(t).name]==="drop"),Y(de,"name",`d-${e(t).name}`),_e(de,e(r)[e(t).name]==="keep"),Y(ue,"name",`d-${e(t).name}`),_e(ue,typeof e(r)[e(t).name]=="object"&&e(r)[e(t).name]!==null&&"rename"in e(r)[e(t).name])},[()=>Pe(e(t).value)]),O("change",fe,()=>v(r,{...e(r),[e(t).name]:"drop"},!0)),O("change",de,()=>v(r,{...e(r),[e(t).name]:"keep"},!0)),O("change",ue,()=>v(r,{...e(r),[e(t).name]:{rename:e(d).currentTemplateFields[0]??""}},!0)),n(q,y)}),n(p,x)};w(C,p=>{e(d).orphans.length>0&&p(I)})}var Q=o(C,2);{var ve=p=>{var x=na(),P=a(x);h(()=>c(P,e(J))),n(p,x)};w(Q,p=>{e(J)&&p(ve)})}var pe=o(Q,2),L=a(pe),ce=a(L);h(()=>{var p;c(ne,((p=e(d).left)==null?void 0:p.html)??"(no snapshot covers this item)"),c(S,`After — ${e(d).right.template??""}`),c(G,e(d).right.html),L.disabled=e(D)||e(d).orphans.length===0,c(ce,e(D)?"Migrating…":"Migrate item")}),O("click",L,Ce),n(i,m)};w(te,i=>{e(Z)?i(le):e(R)?i(se,1):e(d)&&i(re,2)})}h(()=>c(ae,e(j))),O("click",u,ge),n(s,f)},Ne=s=>{var f=ma(),l=H(f),u=o(a(l),2),ee=a(u),ae=o(l,2);{var te=i=>{var m=pa(),k=a(m);h(()=>c(k,g.error)),n(i,m)},le=i=>{var m=ca();n(i,m)},se=i=>{var m=fa();n(i,m)},re=i=>{var m=Ue(),k=H(m);X(k,17,()=>e(qe),E=>E.template,(E,M)=>{var K=ua(),W=a(K),$=a(W),ie=a($),ne=o($,2),oe=a(ne),z=o(W,2);X(z,21,()=>e(M).items,S=>S.path,(S,b)=>{var G=da(),C=a(G),I=a(C),Q=a(I),ve=a(Q),pe=o(I,2),L=a(pe);{var ce=t=>{var y=A();h(U=>c(y,`${e(b).orphanFields.length??""} orphan field${e(b).orphanFields.length===1?"":"s"}:
4
4
  ${U??""}`),[()=>e(b).orphanFields.join(", ")]),n(t,y)};w(L,t=>{e(b).orphanFields.length>0&&t(ce)})}var p=o(L,2);{var x=t=>{var y=A();h(()=>c(y,`· ${e(b).missingRequiredFields.length??""} missing required`)),n(t,y)};w(p,t=>{e(b).missingRequiredFields.length>0&&t(x)})}var P=o(p,2);{var q=t=>{var y=A();h(()=>c(y,`· best-fit: ${e(b).bestFitSnapshot??""}`)),n(t,y)};w(P,t=>{e(b).bestFitSnapshot&&t(q)})}h(()=>c(ve,e(b).path)),O("click",C,()=>Re(e(b).path)),n(S,G)}),h(()=>{c(ie,e(M).template),c(oe,`${e(M).items.length??""} item${e(M).items.length===1?"":"s"}`)}),n(E,K)}),n(i,m)};w(ae,i=>{g.error?i(te):g.loading&&g.list===null?i(le,1):g.count===0?i(se,2):i(re,-1)})}h(()=>{u.disabled=g.loading,c(ee,g.loading?"Refreshing…":"Refresh")}),O("click",u,()=>g.refresh()),n(s,f)};w(xe,s=>{e(j)!==null?s(Be):s(Ne,-1)})}var Ae=o(xe,2);{var De=s=>{};w(Ae,s=>{!e(j)&&g.list===null&&s(De)})}n(Ee,be),Qe()}Ve(["click","change"]);export{ga as default};