@brightsideoy/kama 1.0.0-alpha.13 → 1.0.0-alpha.17

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 (40) hide show
  1. package/bin/cli.js +282 -158
  2. package/content/definitions/taxonomies/categories.yaml +5 -2
  3. package/content/definitions/taxonomies/tags.yaml +5 -2
  4. package/dist/assets/AssetEditor-CCNDGlQ_.js +1 -0
  5. package/dist/assets/AssetEditor-D5j7pwcK.css +1 -0
  6. package/dist/assets/CmsHelp-BO_vWABq.css +1 -0
  7. package/dist/assets/CmsHelp-m9EOY_nE.js +1 -0
  8. package/dist/assets/CmsPublisher-Cs_ys68V.js +3 -0
  9. package/dist/assets/CmsPublisher-CugEqTD8.css +1 -0
  10. package/dist/assets/CmsUserCenter-Ac0GywlR.css +1 -0
  11. package/dist/assets/CmsUserCenter-D-T6HyWF.js +1 -0
  12. package/dist/assets/EditorSplitPreview-BzKh4wFB.css +1 -0
  13. package/dist/assets/EditorSplitPreview-CnWpXZWQ.js +1 -0
  14. package/dist/assets/NodeEditor-B1TvB2eW.css +1 -0
  15. package/dist/assets/NodeEditor-CZGnkwvf.js +147 -0
  16. package/dist/assets/TrashWorkspace-CERX58Ek.js +1 -0
  17. package/dist/assets/TrashWorkspace-DtMgxg13.css +1 -0
  18. package/dist/assets/_plugin-vue_export-helper-CTn6xl4w.js +5 -0
  19. package/dist/assets/history-XvWNE5zO.js +1 -0
  20. package/dist/assets/index-BpOAL4tE.js +14 -0
  21. package/dist/assets/index-C-EkPNvq.css +1 -0
  22. package/dist/assets/layers-D0DLWjff.js +1 -0
  23. package/dist/assets/link-Bs_SUS0O.js +1 -0
  24. package/dist/assets/rotate-ccw-CvD7yNQj.js +1 -0
  25. package/dist/assets/save-C8e-QRkP.js +1 -0
  26. package/dist/assets/smartphone-Wy6xQi_i.js +1 -0
  27. package/dist/{dist-kIJlDMvm.js → dist-BGv2bzzF.js} +633 -539
  28. package/dist/index.html +3 -2
  29. package/dist/index.js +633 -539
  30. package/dist/schema-compiler.js +1 -1
  31. package/package.json +1 -1
  32. package/schema.sql +3 -0
  33. package/templates/astro-starter/src/components/blocks/NodeList.astro +59 -63
  34. package/templates/astro-starter/src/middleware.ts +63 -35
  35. package/templates/astro-starter/src/pages/[...slug].astro +5 -12
  36. package/templates/astro-starter/src/pages/api/load-nodes.ts +42 -14
  37. package/templates/astro-starter/src/pages/api/partials/node-cards.astro +101 -0
  38. package/templates/kama-worker/setup-local-db.mjs +17 -0
  39. package/dist/assets/index-B1ogCRCg.js +0 -164
  40. package/dist/assets/index-CGLx9oqF.css +0 -1
@@ -276,9 +276,9 @@ function D(e, t) {
276
276
  return r && E.setMetadataInRegistry(t, r), t;
277
277
  });
278
278
  }
