@clarify-labs/cli 0.11.11 → 0.11.14

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.
@@ -773,6 +773,8 @@ function buildNavigationFromConfig(routes, config) {
773
773
  title: resolveLocalizedText(item.group, "", "") ?? "",
774
774
  icon: item.icon,
775
775
  layout: item.layout,
776
+ visible: item.visible,
777
+ searchable: item.searchable,
776
778
  children
777
779
  };
778
780
  }
@@ -802,6 +804,8 @@ function buildNavigationFromConfig(routes, config) {
802
804
  path: children[0]?.path ?? "/",
803
805
  title: resolveLocalizedText(group.group, "", "") ?? "",
804
806
  icon: group.icon,
807
+ visible: group.visible,
808
+ searchable: group.searchable,
805
809
  children
806
810
  };
807
811
  });
@@ -827,6 +831,8 @@ function buildLocalizedNavigationForLocale(routes, config, locale, locales) {
827
831
  title: resolveLocalizedText(item.group, locale, locales.default) ?? "",
828
832
  icon: item.icon,
829
833
  layout: item.layout,
834
+ visible: item.visible,
835
+ searchable: item.searchable,
830
836
  children
831
837
  };
832
838
  }
@@ -847,6 +853,8 @@ function buildLocalizedNavigationForLocale(routes, config, locale, locales) {
847
853
  path: children[0]?.path ?? localizedRoutePath("/", locale, locales),
848
854
  title: resolveLocalizedText(group.group, locale, locales.default) ?? "",
849
855
  icon: group.icon,
856
+ visible: group.visible,
857
+ searchable: group.searchable,
850
858
  children
851
859
  };
852
860
  });
@@ -1141,12 +1149,19 @@ var clarifyPagesItemSchema = zod.z.lazy(() => zod.z.union([
1141
1149
  filter: zod.z.object({ tags: zod.z.array(zod.z.string()).optional() }).strict().optional()
1142
1150
  }).strict()
1143
1151
  ]));
1144
- var clarifyPagesGroupSchema = zod.z.lazy(() => zod.z.object({
1152
+ var clarifyPagesGroupShape = {
1145
1153
  group: clarifyLocalizedTextSchema,
1146
1154
  icon: zod.z.string().optional(),
1155
+ visible: zod.z.enum([
1156
+ "always",
1157
+ "active",
1158
+ "never"
1159
+ ]).optional(),
1160
+ searchable: zod.z.boolean().optional(),
1147
1161
  layout: zod.z.enum(["documentation", "blog"]).optional(),
1148
1162
  pages: zod.z.array(clarifyPagesItemSchema)
1149
- }).strict());
1163
+ };
1164
+ var clarifyPagesGroupSchema = zod.z.lazy(() => zod.z.object(clarifyPagesGroupShape).strict());
1150
1165
  var clarifyPagesConfigSchema = zod.z.union([zod.z.array(clarifyPagesGroupSchema), zod.z.literal("FileTree")]);