279
- function O(e) {
279
+ function te(e) {
280
280
  e.ZodType.prototype.openapi === void 0 && (e.ZodType.prototype.openapi = function(...e) {
281
- let { refId: t, metadata: n, options: r } = te(...e), i = n ?? {}, { param: a } = i, o = s(i, ["param"]), c = E.getMetadataFromRegistry(this) ?? {}, { _internal: u } = c, d = s(c, ["_internal"]), f = Object.assign(Object.assign(Object.assign({}, u), r), t ? { refId: t } : void 0), p = Object.assign(Object.assign(Object.assign({}, d), o), d?.param || a ? { param: Object.assign(Object.assign({}, d?.param), a) } : void 0), m = new this.constructor(this._def);
281
+ let { refId: t, metadata: n, options: r } = O(...e), i = n ?? {}, { param: a } = i, o = s(i, ["param"]), c = E.getMetadataFromRegistry(this) ?? {}, { _internal: u } = c, d = s(c, ["_internal"]), f = Object.assign(Object.assign(Object.assign({}, u), r), t ? { refId: t } : void 0), p = Object.assign(Object.assign(Object.assign({}, d), o), d?.param || a ? { param: Object.assign(Object.assign({}, d?.param), a) } : void 0), m = new this.constructor(this._def);
282
282
  function h(e) {
283
283
  E.setMetadataInRegistry(e, Object.assign(Object.assign({}, Object.keys(f).length > 0 ? { _internal: f } : void 0), p));
284
284
  }
@@ -304,7 +304,7 @@ function O(e) {
304
304
  }, m;
305
305
  });
306
306
  }
307
- function te(e, t, n) {
307
+ function O(e, t, n) {
308
308
  return typeof e == "string" ? {
309
309
  refId: e,
310
310
  metadata: t,
@@ -16543,7 +16543,7 @@ var $y = class t extends e {
16543
16543
  };
16544
16544
  return Object.defineProperty(t, "getRoutingPath", { enumerable: !1 });
16545
16545
  };
16546
- O(Xy);
16546
+ te(Xy);
16547
16547
  function tb(e, t) {
16548
16548
  let n = {};
16549
16549
  return Object.keys(e.paths).forEach((r) => {
@@ -20609,9 +20609,14 @@ var Tb = /* @__PURE__ */ o({
20609
20609
  label: "Category",
20610
20610
  hierarchical: !0,
20611
20611
  fields: {
20612
+ label: {
20613
+ type: "text",
20614
+ label: "Label",
20615
+ required: !0,
20616
+ rules: { required: !0 }
20617
+ },
20612
20618
  slug: {
20613
- label: "Slug",
20614
- linkedTo: "key",
20619
+ linkedTo: "label",
20615
20620
  rules: {}
20616
20621
  },
20617
20622
  description: {
@@ -20639,9 +20644,14 @@ var Tb = /* @__PURE__ */ o({
20639
20644
  label: "Tag",
20640
20645
  hierarchical: !1,
20641
20646
  fields: {
20647
+ label: {
20648
+ type: "text",
20649
+ label: "Label",
20650
+ required: !0,
20651
+ rules: { required: !0 }
20652
+ },
20642
20653
  slug: {
20643
- label: "Slug",
20644
- linkedTo: "key",
20654
+ linkedTo: "label",
20645
20655
  rules: {}
20646
20656
  },
20647
20657
  iconName: {
@@ -22030,7 +22040,7 @@ var Tb = /* @__PURE__ */ o({
22030
22040
  channels: "\n id INTEGER PRIMARY KEY AUTOINCREMENT,\n key TEXT UNIQUE NOT NULL,\n label TEXT NOT NULL,\n channelType TEXT,\n domain TEXT,\n baseUrl TEXT,\n defaultLanguage TEXT,\n isHidden INTEGER NOT NULL DEFAULT 0,\n dataJson TEXT,\n createdById TEXT,\n updatedById TEXT,\n createdAt TEXT DEFAULT CURRENT_TIMESTAMP,\n updatedAt TEXT DEFAULT CURRENT_TIMESTAMP,\n FOREIGN KEY (createdById) REFERENCES users(id) ON DELETE SET NULL,\n FOREIGN KEY (updatedById) REFERENCES users(id) ON DELETE SET NULL\n ",
22031
22041
  trees: "\n id INTEGER PRIMARY KEY AUTOINCREMENT,\n key TEXT UNIQUE NOT NULL,\n label TEXT NOT NULL,\n treeType TEXT,\n channelId INTEGER,\n isHidden INTEGER NOT NULL DEFAULT 0,\n dataJson TEXT,\n createdById TEXT,\n updatedById TEXT,\n createdAt TEXT DEFAULT CURRENT_TIMESTAMP,\n updatedAt TEXT DEFAULT CURRENT_TIMESTAMP,\n FOREIGN KEY (channelId) REFERENCES channels(id) ON DELETE SET NULL,\n FOREIGN KEY (createdById) REFERENCES users(id) ON DELETE SET NULL,\n FOREIGN KEY (updatedById) REFERENCES users(id) ON DELETE SET NULL\n ",
22032
22042
  channel_trees: "\n channelId INTEGER NOT NULL,\n treeId INTEGER NOT NULL,\n key TEXT NOT NULL DEFAULT 'main',\n metaJson TEXT,\n PRIMARY KEY (channelId, treeId, key),\n FOREIGN KEY (channelId) REFERENCES channels(id) ON DELETE CASCADE,\n FOREIGN KEY (treeId) REFERENCES trees(id) ON DELETE CASCADE\n ",
22033
- content_nodes: "\n id INTEGER PRIMARY KEY AUTOINCREMENT,\n contentType TEXT NOT NULL,\n title TEXT NOT NULL,\n slug TEXT,\n language TEXT,\n isHidden INTEGER NOT NULL DEFAULT 0,\n status TEXT DEFAULT 'draft',\n hasUnpublishedChanges INTEGER DEFAULT 0,\n disabledRegionsJson TEXT DEFAULT '{}',\n dataJson TEXT,\n draftDataJson TEXT,\n publishedDataJson TEXT,\n publishedAt TEXT,\n createdById TEXT,\n updatedById TEXT,\n createdAt TEXT DEFAULT CURRENT_TIMESTAMP,\n updatedAt TEXT DEFAULT CURRENT_TIMESTAMP,\n deletedAt TEXT,\n FOREIGN KEY (createdById) REFERENCES users(id) ON DELETE SET NULL,\n FOREIGN KEY (updatedById) REFERENCES users(id) ON DELETE SET NULL\n ",
22043
+ content_nodes: "\n id INTEGER PRIMARY KEY AUTOINCREMENT,\n contentType TEXT NOT NULL,\n title TEXT NOT NULL,\n slug TEXT,\n language TEXT,\n isHidden INTEGER NOT NULL DEFAULT 0,\n status TEXT DEFAULT 'draft',\n startShowingAt TEXT,\n stopShowingAt TEXT,\n hasUnpublishedChanges INTEGER DEFAULT 0,\n disabledRegionsJson TEXT DEFAULT '{}',\n dataJson TEXT,\n draftDataJson TEXT,\n publishedDataJson TEXT,\n publishedAt TEXT,\n createdById TEXT,\n updatedById TEXT,\n createdAt TEXT DEFAULT CURRENT_TIMESTAMP,\n updatedAt TEXT DEFAULT CURRENT_TIMESTAMP,\n deletedAt TEXT,\n FOREIGN KEY (createdById) REFERENCES users(id) ON DELETE SET NULL,\n FOREIGN KEY (updatedById) REFERENCES users(id) ON DELETE SET NULL\n ",
22034
22044
  node_channels: "\n nodeId INTEGER NOT NULL,\n channelId INTEGER NOT NULL,\n PRIMARY KEY (nodeId, channelId),\n FOREIGN KEY (nodeId) REFERENCES content_nodes(id) ON DELETE CASCADE,\n FOREIGN KEY (channelId) REFERENCES channels(id) ON DELETE CASCADE\n ",
22035
22045
  tree_nodes: "\n treeId INTEGER NOT NULL,\n contentId INTEGER NOT NULL,\n parentId INTEGER,\n sortOrder INTEGER DEFAULT 0,\n PRIMARY KEY (treeId, contentId),\n FOREIGN KEY (treeId) REFERENCES trees(id) ON DELETE CASCADE,\n FOREIGN KEY (contentId) REFERENCES content_nodes(id) ON DELETE CASCADE,\n FOREIGN KEY (parentId) REFERENCES content_nodes(id) ON DELETE CASCADE\n ",
22036
22046
  content_blocks: "\n id INTEGER PRIMARY KEY AUTOINCREMENT,\n contentId INTEGER NOT NULL,\n region TEXT DEFAULT 'main',\n elementType TEXT NOT NULL,\n dataJson TEXT,\n sortOrder INTEGER DEFAULT 0,\n isDraft INTEGER NOT NULL DEFAULT 1,\n FOREIGN KEY (contentId) REFERENCES content_nodes(id) ON DELETE CASCADE\n ",
@@ -22041,11 +22051,11 @@ var Tb = /* @__PURE__ */ o({
22041
22051
  node_terms: "\n nodeId INTEGER NOT NULL,\n termId INTEGER NOT NULL,\n fieldKey TEXT NOT NULL,\n sortOrder INTEGER DEFAULT 0,\n PRIMARY KEY (nodeId, termId, fieldKey),\n FOREIGN KEY (nodeId) REFERENCES content_nodes(id) ON DELETE CASCADE,\n FOREIGN KEY (termId) REFERENCES taxonomy_terms(id) ON DELETE CASCADE\n ",
22042
22052
  node_relations: "\n sourceNodeId INTEGER NOT NULL,\n targetNodeId INTEGER NOT NULL,\n fieldKey TEXT NOT NULL,\n sortOrder INTEGER DEFAULT 0,\n PRIMARY KEY (sourceNodeId, targetNodeId, fieldKey),\n FOREIGN KEY (sourceNodeId) REFERENCES content_nodes(id) ON DELETE CASCADE,\n FOREIGN KEY (targetNodeId) REFERENCES content_nodes(id) ON DELETE CASCADE\n ",
22043
22053
  node_routes: "\n id INTEGER PRIMARY KEY AUTOINCREMENT,\n path TEXT NOT NULL,\n channelId INTEGER NOT NULL,\n nodeId INTEGER,\n treeId INTEGER,\n isCanonical INTEGER DEFAULT 1,\n redirectUrl TEXT,\n createdAt TEXT DEFAULT CURRENT_TIMESTAMP,\n updatedAt TEXT DEFAULT CURRENT_TIMESTAMP,\n FOREIGN KEY (channelId) REFERENCES channels(id) ON DELETE CASCADE,\n FOREIGN KEY (nodeId) REFERENCES content_nodes(id) ON DELETE CASCADE,\n FOREIGN KEY (treeId) REFERENCES trees(id) ON DELETE CASCADE,\n UNIQUE(path, channelId)\n "
22044
- }, kb = /* @__PURE__ */ "CREATE INDEX IF NOT EXISTS idx_tree_nodes_tree_parent ON tree_nodes(treeId, parentId);.CREATE INDEX IF NOT EXISTS idx_tree_nodes_contentId ON tree_nodes(contentId);.CREATE INDEX IF NOT EXISTS idx_content_nodes_slug_status ON content_nodes(slug, status);.CREATE INDEX IF NOT EXISTS idx_content_blocks_node ON content_blocks(contentId, isDraft);.CREATE INDEX IF NOT EXISTS idx_node_assets_nodeId ON node_assets(nodeId);.CREATE INDEX IF NOT EXISTS idx_node_assets_assetId ON node_assets(assetId);.CREATE INDEX IF NOT EXISTS idx_content_schemas_type ON content_schemas(type);.CREATE INDEX IF NOT EXISTS idx_sessions_user ON sessions(userId);.CREATE INDEX IF NOT EXISTS idx_sessions_expires ON sessions(expiresAt);.CREATE INDEX IF NOT EXISTS idx_channels_visibility ON channels(isHidden);.CREATE INDEX IF NOT EXISTS idx_trees_visibility ON trees(isHidden);.CREATE INDEX IF NOT EXISTS idx_content_nodes_visibility ON content_nodes(isHidden, status);.CREATE INDEX IF NOT EXISTS idx_content_nodes_slug ON content_nodes(slug);.CREATE INDEX IF NOT EXISTS idx_content_nodes_type ON content_nodes(contentType);.CREATE INDEX IF NOT EXISTS idx_content_nodes_deleted_updated ON content_nodes(deletedAt, updatedAt DESC);.CREATE INDEX IF NOT EXISTS idx_tree_nodes_hierarchy ON tree_nodes(treeId, parentId, sortOrder);.CREATE INDEX IF NOT EXISTS idx_tree_nodes_content ON tree_nodes(contentId, treeId);.CREATE INDEX IF NOT EXISTS idx_content_blocks_content ON content_blocks(contentId, isDraft, region, sortOrder);.CREATE INDEX IF NOT EXISTS idx_node_channels_channel ON node_channels(channelId, nodeId);.CREATE INDEX IF NOT EXISTS idx_node_channels_node ON node_channels(nodeId, channelId);.CREATE INDEX IF NOT EXISTS idx_node_assets_node_asset ON node_assets(nodeId, assetId);.CREATE INDEX IF NOT EXISTS idx_node_assets_asset_node ON node_assets(assetId, nodeId);.CREATE UNIQUE INDEX IF NOT EXISTS idx_node_revisions_version ON node_revisions(nodeId, version);.CREATE INDEX IF NOT EXISTS idx_assets_system_created ON assets(isSystemVariant, createdAt DESC);.CREATE INDEX IF NOT EXISTS idx_assets_system_mime ON assets(isSystemVariant, mimeType);.CREATE INDEX IF NOT EXISTS idx_assets_deleted ON assets(deletedAt);.CREATE INDEX IF NOT EXISTS idx_assets_parent ON assets(parentAssetId);.CREATE INDEX IF NOT EXISTS idx_taxonomy_terms_tax ON taxonomy_terms(taxonomy);.CREATE INDEX IF NOT EXISTS idx_node_terms_node ON node_terms(nodeId);.CREATE INDEX IF NOT EXISTS idx_node_terms_term ON node_terms(termId);.CREATE INDEX IF NOT EXISTS idx_node_terms_node_term ON node_terms(nodeId, termId);.CREATE INDEX IF NOT EXISTS idx_node_terms_term_node ON node_terms(termId, nodeId);.CREATE INDEX IF NOT EXISTS idx_node_relations_source ON node_relations(sourceNodeId);.CREATE INDEX IF NOT EXISTS idx_node_relations_target ON node_relations(targetNodeId);.CREATE INDEX IF NOT EXISTS idx_node_routes_lookup ON node_routes(path, channelId);.CREATE INDEX IF NOT EXISTS idx_node_routes_node ON node_routes(nodeId);".split(".");
22054
+ }, kb = /* @__PURE__ */ "CREATE INDEX IF NOT EXISTS idx_tree_nodes_tree_parent ON tree_nodes(treeId, parentId);.CREATE INDEX IF NOT EXISTS idx_tree_nodes_contentId ON tree_nodes(contentId);.CREATE INDEX IF NOT EXISTS idx_content_nodes_slug_status ON content_nodes(slug, status);.CREATE INDEX IF NOT EXISTS idx_content_blocks_node ON content_blocks(contentId, isDraft);.CREATE INDEX IF NOT EXISTS idx_node_assets_nodeId ON node_assets(nodeId);.CREATE INDEX IF NOT EXISTS idx_node_assets_assetId ON node_assets(assetId);.CREATE INDEX IF NOT EXISTS idx_content_schemas_type ON content_schemas(type);.CREATE INDEX IF NOT EXISTS idx_sessions_user ON sessions(userId);.CREATE INDEX IF NOT EXISTS idx_sessions_expires ON sessions(expiresAt);.CREATE INDEX IF NOT EXISTS idx_channels_visibility ON channels(isHidden);.CREATE INDEX IF NOT EXISTS idx_trees_visibility ON trees(isHidden);.CREATE INDEX IF NOT EXISTS idx_content_nodes_visibility ON content_nodes(isHidden, status);.CREATE INDEX IF NOT EXISTS idx_content_nodes_slug ON content_nodes(slug);.CREATE INDEX IF NOT EXISTS idx_content_nodes_type ON content_nodes(contentType);.CREATE INDEX IF NOT EXISTS idx_content_nodes_deleted_updated ON content_nodes(deletedAt, updatedAt DESC);.CREATE INDEX IF NOT EXISTS idx_tree_nodes_hierarchy ON tree_nodes(treeId, parentId, sortOrder);.CREATE INDEX IF NOT EXISTS idx_tree_nodes_content ON tree_nodes(contentId, treeId);.CREATE INDEX IF NOT EXISTS idx_content_blocks_content ON content_blocks(contentId, isDraft, region, sortOrder);.CREATE INDEX IF NOT EXISTS idx_node_channels_channel ON node_channels(channelId, nodeId);.CREATE INDEX IF NOT EXISTS idx_node_channels_node ON node_channels(nodeId, channelId);.CREATE INDEX IF NOT EXISTS idx_node_assets_node_asset ON node_assets(nodeId, assetId);.CREATE INDEX IF NOT EXISTS idx_node_assets_asset_node ON node_assets(assetId, nodeId);.CREATE UNIQUE INDEX IF NOT EXISTS idx_node_revisions_version ON node_revisions(nodeId, version);.CREATE INDEX IF NOT EXISTS idx_assets_system_created ON assets(isSystemVariant, createdAt DESC);.CREATE INDEX IF NOT EXISTS idx_assets_system_mime ON assets(isSystemVariant, mimeType);.CREATE INDEX IF NOT EXISTS idx_assets_deleted ON assets(deletedAt);.CREATE INDEX IF NOT EXISTS idx_assets_parent ON assets(parentAssetId);.CREATE INDEX IF NOT EXISTS idx_taxonomy_terms_tax ON taxonomy_terms(taxonomy);.CREATE INDEX IF NOT EXISTS idx_node_terms_node ON node_terms(nodeId);.CREATE INDEX IF NOT EXISTS idx_node_terms_term ON node_terms(termId);.CREATE INDEX IF NOT EXISTS idx_node_terms_node_term ON node_terms(nodeId, termId);.CREATE INDEX IF NOT EXISTS idx_node_terms_term_node ON node_terms(termId, nodeId);.CREATE INDEX IF NOT EXISTS idx_node_relations_source ON node_relations(sourceNodeId);.CREATE INDEX IF NOT EXISTS idx_node_relations_target ON node_relations(targetNodeId);.CREATE INDEX IF NOT EXISTS idx_node_routes_lookup ON node_routes(path, channelId);.CREATE INDEX IF NOT EXISTS idx_node_routes_node ON node_routes(nodeId);.CREATE INDEX IF NOT EXISTS idx_content_nodes_public_feed ON content_nodes(contentType, isHidden, status, startShowingAt, stopShowingAt, updatedAt DESC);".split(".");
22045
22055
  function Ab(e) {
22046
22056
  let t = /* @__PURE__ */ new Set();
22047
22057
  function n(e) {
22048
- if (!(typeof e != "object" || !e)) for (let [r, i] of Object.entries(e)) typeof i == "object" && i && (i.index === !0 && r !== "id" && r !== "slug" && r !== "contentType" && t.add(`CREATE INDEX IF NOT EXISTS idx_content_nodes_${r} ON content_nodes (json_extract(dataJson, '$.${r}'));`), n(i));
22058
+ if (!(typeof e != "object" || !e)) for (let [r, i] of Object.entries(e)) typeof i == "object" && i && (i.index === !0 && r !== "id" && r !== "slug" && r !== "contentType" && r !== "startShowingAt" && r !== "stopShowingAt" && t.add(`CREATE INDEX IF NOT EXISTS idx_content_nodes_${r} ON content_nodes (json_extract(dataJson, '$.${r}'));`), n(i));
22049
22059
  }
22050
22060
  return n(e), Array.from(t);
22051
22061
  }
@@ -22072,6 +22082,18 @@ async function Mb(e, t) {
22072
22082
  if (!n.has("hasUnpublishedChanges")) try {
22073
22083
  await e.prepare("ALTER TABLE \"content_nodes\" ADD COLUMN hasUnpublishedChanges INTEGER DEFAULT 0;").run();
22074
22084
  } catch {}
22085
+ let t = !1;
22086
+ if (!n.has("startShowingAt")) try {
22087
+ await e.prepare("ALTER TABLE \"content_nodes\" ADD COLUMN startShowingAt TEXT;").run(), t = !0;
22088
+ } catch {}
22089
+ if (!n.has("stopShowingAt")) try {
22090
+ await e.prepare("ALTER TABLE \"content_nodes\" ADD COLUMN stopShowingAt TEXT;").run(), t = !0;
22091
+ } catch {}
22092
+ if (t) try {
22093
+ console.log("[Schema Sync] Migrating visibility dates out of JSON payload..."), await e.prepare("\n UPDATE content_nodes \n SET \n startShowingAt = json_extract(dataJson, '$.startShowingAt'),\n stopShowingAt = json_extract(dataJson, '$.stopShowingAt')\n WHERE json_extract(dataJson, '$.startShowingAt') IS NOT NULL \n OR json_extract(dataJson, '$.stopShowingAt') IS NOT NULL;\n ").run(), console.log("[Schema Sync] Date migration complete.");
22094
+ } catch (e) {
22095
+ console.error("[Schema Sync] Failed to backfill dates:", e);
22096
+ }
22075
22097
  }
22076
22098
  if (t === "assets") {
22077
22099
  if (!n.has("parentAssetId")) try {
@@ -22830,7 +22852,9 @@ var Fb = { hasSubscribers: !1 }, Ib = Fb, Lb = Fb, Rb = typeof performance == "o
22830
22852
  }, Qb = null;
22831
22853
  function $b(e) {
22832
22854
  let t = process.env.CACHE_DRIVER || "lru";
22833
- return t === "none" || t === "off" || t === "false" ? new Zb() : e?.env?.CMS_CACHE_KV ? new Xb(e.env.CMS_CACHE_KV) : t === "lru" ? (Qb ||= new Yb(), Qb) : new Zb();
22855
+ if (t === "none" || t === "off" || t === "false") return new Zb();
22856
+ let n = e?.env?.CACHE_KV || e?.env?.CMS_CACHE_KV;
22857
+ return n ? new Xb(n) : t === "lru" ? (Qb ||= new Yb(), Qb) : new Zb();
22834
22858
  }
22835
22859
  var ex = class {
22836
22860
  customStoragePath;
@@ -23389,6 +23413,7 @@ var mx = class {
23389
23413
  return {
23390
23414
  zoneId: e.env?.CLOUDFLARE_ZONE_ID || this.env.CLOUDFLARE_ZONE_ID,
23391
23415
  apiToken: e.env?.CLOUDFLARE_API_TOKEN || this.env.CLOUDFLARE_API_TOKEN,
23416
+ purgeToken: e.env?.FRONTEND_API_SECRET || this.env.FRONTEND_API_SECRET || e.env?.CLOUDFLARE_API_TOKEN || this.env.CLOUDFLARE_API_TOKEN,
23392
23417
  frontendUrl: (e.env?.PUBLIC_FRONTEND_URL || this.env.PUBLIC_FRONTEND_URL || "http://localhost:4321").replace(/\/+$/, ""),
23393
23418
  cdnDomain: t ? t.replace(/^https?:\/\//, "").replace(/\/+$/, "") : "localhost:8787",
23394
23419
  frontendWorker: e.env?.FRONTEND_WORKER || this.env.FRONTEND_WORKER,
@@ -23416,7 +23441,7 @@ var mx = class {
23416
23441
  return r && n && r.startsWith(`https://${n}/`) && !r.includes("/media/") && (r = r.replace(`https://${n}/`, `https://${n}/media/`)), r;
23417
23442
  }
23418
23443
  async callAstroPurge(e, t, n) {
23419
- let { apiToken: r, frontendUrl: i, frontendWorker: a, disableCachePurge: o } = this.getEnv(e);
23444
+ let { purgeToken: r, frontendUrl: i, frontendWorker: a, disableCachePurge: o } = this.getEnv(e);
23420
23445
  if (o === "true" || o === !0 || o === "1") return new Response(JSON.stringify({ skipped: !0 }), { status: 200 });
23421
23446
  let s = (n || i).replace(/\/+$/, ""), c = `${s}/api/purge`, l = { "Content-Type": "application/json" };
23422
23447
  if (r && (l.Authorization = `Bearer ${r}`), a && typeof a.fetch == "function") try {
@@ -23446,8 +23471,21 @@ var mx = class {
23446
23471
  try {
23447
23472
  let a = $b(e);
23448
23473
  if (n) {
23449
- let e = t.prepare("SELECT treeId FROM tree_nodes WHERE contentId = ?"), r = typeof e.all == "function" ? await e.all(n) : await e.bind(n).all(), i = Array.isArray(r) ? r : r?.results || [];
23450
- for (let e of i) await a.delete(`tree:default:${e.treeId}`), await a.delete(`tree:all:${e.treeId}`);
23474
+ let e = t.prepare("\n SELECT DISTINCT\n t.id AS treeId,\n t.key AS treeKey,\n t.dataJson AS treeDataJson,\n c.id AS channelId,\n c.key AS channelKey,\n c.defaultLanguage AS channelDefaultLanguage\n FROM tree_nodes tn\n JOIN trees t ON t.id = tn.treeId\n LEFT JOIN channel_trees ct ON ct.treeId = t.id\n LEFT JOIN channels c ON c.id = ct.channelId\n WHERE tn.contentId = ?\n "), r = typeof e.all == "function" ? await e.all(n) : await e.bind(n).all(), o = Array.isArray(r) ? r : r?.results || [], s = /* @__PURE__ */ new Set();
23475
+ for (let e of o) {
23476
+ let t = /* @__PURE__ */ new Set(["default", "all"]);
23477
+ e.channelId !== null && e.channelId !== void 0 && t.add(String(e.channelId)), e.channelKey && t.add(String(e.channelKey));
23478
+ let n = /* @__PURE__ */ new Set();
23479
+ e.treeId !== null && e.treeId !== void 0 && n.add(String(e.treeId)), e.treeKey && n.add(String(e.treeKey));
23480
+ let r = /* @__PURE__ */ new Set(["default"]);
23481
+ i && r.add(i.trim()), e.channelDefaultLanguage && r.add(String(e.channelDefaultLanguage).trim());
23482
+ try {
23483
+ let t = typeof e.treeDataJson == "string" ? JSON.parse(e.treeDataJson) : e.treeDataJson;
23484
+ (t?.defaultLanguage || t?.language) && r.add(String(t.defaultLanguage || t.language).trim());
23485
+ } catch {}
23486
+ for (let e of t) for (let t of n) for (let n of r) s.add(`tree:${e}:${t}:${n || "default"}`);
23487
+ }
23488
+ await Promise.all(Array.from(s, (e) => a.delete(e)));
23451
23489
  }
23452
23490
  if (r) {
23453
23491
  let e = r.replace(/^\/+|\/+$/g, ""), o = ["default", "1"];
@@ -23461,9 +23499,37 @@ var mx = class {
23461
23499
  console.warn("[CacheManager] Failed to purge internal worker cache:", e);
23462
23500
  }
23463
23501
  }
23502
+ async purgeVisibilityChange(e, t, n) {
23503
+ try {
23504
+ let r = t.prepare("SELECT slug, language FROM content_nodes WHERE id = ?"), i = typeof r.get == "function" ? await r.get(n) : (await r.bind(n).all())?.results?.[0];
23505
+ await this.purgeInternalWorkerCache(e, t, n, i?.slug, i?.language);
23506
+ let a = await this.callAstroPurge(e, { purge_everything: !0 }), o = await a.json().catch(() => ({}));
23507
+ if (!a.ok || o?.success === !1 || o?.skipped) return console.warn(`[CacheManager] Visibility purge failed at Astro Worker (${a.status}).`), !1;
23508
+ let { zoneId: s, apiToken: c } = this.getEnv(e), l = this.isLocalEnv(e);
23509
+ if (s && c && !this.isLocalEnv(e)) {
23510
+ let e = await fetch(`https://api.cloudflare.com/client/v4/zones/${s}/purge_cache`, {
23511
+ method: "POST",
23512
+ headers: {
23513
+ Authorization: `Bearer ${c}`,
23514
+ "Content-Type": "application/json"
23515
+ },
23516
+ body: JSON.stringify({ purge_everything: !0 })
23517
+ }), t = await e.json().catch(() => ({}));
23518
+ l = e.ok && t?.success === !0, l || console.warn("[CacheManager] Visibility purge failed at Cloudflare Zone cache:", JSON.stringify(t));
23519
+ } else this.isLocalEnv(e) || console.warn("[CacheManager] Visibility purge lacks CLOUDFLARE_ZONE_ID or CLOUDFLARE_API_TOKEN.");
23520
+ return this.dispatch(e, this.warmAllPublishedPages(e, t)), l;
23521
+ } catch (e) {
23522
+ return console.warn("[CacheManager] Visibility cache purge failed:", e), !1;
23523
+ }
23524
+ }
23464
23525
  purgeNode(e, t, n, r = !1, i = []) {
23465
23526
  if (r) {
23466
- console.log(`[CacheManager] Structural change detected on nodeId ${n}. Escalating to Global Purge.`), this.purgeGlobalCache(e, t);
23527
+ console.log(`[CacheManager] Structural change detected on nodeId ${n}. Escalating to Global Purge.`);
23528
+ let r = (async () => {
23529
+ let r = t.prepare("SELECT slug, language FROM content_nodes WHERE id = ?"), i = typeof r.get == "function" ? await r.get(n) : (await r.bind(n).all())?.results?.[0];
23530
+ await this.purgeInternalWorkerCache(e, t, n, i?.slug, i?.language), await this.purgeGlobalCacheDirect(e, t);
23531
+ })();
23532
+ this.dispatch(e, r);
23467
23533
  return;
23468
23534
  }
23469
23535
  let a = (async () => {
@@ -23549,8 +23615,12 @@ var mx = class {
23549
23615
  }
23550
23616
  async purgeGlobalCacheDirect(e, t) {
23551
23617
  try {
23552
- let { zoneId: n, apiToken: r } = this.getEnv(e);
23553
- if (!(await this.callAstroPurge(e, { purge_everything: !0 })).ok) return;
23618
+ let { zoneId: n, apiToken: r } = this.getEnv(e), i = await this.callAstroPurge(e, { purge_everything: !0 });
23619
+ if (!i.ok) {
23620
+ let e = await i.text().catch(() => "");
23621
+ console.warn(`[CacheManager] Astro global purge failed (${i.status}): ${e.slice(0, 500)}`);
23622
+ return;
23623
+ }
23554
23624
  if (n && r && !this.isLocalEnv(e)) try {
23555
23625
  let e = await (await fetch(`https://api.cloudflare.com/client/v4/zones/${n}/purge_cache`, {
23556
23626
  method: "POST",
@@ -23690,8 +23760,9 @@ async function hx(e) {
23690
23760
  await e.prepare("DELETE FROM node_routes").run();
23691
23761
  let h = Array.from(p.values());
23692
23762
  if (h.length === 0) return;
23693
- for (let t = 0; t < h.length; t += 50) {
23694
- let n = h.slice(t, t + 50), r = n.map(() => "(?, ?, ?, ?, ?, ?)").join(","), i = n.flatMap((e) => [
23763
+ let g = [];
23764
+ for (let e = 0; e < h.length; e += 15) {
23765
+ let t = h.slice(e, e + 15), n = t.map(() => "(?, ?, ?, ?, ?, ?)").join(","), r = t.flatMap((e) => [
23695
23766
  e.path,
23696
23767
  e.channelId,
23697
23768
  e.nodeId,
@@ -23699,10 +23770,17 @@ async function hx(e) {
23699
23770
  e.isCanonical,
23700
23771
  e.redirectUrl ?? null
23701
23772
  ]);
23702
- await e.prepare(`
23703
- INSERT INTO node_routes (path, channelId, nodeId, treeId, isCanonical, redirectUrl)
23704
- VALUES ${r}
23705
- `).run(...i);
23773
+ g.push({
23774
+ placeholders: n,
23775
+ params: r
23776
+ });
23777
+ }
23778
+ for (let t = 0; t < g.length; t += 50) {
23779
+ let n = g.slice(t, t + 50);
23780
+ await Promise.all(n.map((t) => e.prepare(`
23781
+ INSERT INTO node_routes (path, channelId, nodeId, treeId, isCanonical, redirectUrl)
23782
+ VALUES ${t.placeholders}
23783
+ `).run(...t.params)));
23706
23784
  }
23707
23785
  console.log(`[Route Generator] Successfully built ${h.length} enterprise routes.`);
23708
23786
  } catch (e) {
@@ -23710,7 +23788,25 @@ async function hx(e) {
23710
23788
  }
23711
23789
  }
23712
23790
  var gx = new e();
23713
- async function _x(e, t, n = []) {
23791
+ function _x(e, t, n = []) {
23792
+ let r = new mx(e.env), i = (async () => {
23793
+ for (let i of n) {
23794
+ let n = t.prepare("SELECT slug, language FROM content_nodes WHERE id = ?"), a = typeof n.get == "function" ? await n.get(i) : (await n.bind(i).all())?.results?.[0];
23795
+ await r.purgeInternalWorkerCache(e, t, i, a?.slug, a?.language);
23796
+ }
23797
+ await hx(t), await r.purgeGlobalCacheDirect(e, t);
23798
+ })().catch((e) => {
23799
+ console.error("[Node Routes] Background rebuild/purge failed:", e);
23800
+ });
23801
+ try {
23802
+ let t = e.executionCtx;
23803
+ if (t && typeof t.waitUntil == "function") {
23804
+ t.waitUntil(i);
23805
+ return;
23806
+ }
23807
+ } catch {}
23808
+ }
23809
+ async function vx(e, t, n = []) {
23714
23810
  let r = e.prepare(t);
23715
23811
  if (typeof r.bind == "function") {
23716
23812
  let e = await r.bind(...n).all();
@@ -23722,75 +23818,50 @@ async function _x(e, t, n = []) {
23722
23818
  }
23723
23819
  return [];
23724
23820
  }
23725
- async function vx(e, t, n = []) {
23821
+ async function yx(e, t, n = []) {
23726
23822
  let r = e.prepare(t);
23727
23823
  if (typeof r.bind == "function") return r.bind(...n).run();
23728
23824
  if (typeof r.run == "function") return r.run(...n);
23729
23825
  }
23730
- function yx(e) {
23826
+ function bx(e) {
23731
23827
  return !e || !e.trim() ? null : e.normalize("NFD").replace(/[\u0300-\u036f]/g, "").toLowerCase().trim().replace(/[^a-z0-9\s-]/g, "").replace(/[\s-]+/g, "-").replace(/^-+|-+$/g, "") || null;
23732
23828
  }
23733
- function bx(e) {
23829
+ function xx(e) {
23734
23830
  return +(e === !0 || e === 1 || e === "1" || e === "true");
23735
23831
  }
23736
- function xx(e) {
23832
+ function Sx(e) {
23737
23833
  if (e == null || e === "null" || e === "" || typeof e == "string" && e.startsWith("draft-")) return null;
23738
23834
  let t = Number(e);
23739
23835
  return isNaN(t) ? null : t;
23740
23836
  }
23741
- function Sx(e) {
23837
+ function Cx(e) {
23742
23838
  let t = { ...e };
23743
23839
  delete t.language, delete t.defaultLanguage;
23744
- for (let e of [
23745
- "id",
23746
- "treeNodeId",
23747
- "isNew",
23748
- "_isTreeDraft",
23749
- "_draftParentId",
23750
- "nodeType",
23751
- "contentType",
23752
- "title",
23753
- "slug",
23754
- "path",
23755
- "routePath",
23756
- "hidden",
23757
- "is_hidden",
23758
- "isHidden",
23759
- "status",
23760
- "createdById",
23761
- "updatedById",
23762
- "draftDataJson",
23763
- "publishedDataJson",
23764
- "publishedAt",
23765
- "deletedAt",
23766
- "channelNames",
23767
- "treeNames",
23768
- "hasUnpublishedChanges"
23769
- ]) delete t[e];
23840
+ for (let e of /* @__PURE__ */ "id.treeNodeId.isNew._isTreeDraft._draftParentId.nodeType.contentType.title.slug.path.routePath.hidden.is_hidden.isHidden.startShowingAt.stopShowingAt.status.createdById.updatedById.draftDataJson.publishedDataJson.publishedAt.deletedAt.channelNames.treeNames.hasUnpublishedChanges".split(".")) delete t[e];
23770
23841
  return t;
23771
23842
  }
23772
- function Cx(e, t = /* @__PURE__ */ new Set()) {
23773
- return e ? typeof e == "string" ? (e.startsWith("ast_") && t.add(e), t) : Array.isArray(e) ? (e.forEach((e) => Cx(e, t)), t) : (typeof e == "object" && Object.values(e).forEach((e) => Cx(e, t)), t) : t;
23843
+ function wx(e, t = /* @__PURE__ */ new Set()) {
23844
+ return e ? typeof e == "string" ? (e.startsWith("ast_") && t.add(e), t) : Array.isArray(e) ? (e.forEach((e) => wx(e, t)), t) : (typeof e == "object" && Object.values(e).forEach((e) => wx(e, t)), t) : t;
23774
23845
  }
23775
- function wx(e, t) {
23846
+ function Tx(e, t) {
23776
23847
  if (!e) return !0;
23777
- let n = t.title !== void 0 && t.title?.trim() !== e.title?.trim(), r = t.slug !== void 0 && t.slug !== e.slug, i = t.isHidden !== void 0 && bx(t.isHidden) !== bx(e.isHidden), a = t.status !== void 0 && t.status !== e.status, o = typeof e.draftDataJson == "string" ? JSON.parse(e.draftDataJson || "{}") : e.draftDataJson || {}, s = t.sanitizedFields || {}, c = s.menuTitle !== void 0 && s.menuTitle !== o.menuTitle;
23778
- return n || r || i || a || c;
23848
+ let n = t.title !== void 0 && t.title?.trim() !== e.title?.trim(), r = t.slug !== void 0 && t.slug !== e.slug, i = t.isHidden !== void 0 && xx(t.isHidden) !== xx(e.isHidden), a = t.status !== void 0 && t.status !== e.status, o = t.startShowingAt !== void 0 && t.startShowingAt !== e.startShowingAt, s = t.stopShowingAt !== void 0 && t.stopShowingAt !== e.stopShowingAt, c = typeof e.draftDataJson == "string" ? JSON.parse(e.draftDataJson || "{}") : e.draftDataJson || {}, l = t.sanitizedFields || {}, u = l.menuTitle !== void 0 && l.menuTitle !== c.menuTitle;
23849
+ return n || r || i || a || o || s || u;
23779
23850
  }
23780
- async function Tx(e, t, n) {
23851
+ async function Ex(e, t, n) {
23781
23852
  for (let r of n) {
23782
- let n = (await _x(e, "\n SELECT id, storageKeyPrivate, isSystemVariant, parentAssetId, filename\n FROM assets WHERE id = ?\n ", [r]))[0];
23783
- if (n && n.isSystemVariant && !((await _x(e, "SELECT 1 FROM node_assets WHERE assetId = ? LIMIT 1", [n.id])).length > 0)) {
23853
+ let n = (await vx(e, "\n SELECT id, storageKeyPrivate, isSystemVariant, parentAssetId, filename\n FROM assets WHERE id = ?\n ", [r]))[0];
23854
+ if (n && n.isSystemVariant && !((await vx(e, "SELECT 1 FROM node_assets WHERE assetId = ? LIMIT 1", [n.id])).length > 0)) {
23784
23855
  if (n.storageKeyPrivate) try {
23785
23856
  await t.delete(n.storageKeyPrivate);
23786
23857
  } catch (e) {
23787
23858
  console.warn(`[Asset Cleanup] Failed to delete crop ${n.storageKeyPrivate}:`, e);
23788
23859
  }
23789
- await vx(e, "DELETE FROM node_assets WHERE assetId = ?", [n.id]), await vx(e, "DELETE FROM assets WHERE id = ?", [n.id]);
23860
+ await yx(e, "DELETE FROM node_assets WHERE assetId = ?", [n.id]), await yx(e, "DELETE FROM assets WHERE id = ?", [n.id]);
23790
23861
  }
23791
23862
  }
23792
23863
  }
23793
- async function Ex(e, t, n) {
23864
+ async function Dx(e, t, n) {
23794
23865
  let r = {}, i = null;
23795
23866
  if (t) {
23796
23867
  let a = await e.prepare("\n WITH RECURSIVE ancestor_path(id, parentId, draftDataJson, dataJson, level) AS (\n SELECT t.contentId as id, t.parentId, c.draftDataJson, c.dataJson, 0\n FROM tree_nodes t\n INNER JOIN content_nodes c ON t.contentId = c.id\n WHERE t.contentId = ? AND t.treeId = ?\n UNION ALL\n SELECT t.contentId as id, t.parentId, c.draftDataJson, c.dataJson, ap.level + 1\n FROM tree_nodes t\n INNER JOIN content_nodes c ON t.contentId = c.id\n INNER JOIN ancestor_path ap ON t.contentId = ap.parentId AND t.treeId = ?\n )\n SELECT draftDataJson, dataJson FROM ancestor_path ORDER BY level ASC\n ").all(t, n, n), o = Array.isArray(a) ? a : a?.results || [];
@@ -23839,6 +23910,8 @@ gx.get("/", async (e) => {
23839
23910
  nodeType: i.contentType,
23840
23911
  contentType: i.contentType,
23841
23912
  isHidden: !!i.isHidden,
23913
+ startShowingAt: i.startShowingAt || null,
23914
+ stopShowingAt: i.stopShowingAt || null,
23842
23915
  status: i.status || "draft",
23843
23916
  publishedAt: i.publishedAt || null,
23844
23917
  hasUnpublishedChanges: s,
@@ -23851,7 +23924,7 @@ gx.get("/", async (e) => {
23851
23924
  if (l) try {
23852
23925
  let n = typeof l == "string" ? JSON.parse(l) : l, a = await t.prepare("SELECT contentId as treeNodeId, treeId, parentId FROM tree_nodes WHERE contentId = ? LIMIT 1").get(r), o = px(e.env?.BUNDLED_DEFINITIONS).nodes?.[i.contentType] || {}, s = n.layoutId || null;
23853
23926
  if (a) {
23854
- let { resolvedLayoutId: e, inheritedFields: r } = await Ex(t, a.parentId, a.treeId);
23927
+ let { resolvedLayoutId: e, inheritedFields: r } = await Dx(t, a.parentId, a.treeId);
23855
23928
  (s === "inherit" || !s) && (s = e);
23856
23929
  for (let [e, t] of Object.entries(r)) e !== "layoutId" && e !== "subpageLayoutId" && (n[e] === void 0 || n[e] === null || n[e] === "") && t !== void 0 && (n[e] = t);
23857
23930
  }
@@ -23866,7 +23939,7 @@ gx.get("/", async (e) => {
23866
23939
  let r = t.allowedLayouts;
23867
23940
  return r ? typeof r == "string" ? r === e : !Array.isArray(r) || r.length === 0 || r.includes(e) : !0;
23868
23941
  })(s) && (s = null), (s === "inherit" || !s) && (s = o.defaultLayout || null);
23869
- let u = await fx(t, Sx(n));
23942
+ let u = await fx(t, Cx(n));
23870
23943
  Object.assign(c, u), c.resolvedLayoutId = s;
23871
23944
  } catch {}
23872
23945
  let u = await t.prepare("SELECT channelId FROM node_channels WHERE nodeId = ?").all(r);
@@ -23894,7 +23967,7 @@ gx.get("/", async (e) => {
23894
23967
  blocks: m
23895
23968
  });
23896
23969
  }
23897
- let m = [], h = [o ? "(cn.deletedAt IS NOT NULL AND cn.deletedAt != '')" : "(cn.deletedAt IS NULL OR cn.deletedAt = '')"];
23970
+ let m = [], h = [o ? "cn.deletedAt IS NOT NULL" : "cn.deletedAt IS NULL"];
23898
23971
  if (a && a !== "all" && (h.push("EXISTS (SELECT 1 FROM node_channels nc WHERE nc.nodeId = cn.id AND nc.channelId = ?)"), m.push(Number(a) || a)), s && (h.push("\n EXISTS (\n SELECT 1 FROM node_assets na_f \n JOIN assets a_f ON a_f.id = na_f.assetId\n WHERE na_f.nodeId = cn.id \n AND (na_f.assetId = ? OR a_f.parentAssetId = ? OR a_f.id = (SELECT parentAssetId FROM assets WHERE id = ?))\n )\n "), m.push(s, s, s)), r && r !== "all") {
23899
23972
  let e = r.split(",").map((e) => e.trim()).filter(Boolean);
23900
23973
  e.length > 0 && (h.push(`cn.contentType IN (${e.map(() => "?").join(",")})`), m.push(...e));
@@ -23971,6 +24044,8 @@ gx.get("/", async (e) => {
23971
24044
  contentType: e.contentType,
23972
24045
  nodeType: e.contentType,
23973
24046
  isHidden: !!e.isHidden,
24047
+ startShowingAt: e.startShowingAt || null,
24048
+ stopShowingAt: e.stopShowingAt || null,
23974
24049
  status: e.status || "draft",
23975
24050
  publishedAt: e.publishedAt || null,
23976
24051
  hasUnpublishedChanges: n,
@@ -23988,7 +24063,7 @@ gx.get("/", async (e) => {
23988
24063
  otherCount: e.otherCount || 0
23989
24064
  }, i = e.draftDataJson || e.dataJson;
23990
24065
  if (i) try {
23991
- let e = typeof i == "string" ? JSON.parse(i) : i, n = await fx(t, Sx(e));
24066
+ let e = typeof i == "string" ? JSON.parse(i) : i, n = await fx(t, Cx(e));
23992
24067
  Object.assign(r, n);
23993
24068
  } catch {}
23994
24069
  return r;
@@ -24001,34 +24076,34 @@ gx.get("/", async (e) => {
24001
24076
  limit: f
24002
24077
  });
24003
24078
  }), gx.post("/", async (e) => {
24004
- let t = e.get("db"), n = await e.req.json(), r = n.node || n.activeNode || n, i = r.id || n.id, a = i != null && i !== "" && !isNaN(Number(i)) ? Number(i) : null, { title: o, slug: s, language: c, nodeType: l, contentType: u, isHidden: d, hidden: f, is_hidden: p, blocks: m, channels: h, trees: g, ..._ } = r, { cleanedData: v, assetRefs: y, termRefs: b, nodeRefs: x } = ax(Sx(_)), S = bx(d === void 0 ? f === void 0 ? p : f : d), C = l || u || "page", w = e.get("user")?.id || null, T = typeof c == "string" && c.trim() !== "" ? c.trim() : null, ee = g && Array.isArray(g) && g.length > 0 ? g[0] : null, E = ee ? ee.treeId || ee.id : null, D = null;
24005
- if (E) {
24006
- let e = await t.prepare("SELECT dataJson FROM trees WHERE id = ? OR key = ? LIMIT 1").get(Number(E) || -1, String(E));
24079
+ let t = e.get("db"), n = await e.req.json(), r = n.node || n.activeNode || n, i = r.id || n.id, a = i != null && i !== "" && !isNaN(Number(i)) ? Number(i) : null, { title: o, slug: s, language: c, nodeType: l, contentType: u, isHidden: d, hidden: f, is_hidden: p, startShowingAt: m, stopShowingAt: h, blocks: g, channels: _, trees: v, ...y } = r, { cleanedData: b, assetRefs: x, termRefs: S, nodeRefs: C } = ax(Cx(y)), w = xx(d === void 0 ? f === void 0 ? p : f : d), T = l || u || "page", ee = e.get("user")?.id || null, E = typeof c == "string" && c.trim() !== "" ? c.trim() : null, D = v && Array.isArray(v) && v.length > 0 ? v[0] : null, te = D ? D.treeId || D.id : null, O = null;
24080
+ if (te) {
24081
+ let e = await t.prepare("SELECT dataJson FROM trees WHERE id = ? OR key = ? LIMIT 1").get(Number(te) || -1, String(te));
24007
24082
  if (e?.dataJson) try {
24008
24083
  let t = typeof e.dataJson == "string" ? JSON.parse(e.dataJson) : e.dataJson;
24009
- D = t.defaultLanguage?.trim() || t.language?.trim() || null;
24084
+ O = t.defaultLanguage?.trim() || t.language?.trim() || null;
24010
24085
  } catch {}
24011
24086
  }
24012
- if (!D && h && Array.isArray(h) && h.length > 0) {
24013
- let e = typeof h[0] == "object" ? h[0].id : h[0];
24087
+ if (!O && _ && Array.isArray(_) && _.length > 0) {
24088
+ let e = typeof _[0] == "object" ? _[0].id : _[0];
24014
24089
  if (e && e !== "all") {
24015
24090
  let n = await t.prepare("SELECT defaultLanguage, dataJson FROM channels WHERE id = ? LIMIT 1").get(Number(e));
24016
24091
  if (n) {
24017
- if (n.defaultLanguage) D = n.defaultLanguage.trim();
24092
+ if (n.defaultLanguage) O = n.defaultLanguage.trim();
24018
24093
  else if (n.dataJson) try {
24019
24094
  let e = typeof n.dataJson == "string" ? JSON.parse(n.dataJson) : n.dataJson;
24020
- D = e.defaultLanguage?.trim() || e.language?.trim() || null;
24095
+ O = e.defaultLanguage?.trim() || e.language?.trim() || null;
24021
24096
  } catch {}
24022
24097
  }
24023
24098
  }
24024
24099
  }
24025
- T && D && T === D && (T = null);
24026
- let O = a, te = /* @__PURE__ */ new Set(), k = !1, A = "draft", ne = 0, j = s === void 0 ? null : yx(s);
24027
- if (j) {
24100
+ E && O && E === O && (E = null);
24101
+ let k = a, A = /* @__PURE__ */ new Set(), ne = !1, j = "draft", re = 0, ie = s === void 0 ? null : bx(s);
24102
+ if (ie) {
24028
24103
  let n = [];
24029
- if (g !== void 0 && Array.isArray(g) && g.length > 0) for (let e of g) n.push({
24104
+ if (v !== void 0 && Array.isArray(v) && v.length > 0) for (let e of v) n.push({
24030
24105
  treeId: Number(e.treeId),
24031
- parentId: xx(e.parentId ?? e._draftParentId ?? null)
24106
+ parentId: Sx(e.parentId ?? e._draftParentId ?? null)
24032
24107
  });
24033
24108
  else if (a) {
24034
24109
  let e = await t.prepare("SELECT treeId, parentId FROM tree_nodes WHERE contentId = ?").all(a), r = Array.isArray(e) ? e : e?.results || [];
@@ -24038,140 +24113,146 @@ gx.get("/", async (e) => {
24038
24113
  });
24039
24114
  }
24040
24115
  for (let r of n) {
24041
- let n = r.parentId === null ? "tn.parentId IS NULL" : "tn.parentId = ?", i = r.parentId === null ? [r.treeId, j] : [
24116
+ let n = r.parentId === null ? "tn.parentId IS NULL" : "tn.parentId = ?", i = r.parentId === null ? [r.treeId, ie] : [
24042
24117
  r.treeId,
24043
24118
  r.parentId,
24044
- j
24119
+ ie
24045
24120
  ], o = `
24046
24121
  SELECT cn.id FROM tree_nodes tn
24047
24122
  INNER JOIN content_nodes cn ON tn.contentId = cn.id
24048
- WHERE tn.treeId = ? AND ${n} AND cn.slug = ? AND (cn.deletedAt IS NULL OR cn.deletedAt = '')
24123
+ WHERE tn.treeId = ? AND ${n} AND cn.slug = ? AND cn.deletedAt IS NULL
24049
24124
  `;
24050
24125
  if (a && (o += " AND cn.id != ?", i.push(a)), o += " LIMIT 1", await t.prepare(o).get(...i)) return e.json({
24051
- error: `The slug '${j}' is already in use by another page in this section.`,
24126
+ error: `The slug '${ie}' is already in use by another page in this section.`,
24052
24127
  field: "slug"
24053
24128
  }, 409);
24054
24129
  }
24055
24130
  }
24056
24131
  if (a) {
24057
- let e = await t.prepare("SELECT title, slug, language, contentType, isHidden, draftDataJson, dataJson, publishedAt, status, hasUnpublishedChanges FROM content_nodes WHERE id = ?").get(a), n = o === void 0 ? e?.title || "Untitled" : o, r = j ?? e?.slug ?? null, i = C || e?.contentType || "page", l = c === void 0 ? e?.language ?? null : T, u = S === void 0 ? bx(e?.isHidden) : S;
24058
- k = wx(e, {
24132
+ let e = await t.prepare("SELECT title, slug, language, contentType, isHidden, startShowingAt, stopShowingAt, draftDataJson, dataJson, publishedAt, status, hasUnpublishedChanges FROM content_nodes WHERE id = ?").get(a), n = o === void 0 ? e?.title || "Untitled" : o, r = ie ?? e?.slug ?? null, i = T || e?.contentType || "page", l = c === void 0 ? e?.language ?? null : E, u = w === void 0 ? xx(e?.isHidden) : w, d = m === void 0 ? e?.startShowingAt ?? null : m, f = h === void 0 ? e?.stopShowingAt ?? null : h;
24133
+ ne = Tx(e, {
24059
24134
  title: n,
24060
24135
  slug: r,
24061
24136
  isHidden: u,
24062
- sanitizedFields: v
24137
+ startShowingAt: d,
24138
+ stopShowingAt: f,
24139
+ sanitizedFields: b
24063
24140
  });
24064
- let d = e?.draftDataJson || e?.dataJson || "{}";
24141
+ let p = e?.draftDataJson || e?.dataJson || "{}";
24065
24142
  try {
24066
- Cx(typeof d == "string" ? JSON.parse(d) : d, te);
24143
+ wx(typeof p == "string" ? JSON.parse(p) : p, A);
24067
24144
  } catch {}
24068
- let f = {};
24145
+ let _ = {};
24069
24146
  try {
24070
- f = JSON.parse(d);
24147
+ _ = JSON.parse(p);
24071
24148
  } catch {}
24072
- let p = {
24149
+ let v = {
24073
24150
  title: n,
24074
24151
  slug: r,
24075
24152
  contentType: i,
24076
24153
  language: l,
24077
24154
  isHidden: u,
24155
+ startShowingAt: d,
24156
+ stopShowingAt: f,
24157
+ ...b
24158
+ }, y = JSON.stringify({
24159
+ ..._,
24078
24160
  ...v
24079
- }, h = JSON.stringify({
24080
- ...f,
24081
- ...p
24082
- }), g = !1;
24083
- if (o !== void 0 && o.trim() !== (e?.title || "Untitled") && (g = !0), s !== void 0 && j !== e?.slug && (g = !0), c !== void 0 && T !== e?.language && (g = !0), !g && Object.keys(v).length > 0) {
24084
- for (let e of Object.keys(v)) if (JSON.stringify(v[e]) !== JSON.stringify(f[e])) {
24085
- g = !0;
24161
+ }), x = !1;
24162
+ if (o !== void 0 && o.trim() !== (e?.title || "Untitled") && (x = !0), s !== void 0 && ie !== e?.slug && (x = !0), c !== void 0 && E !== e?.language && (x = !0), m !== void 0 && d !== e?.startShowingAt && (x = !0), h !== void 0 && f !== e?.stopShowingAt && (x = !0), !x && Object.keys(b).length > 0) {
24163
+ for (let e of Object.keys(b)) if (JSON.stringify(b[e]) !== JSON.stringify(_[e])) {
24164
+ x = !0;
24086
24165
  break;
24087
24166
  }
24088
24167
  }
24089
- if (!g && m !== void 0) {
24168
+ if (!x && g !== void 0) {
24090
24169
  let e = await t.prepare("SELECT region, elementType, dataJson FROM content_blocks WHERE contentId = ? AND isDraft = 1 ORDER BY sortOrder ASC").all(a), n = Array.isArray(e) ? e : e?.results || [];
24091
- if (m.length !== n.length) g = !0;
24092
- else for (let e = 0; e < m.length; e++) {
24093
- let t = m[e], r = n[e], i = t.componentId || t.elementType || "text-block", a = t.region || "content", o = { ...t.data || {} };
24170
+ if (g.length !== n.length) x = !0;
24171
+ else for (let e = 0; e < g.length; e++) {
24172
+ let t = g[e], r = n[e], i = t.componentId || t.elementType || "text-block", a = t.region || "content", o = { ...t.data || {} };
24094
24173
  delete o._instanceId, delete o.blockId;
24095
24174
  let s = {};
24096
24175
  try {
24097
24176
  s = JSON.parse(r.dataJson);
24098
24177
  } catch {}
24099
24178
  if (delete s._instanceId, delete s.blockId, i !== r.elementType || a !== r.region || JSON.stringify(o) !== JSON.stringify(s)) {
24100
- g = !0;
24179
+ x = !0;
24101
24180
  break;
24102
24181
  }
24103
24182
  }
24104
24183
  }
24105
- A = e?.status === "published" || e?.publishedAt ? "published" : "draft";
24106
- let _ = e?.hasUnpublishedChanges === 1 || e?.hasUnpublishedChanges === !0;
24107
- ne = g ? 1 : +!!_;
24108
- let y = e?.publishedAt != null || e?.status === "published", b = y ? e.title : n, x = y ? e.slug : r, ee = y ? e.contentType : i, E = y ? e.language : l, D = y ? e.isHidden : u;
24109
- await t.prepare("\n UPDATE content_nodes \n SET title = ?, slug = ?, language = ?, contentType = ?, isHidden = ?, status = ?, draftDataJson = ?, hasUnpublishedChanges = ?, updatedById = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ").run(b, x, E, ee, D, A, h, ne, w, a);
24184
+ j = e?.status === "published" || e?.publishedAt ? "published" : "draft";
24185
+ let S = e?.hasUnpublishedChanges === 1 || e?.hasUnpublishedChanges === !0;
24186
+ re = x ? 1 : +!!S;
24187
+ let C = e?.publishedAt != null || e?.status === "published", D = C ? e.title : n, te = C ? e.slug : r, O = C ? e.contentType : i, k = C ? e.language : l, ae = C ? e.isHidden : u, oe = C ? e.startShowingAt : d, se = C ? e.stopShowingAt : f;
24188
+ await t.prepare("\n UPDATE content_nodes \n SET title = ?, slug = ?, language = ?, contentType = ?, isHidden = ?, startShowingAt = ?, stopShowingAt = ?, status = ?, draftDataJson = ?, hasUnpublishedChanges = ?, updatedById = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ").run(D, te, k, O, ae, oe, se, j, y, re, ee, a);
24110
24189
  } else {
24111
- k = !0;
24112
- let e = {
24190
+ ne = !0;
24191
+ let e = m === void 0 ? null : m, n = h === void 0 ? null : h, r = {
24113
24192
  title: o || "Untitled",
24114
- slug: j,
24115
- contentType: C,
24116
- language: T,
24117
- isHidden: S,
24118
- ...v
24119
- }, n = await t.prepare("\n INSERT INTO content_nodes (contentType, title, slug, language, isHidden, status, draftDataJson, dataJson, hasUnpublishedChanges, createdById, updatedById)\n VALUES (?, ?, ?, ?, ?, 'draft', ?, NULL, 0, ?, ?)\n ").run(C, o || "Untitled", j, T, S, JSON.stringify(e), w, w);
24120
- O = Number(n.lastInsertRowid);
24121
- }
24122
- if (h !== void 0 && Array.isArray(h) && O) {
24123
- await t.prepare("DELETE FROM node_channels WHERE nodeId = ?").run(O);
24124
- let e = [...new Set(h.map((e) => typeof e == "object" && e ? e.id || e.channelId : e))].filter((e) => e && e !== "all").map((e) => Number(e) || e);
24193
+ slug: ie,
24194
+ contentType: T,
24195
+ language: E,
24196
+ isHidden: w,
24197
+ startShowingAt: e,
24198
+ stopShowingAt: n,
24199
+ ...b
24200
+ }, i = await t.prepare("\n INSERT INTO content_nodes (contentType, title, slug, language, isHidden, startShowingAt, stopShowingAt, status, draftDataJson, dataJson, hasUnpublishedChanges, createdById, updatedById)\n VALUES (?, ?, ?, ?, ?, ?, ?, 'draft', ?, NULL, 0, ?, ?)\n ").run(T, o || "Untitled", ie, E, w, e, n, JSON.stringify(r), ee, ee);
24201
+ k = Number(i.lastInsertRowid);
24202
+ }
24203
+ if (_ !== void 0 && Array.isArray(_) && k) {
24204
+ await t.prepare("DELETE FROM node_channels WHERE nodeId = ?").run(k);
24205
+ let e = [...new Set(_.map((e) => typeof e == "object" && e ? e.id || e.channelId : e))].filter((e) => e && e !== "all").map((e) => Number(e) || e);
24125
24206
  if (e.length > 0) {
24126
- let n = e.map(() => "(?, ?)").join(", "), r = e.flatMap((e) => [O, e]);
24207
+ let n = e.map(() => "(?, ?)").join(", "), r = e.flatMap((e) => [k, e]);
24127
24208
  await t.prepare(`INSERT OR IGNORE INTO node_channels (nodeId, channelId) VALUES ${n}`).run(...r);
24128
24209
  }
24129
24210
  }
24130
- if (g !== void 0 && Array.isArray(g) && g.length > 0 && O) for (let e of g) {
24211
+ if (v !== void 0 && Array.isArray(v) && v.length > 0 && k) for (let e of v) {
24131
24212
  if (!e || !e.treeId) continue;
24132
- let n = Number(e.treeId) || e.treeId, r = xx(e.parentId ?? e._draftParentId ?? null), i = typeof e.sortOrder == "number" ? e.sortOrder : 0, a = await t.prepare("SELECT contentId, parentId, sortOrder FROM tree_nodes WHERE treeId = ? AND contentId = ?").get(n, O);
24133
- a ? ((a.parentId !== r || a.sortOrder !== i) && (k = !0), await t.prepare("UPDATE tree_nodes SET parentId = ?, sortOrder = ? WHERE treeId = ? AND contentId = ?").run(r, i, n, O)) : (k = !0, await t.prepare("INSERT INTO tree_nodes (treeId, contentId, parentId, sortOrder) VALUES (?, ?, ?, ?)").run(n, O, r, i));
24213
+ let n = Number(e.treeId) || e.treeId, r = Sx(e.parentId ?? e._draftParentId ?? null), i = typeof e.sortOrder == "number" ? e.sortOrder : 0, a = await t.prepare("SELECT contentId, parentId, sortOrder FROM tree_nodes WHERE treeId = ? AND contentId = ?").get(n, k);
24214
+ a ? ((a.parentId !== r || a.sortOrder !== i) && (ne = !0), await t.prepare("UPDATE tree_nodes SET parentId = ?, sortOrder = ? WHERE treeId = ? AND contentId = ?").run(r, i, n, k)) : (ne = !0, await t.prepare("INSERT INTO tree_nodes (treeId, contentId, parentId, sortOrder) VALUES (?, ?, ?, ?)").run(n, k, r, i));
24134
24215
  }
24135
- let re = [], ie = [], ae = [];
24136
- if (m !== void 0 && Array.isArray(m) && O) {
24137
- await t.prepare("DELETE FROM content_blocks WHERE contentId = ? AND isDraft = 1").run(O);
24216
+ let ae = [], oe = [], se = [];
24217
+ if (g !== void 0 && Array.isArray(g) && k) {
24218
+ await t.prepare("DELETE FROM content_blocks WHERE contentId = ? AND isDraft = 1").run(k);
24138
24219
  let e = [], n = [];
24139
- for (let t = 0; t < m.length; t++) {
24140
- let r = m[t], i = r.componentId || r.elementType || "text-block", a = r.data || {}, o = String(r.blockId || a.blockId || r.instanceId || r.id || `block-${Date.now()}`), { cleanedData: s, assetRefs: c, termRefs: l, nodeRefs: u } = ax({
24220
+ for (let t = 0; t < g.length; t++) {
24221
+ let r = g[t], i = r.componentId || r.elementType || "text-block", a = r.data || {}, o = String(r.blockId || a.blockId || r.instanceId || r.id || `block-${Date.now()}`), { cleanedData: s, assetRefs: c, termRefs: l, nodeRefs: u } = ax({
24141
24222
  ...a,
24142
24223
  blockId: o,
24143
24224
  _instanceId: o
24144
24225
  });
24145
- c.forEach((e) => re.push({
24226
+ c.forEach((e) => ae.push({
24146
24227
  ...e,
24147
24228
  fieldKey: `blocks[${t}].${e.fieldKey}`
24148
- })), l.forEach((e) => ie.push({
24229
+ })), l.forEach((e) => oe.push({
24149
24230
  ...e,
24150
24231
  fieldKey: `blocks[${t}].${e.fieldKey}`
24151
- })), u.forEach((e) => ae.push({
24232
+ })), u.forEach((e) => se.push({
24152
24233
  ...e,
24153
24234
  fieldKey: `blocks[${t}].${e.fieldKey}`
24154
24235
  }));
24155
24236
  let d = r.region !== void 0 && r.region !== null && String(r.region).trim() !== "" ? String(r.region) : "content";
24156
- e.push("(?, ?, ?, ?, ?, 1)"), n.push(O, t, i, JSON.stringify(s), d);
24237
+ e.push("(?, ?, ?, ?, ?, 1)"), n.push(k, t, i, JSON.stringify(s), d);
24157
24238
  }
24158
24239
  e.length > 0 && await t.prepare(`INSERT INTO content_blocks (contentId, sortOrder, elementType, dataJson, region, isDraft) VALUES ${e.join(", ")}`).run(...n);
24159
24240
  }
24160
- if (O) {
24161
- let n = [...y, ...re], r = [...b, ...ie], i = [...x, ...ae];
24162
- await ox(t, O, n), await sx(t, O, r), await cx(t, O, i);
24163
- let a = new Set(n.map((e) => e.assetId)), o = new Set([...te].filter((e) => !a.has(e)));
24241
+ if (k) {
24242
+ let n = [...x, ...ae], r = [...S, ...oe], i = [...C, ...se];
24243
+ await ox(t, k, n), await sx(t, k, r), await cx(t, k, i);
24244
+ let a = new Set(n.map((e) => e.assetId)), o = new Set([...A].filter((e) => !a.has(e)));
24164
24245
  if (o.size > 0) {
24165
24246
  let { storage: n } = ix(e.env);
24166
- await Tx(t, n, o);
24247
+ await Ex(t, n, o);
24167
24248
  }
24168
24249
  }
24169
24250
  return await $b(e).clear(), e.json({
24170
24251
  success: !0,
24171
- id: O,
24172
- status: A,
24173
- hasUnpublishedChanges: ne === 1 || A === "draft",
24174
- isStructuralChange: k
24252
+ id: k,
24253
+ status: j,
24254
+ hasUnpublishedChanges: re === 1 || j === "draft",
24255
+ isStructuralChange: ne
24175
24256
  });
24176
24257
  }), gx.post("/publish", async (e) => {
24177
24258
  let t = e.get("db"), n = await e.req.json(), r = n.id || n.nodeId;
@@ -24186,34 +24267,36 @@ gx.get("/", async (e) => {
24186
24267
  try {
24187
24268
  c = typeof o.draftDataJson == "string" ? JSON.parse(o.draftDataJson) : o.draftDataJson || {};
24188
24269
  } catch {}
24189
- let l = (s.title ?? o.title ?? "").trim(), u = (c.title ?? n.title ?? o.title ?? "").trim(), d = (s.slug ?? o.slug ?? "").trim(), f = (c.slug ?? n.slug ?? o.slug ?? "").trim(), p = (s.menuTitle ?? "").trim(), m = (c.menuTitle ?? "").trim(), h = l !== "" && u !== "" && l !== u || d !== "" && f !== "" && d !== f || p !== "" && m !== "" && p !== m, g = o.draftDataJson || o.dataJson || "{}", _ = c.title ?? n.title ?? o.title ?? "Untitled", v = c.slug ?? n.slug ?? o.slug ?? null, y = c.language === void 0 ? o.language : c.language, b = c.contentType ?? o.contentType ?? "page", x = c.isHidden === void 0 ? o.isHidden : c.isHidden;
24190
- await t.prepare("\n UPDATE content_nodes\n SET title = ?, slug = ?, language = ?, contentType = ?, isHidden = ?, publishedDataJson = ?, dataJson = ?, publishedAt = CURRENT_TIMESTAMP, status = 'published', hasUnpublishedChanges = 0, updatedById = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ").run(_, v, y, b, x, g, g, a, i), await t.prepare("DELETE FROM content_blocks WHERE contentId = ? AND isDraft = 0").run(i);
24191
- let S = await t.prepare("SELECT * FROM content_blocks WHERE contentId = ? AND isDraft = 1 ORDER BY sortOrder ASC").all(i), C = Array.isArray(S) ? S : S?.results || [];
24192
- if (C.length > 0) {
24270
+ let l = (s.title ?? o.title ?? "").trim(), u = (c.title ?? n.title ?? o.title ?? "").trim(), d = (s.slug ?? o.slug ?? "").trim(), f = (c.slug ?? n.slug ?? o.slug ?? "").trim(), p = (s.menuTitle ?? "").trim(), m = (c.menuTitle ?? "").trim(), h = s.startShowingAt ?? o.startShowingAt ?? "", g = c.startShowingAt ?? n.startShowingAt ?? o.startShowingAt ?? "", _ = s.stopShowingAt ?? o.stopShowingAt ?? "", v = c.stopShowingAt ?? n.stopShowingAt ?? o.stopShowingAt ?? "", y = l !== "" && u !== "" && l !== u || d !== "" && f !== "" && d !== f || p !== "" && m !== "" && p !== m || h !== g || _ !== v, b = o.draftDataJson || o.dataJson || "{}", x = c.title ?? n.title ?? o.title ?? "Untitled", S = c.slug ?? n.slug ?? o.slug ?? null, C = c.language === void 0 ? o.language : c.language, w = c.contentType ?? o.contentType ?? "page", T = c.isHidden === void 0 ? o.isHidden : c.isHidden, ee = c.startShowingAt === void 0 ? n.startShowingAt === void 0 ? o.startShowingAt : n.startShowingAt : c.startShowingAt, E = c.stopShowingAt === void 0 ? n.stopShowingAt === void 0 ? o.stopShowingAt : n.stopShowingAt : c.stopShowingAt;
24271
+ await t.prepare("\n UPDATE content_nodes\n SET title = ?, slug = ?, language = ?, contentType = ?, isHidden = ?, startShowingAt = ?, stopShowingAt = ?, publishedDataJson = ?, dataJson = ?, publishedAt = CURRENT_TIMESTAMP, status = 'published', hasUnpublishedChanges = 0, updatedById = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ").run(x, S, C, w, T, ee, E, b, b, a, i), await t.prepare("DELETE FROM content_blocks WHERE contentId = ? AND isDraft = 0").run(i);
24272
+ let D = await t.prepare("SELECT * FROM content_blocks WHERE contentId = ? AND isDraft = 1 ORDER BY sortOrder ASC").all(i), te = Array.isArray(D) ? D : D?.results || [];
24273
+ if (te.length > 0) {
24193
24274
  let e = [], n = [];
24194
- for (let t of C) {
24275
+ for (let t of te) {
24195
24276
  let r = t.region !== void 0 && t.region !== null && String(t.region).trim() !== "" ? String(t.region) : "content";
24196
24277
  e.push("(?, ?, ?, ?, ?, 0)"), n.push(i, t.sortOrder, t.elementType, t.dataJson, r);
24197
24278
  }
24198
24279
  await t.prepare(`INSERT INTO content_blocks (contentId, sortOrder, elementType, dataJson, region, isDraft) VALUES ${e.join(", ")}`).run(...n);
24199
24280
  }
24200
- let w = ((await t.prepare("SELECT COUNT(*) as count FROM node_revisions WHERE nodeId = ?").get(i))?.count || 0) + 1, T = {
24201
- version: w,
24281
+ let O = ((await t.prepare("SELECT COUNT(*) as count FROM node_revisions WHERE nodeId = ?").get(i))?.count || 0) + 1, k = {
24282
+ version: O,
24202
24283
  publishedAt: (/* @__PURE__ */ new Date()).toISOString(),
24203
24284
  node: {
24204
24285
  ...o,
24205
- dataJson: g
24286
+ dataJson: b
24206
24287
  },
24207
- blocks: C
24288
+ blocks: te
24208
24289
  };
24209
- return await t.prepare("INSERT INTO node_revisions (nodeId, version, snapshotJson, createdById) VALUES (?, ?, ?, ?)").run(i, w, JSON.stringify(T), a), await $b(e).clear(), h && await hx(t), new mx(e.env).purgeNode(e, t, i, h), e.json({
24290
+ await t.prepare("INSERT INTO node_revisions (nodeId, version, snapshotJson, createdById) VALUES (?, ?, ?, ?)").run(i, O, JSON.stringify(k), a), await $b(e).clear();
24291
+ let A = new mx(e.env);
24292
+ return y ? _x(e, t, [i]) : A.purgeNode(e, t, i, !1), e.json({
24210
24293
  success: !0,
24211
24294
  id: i,
24212
24295
  status: "published",
24213
- version: w,
24214
- publishedAt: T.publishedAt,
24296
+ version: O,
24297
+ publishedAt: k.publishedAt,
24215
24298
  hasUnpublishedChanges: !1,
24216
- isStructuralChange: h
24299
+ isStructuralChange: y
24217
24300
  });
24218
24301
  }), gx.post("/publish/batch", async (e) => {
24219
24302
  let t = e.get("db"), n = await e.req.json(), r = n.ids;
@@ -24232,33 +24315,33 @@ gx.get("/", async (e) => {
24232
24315
  try {
24233
24316
  l = typeof s.draftDataJson == "string" ? JSON.parse(s.draftDataJson) : s.draftDataJson || {};
24234
24317
  } catch {}
24235
- let u = (c.title ?? s.title ?? "").trim(), d = (l.title ?? n.title ?? s.title ?? "").trim(), f = (c.slug ?? s.slug ?? "").trim(), p = (l.slug ?? n.slug ?? s.slug ?? "").trim(), m = (c.menuTitle ?? "").trim(), h = (l.menuTitle ?? "").trim();
24236
- (u !== "" && d !== "" && u !== d || f !== "" && p !== "" && f !== p || m !== "" && h !== "" && m !== h) && (a = !0);
24237
- let g = s.draftDataJson || s.dataJson || "{}", _ = l.title ?? n.title ?? s.title ?? "Untitled", v = l.slug ?? n.slug ?? s.slug ?? null, y = l.language === void 0 ? s.language : l.language, b = l.contentType ?? s.contentType ?? "page", x = l.isHidden === void 0 ? s.isHidden : l.isHidden;
24238
- await t.prepare("\n UPDATE content_nodes\n SET title = ?, slug = ?, language = ?, contentType = ?, isHidden = ?, publishedDataJson = ?, dataJson = ?, publishedAt = CURRENT_TIMESTAMP, status = 'published', hasUnpublishedChanges = 0, updatedById = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ").run(_, v, y, b, x, g, g, i, r), await t.prepare("DELETE FROM content_blocks WHERE contentId = ? AND isDraft = 0").run(r);
24239
- let S = await t.prepare("SELECT * FROM content_blocks WHERE contentId = ? AND isDraft = 1 ORDER BY sortOrder ASC").all(r), C = Array.isArray(S) ? S : S?.results || [];
24240
- if (C.length > 0) {
24318
+ let u = (c.title ?? s.title ?? "").trim(), d = (l.title ?? n.title ?? s.title ?? "").trim(), f = (c.slug ?? s.slug ?? "").trim(), p = (l.slug ?? n.slug ?? s.slug ?? "").trim(), m = (c.menuTitle ?? "").trim(), h = (l.menuTitle ?? "").trim(), g = c.startShowingAt ?? s.startShowingAt ?? "", _ = l.startShowingAt ?? n.startShowingAt ?? s.startShowingAt ?? "", v = c.stopShowingAt ?? s.stopShowingAt ?? "", y = l.stopShowingAt ?? n.stopShowingAt ?? s.stopShowingAt ?? "";
24319
+ (u !== "" && d !== "" && u !== d || f !== "" && p !== "" && f !== p || m !== "" && h !== "" && m !== h || g !== _ || v !== y) && (a = !0);
24320
+ let b = s.draftDataJson || s.dataJson || "{}", x = l.title ?? n.title ?? s.title ?? "Untitled", S = l.slug ?? n.slug ?? s.slug ?? null, C = l.language === void 0 ? s.language : l.language, w = l.contentType ?? s.contentType ?? "page", T = l.isHidden === void 0 ? s.isHidden : l.isHidden, ee = l.startShowingAt === void 0 ? n.startShowingAt === void 0 ? s.startShowingAt : n.startShowingAt : l.startShowingAt, E = l.stopShowingAt === void 0 ? n.stopShowingAt === void 0 ? s.stopShowingAt : n.stopShowingAt : l.stopShowingAt;
24321
+ await t.prepare("\n UPDATE content_nodes\n SET title = ?, slug = ?, language = ?, contentType = ?, isHidden = ?, startShowingAt = ?, stopShowingAt = ?, publishedDataJson = ?, dataJson = ?, publishedAt = CURRENT_TIMESTAMP, status = 'published', hasUnpublishedChanges = 0, updatedById = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ").run(x, S, C, w, T, ee, E, b, b, i, r), await t.prepare("DELETE FROM content_blocks WHERE contentId = ? AND isDraft = 0").run(r);
24322
+ let D = await t.prepare("SELECT * FROM content_blocks WHERE contentId = ? AND isDraft = 1 ORDER BY sortOrder ASC").all(r), te = Array.isArray(D) ? D : D?.results || [];
24323
+ if (te.length > 0) {
24241
24324
  let e = [], n = [];
24242
- for (let t of C) {
24325
+ for (let t of te) {
24243
24326
  let i = t.region !== void 0 && t.region !== null && String(t.region).trim() !== "" ? String(t.region) : "content";
24244
24327
  e.push("(?, ?, ?, ?, ?, 0)"), n.push(r, t.sortOrder, t.elementType, t.dataJson, i);
24245
24328
  }
24246
24329
  await t.prepare(`INSERT INTO content_blocks (contentId, sortOrder, elementType, dataJson, region, isDraft) VALUES ${e.join(", ")}`).run(...n);
24247
24330
  }
24248
- let w = ((await t.prepare("SELECT COUNT(*) as count FROM node_revisions WHERE nodeId = ?").get(r))?.count || 0) + 1, T = {
24249
- version: w,
24331
+ let O = ((await t.prepare("SELECT COUNT(*) as count FROM node_revisions WHERE nodeId = ?").get(r))?.count || 0) + 1, k = {
24332
+ version: O,
24250
24333
  publishedAt: (/* @__PURE__ */ new Date()).toISOString(),
24251
24334
  node: {
24252
24335
  ...s,
24253
- dataJson: g
24336
+ dataJson: b
24254
24337
  },
24255
- blocks: C
24338
+ blocks: te
24256
24339
  };
24257
- await t.prepare("INSERT INTO node_revisions (nodeId, version, snapshotJson, createdById) VALUES (?, ?, ?, ?)").run(r, w, JSON.stringify(T), i), o.push(r);
24340
+ await t.prepare("INSERT INTO node_revisions (nodeId, version, snapshotJson, createdById) VALUES (?, ?, ?, ?)").run(r, O, JSON.stringify(k), i), o.push(r);
24258
24341
  }
24259
24342
  await $b(e).clear();
24260
24343
  let s = new mx(e.env);
24261
- if (a) await hx(t), s.purgeGlobalCache(e, t);
24344
+ if (a) _x(e, t, o);
24262
24345
  else for (let n of o) s.purgeNode(e, t, n, !1);
24263
24346
  return e.json({
24264
24347
  success: !0,
@@ -24270,13 +24353,13 @@ gx.get("/", async (e) => {
24270
24353
  let t = e.get("db"), n = e.req.query("id");
24271
24354
  if (!n) return e.json({ error: "Node ID required" }, 400);
24272
24355
  let r = Number(n);
24273
- return await t.prepare("UPDATE content_nodes SET deletedAt = CURRENT_TIMESTAMP WHERE id = ?").run(r), await $b(e).clear(), await hx(t), new mx(e.env).purgeNode(e, t, r, !0), e.json({
24356
+ return await t.prepare("UPDATE content_nodes SET deletedAt = CURRENT_TIMESTAMP WHERE id = ?").run(r), await $b(e).clear(), new mx(e.env), _x(e, t, [r]), e.json({
24274
24357
  success: !0,
24275
24358
  deletedNodeId: r
24276
24359
  });
24277
24360
  }), gx.post("/restore", async (e) => {
24278
24361
  let t = e.get("db"), n = await e.req.json(), r = Number(n.id);
24279
- return r ? await t.prepare("SELECT id FROM content_nodes WHERE id = ?").get(r) ? (await t.prepare("UPDATE content_nodes SET deletedAt = NULL WHERE id = ?").run(r), await $b(e).clear(), await hx(t), new mx(e.env).purgeNode(e, t, r, !0), e.json({
24362
+ return r ? await t.prepare("SELECT id FROM content_nodes WHERE id = ?").get(r) ? (await t.prepare("UPDATE content_nodes SET deletedAt = NULL WHERE id = ?").run(r), await $b(e).clear(), new mx(e.env), _x(e, t, [r]), e.json({
24280
24363
  success: !0,
24281
24364
  restoredNodeId: r
24282
24365
  })) : e.json({ error: "Node not found" }, 404) : e.json({ error: "Node ID required" }, 400);
@@ -24284,7 +24367,7 @@ gx.get("/", async (e) => {
24284
24367
  let t = e.get("db"), n = e.req.query("id");
24285
24368
  if (!n) return e.json({ error: "Node ID required" }, 400);
24286
24369
  let r = Number(n);
24287
- return await t.prepare("DELETE FROM node_channels WHERE nodeId = ?").run(r), await t.prepare("DELETE FROM tree_nodes WHERE contentId = ?").run(r), await t.prepare("DELETE FROM content_blocks WHERE contentId = ?").run(r), await t.prepare("DELETE FROM node_revisions WHERE nodeId = ?").run(r), await t.prepare("DELETE FROM node_assets WHERE nodeId = ?").run(r), await t.prepare("DELETE FROM node_terms WHERE nodeId = ?").run(r), await t.prepare("DELETE FROM content_nodes WHERE id = ?").run(r), await $b(e).clear(), await hx(t), new mx(e.env).purgeNode(e, t, r, !0), e.json({
24370
+ return await new mx(e.env).purgeInternalWorkerCache(e, t, r), await t.prepare("DELETE FROM node_channels WHERE nodeId = ?").run(r), await t.prepare("DELETE FROM tree_nodes WHERE contentId = ?").run(r), await t.prepare("DELETE FROM content_blocks WHERE contentId = ?").run(r), await t.prepare("DELETE FROM node_revisions WHERE nodeId = ?").run(r), await t.prepare("DELETE FROM node_assets WHERE nodeId = ?").run(r), await t.prepare("DELETE FROM node_terms WHERE nodeId = ?").run(r), await t.prepare("DELETE FROM content_nodes WHERE id = ?").run(r), await $b(e).clear(), _x(e, t), e.json({
24288
24371
  success: !0,
24289
24372
  purgedNodeId: r
24290
24373
  });
@@ -24299,7 +24382,7 @@ gx.get("/", async (e) => {
24299
24382
  } catch {}
24300
24383
  return {
24301
24384
  version: e.version,
24302
- publishedAt: t || new DatetoISOString(),
24385
+ publishedAt: t || (/* @__PURE__ */ new Date()).toISOString(),
24303
24386
  createdById: e.createdById
24304
24387
  };
24305
24388
  });
@@ -24357,13 +24440,16 @@ gx.get("/", async (e) => {
24357
24440
  let t = JSON.stringify(e);
24358
24441
  s += ", dataJson = ?, publishedDataJson = ?", c.push(t, t);
24359
24442
  }
24360
- return s += " WHERE id = ?", c.push(n), await t.prepare(s).run(...c), await $b(e).clear(), await hx(t), new mx(e.env).purgeNode(e, t, n, !0), e.json({
24443
+ s += " WHERE id = ?", c.push(n), await t.prepare(s).run(...c), await $b(e).clear();
24444
+ let u = await new mx(e.env).purgeVisibilityChange(e, t, n);
24445
+ return e.json({
24361
24446
  success: !0,
24362
- isHidden: i
24447
+ isHidden: i,
24448
+ cacheInvalidated: u
24363
24449
  });
24364
24450
  });
24365
- var Dx = new e();
24366
- function Ox(e, t = null) {
24451
+ var Ox = new e();
24452
+ function kx(e, t = null) {
24367
24453
  let n = [];
24368
24454
  for (let r = 0; r < e.length; r++) {
24369
24455
  let i = e[r];
@@ -24375,19 +24461,19 @@ function Ox(e, t = null) {
24375
24461
  id: o,
24376
24462
  parentId: t,
24377
24463
  sortOrder: r
24378
- }), i.children && Array.isArray(i.children) && i.children.length > 0 && n.push(...Ox(i.children, o)));
24464
+ }), i.children && Array.isArray(i.children) && i.children.length > 0 && n.push(...kx(i.children, o)));
24379
24465
  }
24380
24466
  return n;
24381
24467
  }
24382
- function kx(e) {
24468
+ function Ax(e) {
24383
24469
  if (e == null || e === "null" || e === "" || typeof e == "string" && e.startsWith("draft-")) return null;
24384
24470
  let t = Number(e);
24385
24471
  return isNaN(t) ? null : t;
24386
24472
  }
24387
- function Ax(e) {
24473
+ function jx(e) {
24388
24474
  return +(e === !0 || e === 1 || e === "1" || e === "true");
24389
24475
  }
24390
- Dx.get("/tree.json", async (e) => {
24476
+ Ox.get("/tree.json", async (e) => {
24391
24477
  try {
24392
24478
  let t = e.get("db"), n = e.req.query("treeId") || "main-nav", r = e.req.query("preview") === "true", i = 1;
24393
24479
  if (isNaN(Number(n))) {
@@ -24398,7 +24484,7 @@ Dx.get("/tree.json", async (e) => {
24398
24484
  e && e.id && (i = Number(e.id));
24399
24485
  }
24400
24486
  } else i = Number(n);
24401
- let a = await t.prepare("\n SELECT \n t.contentId as treeNodeId, \n t.treeId,\n t.contentId,\n t.parentId,\n t.sortOrder,\n c.title,\n c.slug,\n c.language,\n c.contentType as nodeType,\n c.isHidden,\n c.status,\n c.publishedAt,\n c.hasUnpublishedChanges,\n c.dataJson,\n c.draftDataJson,\n (SELECT COUNT(*) FROM node_assets WHERE nodeId = t.contentId) as assetCount\n FROM tree_nodes t\n INNER JOIN content_nodes c ON t.contentId = c.id\n WHERE t.treeId = ? AND (c.deletedAt IS NULL OR c.deletedAt = '')\n ORDER BY t.sortOrder ASC\n ").all(i), o = Array.isArray(a) ? a : a?.results || [], s = [], c = /* @__PURE__ */ new Set();
24487
+ let a = await t.prepare("\n WITH tree_asset_counts AS (\n SELECT na.nodeId, COUNT(*) as assetCount \n FROM node_assets na \n INNER JOIN tree_nodes tn ON na.nodeId = tn.contentId \n WHERE tn.treeId = ? \n GROUP BY na.nodeId\n )\n SELECT \n t.contentId as treeNodeId, \n t.treeId,\n t.contentId,\n t.parentId,\n t.sortOrder,\n c.title,\n c.slug,\n c.language,\n c.contentType as nodeType,\n c.isHidden,\n c.status,\n c.publishedAt,\n c.hasUnpublishedChanges,\n c.dataJson,\n c.draftDataJson,\n COALESCE(ac.assetCount, 0) as assetCount\n FROM tree_nodes t\n INNER JOIN content_nodes c ON t.contentId = c.id\n LEFT JOIN tree_asset_counts ac ON t.contentId = ac.nodeId\n WHERE t.treeId = ? AND c.deletedAt IS NULL\n ORDER BY t.sortOrder ASC\n ").all(i, i), o = Array.isArray(a) ? a : a?.results || [], s = [], c = /* @__PURE__ */ new Set();
24402
24488
  for (let e of o) {
24403
24489
  let t = e.contentId;
24404
24490
  c.has(t) || (c.add(t), s.push(e));
@@ -24440,7 +24526,7 @@ Dx.get("/tree.json", async (e) => {
24440
24526
  } catch (t) {
24441
24527
  return console.error("[CMS Tree API] GET Error:", t), e.json({ error: t.message || "Failed to fetch tree" }, 500);
24442
24528
  }
24443
- }), Dx.post("/tree.json", async (e) => {
24529
+ }), Ox.post("/tree.json", async (e) => {
24444
24530
  try {
24445
24531
  let t = e.get("db"), n = await e.req.json(), r = n.treeId ? String(n.treeId).trim() : "main-nav", i = $b(e), a = new mx(e.env), o = 1;
24446
24532
  if (isNaN(Number(r))) {
@@ -24452,7 +24538,7 @@ Dx.get("/tree.json", async (e) => {
24452
24538
  }
24453
24539
  } else o = Number(r);
24454
24540
  if (n.tree && Array.isArray(n.tree)) {
24455
- let r = Ox(n.tree, null);
24541
+ let r = kx(n.tree, null);
24456
24542
  if (r.length > 0) for (let e = 0; e < r.length; e += 50) {
24457
24543
  let n = r.slice(e, e + 50), i = n.map((e) => e.id), a = i.map(() => "?").join(","), s = "UPDATE tree_nodes SET \n";
24458
24544
  s += "parentId = CASE contentId \n", n.forEach(() => {
@@ -24472,9 +24558,9 @@ Dx.get("/tree.json", async (e) => {
24472
24558
  reorderedCount: r.length
24473
24559
  });
24474
24560
  }
24475
- let { action: s, title: c, nodeType: l, parentId: u, contentId: d, nodeData: f = {}, pageData: p = {} } = n, m = Object.keys(f).length > 0 ? { ...f } : { ...p }, h = Ax(n.isHidden === void 0 ? m.isHidden === void 0 ? m.hidden : m.isHidden : n.isHidden);
24561
+ let { action: s, title: c, nodeType: l, parentId: u, contentId: d, nodeData: f = {}, pageData: p = {} } = n, m = Object.keys(f).length > 0 ? { ...f } : { ...p }, h = jx(n.isHidden === void 0 ? m.isHidden === void 0 ? m.hidden : m.isHidden : n.isHidden);
24476
24562
  delete m._isTreeDraft, delete m._draftParentId, delete m.isNew, delete m.nodeType, delete m.contentType, delete m.title, delete m.slug, delete m.hidden, delete m.is_hidden, delete m.isHidden, delete m.status;
24477
- let g = kx(u), _ = e.get("user")?.id || null;
24563
+ let g = Ax(u), _ = e.get("user")?.id || null;
24478
24564
  if (s === "create") {
24479
24565
  let r = m.slug || n.slug || c, a = r ? String(r).toLowerCase().replace(/[^a-z0-9]+/g, "-").replace(/(^-|-$)/g, "") : null;
24480
24566
  if (a) {
@@ -24582,7 +24668,7 @@ Dx.get("/tree.json", async (e) => {
24582
24668
  details: t.message
24583
24669
  }, 500);
24584
24670
  }
24585
- }), Dx.get("/trees.json", async (e) => {
24671
+ }), Ox.get("/trees.json", async (e) => {
24586
24672
  try {
24587
24673
  let t = e.get("db"), n = await t.prepare("SELECT * FROM trees ORDER BY LOWER(label) ASC").all(), r = Array.isArray(n) ? n : n?.results || [], i = await t.prepare("SELECT channelId, treeId FROM channel_trees").all(), a = (Array.isArray(i) ? i : i?.results || []).reduce((e, t) => {
24588
24674
  let n = Number(t.treeId), r = Number(t.channelId);
@@ -24612,7 +24698,7 @@ Dx.get("/tree.json", async (e) => {
24612
24698
  } catch {
24613
24699
  return e.json([]);
24614
24700
  }
24615
- }), Dx.post("/trees.json", async (e) => {
24701
+ }), Ox.post("/trees.json", async (e) => {
24616
24702
  try {
24617
24703
  let t = e.get("db"), n = await e.req.json(), r = n.id, i = r != null && r !== "" && !isNaN(Number(r)) ? Number(r) : null, a = `tree-${Date.now().toString(36)}`, o = (n.key || n.slug || a).toLowerCase().replace(/[^a-z0-9_-]/g, "-"), s = n.label?.trim() || o, c = n.treeType !== void 0 && n.treeType !== null ? n.treeType : n.type ?? "site", l = n.channelId !== void 0 && n.channelId !== null && Number(n.channelId) || null, u = +(n.isHidden === !0 || n.isHidden === 1 || n.isHidden === "true"), d = e.get("user")?.id || null, f = { ...n };
24618
24704
  if (delete f.id, delete f.key, delete f.label, delete f.treeType, delete f.type, delete f.channelId, delete f.channels, delete f.isHidden, delete f.createdById, delete f.updatedById, delete f.createdAt, delete f.updatedAt, await t.prepare("SELECT id FROM trees WHERE key = ? AND id != ? LIMIT 1").get(o, i ?? -1)) return e.json({
@@ -24651,7 +24737,7 @@ Dx.get("/tree.json", async (e) => {
24651
24737
  } catch (t) {
24652
24738
  return console.error("[API Trees] Error saving tree:", t), e.json({ error: t.message || "Failed to save tree" }, 500);
24653
24739
  }
24654
- }), Dx.delete("/trees.json", async (e) => {
24740
+ }), Ox.delete("/trees.json", async (e) => {
24655
24741
  let t = e.get("db"), n = e.req.query("id");
24656
24742
  if (!n) return e.json({ error: "Tree ID required" }, 400);
24657
24743
  let r = Number(n);
@@ -24664,8 +24750,8 @@ Dx.get("/tree.json", async (e) => {
24664
24750
  return e.json({ error: "Failed to delete tree" }, 500);
24665
24751
  }
24666
24752
  });
24667
- var jx = new e();
24668
- jx.get("/", async (e) => {
24753
+ var Mx = new e();
24754
+ Mx.get("/", async (e) => {
24669
24755
  try {
24670
24756
  let t = e.get("db"), n = await t.prepare("SELECT * FROM channels ORDER BY id ASC").all(), r = Array.isArray(n) ? n : n?.results || [], i = await t.prepare("SELECT channelId, treeId, key, metaJson FROM channel_trees").all(), a = ((Array.isArray(i) ? i : i?.results || []) || []).reduce((e, t) => {
24671
24757
  e[t.channelId] || (e[t.channelId] = []);
@@ -24731,27 +24817,27 @@ jx.get("/", async (e) => {
24731
24817
  error: t.message
24732
24818
  }, 500);
24733
24819
  }
24734
- }), jx.post("/", async (e) => {
24820
+ }), Mx.post("/", async (e) => {
24735
24821
  try {
24736
24822
  let t = e.get("db"), n = await e.req.json(), r = n.channel || n.data || n, i = r.id, a = i != null && i !== "" && !isNaN(Number(i)) ? Number(i) : null, { key: o, label: s, channelType: c = "website", domain: l = "localhost", baseUrl: u = "http://localhost:4321", defaultLanguage: d, default_language: f, language: p, isHidden: m, hidden: h, trees: g = [], createdById: _ = null, updatedById: v = null, id: y, createdAt: b, updatedAt: x, ...S } = r, C = o?.trim() || "main", w = s?.trim() || "Untitled Channel", T = d || f || p || "";
24737
24823
  typeof T == "object" && T && (T = T.value || T.id || ""), T = String(T).trim();
24738
- let ee = m === !0 || m === "true" || m === 1 || h === !0 || h === "true" || h === 1, E = Array.isArray(g) ? g : [], D = JSON.stringify(S || {}), O = e.get("user")?.id || v || _ || null;
24824
+ let ee = m === !0 || m === "true" || m === 1 || h === !0 || h === "true" || h === 1, E = Array.isArray(g) ? g : [], D = JSON.stringify(S || {}), te = e.get("user")?.id || v || _ || null;
24739
24825
  if (await t.prepare("SELECT id FROM channels WHERE key = ? AND id != ? LIMIT 1").get(C, a ?? -1)) return e.json({
24740
24826
  error: `Channel API key "${C}" is already in use.`,
24741
24827
  field: "key"
24742
24828
  }, 409);
24743
- let te = a;
24744
- if (a) await t.prepare("\n UPDATE channels \n SET key = ?, label = ?, channelType = ?, domain = ?, baseUrl = ?, defaultLanguage = ?, \n isHidden = ?, dataJson = ?, updatedById = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ").run(C, w, c, l, u, T, +!!ee, D, O, a);
24829
+ let O = a;
24830
+ if (a) await t.prepare("\n UPDATE channels \n SET key = ?, label = ?, channelType = ?, domain = ?, baseUrl = ?, defaultLanguage = ?, \n isHidden = ?, dataJson = ?, updatedById = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ").run(C, w, c, l, u, T, +!!ee, D, te, a);
24745
24831
  else {
24746
- let e = await t.prepare("\n INSERT INTO channels (key, label, channelType, domain, baseUrl, defaultLanguage, isHidden, dataJson, createdById, updatedById)\n VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)\n RETURNING id\n ").get(C, w, c, l, u, T, +!!ee, D, O, O), n = e?.results?.[0] || e;
24832
+ let e = await t.prepare("\n INSERT INTO channels (key, label, channelType, domain, baseUrl, defaultLanguage, isHidden, dataJson, createdById, updatedById)\n VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)\n RETURNING id\n ").get(C, w, c, l, u, T, +!!ee, D, te, te), n = e?.results?.[0] || e;
24747
24833
  if (!n || !n.id) throw Error("Failed to retrieve newly created Channel ID from Cloudflare D1.");
24748
- te = Number(n.id);
24834
+ O = Number(n.id);
24749
24835
  }
24750
- await t.prepare("DELETE FROM channel_trees WHERE channelId = ?").run(te);
24836
+ await t.prepare("DELETE FROM channel_trees WHERE channelId = ?").run(O);
24751
24837
  let k = E.filter((e) => e && e.treeId && e.key);
24752
24838
  if (k.length > 0) {
24753
24839
  let e = k.map(() => "(?, ?, ?, ?)").join(", "), n = k.flatMap((e) => [
24754
- te,
24840
+ O,
24755
24841
  Number(e.treeId) || e.treeId,
24756
24842
  String(e.key).trim(),
24757
24843
  JSON.stringify(e.meta || {})
@@ -24762,9 +24848,9 @@ jx.get("/", async (e) => {
24762
24848
  `).run(...n);
24763
24849
  }
24764
24850
  let A = $b(e);
24765
- return await A.delete(`channel:${C}`), await A.delete(`channel:${te}`), await A.clear(), await hx(t), new mx(e.env).purgeGlobalCache(e, t), e.json({
24851
+ return await A.delete(`channel:${C}`), await A.delete(`channel:${O}`), await A.clear(), await hx(t), new mx(e.env).purgeGlobalCache(e, t), e.json({
24766
24852
  success: !0,
24767
- id: te
24853
+ id: O
24768
24854
  });
24769
24855
  } catch (t) {
24770
24856
  return console.error("[API Channels] Error saving channel:", t), e.json({
@@ -24772,7 +24858,7 @@ jx.get("/", async (e) => {
24772
24858
  details: t.message
24773
24859
  }, 500);
24774
24860
  }
24775
- }), jx.delete("/", async (e) => {
24861
+ }), Mx.delete("/", async (e) => {
24776
24862
  let t = e.get("db"), n = e.req.query("id");
24777
24863
  if (!n) return e.json({ error: "Channel ID required" }, 400);
24778
24864
  let r = Number(n);
@@ -24790,15 +24876,15 @@ jx.get("/", async (e) => {
24790
24876
  }, 500);
24791
24877
  }
24792
24878
  });
24793
- var Mx = new e();
24794
- function Nx(e) {
24879
+ var Nx = new e();
24880
+ function Px(e) {
24795
24881
  return e.normalize("NFD").replace(/[\u0300-\u036f]/g, "").toLowerCase().trim().replace(/[^a-z0-9\s-]/g, "").replace(/[\s-]+/g, "-").replace(/^-+|-+$/g, "");
24796
24882
  }
24797
- function Px(e) {
24883
+ function Fx(e) {
24798
24884
  let t = (e || "").trim().toLowerCase(), n = px()?.taxonomies || {};
24799
24885
  return n[t] ? t : n[`${t}s`] ? `${t}s` : t.endsWith("s") && n[t.slice(0, -1)] ? t.slice(0, -1) : t;
24800
24886
  }
24801
- async function Fx(e, t, n = []) {
24887
+ async function Ix(e, t, n = []) {
24802
24888
  let r = e.prepare(t);
24803
24889
  if (typeof r.bind == "function") {
24804
24890
  let e = await r.bind(...n).all();
@@ -24810,10 +24896,10 @@ async function Fx(e, t, n = []) {
24810
24896
  }
24811
24897
  return [];
24812
24898
  }
24813
- Mx.get("/:taxonomy", async (e) => {
24814
- let t = e.get("db"), n = Px(e.req.param("taxonomy"));
24899
+ Nx.get("/:taxonomy", async (e) => {
24900
+ let t = e.get("db"), n = Fx(e.req.param("taxonomy"));
24815
24901
  try {
24816
- let r = (await Fx(t, "\n SELECT id, taxonomy, key, label, parentId, sortOrder, dataJson, createdAt, updatedAt\n FROM taxonomy_terms\n WHERE taxonomy = ?\n ORDER BY sortOrder ASC, label ASC\n ", [n])).map((e) => ({
24902
+ let r = (await Ix(t, "\n SELECT id, taxonomy, key, label, parentId, sortOrder, dataJson, createdAt, updatedAt\n FROM taxonomy_terms\n WHERE taxonomy = ?\n ORDER BY sortOrder ASC, label ASC\n ", [n])).map((e) => ({
24817
24903
  ...e,
24818
24904
  data: e.dataJson ? JSON.parse(e.dataJson) : {}
24819
24905
  }));
@@ -24824,12 +24910,12 @@ Mx.get("/:taxonomy", async (e) => {
24824
24910
  } catch (t) {
24825
24911
  return console.error("[Taxonomy API] Error fetching terms:", t), e.json({ error: "Failed to fetch taxonomy terms" }, 500);
24826
24912
  }
24827
- }), Mx.post("/:taxonomy", async (e) => {
24828
- let t = e.get("db"), n = Px(e.req.param("taxonomy")), r = await e.req.json(), i = r.label?.trim();
24913
+ }), Nx.post("/:taxonomy", async (e) => {
24914
+ let t = e.get("db"), n = Fx(e.req.param("taxonomy")), r = await e.req.json(), i = r.label?.trim();
24829
24915
  if (!i) return e.json({ error: "Label is required" }, 400);
24830
- let a = r.key?.trim() || Nx(i), o = r.parentId ? Number(r.parentId) : null, s = r.sortOrder ? Number(r.sortOrder) : 0, c = r.data ? JSON.stringify(r.data) : "{}";
24916
+ let a = r.key?.trim() || Px(i), o = r.parentId ? Number(r.parentId) : null, s = r.sortOrder ? Number(r.sortOrder) : 0, c = r.data ? JSON.stringify(r.data) : "{}";
24831
24917
  try {
24832
- if ((await Fx(t, "SELECT id FROM taxonomy_terms WHERE taxonomy = ? AND key = ?", [n, a])).length > 0) return e.json({ error: `A term with the key '${a}' already exists in this taxonomy.` }, 409);
24918
+ if ((await Ix(t, "SELECT id FROM taxonomy_terms WHERE taxonomy = ? AND key = ?", [n, a])).length > 0) return e.json({ error: `A term with the key '${a}' already exists in this taxonomy.` }, 409);
24833
24919
  let r = t.prepare("\n INSERT INTO taxonomy_terms (taxonomy, key, label, parentId, sortOrder, dataJson)\n VALUES (?, ?, ?, ?, ?, ?)\n "), l;
24834
24920
  return l = typeof r.bind == "function" ? await r.bind(n, a, i, o, s, c).run() : await r.run(n, a, i, o, s, c), e.json({
24835
24921
  success: !0,
@@ -24838,12 +24924,12 @@ Mx.get("/:taxonomy", async (e) => {
24838
24924
  } catch (t) {
24839
24925
  return console.error("[Taxonomy API] Error creating term:", t), e.json({ error: "Failed to create taxonomy term" }, 500);
24840
24926
  }
24841
- }), Mx.put("/:taxonomy/:id", async (e) => {
24842
- let t = e.get("db"), n = Px(e.req.param("taxonomy")), r = Number(e.req.param("id"));
24927
+ }), Nx.put("/:taxonomy/:id", async (e) => {
24928
+ let t = e.get("db"), n = Fx(e.req.param("taxonomy")), r = Number(e.req.param("id"));
24843
24929
  if (isNaN(r)) return e.json({ error: "Invalid term ID" }, 400);
24844
24930
  let i = await e.req.json();
24845
24931
  try {
24846
- let a = await Fx(t, "SELECT * FROM taxonomy_terms WHERE id = ? AND taxonomy = ?", [r, n]);
24932
+ let a = await Ix(t, "SELECT * FROM taxonomy_terms WHERE id = ? AND taxonomy = ?", [r, n]);
24847
24933
  if (a.length === 0) return e.json({ error: "Term not found" }, 404);
24848
24934
  let o = a[0], s = i.label === void 0 ? o.label : i.label.trim(), c = i.key === void 0 ? o.key : i.key.trim(), l = i.parentId === void 0 ? o.parentId : i.parentId ? Number(i.parentId) : null, u = i.sortOrder === void 0 ? o.sortOrder : Number(i.sortOrder), d = o.dataJson;
24849
24935
  if (i.data) {
@@ -24853,14 +24939,14 @@ Mx.get("/:taxonomy", async (e) => {
24853
24939
  ...i.data
24854
24940
  });
24855
24941
  }
24856
- if (c !== o.key && (await Fx(t, "SELECT id FROM taxonomy_terms WHERE taxonomy = ? AND key = ?", [n, c])).length > 0) return e.json({ error: `A term with the key '${c}' already exists in this taxonomy.` }, 409);
24942
+ if (c !== o.key && (await Ix(t, "SELECT id FROM taxonomy_terms WHERE taxonomy = ? AND key = ?", [n, c])).length > 0) return e.json({ error: `A term with the key '${c}' already exists in this taxonomy.` }, 409);
24857
24943
  let f = t.prepare("\n UPDATE taxonomy_terms \n SET label = ?, key = ?, parentId = ?, sortOrder = ?, dataJson = ?, updatedAt = CURRENT_TIMESTAMP\n WHERE id = ?\n ");
24858
24944
  return typeof f.bind == "function" ? await f.bind(s, c, l, u, d, r).run() : await f.run(s, c, l, u, d, r), e.json({ success: !0 });
24859
24945
  } catch (t) {
24860
24946
  return console.error("[Taxonomy API] Error updating term:", t), e.json({ error: "Failed to update taxonomy term" }, 500);
24861
24947
  }
24862
- }), Mx.delete("/:taxonomy/:id", async (e) => {
24863
- let t = e.get("db"), n = Px(e.req.param("taxonomy")), r = Number(e.req.param("id"));
24948
+ }), Nx.delete("/:taxonomy/:id", async (e) => {
24949
+ let t = e.get("db"), n = Fx(e.req.param("taxonomy")), r = Number(e.req.param("id"));
24864
24950
  if (isNaN(r)) return e.json({ error: "Invalid term ID" }, 400);
24865
24951
  try {
24866
24952
  let i = t.prepare("DELETE FROM taxonomy_terms WHERE id = ? AND taxonomy = ?");
@@ -24869,20 +24955,20 @@ Mx.get("/:taxonomy", async (e) => {
24869
24955
  return console.error("[Taxonomy API] Error deleting term:", t), e.json({ error: "Failed to delete taxonomy term" }, 500);
24870
24956
  }
24871
24957
  });
24872
- var Ix = null, Lx = null;
24958
+ var Lx = null, Rx = null;
24873
24959
  if (typeof process < "u" && process?.versions?.node) try {
24874
24960
  let e = i(import.meta.url);
24875
- Ix = e("node:fs"), Lx = e("node:path");
24961
+ Lx = e("node:fs"), Rx = e("node:path");
24876
24962
  } catch {}
24877
- function Rx(e, t = "") {
24963
+ function zx(e, t = "") {
24878
24964
  let n = e.split(/[\\/]/).pop() || "";
24879
24965
  return t && n.endsWith(t) ? n.slice(0, -t.length) : n;
24880
24966
  }
24881
- function zx(e) {
24967
+ function Bx(e) {
24882
24968
  let t = e.match(/\.[^.\\/]+$/);
24883
24969
  return t ? t[0] : "";
24884
24970
  }
24885
- var Bx = {
24971
+ var Vx = {
24886
24972
  nodes: {},
24887
24973
  trees: {},
24888
24974
  blocks: {},
@@ -24892,10 +24978,10 @@ var Bx = {
24892
24978
  nodeLayouts: {},
24893
24979
  blockLayouts: {}
24894
24980
  };
24895
- function Vx(e) {
24981
+ function Hx(e) {
24896
24982
  return e ? typeof e == "string" ? e.trim() : Array.isArray(e) ? e.includes("*") ? "*" : e : "*" : "*";
24897
24983
  }
24898
- function Hx(e = {}, t = {}) {
24984
+ function Ux(e = {}, t = {}) {
24899
24985
  let n = {
24900
24986
  ...e,
24901
24987
  ...t,
@@ -24907,62 +24993,62 @@ function Hx(e = {}, t = {}) {
24907
24993
  };
24908
24994
  return t.required === !0 || String(t.required).toLowerCase() === "true" || t.rules?.required === !0 || String(t.rules?.required).toLowerCase() === "true" || t.required === void 0 && (e.required === !0 || String(e.required).toLowerCase() === "true" || e.rules?.required === !0 || String(e.rules?.required).toLowerCase() === "true") ? (n.required = !0, n.rules.required = !0) : (t.required === !1 || t.rules?.required === !1) && (n.required = !1, n.rules.required = !1), n;
24909
24995
  }
24910
- function Ux(e) {
24996
+ function Wx(e) {
24911
24997
  if (!e || typeof e != "object") return e;
24912
- if (Array.isArray(e)) return e.map(Ux);
24998
+ if (Array.isArray(e)) return e.map(Wx);
24913
24999
  let t = {};
24914
25000
  for (let [n, r] of Object.entries(e)) if (n === "<<" || n === "<<:") {
24915
- let e = Ux(r);
25001
+ let e = Wx(r);
24916
25002
  if (typeof e == "object" && e) {
24917
25003
  if (Array.isArray(e)) for (let n of e) Object.assign(t, n);
24918
25004
  else Object.assign(t, e);
24919
25005
  }
24920
- } else t[n] = Ux(r);
25006
+ } else t[n] = Wx(r);
24921
25007
  return t;
24922
25008
  }
24923
- function Wx(e, t) {
24924
- return e ? Ux(n.parseDocument(e, { customTags: [{
25009
+ function Gx(e, t) {
25010
+ return e ? Wx(n.parseDocument(e, { customTags: [{
24925
25011
  tag: "!include",
24926
25012
  resolve(e) {
24927
- let n = (typeof e == "string" ? e : String(e?.strValue || e?.value || "")).trim(), r = Rx(n);
25013
+ let n = (typeof e == "string" ? e : String(e?.strValue || e?.value || "")).trim(), r = zx(n);
24928
25014
  if (!r) return n;
24929
25015
  if (t && t.fieldSets) {
24930
25016
  let e = Object.keys(t.fieldSets).find((e) => e.endsWith("/" + r) || e === r);
24931
- if (e) return Wx(t.fieldSets[e], t);
25017
+ if (e) return Gx(t.fieldSets[e], t);
24932
25018
  }
24933
25019
  return n;
24934
25020
  }
24935
25021
  }] }).toJS() || {}) : {};
24936
25022
  }
24937
- function Gx(e, t = /* @__PURE__ */ new Set()) {
24938
- if (!Ix || !Lx) return {};
24939
- let r = Lx.resolve(e);
24940
- if (t.has(r) || (t.add(r), !Ix.existsSync(r))) return {};
24941
- let i = Ix.readFileSync(r, "utf-8");
24942
- return Ux(n.parseDocument(i, { customTags: [{
25023
+ function Kx(e, t = /* @__PURE__ */ new Set()) {
25024
+ if (!Lx || !Rx) return {};
25025
+ let r = Rx.resolve(e);
25026
+ if (t.has(r) || (t.add(r), !Lx.existsSync(r))) return {};
25027
+ let i = Lx.readFileSync(r, "utf-8");
25028
+ return Wx(n.parseDocument(i, { customTags: [{
24943
25029
  tag: "!include",
24944
25030
  resolve(e) {
24945
25031
  let n = (typeof e == "string" ? e : String(e?.strValue || e?.value || "")).trim();
24946
- return n ? Gx(Lx.resolve(Lx.dirname(r), n), new Set(t)) : {};
25032
+ return n ? Kx(Rx.resolve(Rx.dirname(r), n), new Set(t)) : {};
24947
25033
  }
24948
25034
  }] }).toJS() || {});
24949
25035
  }
24950
- function Kx() {
24951
- if (!Ix || !Lx || typeof process > "u" || !process?.versions?.node) return null;
25036
+ function qx() {
25037
+ if (!Lx || !Rx || typeof process > "u" || !process?.versions?.node) return null;
24952
25038
  try {
24953
25039
  let e = process.cwd(), t = "", n = [
24954
- Lx.resolve(e, "content/definitions"),
24955
- Lx.resolve(e, "content"),
24956
- Lx.resolve(e, "definitions"),
24957
- Lx.resolve(e, "kama-worker/content/definitions")
25040
+ Rx.resolve(e, "content/definitions"),
25041
+ Rx.resolve(e, "content"),
25042
+ Rx.resolve(e, "definitions"),
25043
+ Rx.resolve(e, "kama-worker/content/definitions")
24958
25044
  ];
24959
25045
  try {
24960
25046
  if (import.meta.url) {
24961
- let e = Lx.dirname(r(import.meta.url));
24962
- n.push(Lx.resolve(e, "../../content/definitions")), n.push(Lx.resolve(e, "../content/definitions"));
25047
+ let e = Rx.dirname(r(import.meta.url));
25048
+ n.push(Rx.resolve(e, "../../content/definitions")), n.push(Rx.resolve(e, "../content/definitions"));
24963
25049
  }
24964
25050
  } catch {}
24965
- for (let e of n) if (Ix.existsSync(e)) {
25051
+ for (let e of n) if (Lx.existsSync(e)) {
24966
25052
  t = e;
24967
25053
  break;
24968
25054
  }
@@ -24970,19 +25056,19 @@ function Kx() {
24970
25056
  let i = (e) => {
24971
25057
  let n = "";
24972
25058
  for (let r of e) {
24973
- let e = Lx.join(t, r);
24974
- if (Ix.existsSync(e)) {
25059
+ let e = Rx.join(t, r);
25060
+ if (Lx.existsSync(e)) {
24975
25061
  n = e;
24976
25062
  break;
24977
25063
  }
24978
25064
  }
24979
25065
  if (!n) return {};
24980
- let r = {}, i = Ix.readdirSync(n);
25066
+ let r = {}, i = Lx.readdirSync(n);
24981
25067
  for (let e of i) {
24982
25068
  if (!e.endsWith(".yaml") && !e.endsWith(".yml")) continue;
24983
- let t = Lx.join(n, e), i = Rx(e, zx(e));
25069
+ let t = Rx.join(n, e), i = zx(e, Bx(e));
24984
25070
  try {
24985
- r[i] = Gx(t);
25071
+ r[i] = Kx(t);
24986
25072
  } catch (t) {
24987
25073
  console.error(`❌ Error parsing ${e}:`, t.message);
24988
25074
  }
@@ -25011,59 +25097,59 @@ function Kx() {
25011
25097
  return console.error("❌ Exception inside readLocalFsBundle:", e), null;
25012
25098
  }
25013
25099
  }
25014
- var qx = null, Jx = null;
25015
- function Yx(e) {
25016
- if (!e) qx = null, Jx = null;
25017
- else if (qx && Jx === e) return qx;
25018
- let t = Xx(e);
25019
- return qx = t, Jx = e, t;
25020
- }
25100
+ var Jx = null, Yx = null;
25021
25101
  function Xx(e) {
25102
+ if (!e) Jx = null, Yx = null;
25103
+ else if (Jx && Yx === e) return Jx;
25104
+ let t = Zx(e);
25105
+ return Jx = t, Yx = e, t;
25106
+ }
25107
+ function Zx(e) {
25022
25108
  if (e) {
25023
25109
  let t = {
25024
25110
  nodes: {
25025
25111
  ...e.nodes || e.rawNodes || {},
25026
- ...Bx.nodes
25112
+ ...Vx.nodes
25027
25113
  },
25028
25114
  trees: {
25029
25115
  ...e.trees || e.rawTrees || {},
25030
- ...Bx.trees
25116
+ ...Vx.trees
25031
25117
  },
25032
25118
  channels: {
25033
25119
  ...e.channels || e.rawChannels || {},
25034
- ...Bx.channels
25120
+ ...Vx.channels
25035
25121
  },
25036
25122
  taxonomies: {
25037
25123
  ...e.taxonomies || e.rawTaxonomies || {},
25038
- ...Bx.taxonomies
25124
+ ...Vx.taxonomies
25039
25125
  },
25040
25126
  blocks: {
25041
25127
  ...e.blocks || e.rawBlocks || {},
25042
- ...Bx.blocks
25128
+ ...Vx.blocks
25043
25129
  },
25044
25130
  nodeLayouts: {
25045
25131
  ...e.nodeLayouts || e.rawNodeLayouts || {},
25046
- ...Bx.nodeLayouts
25132
+ ...Vx.nodeLayouts
25047
25133
  },
25048
25134
  blockLayouts: {
25049
25135
  ...e.blockLayouts || e.rawBlockLayouts || {},
25050
- ...Bx.blockLayouts
25136
+ ...Vx.blockLayouts
25051
25137
  },
25052
25138
  fieldSets: {
25053
25139
  ...e.fieldSets || e.rawFieldSets || {},
25054
- ...Bx.fieldSets
25140
+ ...Vx.fieldSets
25055
25141
  }
25056
25142
  };
25057
25143
  if (typeof Object.values(t.nodes)[0] == "string") {
25058
25144
  let e = (e) => {
25059
25145
  let n = {};
25060
25146
  for (let [r, i] of Object.entries(e || {})) {
25061
- let e = Rx(r, zx(r));
25062
- n[e] = Wx(i, t);
25147
+ let e = zx(r, Bx(r));
25148
+ n[e] = Gx(i, t);
25063
25149
  }
25064
25150
  return n;
25065
25151
  };
25066
- return Zx({
25152
+ return Qx({
25067
25153
  rawNodes: e(t.nodes),
25068
25154
  rawTrees: e(t.trees),
25069
25155
  rawChannels: e(t.channels),
@@ -25074,12 +25160,12 @@ function Xx(e) {
25074
25160
  rawFieldSets: e(t.fieldSets)
25075
25161
  });
25076
25162
  }
25077
- return Zx(t);
25163
+ return Qx(t);
25078
25164
  }
25079
- let t = Kx();
25080
- return t && Object.keys(t.rawNodes || {}).length > 0 ? Zx(t) : Zx(null);
25165
+ let t = qx();
25166
+ return t && Object.keys(t.rawNodes || {}).length > 0 ? Qx(t) : Qx(null);
25081
25167
  }
25082
- function Zx(e) {
25168
+ function Qx(e) {
25083
25169
  if (!e) return {
25084
25170
  nodes: {},
25085
25171
  trees: {},
@@ -25094,7 +25180,7 @@ function Zx(e) {
25094
25180
  channelTemplate: null,
25095
25181
  userTemplate: null
25096
25182
  };
25097
- let { rawNodes: t = {}, rawTrees: n = {}, rawChannels: r = {}, channels: i = {}, rawTaxonomies: a = {}, taxonomies: o = {}, rawBlocks: s = {}, rawElements: c = {}, rawNodeLayouts: l = {}, rawBlockLayouts: u = {}, rawLayouts: d = {}, rawFieldSets: f = {}, rawTemplates: p = {}, nodeTemplate: m = null, treeTemplate: h = null, channelTemplate: g = null, userTemplate: _ = null, nodes: v = {}, trees: y = {}, blocks: b = {}, nodeLayouts: x = {}, blockLayouts: S = {} } = e, C = Object.keys(t).length > 0 ? t : v, w = Object.keys(n).length > 0 ? n : y, T = Object.keys(r).length > 0 ? r : i, ee = Object.keys(a).length > 0 ? a : o, E = Object.keys(s).length > 0 ? s : Object.keys(c).length > 0 ? c : b, D = Object.keys(l).length > 0 ? l : Object.keys(d).length > 0 ? d : x, O = Object.keys(u).length > 0 ? u : S, te = m?.fields || {}, k = {
25183
+ let { rawNodes: t = {}, rawTrees: n = {}, rawChannels: r = {}, channels: i = {}, rawTaxonomies: a = {}, taxonomies: o = {}, rawBlocks: s = {}, rawElements: c = {}, rawNodeLayouts: l = {}, rawBlockLayouts: u = {}, rawLayouts: d = {}, rawFieldSets: f = {}, rawTemplates: p = {}, nodeTemplate: m = null, treeTemplate: h = null, channelTemplate: g = null, userTemplate: _ = null, nodes: v = {}, trees: y = {}, blocks: b = {}, nodeLayouts: x = {}, blockLayouts: S = {} } = e, C = Object.keys(t).length > 0 ? t : v, w = Object.keys(n).length > 0 ? n : y, T = Object.keys(r).length > 0 ? r : i, ee = Object.keys(a).length > 0 ? a : o, E = Object.keys(s).length > 0 ? s : Object.keys(c).length > 0 ? c : b, D = Object.keys(l).length > 0 ? l : Object.keys(d).length > 0 ? d : x, te = Object.keys(u).length > 0 ? u : S, O = m?.fields || {}, k = {
25098
25184
  ...p,
25099
25185
  ...f
25100
25186
  }, A = (e, t = "settings", n, r) => {
@@ -25111,11 +25197,11 @@ function Zx(e) {
25111
25197
  fields: {}
25112
25198
  }), Object.entries(s).forEach(([e, r]) => {
25113
25199
  let i = n[t].fields[e] || {};
25114
- n[t].fields[e] = Hx(i, r);
25200
+ n[t].fields[e] = Ux(i, r);
25115
25201
  });
25116
25202
  } else Object.entries(s).forEach(([e, t]) => {
25117
25203
  let n = i[e] || {};
25118
- i[e] = Hx(n, t);
25204
+ i[e] = Ux(n, t);
25119
25205
  });
25120
25206
  };
25121
25207
  return !Array.isArray(e) && typeof e == "object" && e ? (Object.entries(e).forEach(([e, t]) => {
@@ -25124,15 +25210,15 @@ function Zx(e) {
25124
25210
  a(String(t));
25125
25211
  return;
25126
25212
  }
25127
- let n = i[e] || te[e] || {};
25128
- i[e] = Hx(n, typeof t == "object" && t ? t : { label: String(t) });
25213
+ let n = i[e] || O[e] || {};
25214
+ i[e] = Ux(n, typeof t == "object" && t ? t : { label: String(t) });
25129
25215
  }), i) : (Array.isArray(e) && e.forEach((e) => {
25130
25216
  if (typeof e == "string") {
25131
25217
  if (e.includes("/") || e.endsWith(".yaml") || e.endsWith(".yml")) return;
25132
25218
  if (e.startsWith("fieldSet:")) a(e.replace("fieldSet:", "").trim());
25133
25219
  else {
25134
- let t = i[e] || te[e] || {};
25135
- i[e] = Hx(t, {
25220
+ let t = i[e] || O[e] || {};
25221
+ i[e] = Ux(t, {
25136
25222
  type: "text",
25137
25223
  label: e
25138
25224
  });
@@ -25140,8 +25226,8 @@ function Zx(e) {
25140
25226
  } else typeof e == "object" && e && Object.entries(e).forEach(([e, t]) => {
25141
25227
  if (e === "fieldSet") a(String(t));
25142
25228
  else if (e !== "<<" && e !== "<<:") {
25143
- let n = i[e] || te[e] || {};
25144
- i[e] = Hx(n, typeof t == "object" && t ? t : {});
25229
+ let n = i[e] || O[e] || {};
25230
+ i[e] = Ux(n, typeof t == "object" && t ? t : {});
25145
25231
  }
25146
25232
  });
25147
25233
  }), i);
@@ -25159,7 +25245,7 @@ function Zx(e) {
25159
25245
  let s = A(i.fields || i, a, n, t);
25160
25246
  Object.entries(s).forEach(([e, t]) => {
25161
25247
  let r = n[a].fields[e] || {};
25162
- n[a].fields[e] = Hx(r, t);
25248
+ n[a].fields[e] = Ux(r, t);
25163
25249
  });
25164
25250
  }
25165
25251
  }), n) : (Object.entries(e).forEach(([e, r]) => {
@@ -25175,7 +25261,7 @@ function Zx(e) {
25175
25261
  Object.entries(s).forEach(([t, r]) => {
25176
25262
  if (t === "<<" || t === "<<:" || t === "label") return;
25177
25263
  let i = n[e].fields[t] || {};
25178
- n[e].fields[t] = Hx(i, r);
25264
+ n[e].fields[t] = Ux(i, r);
25179
25265
  });
25180
25266
  }), n);
25181
25267
  }, j = {};
@@ -25193,16 +25279,16 @@ function Zx(e) {
25193
25279
  fields: {}
25194
25280
  }), Object.entries(o).forEach(([e, r]) => {
25195
25281
  let i = n[t].fields[e] || {};
25196
- n[t].fields[e] = Hx(i, r);
25282
+ n[t].fields[e] = Ux(i, r);
25197
25283
  });
25198
25284
  } else Object.entries(o).forEach(([e, t]) => {
25199
- let n = r[e] || te[e] || {};
25200
- r[e] = Hx(n, t);
25285
+ let n = r[e] || O[e] || {};
25286
+ r[e] = Ux(n, t);
25201
25287
  });
25202
25288
  }), Object.values(n).forEach((e) => {
25203
25289
  Object.entries(e.fields).forEach(([e, t]) => {
25204
25290
  let n = r[e] || {};
25205
- r[e] = Hx(n, t);
25291
+ r[e] = Ux(n, t);
25206
25292
  });
25207
25293
  }), Object.keys(n).length === 0 && Object.keys(r).length > 0 && (n.settings = {
25208
25294
  label: t.label || "Settings",
@@ -25215,8 +25301,8 @@ function Zx(e) {
25215
25301
  inVault: t.inVault !== !1,
25216
25302
  hasCanvas: t.hasCanvas === !0,
25217
25303
  defaultLayout: t.defaultLayout,
25218
- allowedBlocks: Vx(t.allowedBlocks),
25219
- disallowedBlocks: t.disallowedBlocks ? Vx(t.disallowedBlocks) : void 0,
25304
+ allowedBlocks: Hx(t.allowedBlocks),
25305
+ disallowedBlocks: t.disallowedBlocks ? Hx(t.disallowedBlocks) : void 0,
25220
25306
  tabs: n,
25221
25307
  fields: r
25222
25308
  };
@@ -25227,11 +25313,11 @@ function Zx(e) {
25227
25313
  Array.isArray(t.fieldSets) && t.fieldSets.forEach((e) => {
25228
25314
  let t = k[e] || {}, i = t.fields || t, a = A(i, "settings", n);
25229
25315
  Object.entries(a).forEach(([e, t]) => {
25230
- r[e] = Hx(r[e] || {}, t);
25316
+ r[e] = Ux(r[e] || {}, t);
25231
25317
  });
25232
25318
  }), Object.values(n).forEach((e) => {
25233
25319
  Object.entries(e.fields).forEach(([e, t]) => {
25234
- r[e] = Hx(r[e] || {}, t);
25320
+ r[e] = Ux(r[e] || {}, t);
25235
25321
  });
25236
25322
  }), re[e] = {
25237
25323
  ...t,
@@ -25247,11 +25333,11 @@ function Zx(e) {
25247
25333
  Array.isArray(t.fieldSets) && t.fieldSets.forEach((e) => {
25248
25334
  let t = k[e] || {}, n = t.fields || t, i = A(n);
25249
25335
  Object.entries(i).forEach(([e, t]) => {
25250
- r[e] = Hx(r[e] || {}, t);
25336
+ r[e] = Ux(r[e] || {}, t);
25251
25337
  });
25252
25338
  }), Object.values(n).forEach((e) => {
25253
25339
  Object.entries(e.fields).forEach(([e, t]) => {
25254
- r[e] = Hx(r[e] || {}, t);
25340
+ r[e] = Ux(r[e] || {}, t);
25255
25341
  });
25256
25342
  }), ie[e] = {
25257
25343
  ...t,
@@ -25268,11 +25354,11 @@ function Zx(e) {
25268
25354
  Array.isArray(t.fieldSets) && t.fieldSets.forEach((e) => {
25269
25355
  let t = k[e] || {}, i = t.fields || t, a = A(i, "settings", n);
25270
25356
  Object.entries(a).forEach(([e, t]) => {
25271
- r[e] = Hx(r[e] || {}, t);
25357
+ r[e] = Ux(r[e] || {}, t);
25272
25358
  });
25273
25359
  }), Object.values(n).forEach((e) => {
25274
25360
  Object.entries(e.fields).forEach(([e, t]) => {
25275
- r[e] = Hx(r[e] || {}, t);
25361
+ r[e] = Ux(r[e] || {}, t);
25276
25362
  });
25277
25363
  }), ae[e] = {
25278
25364
  ...t,
@@ -25289,7 +25375,7 @@ function Zx(e) {
25289
25375
  Array.isArray(t.fieldSets) && t.fieldSets.forEach((e) => {
25290
25376
  let t = k[e] || {}, r = t.fields || t, i = A(r);
25291
25377
  Object.entries(i).forEach(([e, t]) => {
25292
- n[e] = Hx(n[e] || {}, t);
25378
+ n[e] = Ux(n[e] || {}, t);
25293
25379
  });
25294
25380
  }), oe[e] = {
25295
25381
  ...t,
@@ -25306,8 +25392,8 @@ function Zx(e) {
25306
25392
  i[e] = {
25307
25393
  ...t,
25308
25394
  label: t.label || e,
25309
- allowedBlocks: Vx(t.allowedBlocks),
25310
- disallowedBlocks: t.disallowedBlocks ? Vx(t.disallowedBlocks) : void 0
25395
+ allowedBlocks: Hx(t.allowedBlocks),
25396
+ disallowedBlocks: t.disallowedBlocks ? Hx(t.disallowedBlocks) : void 0
25311
25397
  };
25312
25398
  }), se[e] = {
25313
25399
  ...t,
@@ -25323,14 +25409,14 @@ function Zx(e) {
25323
25409
  };
25324
25410
  });
25325
25411
  let ce = {};
25326
- Object.entries(O).forEach(([e, t]) => {
25412
+ Object.entries(te).forEach(([e, t]) => {
25327
25413
  let n = ne(t.tabs), r = A(t.fields || [], "settings", n), i = {}, a = t.regions || { main: { label: "Main Content" } };
25328
25414
  Object.entries(a).forEach(([e, t]) => {
25329
25415
  i[e] = {
25330
25416
  ...t,
25331
25417
  label: t.label || e,
25332
- allowedBlocks: Vx(t.allowedBlocks),
25333
- disallowedBlocks: t.disallowedBlocks ? Vx(t.disallowedBlocks) : void 0
25418
+ allowedBlocks: Hx(t.allowedBlocks),
25419
+ disallowedBlocks: t.disallowedBlocks ? Hx(t.disallowedBlocks) : void 0
25334
25420
  };
25335
25421
  }), ce[e] = {
25336
25422
  ...t,
@@ -25349,7 +25435,7 @@ function Zx(e) {
25349
25435
  Array.isArray(g?.fieldSets) && g?.fieldSets.forEach((e) => {
25350
25436
  let t = k[e] || {}, n = t.fields || t, r = A(n);
25351
25437
  Object.entries(r).forEach(([e, t]) => {
25352
- le[e] = Hx(le[e] || {}, t);
25438
+ le[e] = Ux(le[e] || {}, t);
25353
25439
  });
25354
25440
  });
25355
25441
  let ue = g ? {
@@ -25359,7 +25445,7 @@ function Zx(e) {
25359
25445
  Array.isArray(_?.fieldSets) && _?.fieldSets.forEach((e) => {
25360
25446
  let t = k[e] || {}, n = t.fields || t, r = A(n);
25361
25447
  Object.entries(r).forEach(([e, t]) => {
25362
- de[e] = Hx(de[e] || {}, t);
25448
+ de[e] = Ux(de[e] || {}, t);
25363
25449
  });
25364
25450
  });
25365
25451
  let fe = _ ? {
@@ -25381,11 +25467,11 @@ function Zx(e) {
25381
25467
  userTemplate: fe
25382
25468
  };
25383
25469
  }
25384
- var Qx = new e(), $x = (e) => {
25470
+ var $x = new e(), eS = (e) => {
25385
25471
  try {
25386
25472
  let t = e.env?.BUNDLED_DEFINITIONS;
25387
25473
  (!t || Object.keys(t).length === 0) && (t = Db || Eb || Tb);
25388
- let n = Yx(t);
25474
+ let n = Xx(t);
25389
25475
  return e.json(n, 200, { "Cache-Control": "no-cache, no-store, must-revalidate" });
25390
25476
  } catch (t) {
25391
25477
  return console.error("[CMS API] Error loading schemas:", t), e.json({
@@ -25394,8 +25480,8 @@ var Qx = new e(), $x = (e) => {
25394
25480
  }, 500);
25395
25481
  }
25396
25482
  };
25397
- Qx.get("/", $x), Qx.get("/schemas.json", $x);
25398
- var eS = new e(), tS = {
25483
+ $x.get("/", eS), $x.get("/schemas.json", eS);
25484
+ var tS = new e(), nS = {
25399
25485
  node: "content_nodes",
25400
25486
  nodes: "content_nodes",
25401
25487
  content_node: "content_nodes",
@@ -25407,7 +25493,7 @@ var eS = new e(), tS = {
25407
25493
  user: "users",
25408
25494
  users: "users",
25409
25495
  user_account: "user_accounts"
25410
- }, nS = {
25496
+ }, rS = {
25411
25497
  content_nodes: [
25412
25498
  "id",
25413
25499
  "title",
@@ -25464,11 +25550,11 @@ var eS = new e(), tS = {
25464
25550
  "createdAt"
25465
25551
  ]
25466
25552
  };
25467
- eS.post("/validate-unique", async (e) => {
25553
+ tS.post("/validate-unique", async (e) => {
25468
25554
  try {
25469
25555
  let t = e.get("db"), { entityType: n, field: r, value: i, excludeId: a } = await e.req.json();
25470
25556
  if (!r || i == null || String(i).trim() === "") return e.json({ isUnique: !0 });
25471
- let o = tS[n] || "content_nodes", s = r.replace(/[^a-zA-Z0-9_]/g, ""), c = (nS[o] || nS.content_nodes).includes(s), l = -1;
25557
+ let o = nS[n] || "content_nodes", s = r.replace(/[^a-zA-Z0-9_]/g, ""), c = (rS[o] || rS.content_nodes).includes(s), l = -1;
25472
25558
  if (a != null && String(a).trim() !== "") {
25473
25559
  let e = Number(a);
25474
25560
  l = isNaN(e) ? String(a) : e;
@@ -25480,14 +25566,14 @@ eS.post("/validate-unique", async (e) => {
25480
25566
  } catch (t) {
25481
25567
  return console.error("[API Validation] Error validating global uniqueness:", t), e.json({ error: "Failed to validate uniqueness" }, 500);
25482
25568
  }
25483
- }), eS.post("/validate-unique-sibling", async (e) => e.json({ isUnique: !0 }));
25484
- var rS = new e();
25485
- rS.get("/", async (e) => {
25569
+ }), tS.post("/validate-unique-sibling", async (e) => e.json({ isUnique: !0 }));
25570
+ var iS = new e();
25571
+ iS.get("/", async (e) => {
25486
25572
  try {
25487
- let t = e.get("db"), n = await t.prepare("\n SELECT \n COUNT(*) as total,\n SUM(CASE WHEN isHidden = 0 THEN 1 ELSE 0 END) as published,\n SUM(CASE WHEN isHidden = 1 THEN 1 ELSE 0 END) as hidden\n FROM content_nodes\n WHERE deletedAt IS NULL OR deletedAt = ''\n ").get(), r = Number(n?.total) || 0, i = Number(n?.published) || 0, a = Number(n?.hidden) || 0, o = await t.prepare("\n SELECT \n (SELECT COUNT(*) FROM channels) as totalChannels,\n (SELECT COUNT(*) FROM trees) as totalTrees,\n (SELECT COUNT(*) FROM users) as totalUsers\n ").get(), s = await t.prepare("\n SELECT contentType as type, COUNT(*) as count \n FROM content_nodes \n WHERE deletedAt IS NULL OR deletedAt = ''\n GROUP BY contentType \n ORDER BY count DESC\n ").all(), c = Array.isArray(s) ? s : s?.results || [], l = await t.prepare("\n SELECT id, title, slug, contentType, isHidden, status, updatedAt \n FROM content_nodes \n WHERE deletedAt IS NULL OR deletedAt = ''\n ORDER BY updatedAt DESC \n LIMIT 5\n ").all(), u = (Array.isArray(l) ? l : l?.results || []).map((e) => ({
25573
+ let t = e.get("db"), n = await t.prepare("\n SELECT \n COUNT(*) as total,\n SUM(CASE WHEN isHidden = 0 THEN 1 ELSE 0 END) as published,\n SUM(CASE WHEN isHidden = 1 THEN 1 ELSE 0 END) as hidden\n FROM content_nodes\n WHERE deletedAt IS NULL\n ").get(), r = Number(n?.total) || 0, i = Number(n?.published) || 0, a = Number(n?.hidden) || 0, o = await t.prepare("\n SELECT \n (SELECT COUNT(*) FROM channels) as totalChannels,\n (SELECT COUNT(*) FROM trees) as totalTrees,\n (SELECT COUNT(*) FROM users) as totalUsers\n ").get(), s = await t.prepare("\n SELECT contentType as type, COUNT(*) as count \n FROM content_nodes \n WHERE deletedAt IS NULL\n GROUP BY contentType \n ORDER BY count DESC\n ").all(), c = Array.isArray(s) ? s : s?.results || [], l = await t.prepare("\n SELECT id, title, slug, contentType, isHidden, status, updatedAt \n FROM content_nodes \n WHERE deletedAt IS NULL\n ORDER BY updatedAt DESC \n LIMIT 5\n ").all(), u = (Array.isArray(l) ? l : l?.results || []).map((e) => ({
25488
25574
  ...e,
25489
25575
  isHidden: !!e.isHidden
25490
- })), d = await t.prepare("\n SELECT \n cn.id, \n cn.title, \n cn.slug, \n cn.contentType, \n cn.isHidden, \n cn.status, \n cn.publishedAt,\n cn.hasUnpublishedChanges,\n cn.updatedAt,\n GROUP_CONCAT(DISTINCT ch.label) as channelLabels,\n GROUP_CONCAT(DISTINCT t.label) as treeLabels\n FROM content_nodes cn\n LEFT JOIN node_channels nc ON cn.id = nc.nodeId\n LEFT JOIN channels ch ON nc.channelId = ch.id\n LEFT JOIN tree_nodes tn ON cn.id = tn.contentId\n LEFT JOIN trees t ON tn.treeId = t.id\n WHERE (cn.deletedAt IS NULL OR cn.deletedAt = '')\n AND (cn.status = 'draft' OR cn.hasUnpublishedChanges = 1)\n GROUP BY cn.id\n ORDER BY cn.updatedAt DESC\n ").all(), f = (Array.isArray(d) ? d : d?.results || []).map((e) => ({
25576
+ })), d = await t.prepare("\n WITH pending_drafts AS (\n SELECT id, title, slug, contentType, isHidden, status, publishedAt, hasUnpublishedChanges, updatedAt\n FROM content_nodes\n WHERE deletedAt IS NULL\n AND (status = 'draft' OR hasUnpublishedChanges = 1)\n ORDER BY updatedAt DESC\n LIMIT 100\n )\n SELECT \n pd.*,\n GROUP_CONCAT(DISTINCT ch.label) as channelLabels,\n GROUP_CONCAT(DISTINCT t.label) as treeLabels\n FROM pending_drafts pd\n LEFT JOIN node_channels nc ON pd.id = nc.nodeId\n LEFT JOIN channels ch ON nc.channelId = ch.id\n LEFT JOIN tree_nodes tn ON pd.id = tn.contentId\n LEFT JOIN trees t ON tn.treeId = t.id\n GROUP BY pd.id\n ORDER BY pd.updatedAt DESC\n ").all(), f = (Array.isArray(d) ? d : d?.results || []).map((e) => ({
25491
25577
  id: e.id,
25492
25578
  title: e.title,
25493
25579
  slug: e.slug,
@@ -25525,8 +25611,8 @@ rS.get("/", async (e) => {
25525
25611
  }, 500);
25526
25612
  }
25527
25613
  });
25528
- var iS = new e();
25529
- async function aS(e, t, n = []) {
25614
+ var aS = new e();
25615
+ async function oS(e, t, n = []) {
25530
25616
  let r = e.prepare(t);
25531
25617
  if (typeof r.bind == "function") {
25532
25618
  let e = await r.bind(...n).all();
@@ -25538,16 +25624,16 @@ async function aS(e, t, n = []) {
25538
25624
  }
25539
25625
  return [];
25540
25626
  }
25541
- async function oS(e, t, n = []) {
25627
+ async function sS(e, t, n = []) {
25542
25628
  let r = e.prepare(t);
25543
25629
  if (typeof r.bind == "function") return await r.bind(...n).run();
25544
25630
  if (typeof r.run == "function") return await r.run(...n);
25545
25631
  }
25546
- function sS(e, t, n) {
25632
+ function cS(e, t, n) {
25547
25633
  let r = e || (t ? `/media/${t}` : "");
25548
25634
  return r && n && r.startsWith(`https://${n}/`) && !r.includes("/media/") && (r = r.replace(`https://${n}/`, `https://${n}/media/`)), r;
25549
25635
  }
25550
- iS.get("/", async (e) => {
25636
+ aS.get("/", async (e) => {
25551
25637
  try {
25552
25638
  let t = wb(e), { search: n = "", type: r = "all", page: i = "1", limit: a = "24", sort: o = "createdAt", order: s = "DESC", nodeId: c, channelId: l, trashed: u } = e.req.query(), d = Math.max(1, parseInt(i, 10) || 1), f = Math.max(1, Math.min(100, parseInt(a, 10) || 24)), p = (d - 1) * f, m = {
25553
25639
  createdAt: "a.createdAt",
@@ -25557,7 +25643,7 @@ iS.get("/", async (e) => {
25557
25643
  sizeBytes: "a.sizeBytes"
25558
25644
  }[o] || "a.createdAt", h = s.toUpperCase() === "ASC" ? "ASC" : "DESC", g = [], _ = ["(a.isSystemVariant = 0 OR a.isSystemVariant IS NULL)", u === "true" || u === "1" ? "(a.deletedAt IS NOT NULL AND a.deletedAt != '')" : "(a.deletedAt IS NULL OR a.deletedAt = '')"];
25559
25645
  if (c) {
25560
- let e = await aS(t, "SELECT a.id, a.filename, a.isSystemVariant FROM node_assets na JOIN assets a ON na.assetId = a.id WHERE na.nodeId = ?", [Number(c)]);
25646
+ let e = await oS(t, "SELECT a.id, a.filename, a.isSystemVariant FROM node_assets na JOIN assets a ON na.assetId = a.id WHERE na.nodeId = ?", [Number(c)]);
25561
25647
  if (e.length === 0) _.push("1 = 0");
25562
25648
  else {
25563
25649
  let t = e.map((e) => e.isSystemVariant ? `(a.id = '${e.id}' OR a.id IN (SELECT parentAssetId FROM assets WHERE id = '${e.id}'))` : `a.id = '${e.id}'`).join(" OR ");
@@ -25571,10 +25657,10 @@ iS.get("/", async (e) => {
25571
25657
  n && n.trim() !== "" && (_.push("a.filename LIKE ?"), g.push(`%${n.trim()}%`)), r && r !== "all" && (r === "image" ? (_.push("a.mimeType LIKE ?"), g.push("image/%")) : r === "document" ? (_.push("(a.mimeType LIKE ? OR a.mimeType LIKE ? OR a.mimeType LIKE ?)"), g.push("application/pdf%", "application/msword%", "application/vnd%")) : r === "video" && (_.push("(a.mimeType LIKE ? OR a.mimeType LIKE ?)"), g.push("video/%", "audio/%")));
25572
25658
  let v = `SELECT a.id, a.filename, a.mimeType, a.sizeBytes, a.cdnUrl, a.storageKeyPrivate, a.createdAt, a.updatedAt, a.deletedAt, a.dataJson FROM assets a ${` WHERE ${_.join(" AND ")}`} ORDER BY ${m} ${h} LIMIT ? OFFSET ?`;
25573
25659
  g.push(f, p);
25574
- let y = await aS(t, v, g), b = y.map((e) => e.id), x = /* @__PURE__ */ new Map(), S = /* @__PURE__ */ new Map();
25660
+ let y = await oS(t, v, g), b = y.map((e) => e.id), x = /* @__PURE__ */ new Map(), S = /* @__PURE__ */ new Map();
25575
25661
  if (b.length > 0) {
25576
25662
  let e = b.map(() => "?").join(",");
25577
- (await aS(t, `
25663
+ (await oS(t, `
25578
25664
  SELECT master.id AS assetId, COUNT(DISTINCT na.nodeId) AS count
25579
25665
  FROM assets master
25580
25666
  INNER JOIN node_assets na ON (
@@ -25582,7 +25668,7 @@ iS.get("/", async (e) => {
25582
25668
  EXISTS (SELECT 1 FROM assets crop WHERE crop.id = na.assetId AND crop.isSystemVariant = 1 AND crop.parentAssetId = master.id)
25583
25669
  )
25584
25670
  WHERE master.id IN (${e})
25585
- GROUP BY master.id`, b)).forEach((e) => x.set(String(e.assetId), e.count || 0)), (await aS(t, `
25671
+ GROUP BY master.id`, b)).forEach((e) => x.set(String(e.assetId), e.count || 0)), (await oS(t, `
25586
25672
  SELECT parentAssetId, COUNT(id) AS count
25587
25673
  FROM assets
25588
25674
  WHERE isSystemVariant = 1 AND parentAssetId IN (${e})
@@ -25600,7 +25686,7 @@ iS.get("/", async (e) => {
25600
25686
  ...JSON.parse(t.dataJson || "{}")
25601
25687
  };
25602
25688
  } catch {}
25603
- let r = sS(t.cdnUrl, t.storageKeyPrivate, e.env?.CDN_DOMAIN);
25689
+ let r = cS(t.cdnUrl, t.storageKeyPrivate, e.env?.CDN_DOMAIN);
25604
25690
  return {
25605
25691
  id: t.id,
25606
25692
  filename: t.filename || "Untitled Asset",
@@ -25625,7 +25711,7 @@ iS.get("/", async (e) => {
25625
25711
  details: t.message || String(t)
25626
25712
  }, 500);
25627
25713
  }
25628
- }), iS.post("/upload", async (e) => {
25714
+ }), aS.post("/upload", async (e) => {
25629
25715
  try {
25630
25716
  let t = wb(e), { storage: n } = ix(e.env), r = await e.req.parseBody(), i = r.file, a = r.isVariant === "true" || r.isVariant === "1" || r.temporary === "true", o = r.replaceAssetId, s = typeof o == "string" && o.trim().length > 0 ? o.trim() : null, c = r.parentAssetId || r.parentAsset, l = typeof c == "string" && c.trim().length > 0 ? c.trim() : null;
25631
25717
  if (!i || !(i instanceof File)) return e.json({ error: "No file uploaded" }, 400);
@@ -25641,13 +25727,13 @@ iS.get("/", async (e) => {
25641
25727
  let p = crypto.randomUUID().replace(/-/g, "").slice(0, 12), m = (/* @__PURE__ */ new Date()).toISOString().slice(0, 7).replace("-", "/"), h = a || i.name.startsWith("crop_"), g = h ? `kama/cache/${m}/${p}` : `kama/uploads/${m}/${p}`, _ = await n.upload(i, g), v = typeof _ == "string" ? _ : _?.key || _?.storageKeyPrivate || _?.storageKey || `${g}/${p}_${i.name}`;
25642
25728
  if (!v) throw Error("Storage provider failed to return a valid storage key");
25643
25729
  let y = e.env.CDN_DOMAIN, b = v.replace(/^\//, ""), x = y ? `https://${y}/media/${b}` : `/media/${b}`, S = i.type || "application/octet-stream", C = i.size || 0, w = e.get("userId"), T = typeof w == "string" && w.trim().length > 0 ? w : null;
25644
- T && (await aS(t, "SELECT id FROM users WHERE id = ?", [T])).length === 0 && (T = null);
25730
+ T && (await oS(t, "SELECT id FROM users WHERE id = ?", [T])).length === 0 && (T = null);
25645
25731
  let ee = new mx(e.env);
25646
25732
  if (s) {
25647
- let r = await aS(t, "SELECT storageKeyPrivate, isSystemVariant, parentAssetId FROM assets WHERE id = ?", [s]);
25733
+ let r = await oS(t, "SELECT storageKeyPrivate, isSystemVariant, parentAssetId FROM assets WHERE id = ?", [s]);
25648
25734
  if (r.length > 0) {
25649
25735
  let a = r[0];
25650
- if (await oS(t, "UPDATE assets SET filename = ?, mimeType = ?, sizeBytes = ?, storageKeyPrivate = ?, cdnUrl = ?, updatedAt = CURRENT_TIMESTAMP WHERE id = ?", [
25736
+ if (await sS(t, "UPDATE assets SET filename = ?, mimeType = ?, sizeBytes = ?, storageKeyPrivate = ?, cdnUrl = ?, updatedAt = CURRENT_TIMESTAMP WHERE id = ?", [
25651
25737
  i.name,
25652
25738
  S,
25653
25739
  C,
@@ -25676,7 +25762,7 @@ iS.get("/", async (e) => {
25676
25762
  }
25677
25763
  }
25678
25764
  let E = `ast_${p}`, D = +!!h;
25679
- await oS(t, "INSERT INTO assets (id, filename, mimeType, sizeBytes, storageKeyPrivate, cdnUrl, createdById, isSystemVariant, parentAssetId, cropCoordinatesJson) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", [
25765
+ await sS(t, "INSERT INTO assets (id, filename, mimeType, sizeBytes, storageKeyPrivate, cdnUrl, createdById, isSystemVariant, parentAssetId, cropCoordinatesJson) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?)", [
25680
25766
  E,
25681
25767
  i.name,
25682
25768
  S,
@@ -25688,15 +25774,15 @@ iS.get("/", async (e) => {
25688
25774
  l,
25689
25775
  d
25690
25776
  ]);
25691
- let O = x;
25777
+ let te = x;
25692
25778
  if (l) {
25693
- let n = await aS(t, "SELECT cdnUrl, storageKeyPrivate FROM assets WHERE id = ?", [l]);
25694
- n.length > 0 && (O = sS(n[0].cdnUrl, n[0].storageKeyPrivate, y)), ee.purgeAsset(e, t, l);
25779
+ let n = await oS(t, "SELECT cdnUrl, storageKeyPrivate FROM assets WHERE id = ?", [l]);
25780
+ n.length > 0 && (te = cS(n[0].cdnUrl, n[0].storageKeyPrivate, y)), ee.purgeAsset(e, t, l);
25695
25781
  }
25696
25782
  return e.json({
25697
25783
  id: E,
25698
25784
  url: x,
25699
- originalUrl: O,
25785
+ originalUrl: te,
25700
25786
  parentAssetId: l,
25701
25787
  cropCoordinates: f,
25702
25788
  filename: i.name,
@@ -25710,11 +25796,11 @@ iS.get("/", async (e) => {
25710
25796
  details: t.message || String(t)
25711
25797
  }, 500);
25712
25798
  }
25713
- }), iS.get("/:id/details", async (e) => {
25799
+ }), aS.get("/:id/details", async (e) => {
25714
25800
  try {
25715
- let t = wb(e), n = e.req.param("id"), r = await aS(t, "SELECT * FROM assets WHERE id = ?", [n]);
25801
+ let t = wb(e), n = e.req.param("id"), r = await oS(t, "SELECT * FROM assets WHERE id = ?", [n]);
25716
25802
  if (!r || r.length === 0) return e.json({ error: "Asset not found" }, 404);
25717
- let i = r[0], a = await aS(t, "\n SELECT DISTINCT cn.id, cn.title, cn.contentType, cn.slug, na.fieldKey, na.assetId \n FROM node_assets na \n INNER JOIN content_nodes cn ON na.nodeId = cn.id \n LEFT JOIN assets crop ON na.assetId = crop.id \n WHERE na.assetId = ? OR (crop.isSystemVariant = 1 AND crop.parentAssetId = ?)\n ", [n, n]), o = await aS(t, "\n SELECT id, filename, mimeType, sizeBytes, cdnUrl, storageKeyPrivate, parentAssetId, cropCoordinatesJson, createdAt, updatedAt \n FROM assets \n WHERE isSystemVariant = 1 AND parentAssetId = ? \n ORDER BY createdAt DESC\n ", [n]), s = {
25803
+ let i = r[0], a = await oS(t, "\n SELECT DISTINCT cn.id, cn.title, cn.contentType, cn.slug, na.fieldKey, na.assetId \n FROM node_assets na \n INNER JOIN content_nodes cn ON na.nodeId = cn.id \n LEFT JOIN assets crop ON na.assetId = crop.id \n WHERE na.assetId = ? OR (crop.isSystemVariant = 1 AND crop.parentAssetId = ?)\n ", [n, n]), o = await oS(t, "\n SELECT id, filename, mimeType, sizeBytes, cdnUrl, storageKeyPrivate, parentAssetId, cropCoordinatesJson, createdAt, updatedAt \n FROM assets \n WHERE isSystemVariant = 1 AND parentAssetId = ? \n ORDER BY createdAt DESC\n ", [n]), s = {
25718
25804
  title: "",
25719
25805
  alt: "",
25720
25806
  description: ""
@@ -25725,7 +25811,7 @@ iS.get("/", async (e) => {
25725
25811
  ...JSON.parse(i.dataJson || "{}")
25726
25812
  };
25727
25813
  } catch {}
25728
- let c = i.updatedAt ? new Date(i.updatedAt).getTime() : Date.now(), l = `${sS(i.cdnUrl, i.storageKeyPrivate, e.env?.CDN_DOMAIN)}?v=${c}`;
25814
+ let c = i.updatedAt ? new Date(i.updatedAt).getTime() : Date.now(), l = `${cS(i.cdnUrl, i.storageKeyPrivate, e.env?.CDN_DOMAIN)}?v=${c}`;
25729
25815
  return e.json({
25730
25816
  id: i.id,
25731
25817
  filename: i.filename,
@@ -25744,7 +25830,7 @@ iS.get("/", async (e) => {
25744
25830
  if (t.cropCoordinatesJson) try {
25745
25831
  n = JSON.parse(t.cropCoordinatesJson);
25746
25832
  } catch {}
25747
- let r = t.updatedAt ? new Date(t.updatedAt).getTime() : c, a = sS(t.cdnUrl, t.storageKeyPrivate, e.env?.CDN_DOMAIN);
25833
+ let r = t.updatedAt ? new Date(t.updatedAt).getTime() : c, a = cS(t.cdnUrl, t.storageKeyPrivate, e.env?.CDN_DOMAIN);
25748
25834
  return {
25749
25835
  id: t.id,
25750
25836
  filename: t.filename,
@@ -25761,15 +25847,15 @@ iS.get("/", async (e) => {
25761
25847
  } catch {
25762
25848
  return e.json({ error: "Failed to load details" }, 500);
25763
25849
  }
25764
- }), iS.put("/:id", async (e) => {
25850
+ }), aS.put("/:id", async (e) => {
25765
25851
  try {
25766
- let t = wb(e), n = e.req.param("id"), r = await e.req.json(), i = await aS(t, "SELECT filename, dataJson FROM assets WHERE id = ?", [n]);
25852
+ let t = wb(e), n = e.req.param("id"), r = await e.req.json(), i = await oS(t, "SELECT filename, dataJson FROM assets WHERE id = ?", [n]);
25767
25853
  if (!i || i.length === 0) return e.json({ error: "Asset not found" }, 404);
25768
25854
  let a = i[0], o = {};
25769
25855
  try {
25770
25856
  o = JSON.parse(a.dataJson || "{}");
25771
25857
  } catch {}
25772
- return r.title !== void 0 && (o.title = r.title), r.alt !== void 0 && (o.alt = r.alt), r.description !== void 0 && (o.description = r.description), await oS(t, "UPDATE assets SET filename = ?, dataJson = ?, updatedAt = CURRENT_TIMESTAMP WHERE id = ?", [
25858
+ return r.title !== void 0 && (o.title = r.title), r.alt !== void 0 && (o.alt = r.alt), r.description !== void 0 && (o.description = r.description), await sS(t, "UPDATE assets SET filename = ?, dataJson = ?, updatedAt = CURRENT_TIMESTAMP WHERE id = ?", [
25773
25859
  r.filename === void 0 ? a.filename : r.filename,
25774
25860
  JSON.stringify(o),
25775
25861
  n
@@ -25777,10 +25863,10 @@ iS.get("/", async (e) => {
25777
25863
  } catch {
25778
25864
  return e.json({ error: "Failed to update asset" }, 500);
25779
25865
  }
25780
- }), iS.delete("/:id", async (e) => {
25866
+ }), aS.delete("/:id", async (e) => {
25781
25867
  try {
25782
- let t = wb(e), n = e.req.param("id"), r = (await aS(t, "SELECT id, filename, isSystemVariant FROM assets WHERE id = ?", [n]))[0];
25783
- return r ? (new mx(e.env).purgeAsset(e, t, n), r.isSystemVariant ? await oS(t, "UPDATE assets SET deletedAt = CURRENT_TIMESTAMP WHERE id = ?", [n]) : await oS(t, "UPDATE assets SET deletedAt = CURRENT_TIMESTAMP WHERE id = ? OR (isSystemVariant = 1 AND parentAssetId = ?)", [n, n]), e.json({
25868
+ let t = wb(e), n = e.req.param("id"), r = (await oS(t, "SELECT id, filename, isSystemVariant FROM assets WHERE id = ?", [n]))[0];
25869
+ return r ? (new mx(e.env).purgeAsset(e, t, n), r.isSystemVariant ? await sS(t, "UPDATE assets SET deletedAt = CURRENT_TIMESTAMP WHERE id = ?", [n]) : await sS(t, "UPDATE assets SET deletedAt = CURRENT_TIMESTAMP WHERE id = ? OR (isSystemVariant = 1 AND parentAssetId = ?)", [n, n]), e.json({
25784
25870
  success: !0,
25785
25871
  id: n,
25786
25872
  trashed: !0
@@ -25791,10 +25877,10 @@ iS.get("/", async (e) => {
25791
25877
  details: t.message || String(t)
25792
25878
  }, 500);
25793
25879
  }
25794
- }), iS.post("/restore", async (e) => {
25880
+ }), aS.post("/restore", async (e) => {
25795
25881
  try {
25796
25882
  let t = wb(e), n = await e.req.json(), r = n.id || n.assetId;
25797
- return r ? (await aS(t, "SELECT id, filename FROM assets WHERE id = ?", [r]))[0] ? (await oS(t, "UPDATE assets SET deletedAt = NULL WHERE id = ? OR (isSystemVariant = 1 AND parentAssetId = ?)", [r, r]), new mx(e.env).purgeAsset(e, t, r), e.json({
25883
+ return r ? (await oS(t, "SELECT id, filename FROM assets WHERE id = ?", [r]))[0] ? (await sS(t, "UPDATE assets SET deletedAt = NULL WHERE id = ? OR (isSystemVariant = 1 AND parentAssetId = ?)", [r, r]), new mx(e.env).purgeAsset(e, t, r), e.json({
25798
25884
  success: !0,
25799
25885
  id: r,
25800
25886
  restored: !0
@@ -25805,13 +25891,13 @@ iS.get("/", async (e) => {
25805
25891
  details: t.message
25806
25892
  }, 500);
25807
25893
  }
25808
- }), iS.delete("/purge/:id", async (e) => {
25894
+ }), aS.delete("/purge/:id", async (e) => {
25809
25895
  try {
25810
- let t = wb(e), { storage: n } = ix(e.env), r = e.req.param("id"), i = (await aS(t, "SELECT id, filename, storageKeyPrivate, isSystemVariant FROM assets WHERE id = ?", [r]))[0];
25896
+ let t = wb(e), { storage: n } = ix(e.env), r = e.req.param("id"), i = (await oS(t, "SELECT id, filename, storageKeyPrivate, isSystemVariant FROM assets WHERE id = ?", [r]))[0];
25811
25897
  if (!i) return e.json({ error: "Asset not found" }, 404);
25812
25898
  new mx(e.env).purgeAsset(e, t, r);
25813
25899
  let a = [i];
25814
- i.isSystemVariant || (a = [i, ...await aS(t, "SELECT id, storageKeyPrivate FROM assets WHERE isSystemVariant = 1 AND parentAssetId = ?", [r])]);
25900
+ i.isSystemVariant || (a = [i, ...await oS(t, "SELECT id, storageKeyPrivate FROM assets WHERE isSystemVariant = 1 AND parentAssetId = ?", [r])]);
25815
25901
  let o = a.map((e) => e.id);
25816
25902
  if (typeof n.delete == "function") {
25817
25903
  for (let e of a) if (e.storageKeyPrivate) try {
@@ -25821,7 +25907,7 @@ iS.get("/", async (e) => {
25821
25907
  }
25822
25908
  }
25823
25909
  let s = o.map(() => "?").join(",");
25824
- return await oS(t, `DELETE FROM node_assets WHERE assetId IN (${s})`, o), await oS(t, `DELETE FROM assets WHERE id IN (${s})`, o), e.json({
25910
+ return await sS(t, `DELETE FROM node_assets WHERE assetId IN (${s})`, o), await sS(t, `DELETE FROM assets WHERE id IN (${s})`, o), e.json({
25825
25911
  success: !0,
25826
25912
  id: r,
25827
25913
  purged: !0,
@@ -25835,8 +25921,8 @@ iS.get("/", async (e) => {
25835
25921
  }, 500);
25836
25922
  }
25837
25923
  });
25838
- var cS = new $y();
25839
- function lS() {
25924
+ var lS = new $y();
25925
+ function uS() {
25840
25926
  return {
25841
25927
  fullPath: /* @__PURE__ */ new Map(),
25842
25928
  treeEdges: /* @__PURE__ */ new Map(),
@@ -25844,7 +25930,7 @@ function lS() {
25844
25930
  assetUrls: /* @__PURE__ */ new Map()
25845
25931
  };
25846
25932
  }
25847
- function uS(e, t, n = []) {
25933
+ function dS(e, t, n = []) {
25848
25934
  let r = Date.now();
25849
25935
  if (e && String(e).trim() !== "") {
25850
25936
  let t = Date.parse(e);
@@ -25855,7 +25941,7 @@ function uS(e, t, n = []) {
25855
25941
  !isNaN(e) && e > r && n.push(e);
25856
25942
  }
25857
25943
  }
25858
- function dS(e, t) {
25944
+ function fS(e, t) {
25859
25945
  let n = Date.now();
25860
25946
  if (e && String(e).trim() !== "") {
25861
25947
  let t = Date.parse(e);
@@ -25867,13 +25953,15 @@ function dS(e, t) {
25867
25953
  }
25868
25954
  return !0;
25869
25955
  }
25870
- async function fS(e, t, n, r, i) {
25956
+ async function pS(e, t, n, r, i) {
25871
25957
  let a = t.filter((e) => e.componentId === "content-feed" || e.componentId === "article-list" || e.componentId === "nodeList" || e.componentId === "node-list");
25872
25958
  await Promise.all(a.map(async (t) => {
25873
25959
  let a = t.data || {}, o = a.nodeType || ["article"], s = (Array.isArray(o) ? o : String(o).split(",")).map((e) => String(e).trim()).filter(Boolean), c = Number(a.limit) || 12, l = Number(a.offset) || 0, u = a.sortBy || "updatedAt", d = new URLSearchParams();
25874
25960
  d.set("nodeType", s.join(",")), d.set("limit", c.toString()), d.set("offset", (l + c).toString()), d.set("sortBy", u), n && n !== "all" && d.set("channelId", String(n));
25875
- let f = `FROM content_nodes WHERE contentType IN (${s.map(() => "?").join(",")}) AND isHidden = 0 AND (status = 'published' OR status IS NULL)`, p = [...s];
25876
- n && n !== "all" && (f += " AND id IN (SELECT nodeId FROM node_channels WHERE channelId = ?)", p.push(Number(n) || n));
25961
+ let f = `FROM content_nodes WHERE contentType IN (${s.map(() => "?").join(",")}) AND isHidden = 0 AND IFNULL(status, 'published') = 'published'`, p = [...s];
25962
+ n && n !== "all" && (f += " AND EXISTS (SELECT 1 FROM node_channels nc WHERE nc.nodeId = content_nodes.id AND nc.channelId = ?)", p.push(Number(n) || n));
25963
+ let m = (/* @__PURE__ */ new Date()).toISOString();
25964
+ f += " AND IFNULL(json_extract(dataJson, '$.startShowingAt'), '') <= ?", p.push(m), f += " AND IFNULL(json_extract(dataJson, '$.stopShowingAt'), '9999-12-31') >= ?", p.push(m);
25877
25965
  for (let e of [
25878
25966
  "authors",
25879
25967
  "categories",
@@ -25893,18 +25981,18 @@ async function fS(e, t, n, r, i) {
25893
25981
  f += e === "authors" ? ` AND EXISTS (SELECT 1 FROM node_relations nr WHERE nr.sourceNodeId = content_nodes.id AND nr.fieldKey = ? AND nr.targetNodeId IN (${n}))` : ` AND EXISTS (SELECT 1 FROM node_terms nt INNER JOIN taxonomy_terms tt ON nt.termId = tt.id WHERE nt.nodeId = content_nodes.id AND tt.taxonomy = ? AND tt.key IN (${n}))`, p.push(e, ...t);
25894
25982
  }
25895
25983
  }
25896
- let m = "ORDER BY updatedAt DESC";
25897
- u === "published_desc" || u === "createdAt" ? m = "ORDER BY createdAt DESC" : u === "title_asc" && (m = "ORDER BY LOWER(title) ASC");
25898
- let h = `SELECT id, title, slug, language, dataJson, createdAt, updatedAt ${f} ${m} LIMIT ? OFFSET ?`;
25984
+ let h = "ORDER BY updatedAt DESC";
25985
+ u === "published_desc" || u === "createdAt" ? h = "ORDER BY createdAt DESC" : u === "title_asc" && (h = "ORDER BY LOWER(title) ASC");
25986
+ let g = `SELECT id, title, slug, language, dataJson, createdAt, updatedAt ${f} ${h} LIMIT ? OFFSET ?`;
25899
25987
  p.push(c, l);
25900
25988
  try {
25901
- let n = await e.prepare(h).all(...p), a = Array.isArray(n) ? n : n?.results || [];
25902
- t.data.initialItems = a.map((e) => {
25989
+ let n = await e.prepare(g).all(...p), o = Array.isArray(n) ? n : n?.results || [];
25990
+ t.data.initialItems = o.map((e) => {
25903
25991
  let t = {};
25904
25992
  if (e.dataJson) try {
25905
25993
  t = typeof e.dataJson == "string" ? JSON.parse(e.dataJson) : e.dataJson;
25906
25994
  } catch {}
25907
- return i && uS(t.startShowingAt, t.stopShowingAt, i), dS(t.startShowingAt, t.stopShowingAt) ? {
25995
+ return i && dS(t.startShowingAt, t.stopShowingAt, i), {
25908
25996
  id: e.id,
25909
25997
  title: e.title,
25910
25998
  slug: e.slug,
@@ -25914,14 +26002,14 @@ async function fS(e, t, n, r, i) {
25914
26002
  excerpt: t.excerpt || "",
25915
26003
  image: t.image || t.coverImage || null,
25916
26004
  author: t.author || null
25917
- } : null;
25918
- }).filter(Boolean), t.data.initialItems.length === c ? t.data.loadMoreUrl = `/api/v1/nodes?${d.toString()}` : t.data.loadMoreUrl = null;
26005
+ };
26006
+ }), a.disablePagination !== !0 && a.disablePagination !== "1" && o.length === c ? t.data.loadMoreUrl = `/api/v1/nodes?${d.toString()}` : t.data.loadMoreUrl = null;
25919
26007
  } catch (e) {
25920
26008
  console.error("[CMS Hydration] Failed to hydrate content feed block", e), t.data.initialItems = [], t.data.loadMoreUrl = null;
25921
26009
  }
25922
26010
  }));
25923
26011
  }
25924
- async function pS(e, t, n, r, i, a = !1, o, s) {
26012
+ async function mS(e, t, n, r, i, a = !1, o, s) {
25925
26013
  if (!t) return { blocks: [] };
25926
26014
  let c = await e.prepare("\n WITH RECURSIVE ancestor_path(contentId, title, slug, parentId, level) AS (\n SELECT t.contentId, c.title, c.slug, t.parentId, 0 FROM tree_nodes t INNER JOIN content_nodes c ON t.contentId = c.id WHERE t.contentId = ? AND t.treeId = ?\n UNION ALL\n SELECT t.contentId, c.title, c.slug, t.parentId, ap.level + 1 FROM tree_nodes t INNER JOIN content_nodes c ON t.contentId = c.id INNER JOIN ancestor_path ap ON t.contentId = ap.parentId AND t.treeId = ?\n )\n SELECT * FROM ancestor_path ORDER BY level ASC\n ").all(t, n, n), l = Array.isArray(c) ? c : c?.results || [];
25927
26015
  if (!l || l.length === 0) return { blocks: [] };
@@ -25957,11 +26045,11 @@ async function pS(e, t, n, r, i, a = !1, o, s) {
25957
26045
  try {
25958
26046
  n = (typeof t.dataJson == "string" ? JSON.parse(t.dataJson) : t.dataJson) || {};
25959
26047
  } catch {}
25960
- s && uS(n.startShowingAt, n.stopShowingAt, s);
25961
- let o = n.hidden === !0 || n.hidden === 1 || n.hidden === "1" || n.hidden === "true", c = dS(n.startShowingAt, n.stopShowingAt);
26048
+ s && dS(n.startShowingAt, n.stopShowingAt, s);
26049
+ let o = n.hidden === !0 || n.hidden === 1 || n.hidden === "1" || n.hidden === "true", c = fS(n.startShowingAt, n.stopShowingAt);
25962
26050
  if (!a && (o || !c)) return null;
25963
- let l = t.elementType || t.componentId || "text-block", u = i.blocks?.[l]?.fields || i.elements?.[l]?.fields || i.components?.[l]?.fields || {}, d = String(n.blockId || n._instanceId || n.id || t.blockId || t.id), f = mS(n, u);
25964
- return f = await fx(e, f), f = hS(f), f.blockId = d, {
26051
+ let l = t.elementType || t.componentId || "text-block", u = i.blocks?.[l]?.fields || i.elements?.[l]?.fields || i.components?.[l]?.fields || {}, d = String(n.blockId || n._instanceId || n.id || t.blockId || t.id), f = hS(n, u);
26052
+ return f = await fx(e, f), f = gS(f), f.blockId = d, {
25965
26053
  region: t.region || r,
25966
26054
  block: {
25967
26055
  instanceId: t.id,
@@ -25981,7 +26069,7 @@ async function pS(e, t, n, r, i, a = !1, o, s) {
25981
26069
  }
25982
26070
  return { blocks: [] };
25983
26071
  }
25984
- function mS(e, t = {}) {
26072
+ function hS(e, t = {}) {
25985
26073
  let n = {};
25986
26074
  for (let [r, i] of Object.entries(e)) r.endsWith("_meta") || [
25987
26075
  "disabledRegions",
@@ -25997,14 +26085,14 @@ function mS(e, t = {}) {
25997
26085
  ].includes(r) || r.startsWith("_") || (!t[r] || t[r].public !== !1) && (n[r] = i);
25998
26086
  return n;
25999
26087
  }
26000
- function hS(e) {
26001
- if (Array.isArray(e)) return e.map(hS);
26088
+ function gS(e) {
26089
+ if (Array.isArray(e)) return e.map(gS);
26002
26090
  if (!e || typeof e != "object") return e;
26003
26091
  if (typeof e.id == "string" && e.id.startsWith("ast_") && typeof e.url == "string") {
26004
26092
  let t = e.metadataOverrides || {}, n = e.variants && typeof e.variants == "object" ? e.variants : {}, r = Object.entries(n).find(([, t]) => t?.id === e.id)?.[0], i = r ? {
26005
26093
  ...t,
26006
26094
  ...t.crops?.[r] || {}
26007
- } : t, a = Object.fromEntries(Object.entries(n).filter(([, t]) => t?.id !== e.id).map(([t, n]) => [t, hS({
26095
+ } : t, a = Object.fromEntries(Object.entries(n).filter(([, t]) => t?.id !== e.id).map(([t, n]) => [t, gS({
26008
26096
  ...n,
26009
26097
  title: n?.title ?? e.title ?? "",
26010
26098
  alt: n?.alt ?? e.alt ?? "",
@@ -26018,9 +26106,9 @@ function hS(e) {
26018
26106
  ...Object.keys(a).length > 0 ? { variants: a } : {}
26019
26107
  };
26020
26108
  }
26021
- return Object.fromEntries(Object.entries(e).map(([e, t]) => [e, hS(t)]));
26109
+ return Object.fromEntries(Object.entries(e).map(([e, t]) => [e, gS(t)]));
26022
26110
  }
26023
- async function gS(e, t, n, r) {
26111
+ async function _S(e, t, n, r) {
26024
26112
  if (typeof t == "string") {
26025
26113
  if (!t.includes("#node:") && !t.includes("data-node-id") && !t.includes("#asset:") && !t.includes("data-asset-id")) return t;
26026
26114
  let r = (e, t) => {
@@ -26053,25 +26141,25 @@ async function gS(e, t, n, r) {
26053
26141
  return /href\s*=\s*["'][^"']*["']/i.test(d) ? d = d.replace(/href\s*=\s*["'][^"']*["']/i, `href="${u}"`) : d += ` href="${u}"`, `<a ${d}>`;
26054
26142
  });
26055
26143
  }
26056
- if (Array.isArray(t)) return Promise.all(t.map((t) => gS(e, t, n, r)));
26144
+ if (Array.isArray(t)) return Promise.all(t.map((t) => _S(e, t, n, r)));
26057
26145
  if (t && typeof t == "object") {
26058
26146
  if (typeof t.href == "string" && (t.href.startsWith("#node:") || t.href.startsWith("#asset:"))) return {
26059
26147
  ...t,
26060
- href: await _S(e, t, n, r)
26148
+ href: await vS(e, t, n, r)
26061
26149
  };
26062
- let i = await Promise.all(Object.entries(t).map(async ([t, i]) => [t, await gS(e, i, n, r)]));
26150
+ let i = await Promise.all(Object.entries(t).map(async ([t, i]) => [t, await _S(e, i, n, r)]));
26063
26151
  return Object.fromEntries(i);
26064
26152
  }
26065
26153
  return t;
26066
26154
  }
26067
- async function _S(e, t, n, r) {
26155
+ async function vS(e, t, n, r) {
26068
26156
  let i = t.href.match(/^#node:(.+)$/), a = t.href.match(/^#asset:(.+)$/);
26069
- if (a) return vS(e, a[1], r);
26157
+ if (a) return yS(e, a[1], r);
26070
26158
  if (!i) return t.href;
26071
26159
  let o = i[1];
26072
26160
  return (await e.prepare("SELECT path FROM node_routes WHERE nodeId = ? AND channelId = ? AND isCanonical = 1 LIMIT 1").get(Number(o), n))?.path || "#";
26073
26161
  }
26074
- async function vS(e, t, n) {
26162
+ async function yS(e, t, n) {
26075
26163
  let r = String(t), i = n.assetUrls.get(r);
26076
26164
  if (i) return i;
26077
26165
  let a = (async () => {
@@ -26080,7 +26168,7 @@ async function vS(e, t, n) {
26080
26168
  })();
26081
26169
  return n.assetUrls.set(r, a), a;
26082
26170
  }
26083
- function yS(e) {
26171
+ function bS(e) {
26084
26172
  let t = e.socialImage;
26085
26173
  if (!t || typeof t != "object") return null;
26086
26174
  let n = (e, t) => {
@@ -26111,7 +26199,7 @@ function yS(e) {
26111
26199
  ])
26112
26200
  };
26113
26201
  }
26114
- async function bS(e, t, n, r, i) {
26202
+ async function xS(e, t, n, r, i) {
26115
26203
  let a = {}, o = null;
26116
26204
  if (t) {
26117
26205
  let i = await e.prepare("\n WITH RECURSIVE ancestor_path(contentId, title, slug, parentId, level) AS (\n SELECT t.contentId, c.title, c.slug, t.parentId, 0 FROM tree_nodes t INNER JOIN content_nodes c ON t.contentId = c.id WHERE t.contentId = ? AND t.treeId = ?\n UNION ALL\n SELECT t.contentId, c.title, c.slug, t.parentId, ap.level + 1 FROM tree_nodes t INNER JOIN content_nodes c ON t.contentId = c.id INNER JOIN ancestor_path ap ON t.contentId = ap.parentId AND t.treeId = ?\n )\n SELECT c.dataJson, c.draftDataJson FROM ancestor_path ap INNER JOIN content_nodes c ON ap.contentId = c.id ORDER BY ap.level ASC\n ").all(t, n, n), s = Array.isArray(i) ? i : i?.results || [], c = /* @__PURE__ */ new Set([
@@ -26149,20 +26237,20 @@ async function bS(e, t, n, r, i) {
26149
26237
  inheritedFields: a
26150
26238
  };
26151
26239
  }
26152
- function xS(e) {
26240
+ function SS(e) {
26153
26241
  let t = Number(e?.env?.CMS_NODE_CACHE_TTL);
26154
26242
  return Number.isFinite(t) && t >= 60 ? Math.floor(t) : 300;
26155
26243
  }
26156
- async function SS(e, t, n, r) {
26244
+ async function CS(e, t, n, r) {
26157
26245
  try {
26158
26246
  await e.set(t, n, r);
26159
26247
  } catch (e) {
26160
26248
  console.warn("[CMS Cache] Failed to write node response to cache:", e);
26161
26249
  }
26162
26250
  }
26163
- async function CS(e) {
26251
+ async function wS(e) {
26164
26252
  try {
26165
- let t = e.get("db"), n = lS(), r = [], i = new URL(e.req.url), a = i.searchParams.get("channelId") || i.searchParams.get("channel"), o = i.searchParams.get("lang"), s = i.searchParams.get("preview") === "true", c = i.searchParams.get("revisionId"), l = i.searchParams.get("treeId"), u = i.pathname, d = "";
26253
+ let t = e.get("db"), n = uS(), r = [], i = new URL(e.req.url), a = i.searchParams.get("channelId") || i.searchParams.get("channel"), o = i.searchParams.get("lang"), s = i.searchParams.get("preview") === "true", c = i.searchParams.get("revisionId"), l = i.searchParams.get("treeId"), u = i.pathname, d = "";
26166
26254
  u.includes("/node/") ? d = u.substring(u.indexOf("/node/") + 6) : u.endsWith("/node") && (d = "");
26167
26255
  try {
26168
26256
  d = decodeURIComponent(d);
@@ -26212,9 +26300,9 @@ async function CS(e) {
26212
26300
  e.defaultLanguage ? w = String(e.defaultLanguage).trim() : e.language && (w = String(e.language).trim());
26213
26301
  } catch {}
26214
26302
  }
26215
- let T = y.language?.trim() || null, ee = C || w || o?.trim() || null, E = T || ee || null, D = `node:${g || _}:${E || "default"}:${d}`, O = e.req.header("x-bypass-cache") === "true" || !!c, te = $b(e), k = xS(e);
26216
- if (!s && !O) {
26217
- let t = await te.get(D);
26303
+ let T = y.language?.trim() || null, ee = C || w || o?.trim() || null, E = T || ee || null, D = `node:${g || _}:${E || "default"}:${d}`, te = e.req.header("x-bypass-cache") === "true" || !!c, O = $b(e), k = SS(e);
26304
+ if (!s && !te) {
26305
+ let t = await O.get(D);
26218
26306
  if (t) {
26219
26307
  e.header("X-Cache", "HIT");
26220
26308
  let n = k;
@@ -26242,14 +26330,14 @@ async function CS(e) {
26242
26330
  if (x && x.node && x.node.dataJson && (fe = x.node.dataJson), fe) try {
26243
26331
  de = typeof fe == "string" ? JSON.parse(fe) : fe;
26244
26332
  } catch {}
26245
- de.disabledRegions && (se = de.disabledRegions), ue = de.hidden === !0 || de.hidden === 1 || de.hidden === "1" || de.hidden === "true", ce = de.startShowingAt || null, le = de.stopShowingAt || null, uS(ce, le, r);
26246
- let pe = de.layoutId, me = pe && pe !== "inherit", { resolvedLayoutId: he, inheritedFields: ge } = await bS(t, A, b, s, oe), _e = me ? pe : he || ae.defaultLayout || null;
26333
+ de.disabledRegions && (se = de.disabledRegions), ue = de.hidden === !0 || de.hidden === 1 || de.hidden === "1" || de.hidden === "true", ce = de.startShowingAt || null, le = de.stopShowingAt || null, dS(ce, le, r);
26334
+ let pe = de.layoutId, me = pe && pe !== "inherit", { resolvedLayoutId: he, inheritedFields: ge } = await xS(t, A, b, s, oe), _e = me ? pe : he || ae.defaultLayout || null;
26247
26335
  for (let [e, t] of Object.entries(ge)) (de[e] === void 0 || de[e] === null || de[e] === "" || de[e] === "inherit") && t !== void 0 && (de[e] = t);
26248
- let ve = await fx(t, mS(de, oe));
26249
- ve = hS(ve), ve = await gS(t, ve, g, n), delete ve.language;
26250
- let ye = yS(ve);
26336
+ let ve = await fx(t, hS(de, oe));
26337
+ ve = gS(ve), ve = await _S(t, ve, g, n), delete ve.language;
26338
+ let ye = bS(ve);
26251
26339
  delete ve.socialImage, delete ve.fbImage, delete ve.xImage, delete ve.whatsappImage, ye && (ve.socialImages = ye), Object.assign(j, ve), j.id = y.id, j.slug = y.slug, j.title = y.title, j.path = ne, j.layoutId = _e;
26252
- let be = Number(y.isHidden) === 1 || ue, xe = !dS(ce, le), Se = y.status === "draft" || y.status === "new", Ce = y.dataJson && y.dataJson !== "{}" && y.dataJson !== "null";
26340
+ let be = Number(y.isHidden) === 1 || ue, xe = !fS(ce, le), Se = y.status === "draft" || y.status === "new", Ce = y.dataJson && y.dataJson !== "{}" && y.dataJson !== "null";
26253
26341
  if (!s && (be || xe || Se && !Ce)) return e.json({ error: "Node is hidden, offline, or has never been published." }, 404);
26254
26342
  let we = [];
26255
26343
  if (S?.treeNodeId) {
@@ -26260,8 +26348,8 @@ async function CS(e) {
26260
26348
  try {
26261
26349
  t = (typeof n == "string" ? JSON.parse(n) : n) || {};
26262
26350
  } catch {}
26263
- let i = Number(e.isHidden) === 1 || t.hidden === !0 || t.hidden === 1 || t.hidden === "1", o = dS(t.startShowingAt, t.stopShowingAt), c = (e.slug || "").replace(/^\/+|\/+$/g, "");
26264
- return uS(t.startShowingAt, t.stopShowingAt, r), !s && (i || !o) ? null : {
26351
+ let i = Number(e.isHidden) === 1 || t.hidden === !0 || t.hidden === 1 || t.hidden === "1", o = fS(t.startShowingAt, t.stopShowingAt), c = (e.slug || "").replace(/^\/+|\/+$/g, "");
26352
+ return dS(t.startShowingAt, t.stopShowingAt, r), !s && (i || !o) ? null : {
26265
26353
  treeNodeId: e.treeNodeId,
26266
26354
  id: e.id,
26267
26355
  title: e.title,
@@ -26287,11 +26375,11 @@ async function CS(e) {
26287
26375
  try {
26288
26376
  a = (typeof e.dataJson == "string" ? JSON.parse(e.dataJson) : e.dataJson) || {};
26289
26377
  } catch {}
26290
- uS(a.startShowingAt, a.stopShowingAt, r);
26291
- let o = a.hidden === !0 || a.hidden === 1 || a.hidden === "1" || a.hidden === "true", c = dS(a.startShowingAt, a.stopShowingAt);
26378
+ dS(a.startShowingAt, a.stopShowingAt, r);
26379
+ let o = a.hidden === !0 || a.hidden === 1 || a.hidden === "1" || a.hidden === "true", c = fS(a.startShowingAt, a.stopShowingAt);
26292
26380
  if (!s && (o || !c)) return null;
26293
- let l = e.elementType || e.componentId || "text-block", u = re.blocks?.[l]?.fields || re.elements?.[l]?.fields || re.components?.[l]?.fields || {}, d = String(a.blockId || a._instanceId || a.id || e.blockId || e.id), f = mS(a, u);
26294
- return f = await fx(t, f), f = hS(f), f = await gS(t, f, g, n), f.blockId = d, {
26381
+ let l = e.elementType || e.componentId || "text-block", u = re.blocks?.[l]?.fields || re.elements?.[l]?.fields || re.components?.[l]?.fields || {}, d = String(a.blockId || a._instanceId || a.id || e.blockId || e.id), f = hS(a, u);
26382
+ return f = await fx(t, f), f = gS(f), f = await _S(t, f, g, n), f.blockId = d, {
26295
26383
  region: i,
26296
26384
  block: {
26297
26385
  instanceId: e.id,
@@ -26316,7 +26404,7 @@ async function CS(e) {
26316
26404
  for (let [e, i] of Object.entries(ke)) {
26317
26405
  let a = Ee[e] && Ee[e].length > 0, o = !!se[e];
26318
26406
  if (Ee[e] || (Ee[e] = [], De[e] = { isInherited: !1 }), (i?.inherit === "parent" || i?.inherit === !0 || i?.inherit === "true" || e === "header" || e === "footer") && !a && !o && A) {
26319
- let i = await pS(t, A, String(b), e, re, s, n, r);
26407
+ let i = await mS(t, A, String(b), e, re, s, n, r);
26320
26408
  if (i.blocks.length > 0 && (Ee[e] = i.blocks, De[e] = {
26321
26409
  isInherited: !0,
26322
26410
  inheritedFromId: i.inheritedFromId,
@@ -26328,7 +26416,7 @@ async function CS(e) {
26328
26416
  });
26329
26417
  }
26330
26418
  }
26331
- await Promise.all(Object.keys(Ee).map((e) => fS(t, Ee[e], g, E, r)));
26419
+ await Promise.all(Object.keys(Ee).map((e) => pS(t, Ee[e], g, E, r)));
26332
26420
  let Ae = null, je = null;
26333
26421
  if (r.length > 0) {
26334
26422
  je = Math.min(...r);
@@ -26347,10 +26435,10 @@ async function CS(e) {
26347
26435
  content: Ee,
26348
26436
  regionMeta: De
26349
26437
  };
26350
- if (!s && !O) {
26438
+ if (!s && !te) {
26351
26439
  e.header("X-Cache", "MISS");
26352
26440
  let t = Ae === null ? k : Ae;
26353
- e.header("Cache-Control", `public, max-age=${t}, s-maxage=${t}`), await SS(te, D, Me, t);
26441
+ e.header("Cache-Control", `public, max-age=${t}, s-maxage=${t}`), await CS(O, D, Me, t);
26354
26442
  } else e.header("Cache-Control", "no-cache, no-store, must-revalidate");
26355
26443
  return e.json(Me, 200);
26356
26444
  } catch (t) {
@@ -26360,17 +26448,17 @@ async function CS(e) {
26360
26448
  }, 500);
26361
26449
  }
26362
26450
  }
26363
- var wS = X({
26451
+ var TS = X({
26364
26452
  channelId: J().optional().openapi({ description: "The ID or key of the channel" }),
26365
26453
  channel: J().optional().openapi({ description: "Legacy alias for channelId" }),
26366
26454
  lang: J().optional().openapi({ description: "Requested language code" }),
26367
26455
  preview: lv(["true", "false"]).optional().openapi({ description: "Request unpublished draft data" }),
26368
26456
  revisionId: J().optional().openapi({ description: "Historical revision version to load" }),
26369
26457
  treeId: J().optional().openapi({ description: "The ID of the tree to resolve paths against" })
26370
- }), TS = X({
26458
+ }), ES = X({
26371
26459
  error: J(),
26372
26460
  details: J().optional()
26373
- }).openapi("ErrorResponse"), ES = X({
26461
+ }).openapi("ErrorResponse"), DS = X({
26374
26462
  channelId: G_([J(), c_()]),
26375
26463
  treeId: J().nullable(),
26376
26464
  language: J().nullable(),
@@ -26385,7 +26473,7 @@ var wS = X({
26385
26473
  inheritedFromId: J().optional(),
26386
26474
  inheritedFromTitle: J().optional()
26387
26475
  }))
26388
- }).openapi("NodeResponse"), DS = eb({
26476
+ }).openapi("NodeResponse"), OS = eb({
26389
26477
  method: "get",
26390
26478
  path: "/{path}",
26391
26479
  summary: "Fetch CMS Node Content",
@@ -26393,25 +26481,25 @@ var wS = X({
26393
26481
  tags: ["Public Node API"],
26394
26482
  request: {
26395
26483
  params: X({ path: J().optional().openapi({ description: "The full URL path or slug of the requested node" }) }),
26396
- query: wS
26484
+ query: TS
26397
26485
  },
26398
26486
  responses: {
26399
26487
  200: {
26400
26488
  description: "Fully hydrated CMS Node",
26401
- content: { "application/json": { schema: ES } }
26489
+ content: { "application/json": { schema: DS } }
26402
26490
  },
26403
26491
  404: {
26404
26492
  description: "Node or Channel not found",
26405
- content: { "application/json": { schema: TS } }
26493
+ content: { "application/json": { schema: ES } }
26406
26494
  },
26407
26495
  500: {
26408
26496
  description: "Server error during hydration",
26409
- content: { "application/json": { schema: TS } }
26497
+ content: { "application/json": { schema: ES } }
26410
26498
  }
26411
26499
  }
26412
26500
  });
26413
- cS.openapi(DS, CS), cS.get("*", CS);
26414
- var OS = new $y(), kS = X({
26501
+ lS.openapi(OS, wS), lS.get("*", wS);
26502
+ var kS = new $y(), AS = X({
26415
26503
  nodeType: J().default("article").openapi({ description: "Content types (comma separated)" }),
26416
26504
  channelId: J().optional().openapi({ description: "Channel ID or key" }),
26417
26505
  limit: Ky().min(1).max(50).default(12).openapi({ description: "Number of items (max 50)" }),
@@ -26424,34 +26512,29 @@ var OS = new $y(), kS = X({
26424
26512
  authors: G_([J(), z_(J())]).optional(),
26425
26513
  categories: G_([J(), z_(J())]).optional(),
26426
26514
  tags: G_([J(), z_(J())]).optional()
26427
- }), AS = async (e) => {
26515
+ }), jS = async (e) => {
26428
26516
  try {
26429
- let t = e.get("db"), n = e.req.valid("query"), r = n.nodeType || "article", i = String(r).split(",").map((e) => e.trim()).filter(Boolean), a = `FROM content_nodes WHERE contentType IN (${i.map(() => "?").join(",")}) AND isHidden = 0 AND (status = 'published' OR status IS NULL)`, o = [...i];
26430
- n.channelId && n.channelId !== "all" && (a += " AND id IN (SELECT nodeId FROM node_channels WHERE channelId = ?)", o.push(Number(n.channelId) || n.channelId));
26431
- let s = (e, t, n = !1) => {
26517
+ let t = e.get("db"), n = e.req.valid("query"), r = n.nodeType || "article", i = String(r).split(",").map((e) => e.trim()).filter(Boolean), a = `FROM content_nodes WHERE contentType IN (${i.map(() => "?").join(",")}) AND isHidden = 0 AND IFNULL(status, 'published') = 'published'`, o = [...i];
26518
+ n.channelId && n.channelId !== "all" && (a += " AND EXISTS (SELECT 1 FROM node_channels nc WHERE nc.nodeId = content_nodes.id AND nc.channelId = ?)", o.push(Number(n.channelId) || n.channelId));
26519
+ let s = (/* @__PURE__ */ new Date()).toISOString();
26520
+ a += " AND IFNULL(json_extract(dataJson, '$.startShowingAt'), '') <= ?", o.push(s), a += " AND IFNULL(json_extract(dataJson, '$.stopShowingAt'), '9999-12-31') >= ?", o.push(s);
26521
+ let c = (e, t, n = !1) => {
26432
26522
  let r = Array.isArray(t) ? t : t.split(",").map((e) => e.trim());
26433
26523
  if (r.length === 0) return;
26434
26524
  let i = r.map(() => "?").join(",");
26435
- n ? (a += ` AND EXISTS (
26436
- SELECT 1 FROM node_relations nr
26437
- WHERE nr.sourceNodeId = content_nodes.id AND nr.fieldKey = ? AND nr.targetNodeId IN (${i})
26438
- )`, o.push(e, ...r)) : (a += ` AND EXISTS (
26439
- SELECT 1 FROM node_terms nt
26440
- INNER JOIN taxonomy_terms tt ON nt.termId = tt.id
26441
- WHERE nt.nodeId = content_nodes.id AND tt.taxonomy = ? AND tt.key IN (${i})
26442
- )`, o.push(e, ...r));
26525
+ n ? (a += ` AND EXISTS (SELECT 1 FROM node_relations nr WHERE nr.sourceNodeId = content_nodes.id AND nr.fieldKey = ? AND nr.targetNodeId IN (${i}))`, o.push(e, ...r)) : (a += ` AND EXISTS (SELECT 1 FROM node_terms nt INNER JOIN taxonomy_terms tt ON nt.termId = tt.id WHERE nt.nodeId = content_nodes.id AND tt.taxonomy = ? AND tt.key IN (${i}))`, o.push(e, ...r));
26443
26526
  };
26444
- n.authors && s("authors", n.authors, !0), n.categories && s("categories", n.categories, !1), n.tags && s("tags", n.tags, !1);
26445
- let c = "ORDER BY updatedAt DESC";
26446
- n.sortBy === "createdAt" ? c = "ORDER BY createdAt DESC" : n.sortBy === "title_asc" && (c = "ORDER BY LOWER(title) ASC");
26447
- let l = `SELECT id, title, slug, language, dataJson, createdAt, updatedAt ${a} ${c} LIMIT ? OFFSET ?`;
26527
+ n.authors && c("authors", n.authors, !0), n.categories && c("categories", n.categories, !1), n.tags && c("tags", n.tags, !1);
26528
+ let l = "ORDER BY updatedAt DESC";
26529
+ n.sortBy === "createdAt" ? l = "ORDER BY createdAt DESC" : n.sortBy === "title_asc" && (l = "ORDER BY LOWER(title) ASC");
26530
+ let u = `SELECT id, title, slug, language, dataJson, createdAt, updatedAt ${a} ${l} LIMIT ? OFFSET ?`;
26448
26531
  o.push(n.limit, n.offset);
26449
- let u = await t.prepare(l).all(...o), d = Array.isArray(u) ? u : u?.results || [], f = Date.now(), p = d.map((e) => {
26532
+ let d = await t.prepare(u).all(...o), f = Array.isArray(d) ? d : d?.results || [], p = f.map((e) => {
26450
26533
  let t = {};
26451
26534
  try {
26452
26535
  t = typeof e.dataJson == "string" ? JSON.parse(e.dataJson) : e.dataJson || {};
26453
26536
  } catch {}
26454
- return t.startShowingAt && Date.parse(t.startShowingAt) > f || t.stopShowingAt && Date.parse(t.stopShowingAt) < f ? null : {
26537
+ return {
26455
26538
  id: e.id,
26456
26539
  title: e.title,
26457
26540
  slug: e.slug,
@@ -26462,22 +26545,23 @@ var OS = new $y(), kS = X({
26462
26545
  image: t.image || t.coverImage || null,
26463
26546
  author: t.author || null
26464
26547
  };
26465
- }).filter(Boolean);
26548
+ });
26466
26549
  return e.json({
26467
26550
  items: p,
26468
26551
  count: p.length,
26552
+ rawCount: f.length,
26469
26553
  limit: n.limit,
26470
26554
  offset: n.offset
26471
26555
  }, 200);
26472
26556
  } catch (t) {
26473
26557
  return console.error("[CMS API] Error fetching nodes list:", t), e.json({ error: "Failed to fetch nodes list" }, 500);
26474
26558
  }
26475
- }, jS = eb({
26559
+ }, MS = eb({
26476
26560
  method: "get",
26477
26561
  path: "/",
26478
26562
  summary: "Fetch filtered list of nodes",
26479
26563
  tags: ["Public Node API"],
26480
- request: { query: kS },
26564
+ request: { query: AS },
26481
26565
  responses: {
26482
26566
  200: {
26483
26567
  description: "List of nodes",
@@ -26486,9 +26570,9 @@ var OS = new $y(), kS = X({
26486
26570
  500: { description: "Server error" }
26487
26571
  }
26488
26572
  });
26489
- OS.openapi(jS, AS);
26490
- var MS = new $y();
26491
- function NS(e, t) {
26573
+ kS.openapi(MS, jS);
26574
+ var NS = new $y();
26575
+ function PS(e, t) {
26492
26576
  let n = /* @__PURE__ */ new Date();
26493
26577
  if (e && String(e).trim() !== "") {
26494
26578
  let t = new Date(e);
@@ -26500,22 +26584,22 @@ function NS(e, t) {
26500
26584
  }
26501
26585
  return !0;
26502
26586
  }
26503
- async function PS(e, t, n, r) {
26587
+ async function FS(e, t, n, r) {
26504
26588
  try {
26505
26589
  await e.set(t, n, r);
26506
26590
  } catch (e) {
26507
26591
  console.warn("[CMS Cache] Failed to write tree response to cache:", e);
26508
26592
  }
26509
26593
  }
26510
- var FS = X({ treeParam: J().openapi({ description: "The ID or key of the requested tree (e.g., \"main-nav\")" }) }), IS = X({
26594
+ var IS = X({ treeParam: J().openapi({ description: "The ID or key of the requested tree (e.g., \"main-nav\")" }) }), LS = X({
26511
26595
  channelId: J().optional().openapi({ description: "Channel ID to resolve context-aware routing" }),
26512
26596
  channel: J().optional().openapi({ description: "Legacy alias for channelId" }),
26513
26597
  lang: J().optional().openapi({ description: "Requested language code for tree nodes" }),
26514
26598
  preview: lv(["true", "false"]).optional().openapi({ description: "Set to true to retrieve unpublished draft data" })
26515
- }), LS = X({
26599
+ }), RS = X({
26516
26600
  error: J(),
26517
26601
  details: J().optional()
26518
- }).openapi("ErrorResponse"), RS = qv(() => X({
26602
+ }).openapi("ErrorResponse"), zS = qv(() => X({
26519
26603
  id: G_([J(), c_()]),
26520
26604
  treeNodeId: G_([J(), c_()]),
26521
26605
  parentId: G_([J(), c_()]).nullable(),
@@ -26528,40 +26612,40 @@ var FS = X({ treeParam: J().openapi({ description: "The ID or key of the request
26528
26612
  summary: J(),
26529
26613
  url: J().optional(),
26530
26614
  target: J().optional(),
26531
- children: z_(RS).optional()
26532
- })).openapi("TreeItem"), zS = X({
26615
+ children: z_(zS).optional()
26616
+ })).openapi("TreeItem"), BS = X({
26533
26617
  treeId: G_([c_(), J()]),
26534
26618
  key: J(),
26535
26619
  channelId: J(),
26536
26620
  language: J().nullable(),
26537
26621
  label: J(),
26538
- items: z_(RS)
26539
- }).catchall(k_()).openapi("TreeResponse"), BS = eb({
26622
+ items: z_(zS)
26623
+ }).catchall(k_()).openapi("TreeResponse"), VS = eb({
26540
26624
  method: "get",
26541
26625
  path: "/{treeParam}",
26542
26626
  summary: "Fetch CMS Navigation Tree",
26543
26627
  description: "Retrieves a fully hydrated, recursive navigation tree structure. Uses $O(1)$ pre-computed routing table paths.",
26544
26628
  tags: ["Public Tree API"],
26545
26629
  request: {
26546
- params: FS,
26547
- query: IS
26630
+ params: IS,
26631
+ query: LS
26548
26632
  },
26549
26633
  responses: {
26550
26634
  200: {
26551
26635
  description: "Fully hydrated CMS Tree payload",
26552
- content: { "application/json": { schema: zS } }
26636
+ content: { "application/json": { schema: BS } }
26553
26637
  },
26554
26638
  404: {
26555
26639
  description: "Tree or Channel not found / inactive",
26556
- content: { "application/json": { schema: LS } }
26640
+ content: { "application/json": { schema: RS } }
26557
26641
  },
26558
26642
  500: {
26559
26643
  description: "Server error during hydration",
26560
- content: { "application/json": { schema: LS } }
26644
+ content: { "application/json": { schema: RS } }
26561
26645
  }
26562
26646
  }
26563
26647
  });
26564
- MS.openapi(BS, async (e) => {
26648
+ NS.openapi(VS, async (e) => {
26565
26649
  try {
26566
26650
  let t = e.get("db"), { treeParam: n } = e.req.valid("param"), r = e.req.valid("query"), i = r.channelId || r.channel || "default", a = r.lang, o = r.preview === "true", s = null, c = -1;
26567
26651
  if (i && i !== "default" && i !== "all") {
@@ -26596,7 +26680,7 @@ MS.openapi(BS, async (e) => {
26596
26680
  }
26597
26681
  let v = [];
26598
26682
  if (g !== null) {
26599
- let e = await t.prepare("\n SELECT \n t.contentId as treeNodeId,\n t.treeId,\n t.contentId as id,\n t.parentId,\n t.sortOrder,\n c.title,\n c.slug,\n c.language,\n c.contentType as nodeType,\n c.isHidden,\n c.status,\n c.dataJson,\n c.draftDataJson,\n (\n SELECT path \n FROM node_routes \n WHERE nodeId = c.id AND channelId = ? \n ORDER BY CASE WHEN treeId = t.treeId THEN 0 ELSE 1 END ASC \n LIMIT 1\n ) as materializedPath\n FROM tree_nodes t\n INNER JOIN content_nodes c ON t.contentId = c.id\n WHERE t.treeId = ? AND (c.deletedAt IS NULL OR c.deletedAt = '')\n ORDER BY t.sortOrder ASC\n ").all(c, g);
26683
+ let e = await t.prepare("\n SELECT \n t.contentId as treeNodeId,\n t.treeId,\n t.contentId as id,\n t.parentId,\n t.sortOrder,\n c.title,\n c.slug,\n c.language,\n c.contentType as nodeType,\n c.isHidden,\n c.startShowingAt,\n c.stopShowingAt,\n c.status,\n c.dataJson,\n c.draftDataJson,\n (\n SELECT path \n FROM node_routes \n WHERE nodeId = c.id AND channelId = ? \n ORDER BY CASE WHEN treeId = t.treeId THEN 0 ELSE 1 END ASC \n LIMIT 1\n ) as materializedPath\n FROM tree_nodes t\n INNER JOIN content_nodes c ON t.contentId = c.id\n WHERE t.treeId = ? AND (c.deletedAt IS NULL OR c.deletedAt = '')\n ORDER BY t.sortOrder ASC\n ").all(c, g);
26600
26684
  v = Array.isArray(e) ? e : e?.results || [];
26601
26685
  }
26602
26686
  if ((!v || v.length === 0) && !u) return e.json({ error: `Tree '${n}' not found` }, 404);
@@ -26624,7 +26708,7 @@ MS.openapi(BS, async (e) => {
26624
26708
  return (y.get(n) || []).map((e) => {
26625
26709
  let n = b.get(String(e.id)) || {}, r = {};
26626
26710
  for (let [e, t] of Object.entries(n)) e !== "_isTreeDraft" && e !== "_draftParentId" && e !== "isNew" && e !== "hidden" && e !== "is_hidden" && e !== "isHidden" && e !== "status" && (r[e] = t);
26627
- let i = !o && (e.status === "draft" || e.status === "new"), a = Number(e.isHidden) === 1 || i || n.hidden === !0 || n.hidden === 1 || n.hidden === "1" || n.hidden === "true", s = NS(n.startShowingAt, n.stopShowingAt), c = (e.slug || "").replace(/^\/+|\/+$/g, ""), l = !e.parentId || e.parentId === "null" || e.parentId === "", u = e.materializedPath || (l ? `/${c}` : `${t}/${c}`.replace(/\/+/g, "/")), d = e.language && String(e.language).trim() !== "" ? e.language.trim() : f, p = {
26711
+ let i = !o && (e.status === "draft" || e.status === "new"), a = Number(e.isHidden) === 1 || i || n.hidden === !0 || n.hidden === 1 || n.hidden === "1" || n.hidden === "true", s = PS(e.startShowingAt === void 0 ? n.startShowingAt : e.startShowingAt, e.stopShowingAt === void 0 ? n.stopShowingAt : e.stopShowingAt), c = (e.slug || "").replace(/^\/+|\/+$/g, ""), l = !e.parentId || e.parentId === "null" || e.parentId === "", u = e.materializedPath || (l ? `/${c}` : `${t}/${c}`.replace(/\/+/g, "/")), d = e.language && String(e.language).trim() !== "" ? e.language.trim() : f, p = {
26628
26712
  id: e.id,
26629
26713
  treeNodeId: e.id,
26630
26714
  parentId: e.parentId || null,
@@ -26650,7 +26734,7 @@ MS.openapi(BS, async (e) => {
26650
26734
  ..._,
26651
26735
  items: x(null)
26652
26736
  };
26653
- return !o && !h && (e.header("X-Cache", "MISS"), await PS(p, m, S, 300)), e.json(S, 200);
26737
+ return !o && !h && (e.header("X-Cache", "MISS"), await FS(p, m, S, 300)), e.json(S, 200);
26654
26738
  } catch (t) {
26655
26739
  return console.error("[CMS Public Tree API] Error:", t), e.json({
26656
26740
  error: "Failed to fetch public tree",
@@ -26658,19 +26742,19 @@ MS.openapi(BS, async (e) => {
26658
26742
  }, 500);
26659
26743
  }
26660
26744
  });
26661
- var VS = new $y();
26662
- function HS(e) {
26745
+ var HS = new $y();
26746
+ function US(e) {
26663
26747
  let t = Number(e?.env?.CMS_CHANNEL_CACHE_TTL);
26664
26748
  return Number.isFinite(t) && t >= 60 ? Math.floor(t) : 300;
26665
26749
  }
26666
- async function US(e, t, n, r) {
26750
+ async function WS(e, t, n, r) {
26667
26751
  try {
26668
26752
  await e.set(t, n, r);
26669
26753
  } catch (e) {
26670
26754
  console.warn("[CMS Cache] Failed to write channel response to cache:", e);
26671
26755
  }
26672
26756
  }
26673
- function WS(e, t) {
26757
+ function GS(e, t) {
26674
26758
  let n = {}, r = (e) => {
26675
26759
  if (!e || typeof e != "string") return;
26676
26760
  let n = t?.fieldSets?.[e] || t?.fieldsets?.[e] || t?.definitions?.[e] || t?.channels?.[e] || t?.[e];
@@ -26681,7 +26765,7 @@ function WS(e, t) {
26681
26765
  if (e?.fieldSets && Array.isArray(e.fieldSets) && e.fieldSets.forEach((e) => r(e)), e?.fields && i(e.fields), e?.tabs && typeof e.tabs == "object") for (let t of Object.values(e.tabs)) t?.fields && i(t.fields);
26682
26766
  return n;
26683
26767
  }
26684
- function GS(e, t = {}) {
26768
+ function KS(e, t = {}) {
26685
26769
  let n = {}, r = Object.keys(t).length > 0;
26686
26770
  for (let [i, a] of Object.entries(e)) {
26687
26771
  if (i.endsWith("_meta") || [
@@ -26700,14 +26784,14 @@ function GS(e, t = {}) {
26700
26784
  }
26701
26785
  return n;
26702
26786
  }
26703
- function KS(e) {
26704
- if (Array.isArray(e)) return e.map(KS);
26787
+ function qS(e) {
26788
+ if (Array.isArray(e)) return e.map(qS);
26705
26789
  if (!e || typeof e != "object") return e;
26706
26790
  if (typeof e.id == "string" && e.id.startsWith("ast_") && typeof e.url == "string") {
26707
26791
  let t = e.metadataOverrides || {}, n = e.variants && typeof e.variants == "object" ? e.variants : {}, r = Object.entries(n).find(([, t]) => t?.id === e.id)?.[0], i = r ? {
26708
26792
  ...t,
26709
26793
  ...t.crops?.[r] || {}
26710
- } : t, a = Object.fromEntries(Object.entries(n).filter(([, t]) => t?.id !== e.id).map(([t, n]) => [t, KS({
26794
+ } : t, a = Object.fromEntries(Object.entries(n).filter(([, t]) => t?.id !== e.id).map(([t, n]) => [t, qS({
26711
26795
  ...n,
26712
26796
  title: n?.title ?? e.title ?? "",
26713
26797
  alt: n?.alt ?? e.alt ?? "",
@@ -26721,9 +26805,19 @@ function KS(e) {
26721
26805
  ...Object.keys(a).length > 0 ? { variants: a } : {}
26722
26806
  };
26723
26807
  }
26724
- return Object.fromEntries(Object.entries(e).map(([e, t]) => [e, KS(t)]));
26808
+ return Object.fromEntries(Object.entries(e).map(([e, t]) => [e, qS(t)]));
26725
26809
  }
26726
- async function qS(e, t, n) {
26810
+ async function JS(e, t, n) {
26811
+ let r = t.href.match(/^#node:(.+)$/), i = t.href.match(/^#asset:(.+)$/);
26812
+ if (i) {
26813
+ let t = i[1], n = await e.prepare("SELECT cdnUrl, storageKeyPrivate FROM assets WHERE id = ?").get(t);
26814
+ return n?.cdnUrl || (n?.storageKeyPrivate ? `/media/${n.storageKeyPrivate}` : "#");
26815
+ }
26816
+ if (!r) return t.href;
26817
+ let a = r[1];
26818
+ return (await e.prepare("SELECT path FROM node_routes WHERE nodeId = ? AND channelId = ? AND isCanonical = 1 LIMIT 1").get(Number(a), n))?.path || "#";
26819
+ }
26820
+ async function YS(e, t, n) {
26727
26821
  if (typeof t == "string") {
26728
26822
  if (!t.includes("#node:") && !t.includes("data-node-id") && !t.includes("#asset:") && !t.includes("data-asset-id")) return t;
26729
26823
  let r = /* @__PURE__ */ new Set(), i = /* @__PURE__ */ new Set();
@@ -26756,45 +26850,52 @@ async function qS(e, t, n) {
26756
26850
  return /href\s*=\s*["'][^"']*["']/i.test(d) ? d = d.replace(/href\s*=\s*["'][^"']*["']/i, `href="${u}"`) : d += ` href="${u}"`, `<a ${d}>`;
26757
26851
  });
26758
26852
  }
26759
- if (Array.isArray(t)) return Promise.all(t.map((t) => qS(e, t, n)));
26853
+ if (Array.isArray(t)) return Promise.all(t.map((t) => YS(e, t, n)));
26760
26854
  if (t && typeof t == "object") {
26761
- let r = await Promise.all(Object.entries(t).map(async ([t, r]) => [t, await qS(e, r, n)]));
26855
+ if (typeof t.href == "string" && (t.href.startsWith("#node:") || t.href.startsWith("#asset:"))) {
26856
+ let r = await JS(e, t, n), i = await Promise.all(Object.entries(t).filter(([e]) => e !== "href").map(async ([t, r]) => [t, await YS(e, r, n)]));
26857
+ return {
26858
+ ...Object.fromEntries(i),
26859
+ href: r
26860
+ };
26861
+ }
26862
+ let r = await Promise.all(Object.entries(t).map(async ([t, r]) => [t, await YS(e, r, n)]));
26762
26863
  return Object.fromEntries(r);
26763
26864
  }
26764
26865
  return t;
26765
26866
  }
26766
- var JS = X({ channelParam: J().openapi({ description: "The ID or key (slug) of the requested channel" }) }), YS = X({ preview: lv(["true", "false"]).optional().openapi({ description: "Set to true to retrieve unpublished draft data" }) }), XS = X({
26867
+ var XS = X({ channelParam: J().openapi({ description: "The ID or key (slug) of the requested channel" }) }), ZS = X({ preview: lv(["true", "false"]).optional().openapi({ description: "Set to true to retrieve unpublished draft data" }) }), QS = X({
26767
26868
  error: J(),
26768
26869
  details: J().optional()
26769
- }).openapi("ErrorResponse"), ZS = X({
26870
+ }).openapi("ErrorResponse"), $S = X({
26770
26871
  id: G_([c_(), J()]),
26771
26872
  key: J()
26772
- }).catchall(k_()).openapi("ChannelResponse"), QS = eb({
26873
+ }).catchall(k_()).openapi("ChannelResponse"), eC = eb({
26773
26874
  method: "get",
26774
26875
  path: "/{channelParam}",
26775
26876
  summary: "Fetch CMS Channel Settings",
26776
26877
  description: "Retrieves the fully hydrated, public-facing settings and payload for a specific CMS channel.",
26777
26878
  tags: ["Public Channel API"],
26778
26879
  request: {
26779
- params: JS,
26780
- query: YS
26880
+ params: XS,
26881
+ query: ZS
26781
26882
  },
26782
26883
  responses: {
26783
26884
  200: {
26784
26885
  description: "Fully hydrated CMS Channel payload",
26785
- content: { "application/json": { schema: ZS } }
26886
+ content: { "application/json": { schema: $S } }
26786
26887
  },
26787
26888
  404: {
26788
26889
  description: "Channel not found or inactive",
26789
- content: { "application/json": { schema: XS } }
26890
+ content: { "application/json": { schema: QS } }
26790
26891
  },
26791
26892
  500: {
26792
26893
  description: "Server error during hydration",
26793
- content: { "application/json": { schema: XS } }
26894
+ content: { "application/json": { schema: QS } }
26794
26895
  }
26795
26896
  }
26796
26897
  });
26797
- VS.openapi(QS, async (e) => {
26898
+ HS.openapi(eC, async (e) => {
26798
26899
  try {
26799
26900
  let t = e.get("db"), { channelParam: n } = e.req.valid("param"), { preview: r } = e.req.valid("query"), i = r === "true", a = e.req.header("x-bypass-cache") === "true", o = `channel:${n}:${i ? "preview" : "live"}`, s = $b(e);
26800
26901
  if (!i && !a) {
@@ -26805,23 +26906,23 @@ VS.openapi(QS, async (e) => {
26805
26906
  if (!c) return e.json({ error: `Channel '${n}' not found` }, 404);
26806
26907
  let l = c.status === "disabled" || c.status === "inactive" || c.isEnabled === 0 || c.isEnabled === !1;
26807
26908
  if (!i && l) return e.json({ error: `Channel '${c.key || n}' is currently inactive` }, 404);
26808
- let u = Number(c.id), d = e.env?.BUNDLED_DEFINITIONS, f = px(d), p = c.channelType || c.key || "website", m = WS(f.channels?.[p] || f.channels?.[c.key] || f.channels?.website || f.definitions?.["channel-base"] || {}, f), h = {}, g = i && c.draftDataJson || c.dataJson;
26909
+ let u = Number(c.id), d = e.env?.BUNDLED_DEFINITIONS, f = px(d), p = c.channelType || c.key || "website", m = GS(f.channels?.[p] || f.channels?.[c.key] || f.channels?.website || f.definitions?.["channel-base"] || {}, f), h = {}, g = i && c.draftDataJson || c.dataJson;
26809
26910
  if (g) try {
26810
26911
  h = typeof g == "string" ? JSON.parse(g) : g;
26811
26912
  } catch (e) {
26812
26913
  console.warn("[CMS Public Channel API] Failed to parse channel dataJson:", e);
26813
26914
  }
26814
- let _ = GS({
26915
+ let _ = KS({
26815
26916
  ...h,
26816
26917
  ...c
26817
26918
  }, m);
26818
- _ = await fx(t, _), _ = KS(_), _ = await qS(t, _, u);
26919
+ _ = await fx(t, _), _ = qS(_), _ = await YS(t, _, u);
26819
26920
  let v = {
26820
26921
  id: c.id,
26821
26922
  key: c.key,
26822
26923
  ..._
26823
26924
  };
26824
- return !i && !a && (e.header("X-Cache", "MISS"), await US(s, o, v, HS(e))), e.json(v, 200);
26925
+ return !i && !a && (e.header("X-Cache", "MISS"), await WS(s, o, v, US(e))), e.json(v, 200);
26825
26926
  } catch (t) {
26826
26927
  return console.error("[CMS Public Channel API] Error:", t), e.json({
26827
26928
  error: "Failed to fetch public channel",
@@ -26829,8 +26930,8 @@ VS.openapi(QS, async (e) => {
26829
26930
  }, 500);
26830
26931
  }
26831
26932
  });
26832
- var $S = new $y();
26833
- function eC(e, t) {
26933
+ var tC = new $y();
26934
+ function nC(e, t) {
26834
26935
  if (t === "webp") return "image/webp";
26835
26936
  if (t === "avif") return "image/avif";
26836
26937
  if (t === "jpeg" || t === "jpg") return "image/jpeg";
@@ -26839,7 +26940,7 @@ function eC(e, t) {
26839
26940
  let n = e.toLowerCase();
26840
26941
  return n.endsWith(".jpg") || n.endsWith(".jpeg") ? "image/jpeg" : n.endsWith(".png") ? "image/png" : n.endsWith(".webp") ? "image/webp" : n.endsWith(".gif") ? "image/gif" : n.endsWith(".svg") ? "image/svg+xml" : n.endsWith(".pdf") ? "application/pdf" : n.endsWith(".mp4") ? "video/mp4" : "application/octet-stream";
26841
26942
  }
26842
- var tC = [
26943
+ var rC = [
26843
26944
  320,
26844
26945
  640,
26845
26946
  768,
@@ -26849,10 +26950,10 @@ var tC = [
26849
26950
  2560,
26850
26951
  3840
26851
26952
  ];
26852
- function nC(e) {
26853
- if (!(!e || isNaN(e) || e <= 0)) return tC.reduce((t, n) => Math.abs(n - e) < Math.abs(t - e) ? n : t);
26953
+ function iC(e) {
26954
+ if (!(!e || isNaN(e) || e <= 0)) return rC.reduce((t, n) => Math.abs(n - e) < Math.abs(t - e) ? n : t);
26854
26955
  }
26855
- var rC = eb({
26956
+ var aC = eb({
26856
26957
  method: "get",
26857
26958
  path: "/*",
26858
26959
  summary: "Serve & Optimize Media Assets",
@@ -26912,11 +27013,11 @@ var rC = eb({
26912
27013
  }
26913
27014
  }
26914
27015
  });
26915
- $S.openapi(rC, async (e) => {
27016
+ tC.openapi(aC, async (e) => {
26916
27017
  try {
26917
27018
  let t = e.req.path.replace(/^\/media\//, "").replace(/^\//, "");
26918
27019
  if (!t) return e.text("Asset key missing", 400);
26919
- let { w: n, h: r, q: i, f: a } = e.req.valid("query"), o = !!(n || r || i || a), s = nC(n ? parseInt(n, 10) : void 0), c = e.req.header("Accept") || "", l = "";
27020
+ let { w: n, h: r, q: i, f: a } = e.req.valid("query"), o = !!(n || r || i || a), s = iC(n ? parseInt(n, 10) : void 0), c = e.req.header("Accept") || "", l = "";
26920
27021
  if (o) {
26921
27022
  let e = !a || a === "auto";
26922
27023
  a === "avif" || e && c.includes("image/avif") ? l = "avif" : a === "webp" || e && c.includes("image/webp") ? l = "webp" : a === "jpeg" || a === "jpg" ? l = "jpeg" : a === "png" && (l = "png");
@@ -26935,7 +27036,7 @@ $S.openapi(rC, async (e) => {
26935
27036
  if (!h) return e.text(`Asset not found: ${t}`, 404);
26936
27037
  if (!o) {
26937
27038
  let n = e.body(h, 200, {
26938
- "Content-Type": eC(t),
27039
+ "Content-Type": nC(t),
26939
27040
  "Cache-Control": "public, max-age=31536000, immutable"
26940
27041
  });
26941
27042
  return u && f && e.executionCtx?.waitUntil && e.executionCtx.waitUntil(u.put(f, n.clone())), n;
@@ -26949,7 +27050,7 @@ $S.openapi(rC, async (e) => {
26949
27050
  key: t,
26950
27051
  env: e.env,
26951
27052
  req: e.req.raw
26952
- }), v = eC(t, l), y = e.body(_, 200, {
27053
+ }), v = nC(t, l), y = e.body(_, 200, {
26953
27054
  "Content-Type": v,
26954
27055
  "Cache-Control": "public, max-age=31536000, immutable"
26955
27056
  });
@@ -26958,8 +27059,8 @@ $S.openapi(rC, async (e) => {
26958
27059
  return console.error("❌ [Public Assets Error]:", t), e.text("Internal Server Error", 500);
26959
27060
  }
26960
27061
  });
26961
- var iC = new $y();
26962
- function aC(e, t) {
27062
+ var oC = new $y();
27063
+ function sC(e, t) {
26963
27064
  let n = /* @__PURE__ */ new Date();
26964
27065
  if (e && String(e).trim() !== "") {
26965
27066
  let t = new Date(e);
@@ -26971,31 +27072,31 @@ function aC(e, t) {
26971
27072
  }
26972
27073
  return !0;
26973
27074
  }
26974
- var oC = X({
27075
+ var cC = X({
26975
27076
  channelId: J().optional().openapi({ description: "Optional channel ID/key to filter and resolve root paths for" }),
26976
27077
  channel: J().optional().openapi({ description: "Legacy alias for channelId" })
26977
- }), sC = z_(J()).openapi("PathsResponse"), cC = X({
27078
+ }), lC = z_(J()).openapi("PathsResponse"), uC = X({
26978
27079
  error: J(),
26979
27080
  details: J().optional()
26980
- }).openapi("ErrorResponse"), lC = eb({
27081
+ }).openapi("ErrorResponse"), dC = eb({
26981
27082
  method: "get",
26982
27083
  path: "/",
26983
27084
  summary: "Fetch All Public Paths",
26984
27085
  description: "Retrieves a deduplicated array of all active, published node paths leveraging the $O(1)$ node_routes table. Includes both tree-bound and standalone pages.",
26985
27086
  tags: ["Public Paths API"],
26986
- request: { query: oC },
27087
+ request: { query: cC },
26987
27088
  responses: {
26988
27089
  200: {
26989
27090
  description: "Array of valid public URL paths",
26990
- content: { "application/json": { schema: sC } }
27091
+ content: { "application/json": { schema: lC } }
26991
27092
  },
26992
27093
  500: {
26993
27094
  description: "Server error fetching paths",
26994
- content: { "application/json": { schema: cC } }
27095
+ content: { "application/json": { schema: uC } }
26995
27096
  }
26996
27097
  }
26997
27098
  });
26998
- iC.openapi(lC, async (e) => {
27099
+ oC.openapi(dC, async (e) => {
26999
27100
  try {
27000
27101
  let t = e.get("db"), n = e.req.valid("query"), r = n.channelId || n.channel, i = "", a = [];
27001
27102
  if (r && r !== "all") {
@@ -27006,7 +27107,8 @@ iC.openapi(lC, async (e) => {
27006
27107
  SELECT
27007
27108
  nr.path,
27008
27109
  cn.contentType as nodeType,
27009
- cn.dataJson
27110
+ cn.startShowingAt,
27111
+ cn.stopShowingAt
27010
27112
  FROM node_routes nr
27011
27113
  INNER JOIN content_nodes cn ON nr.nodeId = cn.id
27012
27114
  WHERE nr.isCanonical = 1
@@ -27015,27 +27117,19 @@ iC.openapi(lC, async (e) => {
27015
27117
  ${i}
27016
27118
  ORDER BY nr.path ASC
27017
27119
  `).all(...a), s = Array.isArray(o) ? o : o?.results || [], c = [];
27018
- for (let e of s) {
27019
- if (e.nodeType === "external-link" || !e.path) continue;
27020
- let t = !0;
27021
- if (e.dataJson) try {
27022
- let n = typeof e.dataJson == "string" ? JSON.parse(e.dataJson) : e.dataJson;
27023
- t = aC(n?.startShowingAt, n?.stopShowingAt);
27024
- } catch {}
27025
- t && c.push(e.path);
27026
- }
27120
+ for (let e of s) e.nodeType !== "external-link" && e.path && sC(e.startShowingAt, e.stopShowingAt) && c.push(e.path);
27027
27121
  let l = [...new Set(c)];
27028
27122
  return e.json(l, 200);
27029
27123
  } catch (t) {
27030
27124
  return console.error("[CMS Paths API] Error:", t), e.json({ error: "Failed to fetch paths" }, 500);
27031
27125
  }
27032
27126
  });
27033
- var uC = new $y();
27034
- function dC(e) {
27127
+ var fC = new $y();
27128
+ function pC(e) {
27035
27129
  let t = (e || "").trim().toLowerCase(), n = px()?.taxonomies || {};
27036
27130
  return n[t] ? t : n[`${t}s`] ? `${t}s` : t.endsWith("s") && n[t.slice(0, -1)] ? t.slice(0, -1) : t;
27037
27131
  }
27038
- var fC = X({
27132
+ var mC = X({
27039
27133
  id: c_(),
27040
27134
  taxonomy: J(),
27041
27135
  key: J(),
@@ -27045,14 +27139,14 @@ var fC = X({
27045
27139
  data: tv(k_()),
27046
27140
  createdAt: J(),
27047
27141
  updatedAt: J()
27048
- }), pC = X({
27142
+ }), hC = X({
27049
27143
  taxonomy: J(),
27050
- items: z_(fC),
27144
+ items: z_(mC),
27051
27145
  total: c_()
27052
- }).openapi("TaxonomyResponse"), mC = X({
27146
+ }).openapi("TaxonomyResponse"), gC = X({
27053
27147
  error: J(),
27054
27148
  details: J().optional()
27055
- }).openapi("ErrorResponse"), hC = eb({
27149
+ }).openapi("ErrorResponse"), _C = eb({
27056
27150
  method: "get",
27057
27151
  path: "/{taxonomy}",
27058
27152
  summary: "Fetch Public Taxonomy Terms",
@@ -27062,17 +27156,17 @@ var fC = X({
27062
27156
  responses: {
27063
27157
  200: {
27064
27158
  description: "List of taxonomy terms",
27065
- content: { "application/json": { schema: pC } }
27159
+ content: { "application/json": { schema: hC } }
27066
27160
  },
27067
27161
  500: {
27068
27162
  description: "Server error",
27069
- content: { "application/json": { schema: mC } }
27163
+ content: { "application/json": { schema: gC } }
27070
27164
  }
27071
27165
  }
27072
27166
  });
27073
- uC.openapi(hC, async (e) => {
27167
+ fC.openapi(_C, async (e) => {
27074
27168
  try {
27075
- let t = e.get("db"), n = $b(e), r = e.req.valid("param").taxonomy, i = dC(r), a = `taxonomy:public:${i}`, o = e.req.header("x-bypass-cache") === "true";
27169
+ let t = e.get("db"), n = $b(e), r = e.req.valid("param").taxonomy, i = pC(r), a = `taxonomy:public:${i}`, o = e.req.header("x-bypass-cache") === "true";
27076
27170
  if (!o) {
27077
27171
  let t = await n.get(a);
27078
27172
  if (t) return e.header("X-Cache", "HIT"), e.json(t);
@@ -27106,7 +27200,7 @@ uC.openapi(hC, async (e) => {
27106
27200
  return console.error("[Public Taxonomy API] Error fetching terms:", t), e.json({ error: "Failed to fetch taxonomy terms" }, 500);
27107
27201
  }
27108
27202
  });
27109
- var $ = new $y(), gC = !1;
27203
+ var $ = new $y(), vC = !1;
27110
27204
  $.use("*", t()), $.use("/media/*", t({
27111
27205
  origin: "*",
27112
27206
  allowMethods: [
@@ -27127,20 +27221,20 @@ $.use("*", t()), $.use("/media/*", t({
27127
27221
  let n = new URL(e.req.url), r = (e.req.header("host") || n.hostname).split(":")[0];
27128
27222
  e.set("currentDomain", r);
27129
27223
  let i = wb(e);
27130
- if (e.set("db", i), !gC) try {
27131
- await Mb(i), gC = !0;
27224
+ if (e.set("db", i), !vC) try {
27225
+ await Mb(i), vC = !0;
27132
27226
  } catch (e) {
27133
27227
  console.error("❌ [CMS Server] Failed to initialize system tables on cold start:", e);
27134
27228
  }
27135
27229
  await t();
27136
- }), $.route("/media", $S), $.use("/media/*", Pb()), $.route("/api/cms/nodes", gx), $.route("/api/cms/nodes.json", gx), $.route("/api/cms/formcsv", gx), $.route("/api/cms/formcsv.json", gx), $.route("/api/cms/stats", rS), $.route("/api/cms/stats.json", rS), $.route("/api/cms", Dx), $.route("/api/cms/trees.json", Dx), $.route("/api/cms/channels", jx), $.route("/api/cms/channels.json", jx), $.route("/api/cms/taxonomies", Mx), $.route("/api/cms/taxonomies.json", Mx), $.route("/api/cms/schemas", Qx), $.route("/api/cms/schemas.json", Qx), $.route("/api/cms", eS), $.route("/api/admin/assets", iS), $.use("/api/v1/*", async (e, t) => {
27230
+ }), $.route("/media", tC), $.use("/media/*", Pb()), $.route("/api/cms/nodes", gx), $.route("/api/cms/nodes.json", gx), $.route("/api/cms/formcsv", gx), $.route("/api/cms/formcsv.json", gx), $.route("/api/cms/stats", iS), $.route("/api/cms/stats.json", iS), $.route("/api/cms", Ox), $.route("/api/cms/trees.json", Ox), $.route("/api/cms/channels", Mx), $.route("/api/cms/channels.json", Mx), $.route("/api/cms/taxonomies", Nx), $.route("/api/cms/taxonomies.json", Nx), $.route("/api/cms/schemas", $x), $.route("/api/cms/schemas.json", $x), $.route("/api/cms", tS), $.route("/api/admin/assets", aS), $.use("/api/v1/*", async (e, t) => {
27137
27231
  let n = e.env?.FRONTEND_API_SECRET;
27138
27232
  if (n) {
27139
27233
  let t = e.req.header("Authorization"), r = e.req.header("x-api-key"), i = t?.startsWith("Bearer ") ? t.substring(7).trim() : r?.trim();
27140
27234
  if (!i || i !== n) return e.json({ error: "Unauthorized: Invalid or missing API secret." }, 401);
27141
27235
  } else console.warn("⚠️ [CMS Security] FRONTEND_API_SECRET is not set in .env. The API is completely exposed to the public.");
27142
27236
  return t();
27143
- }), $.route("/api/v1/node", cS), $.route("/api/v1/nodes", OS), $.route("/api/v1/tree", MS), $.route("/api/v1/channel", VS), $.route("/api/v1/all-paths", iC), $.route("/api/v1/taxonomies", uC), $.doc("/api/openapi.json", {
27237
+ }), $.route("/api/v1/node", lS), $.route("/api/v1/nodes", kS), $.route("/api/v1/tree", NS), $.route("/api/v1/channel", HS), $.route("/api/v1/all-paths", oC), $.route("/api/v1/taxonomies", fC), $.doc("/api/openapi.json", {
27144
27238
  openapi: "3.0.0",
27145
27239
  info: {
27146
27240
  title: "KAMA Engine Public API",
@@ -27159,4 +27253,4 @@ $.use("*", t()), $.use("/media/*", t({
27159
27253
  return t();
27160
27254
  });
27161
27255
  //#endregion
27162
- export { Yx as compileDefinitions };
27256
+ export { Xx as compileDefinitions };