1151
1166
  var clarifyTabItemSchema = zod.z.object({
1152
1167
  tab: clarifyLocalizedTextSchema,
@@ -1473,6 +1488,7 @@ function routeToRuntimeManifestEntry(route, component, mode) {
1473
1488
  if (route.locale) entry.locale = route.locale;
1474
1489
  if (route.isFallback) entry.isFallback = true;
1475
1490
  if (route.isBareAlias) entry.isBareAlias = true;
1491
+ if (route.searchable === false) entry.searchable = false;
1476
1492
  if (route.alternates) entry.alternates = route.alternates;
1477
1493
  if (route.meta.description) entry.description = route.meta.description;
1478
1494
  if (route.meta.keywords?.length) entry.keywords = route.meta.keywords;
@@ -1804,7 +1820,7 @@ function createViteAdapter(engine) {
1804
1820
  }
1805
1821
  var cliPackageVersion = {
1806
1822
  name: "@clarify-labs/cli",
1807
- version: "0.11.11",
1823
+ version: "0.11.14",
1808
1824
  license: "AGPL-3.0-only",
1809
1825
  type: "module",
1810
1826
  repository: {
@@ -1880,6 +1896,9 @@ var cliPackageVersion = {
1880
1896
  }
1881
1897
  }.version ?? "0.0.0";
1882
1898
  var cliPackageVersionWithCaret = `^${cliPackageVersion}`;
1899
+ function printCliVersion() {
1900
+ console.error(`[clarify] v${cliPackageVersion}`);
1901
+ }
1883
1902
  //#endregion
1884
1903
  //#region source/core/config/options.ts
1885
1904
  function resolveBuildOptions(options = {}) {
@@ -1927,6 +1946,49 @@ function readRouteArtifactContent(route) {
1927
1946
  const content = readRouteContent(route);
1928
1947
  return shouldUseUtf8Signature(route) ? withUtf8Signature(content) : content;
1929
1948
  }
1949
+ function mergeOpenAPIRecord(target, source, section, filePath) {
1950
+ if (!source) return;
1951
+ for (const [key, value] of Object.entries(source)) {
1952
+ const existing = target[key];
1953
+ if (existing !== void 0 && JSON.stringify(existing) !== JSON.stringify(value)) throw new Error(`[clarify] Cannot aggregate OpenAPI specs: conflicting ${section} entry "${key}" in ${filePath}.`);
1954
+ target[key] = value;
1955
+ }
1956
+ }
1957
+ function createRootOpenAPISpec(routes, projectConfig) {
1958
+ const paths = {};
1959
+ const webhooks = {};
1960
+ const components = {};
1961
+ const tags = /* @__PURE__ */ new Map();
1962
+ const defaultLocale = projectConfig.locales?.default;
1963
+ for (const route of routes) {
1964
+ if (route.kind !== "openapi" || route.diagnostic || !route.source.content || defaultLocale && route.locale && route.locale !== defaultLocale) continue;
1965
+ const filePath = route.source.filePath;
1966
+ const spec = JSON.parse(route.source.content);
1967
+ mergeOpenAPIRecord(paths, spec.paths, "paths", filePath);
1968
+ mergeOpenAPIRecord(webhooks, "webhooks" in spec ? spec.webhooks : void 0, "webhooks", filePath);
1969
+ for (const [section, entries] of Object.entries(spec.components ?? {})) {
1970
+ components[section] ??= {};
1971
+ mergeOpenAPIRecord(components[section], entries, `components.${section}`, filePath);
1972
+ }
1973
+ for (const tag of spec.tags ?? []) {
1974
+ const existing = tags.get(tag.name);
1975
+ if (existing !== void 0 && JSON.stringify(existing) !== JSON.stringify(tag)) throw new Error(`[clarify] Cannot aggregate OpenAPI specs: conflicting tag "${tag.name}" in ${filePath}.`);
1976
+ tags.set(tag.name, tag);
1977
+ }
1978
+ }
1979
+ return {
1980
+ openapi: "3.1.0",
1981
+ info: {
1982
+ title: projectConfig.title,
1983
+ description: projectConfig.description,
1984
+ version: "1.0.0"
1985
+ },
1986
+ paths,
1987
+ ...Object.keys(webhooks).length > 0 ? { webhooks } : {},
1988
+ ...Object.keys(components).length > 0 ? { components } : {},
1989
+ ...tags.size > 0 ? { tags: [...tags.values()] } : {}
1990
+ };
1991
+ }
1930
1992
  function isLlmsTxtRoute(route) {
1931
1993
  return !route.path.split("/").includes("404");
1932
1994
  }
@@ -2026,6 +2088,14 @@ function serveContentArtifacts(req, res, projectConfig, routes) {
2026
2088
  res.end(createLlmsTxtArtifact(routes, projectConfig), "utf8");
2027
2089
  return true;
2028
2090
  }
2091
+ if (contentPath === "/openapi.json" || contentPath === "/openapi.yml") {
2092
+ const spec = createRootOpenAPISpec(routes, projectConfig);
2093
+ const isJson = contentPath.endsWith(".json");
2094
+ res.statusCode = 200;
2095
+ res.setHeader("Content-Type", isJson ? "application/json; charset=utf-8" : "text/yaml; charset=utf-8");
2096
+ res.end(isJson ? JSON.stringify(spec, null, 2) : (0, yaml.stringify)(spec, { lineWidth: 0 }), "utf8");
2097
+ return true;
2098
+ }
2029
2099
  if (contentPath.endsWith(".openapi.yaml")) {
2030
2100
  const jsonPath = contentPath.replace(/\.yaml$/, ".json");
2031
2101
  const route = routes.find((route) => route.artifacts?.contentArtifactUrl === jsonPath);
@@ -2085,6 +2155,14 @@ function createContentArtifactsPlugin() {
2085
2155
  fileName: "llms.txt",
2086
2156
  source: createLlmsTxtArtifact(ctx.routes, ctx.projectConfig)
2087
2157
  });
2158
+ const rootOpenAPISpec = createRootOpenAPISpec(ctx.routes, ctx.projectConfig);
2159
+ assets.push({
2160
+ fileName: "openapi.json",
2161
+ source: JSON.stringify(rootOpenAPISpec, null, 2)
2162
+ }, {
2163
+ fileName: "openapi.yml",
2164
+ source: (0, yaml.stringify)(rootOpenAPISpec, { lineWidth: 0 })
2165
+ });
2088
2166
  return assets;
2089
2167
  }
2090
2168
  }
@@ -2312,7 +2390,7 @@ function routeSearchContent(route) {
2312
2390
  * Convert a `ContentRoute` into the document shape stored in the Orama index.
2313
2391
  */
2314
2392
  function routeToSearchDocument(route, defaultLocale) {
2315
- if (route.isBareAlias) return null;
2393
+ if (route.isBareAlias || route.searchable === false) return null;
2316
2394
  const content = routeSearchContent(route);
2317
2395
  if (!content.trim()) return null;
2318
2396
  return {
@@ -2375,7 +2453,7 @@ function collectIndexedLocales(routes, defaultLocale) {
2375
2453
  const seen = /* @__PURE__ */ new Set();
2376
2454
  const locales = [];
2377
2455
  for (const route of routes) {
2378
- if (route.isBareAlias) continue;
2456
+ if (route.isBareAlias || route.searchable === false) continue;
2379
2457
  const code = route.locale ?? defaultLocale ?? "en";
2380
2458
  if (!seen.has(code)) {
2381
2459
  seen.add(code);
@@ -3005,7 +3083,7 @@ async function generateDevSearchIndex(ctx, root, pagefind) {
3005
3083
  try {
3006
3084
  let pageCount = 0;
3007
3085
  for (const route of ctx.routes) {
3008
- if (route.isBareAlias) continue;
3086
+ if (route.isBareAlias || route.searchable === false) continue;
3009
3087
  const content = routeSearchContent(route);
3010
3088
  if (!content.trim()) continue;
3011
3089
  const result = await index.addCustomRecord({
@@ -3465,6 +3543,38 @@ function handleRouteConflicts(routes, development) {
3465
3543
  assertNoRouteConflicts(routes);
3466
3544
  return routes;
3467
3545
  }
3546
+ function unsearchablePaths(navigation) {
3547
+ const paths = /* @__PURE__ */ new Set();
3548
+ const visit = (nodes, inherited = true) => {
3549
+ for (const node of nodes) {
3550
+ const searchable = inherited && node.searchable !== false;
3551
+ if (!searchable) paths.add(node.path);
3552
+ visit(node.children ?? [], searchable);
3553
+ }
3554
+ };
3555
+ switch (navigation.kind) {
3556
+ case "flat":
3557
+ visit(navigation.nodes);
3558
+ break;
3559
+ case "tabbed":
3560
+ navigation.tabs.forEach((tab) => visit(tab.children));
3561
+ break;
3562
+ case "localized":
3563
+ Object.values(navigation.locales).forEach((nodes) => visit(nodes));
3564
+ break;
3565
+ case "localized-tabbed":
3566
+ Object.values(navigation.locales).forEach((locale) => locale.tabs.forEach((tab) => visit(tab.children)));
3567
+ break;
3568
+ }
3569
+ return paths;
3570
+ }
3571
+ function applySearchability(routes, navigation) {
3572
+ const excludedPaths = unsearchablePaths(navigation);
3573
+ return routes.map((route) => excludedPaths.has(route.path) ? {
3574
+ ...route,
3575
+ searchable: false
3576
+ } : route);
3577
+ }
3468
3578
  async function resolveRouteState(routes, plugins, ctx, development) {
3469
3579
  const tabs = ctx.projectConfig.navigation?.tabs;
3470
3580
  const configuredRoutes = applyConfiguredPageRoutePaths(routes, tabs, ctx.projectConfig.locales);
@@ -3472,10 +3582,11 @@ async function resolveRouteState(routes, plugins, ctx, development) {
3472
3582
  routes: configuredRoutes,
3473
3583
  navigation: buildNavigationTree(configuredRoutes, ctx)
3474
3584
  }, ctx);
3475
- const finalRoutes = handleRouteConflicts(resolved.routes, development);
3585
+ const conflictRoutes = handleRouteConflicts(resolved.routes, development);
3586
+ const finalNavigation = conflictRoutes === resolved.routes ? resolved.navigation : buildNavigationTree(conflictRoutes, ctx);
3476
3587
  return {
3477
- routes: finalRoutes,
3478
- navigation: finalRoutes === resolved.routes ? resolved.navigation : buildNavigationTree(finalRoutes, ctx)
3588
+ routes: applySearchability(conflictRoutes, finalNavigation),
3589
+ navigation: finalNavigation
3479
3590
  };
3480
3591
  }
3481
3592
  //#endregion
@@ -3587,7 +3698,7 @@ function injectSSRIntoTemplate(template, appHtml, contextOrConfig, route) {
3587
3698
  html = setNamedMeta(html, "description", route?.meta.description ?? projectConfig.description);
3588
3699
  html = setNamedMeta(html, "keywords", route?.meta.keywords?.join(", "));
3589
3700
  html = injectCanonicalUrl(html, contextOrConfig, route);
3590
- const dataPagefindIgnore = route?.isBareAlias ? " data-pagefind-ignore" : "";
3701
+ const dataPagefindIgnore = route?.isBareAlias || route?.searchable === false ? " data-pagefind-ignore" : "";
3591
3702
  html = html.replace(/<div id="root">([\s\S]*?)<\/div>/, `<div id="root"${dataPagefindIgnore}>${appHtml}</div>`);
3592
3703
  return html;
3593
3704
  }
@@ -4096,7 +4207,7 @@ var ClarifyEngine = class {
4096
4207
  assertNoContentDiagnostics(this.routes);
4097
4208
  const outputDir = this.runtime.outputDirectory ?? this.generateOptions.outputDirectory;
4098
4209
  if (!outputDir) throw new Error("[clarify] outputDirectory is required before SSG runs");
4099
- const ssrOutputDir = (0, node_path.join)(outputDir, ".ssr");
4210
+ const ssrOutputDir = createClarifyTempDir("ssr-output");
4100
4211
  let tempEntryPath;
4101
4212
  try {
4102
4213
  tempEntryPath = createTempEntryFile(SSR_ENTRY_CODE);
@@ -4112,6 +4223,7 @@ var ClarifyEngine = class {
4112
4223
  console.error("[clarify] SSG failed:", err);
4113
4224
  throw err;
4114
4225
  } finally {
4226
+ removeClarifyTempDir(ssrOutputDir);
4115
4227
  if (tempEntryPath) try {
4116
4228
  (0, node_fs.rmSync)(tempEntryPath, { force: true });
4117
4229
  } catch {}
@@ -4212,6 +4324,12 @@ Object.defineProperty(exports, "findRouteConflicts", {
4212
4324
  return findRouteConflicts;
4213
4325
  }
4214
4326
  });
4327
+ Object.defineProperty(exports, "printCliVersion", {
4328
+ enumerable: true,
4329
+ get: function() {
4330
+ return printCliVersion;
4331
+ }
4332
+ });
4215
4333
  Object.defineProperty(exports, "searchMcpIndex", {
4216
4334
  enumerable: true,
4217
4335
  get: function() {
@@ -4219,4 +4337,4 @@ Object.defineProperty(exports, "searchMcpIndex", {
4219
4337
  }
4220
4338
  });
4221
4339
 
4222
- //# sourceMappingURL=engine-BzxBO-E9.cjs.map
4340
+ //# sourceMappingURL=engine-CkWY8FUi.cjs.map