@clarify-labs/cli 0.6.7 → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/output/cli.cjs +5 -4
- package/output/cli.cjs.map +1 -1
- package/output/cli.js +5 -4
- package/output/cli.js.map +1 -1
- package/output/core/config-schema.d.ts +13 -4
- package/output/core/search-language.d.ts +1 -0
- package/output/core/ssg.d.ts +1 -1
- package/output/core/temp-dir.d.ts +2 -0
- package/output/core/virtual-modules.d.ts +8 -1
- package/output/index.cjs +1 -1
- package/output/index.js +1 -1
- package/output/{plugin-Cx9lFenc.js → plugin-BNzlJ4o7.js} +337 -92
- package/output/plugin-BNzlJ4o7.js.map +1 -0
- package/output/{plugin-hJcy-YdO.cjs → plugin-dzXRzjdX.cjs} +341 -90
- package/output/plugin-dzXRzjdX.cjs.map +1 -0
- package/output/plugins/openapi/virtual-modules.d.ts +1 -1
- package/output/plugins/search-index/index.d.ts +2 -0
- package/output/types.d.ts +3 -1
- package/package.json +5 -3
- package/output/plugin-Cx9lFenc.js.map +0 -1
- package/output/plugin-hJcy-YdO.cjs.map +0 -1
|
@@ -40,9 +40,9 @@ let gray_matter = require("gray-matter");
|
|
|
40
40
|
gray_matter = __toESM(gray_matter, 1);
|
|
41
41
|
let _apidevtools_swagger_parser = require("@apidevtools/swagger-parser");
|
|
42
42
|
_apidevtools_swagger_parser = __toESM(_apidevtools_swagger_parser, 1);
|
|
43
|
+
let node_os = require("node:os");
|
|
43
44
|
let node_fs_promises = require("node:fs/promises");
|
|
44
45
|
let zod = require("zod");
|
|
45
|
-
let node_os = require("node:os");
|
|
46
46
|
let node_url = require("node:url");
|
|
47
47
|
let vite = require("vite");
|
|
48
48
|
let node_module = require("node:module");
|
|
@@ -261,8 +261,80 @@ function createContentArtifactsPlugin() {
|
|
|
261
261
|
};
|
|
262
262
|
}
|
|
263
263
|
//#endregion
|
|
264
|
+
//#region source/core/theme.ts
|
|
265
|
+
var clarifyThemePresets = {
|
|
266
|
+
default: {
|
|
267
|
+
preset: "default",
|
|
268
|
+
tokens: {
|
|
269
|
+
colors: {
|
|
270
|
+
primary: "#047857",
|
|
271
|
+
accent: "#0D9488",
|
|
272
|
+
background: "#ffffff",
|
|
273
|
+
foreground: "#111827",
|
|
274
|
+
surface: "#ffffff",
|
|
275
|
+
muted: "#64748b",
|
|
276
|
+
border: "rgb(15 23 42 / 0.12)",
|
|
277
|
+
codeBackground: "#f6fbf8"
|
|
278
|
+
},
|
|
279
|
+
radius: {
|
|
280
|
+
sm: "6px",
|
|
281
|
+
md: "10px",
|
|
282
|
+
lg: "14px",
|
|
283
|
+
xl: "18px"
|
|
284
|
+
}
|
|
285
|
+
},
|
|
286
|
+
layout: { maxWidth: "82rem" },
|
|
287
|
+
editor: false
|
|
288
|
+
},
|
|
289
|
+
base: {
|
|
290
|
+
preset: "base",
|
|
291
|
+
tokens: {
|
|
292
|
+
colors: {
|
|
293
|
+
primary: "#18181b",
|
|
294
|
+
accent: "#52525b",
|
|
295
|
+
background: "#ffffff",
|
|
296
|
+
foreground: "#18181b",
|
|
297
|
+
surface: "#ffffff",
|
|
298
|
+
muted: "#71717a",
|
|
299
|
+
border: "rgb(24 24 27 / 0.12)",
|
|
300
|
+
codeBackground: "#f4f4f5"
|
|
301
|
+
},
|
|
302
|
+
radius: {
|
|
303
|
+
sm: "6px",
|
|
304
|
+
md: "8px",
|
|
305
|
+
lg: "12px",
|
|
306
|
+
xl: "16px"
|
|
307
|
+
}
|
|
308
|
+
},
|
|
309
|
+
layout: { maxWidth: "80rem" },
|
|
310
|
+
editor: false
|
|
311
|
+
}
|
|
312
|
+
};
|
|
313
|
+
function resolveThemeConfig(theme = {}) {
|
|
314
|
+
const preset = theme.preset ?? "default";
|
|
315
|
+
const presetTheme = clarifyThemePresets[preset];
|
|
316
|
+
return {
|
|
317
|
+
preset,
|
|
318
|
+
tokens: {
|
|
319
|
+
colors: {
|
|
320
|
+
...presetTheme.tokens.colors,
|
|
321
|
+
...theme.tokens?.colors
|
|
322
|
+
},
|
|
323
|
+
radius: {
|
|
324
|
+
...presetTheme.tokens.radius,
|
|
325
|
+
...theme.tokens?.radius
|
|
326
|
+
}
|
|
327
|
+
},
|
|
328
|
+
layout: {
|
|
329
|
+
...presetTheme.layout,
|
|
330
|
+
...theme.layout
|
|
331
|
+
},
|
|
332
|
+
editor: theme.editor ?? presetTheme.editor
|
|
333
|
+
};
|
|
334
|
+
}
|
|
335
|
+
//#endregion
|
|
264
336
|
//#region source/plugins/html-shell/index.ts
|
|
265
|
-
var
|
|
337
|
+
var THEME_STORAGE_KEY = "clarify:theme";
|
|
266
338
|
var REL_ICON_RE = /<link\s+[^>]*rel=["'][^"']*\bicon\b[^"']*["'][^>]*>/i;
|
|
267
339
|
function inferIconType(href) {
|
|
268
340
|
const path = href.split(/[?#]/, 1)[0]?.toLowerCase() ?? href.toLowerCase();
|
|
@@ -292,6 +364,62 @@ function createIconTags(icon) {
|
|
|
292
364
|
if (lightIcon === darkIcon) return [createIconTag(lightIcon)];
|
|
293
365
|
return [createIconTag(lightIcon, "(prefers-color-scheme: light)"), createIconTag(darkIcon, "(prefers-color-scheme: dark)")];
|
|
294
366
|
}
|
|
367
|
+
function matchesPresetTheme(theme) {
|
|
368
|
+
const preset = clarifyThemePresets[theme.preset];
|
|
369
|
+
return JSON.stringify({
|
|
370
|
+
tokens: theme.tokens,
|
|
371
|
+
layout: theme.layout
|
|
372
|
+
}) === JSON.stringify({
|
|
373
|
+
tokens: preset.tokens,
|
|
374
|
+
layout: preset.layout
|
|
375
|
+
});
|
|
376
|
+
}
|
|
377
|
+
function effectiveTheme(theme, resolvedTheme) {
|
|
378
|
+
if (resolvedTheme !== "dark" || !matchesPresetTheme(theme)) return theme;
|
|
379
|
+
return {
|
|
380
|
+
...theme,
|
|
381
|
+
tokens: {
|
|
382
|
+
...theme.tokens,
|
|
383
|
+
colors: {
|
|
384
|
+
...theme.tokens.colors,
|
|
385
|
+
background: "#09090b",
|
|
386
|
+
foreground: "#ffffff",
|
|
387
|
+
surface: "#18181b",
|
|
388
|
+
muted: "#a1a1aa",
|
|
389
|
+
border: "rgb(255 255 255 / 0.1)",
|
|
390
|
+
codeBackground: "#18181b"
|
|
391
|
+
}
|
|
392
|
+
}
|
|
393
|
+
};
|
|
394
|
+
}
|
|
395
|
+
function resolveThemeColorValue(value, resolvedTheme) {
|
|
396
|
+
return typeof value === "string" ? value : value[resolvedTheme] ?? value.light ?? value.dark ?? "";
|
|
397
|
+
}
|
|
398
|
+
function themeToCssVariables(theme, resolvedTheme) {
|
|
399
|
+
const resolved = effectiveTheme(theme, resolvedTheme);
|
|
400
|
+
const { colors } = resolved.tokens;
|
|
401
|
+
const { radius } = resolved.tokens;
|
|
402
|
+
return {
|
|
403
|
+
"--clarify-theme-tokens-colors-primary": resolveThemeColorValue(colors.primary, resolvedTheme),
|
|
404
|
+
"--clarify-theme-tokens-colors-accent": resolveThemeColorValue(colors.accent, resolvedTheme),
|
|
405
|
+
"--clarify-theme-tokens-colors-background": resolveThemeColorValue(colors.background, resolvedTheme),
|
|
406
|
+
"--clarify-theme-tokens-colors-foreground": resolveThemeColorValue(colors.foreground, resolvedTheme),
|
|
407
|
+
"--clarify-theme-tokens-colors-surface": resolveThemeColorValue(colors.surface, resolvedTheme),
|
|
408
|
+
"--clarify-theme-tokens-colors-muted": resolveThemeColorValue(colors.muted, resolvedTheme),
|
|
409
|
+
"--clarify-theme-tokens-colors-border": resolveThemeColorValue(colors.border, resolvedTheme),
|
|
410
|
+
"--clarify-theme-tokens-colors-code-background": resolveThemeColorValue(colors.codeBackground, resolvedTheme),
|
|
411
|
+
"--clarify-theme-tokens-radius-sm": radius.sm,
|
|
412
|
+
"--clarify-theme-tokens-radius-md": radius.md,
|
|
413
|
+
"--clarify-theme-tokens-radius-lg": radius.lg,
|
|
414
|
+
"--clarify-theme-tokens-radius-xl": radius.xl,
|
|
415
|
+
"--clarify-theme-layout-max-width": resolved.layout.maxWidth
|
|
416
|
+
};
|
|
417
|
+
}
|
|
418
|
+
function themeBootstrapScript(theme) {
|
|
419
|
+
const darkVariables = themeToCssVariables(theme, "dark");
|
|
420
|
+
const lightVariables = themeToCssVariables(theme, "light");
|
|
421
|
+
return `(function(){try{var e=localStorage.getItem(${JSON.stringify(THEME_STORAGE_KEY)});var t=e==='dark'||e==='light'||e==='system'?e:'system';var r=t==='system'?window.matchMedia('(prefers-color-scheme: dark)').matches:t==='dark';var v=r?${JSON.stringify(darkVariables)}:${JSON.stringify(lightVariables)};var s=document.documentElement.style;for(var k in v)s.setProperty(k,v[k]);document.documentElement.classList.toggle('dark',r);document.documentElement.style.colorScheme=r?'dark':'light'}catch(e){}})();`;
|
|
422
|
+
}
|
|
295
423
|
function createHtmlShellPlugin() {
|
|
296
424
|
return {
|
|
297
425
|
name: "clarify:html-shell",
|
|
@@ -302,7 +430,7 @@ function createHtmlShellPlugin() {
|
|
|
302
430
|
...REL_ICON_RE.test(input.html) ? [] : createIconTags(ctx.projectConfig.favicon ?? ctx.projectConfig.logo),
|
|
303
431
|
{
|
|
304
432
|
tag: "script",
|
|
305
|
-
children:
|
|
433
|
+
children: themeBootstrapScript(ctx.projectConfig.theme),
|
|
306
434
|
injectTo: "head-prepend"
|
|
307
435
|
},
|
|
308
436
|
{
|
|
@@ -779,8 +907,10 @@ function generateRoutesModule(routes, resolvedNavigation, projectConfig, mode =
|
|
|
779
907
|
const navigation = resolvedNavigation ?? (projectConfig?.tabs ? projectConfig.i18n ? buildLocalizedNavigationFromTabsConfig(routes, projectConfig.tabs, projectConfig.i18n) ?? {} : buildNavigationFromTabsConfig(routes, projectConfig.tabs) : buildNavigation(routes));
|
|
780
908
|
return `${imports}\n\nexport const routes = [\n${routesArray}\n];\n\nexport const navigation = ${JSON.stringify(navigation, null, 2)};\n`;
|
|
781
909
|
}
|
|
782
|
-
function createRuntimeModule() {
|
|
783
|
-
return "
|
|
910
|
+
function createRuntimeModule(options = {}) {
|
|
911
|
+
return `${options.footerComponentSource === "path" && options.imports?.footerComponent ? `import FooterComponent from ${moduleSpecifier(options.imports.footerComponent)};` : ""}
|
|
912
|
+
export const openApis = {};
|
|
913
|
+
export const footerComponent = ${options.footerComponentSource === "path" ? "FooterComponent" : "undefined"};`;
|
|
784
914
|
}
|
|
785
915
|
function createClientEntryModule(options = {}) {
|
|
786
916
|
return `
|
|
@@ -788,16 +918,22 @@ import '@clarify-labs/renderer/style.css';
|
|
|
788
918
|
import { render } from '@clarify-labs/renderer/client';
|
|
789
919
|
import { routes, navigation } from '${VIRTUAL_ROUTES}';
|
|
790
920
|
import { config } from '${VIRTUAL_CONFIG}';
|
|
791
|
-
import { openApis } from '${VIRTUAL_RUNTIME}';
|
|
792
|
-
render({ config, routes, navigation, openApis, themeEditor: ${JSON.stringify(options.themeEditor ?? false)} });`;
|
|
921
|
+
import { openApis, footerComponent } from '${VIRTUAL_RUNTIME}';
|
|
922
|
+
render({ config, routes, navigation, openApis, footerComponent, themeEditor: ${JSON.stringify(options.themeEditor ?? false)} });`;
|
|
793
923
|
}
|
|
794
924
|
function buildVirtualModules(args) {
|
|
795
925
|
const modules = /* @__PURE__ */ new Map();
|
|
796
926
|
const clientEntryModule = createClientEntryModule({ themeEditor: args.themeEditor });
|
|
927
|
+
const footerComponent = args.projectConfig.footer;
|
|
928
|
+
const footerComponentSource = typeof footerComponent === "string" ? "path" : void 0;
|
|
929
|
+
const footerComponentImport = typeof footerComponent === "string" ? footerComponent : void 0;
|
|
797
930
|
modules.set(VIRTUAL_CONFIG, generateConfigModule(args.projectConfig, args.generateOptions));
|
|
798
931
|
modules.set(VIRTUAL_ROUTES, generateRoutesModule(args.routes, args.navigation, args.projectConfig, "client"));
|
|
799
932
|
modules.set(VIRTUAL_SERVER_ROUTES, generateRoutesModule(args.routes, args.navigation, args.projectConfig, "server"));
|
|
800
|
-
modules.set(VIRTUAL_RUNTIME, createRuntimeModule(
|
|
933
|
+
modules.set(VIRTUAL_RUNTIME, createRuntimeModule({
|
|
934
|
+
footerComponentSource,
|
|
935
|
+
imports: { footerComponent: footerComponentImport }
|
|
936
|
+
}));
|
|
801
937
|
modules.set(VIRTUAL_CLIENT_ENTRY, clientEntryModule);
|
|
802
938
|
modules.set(RESOLVED_CLIENT_ENTRY, clientEntryModule);
|
|
803
939
|
for (const route of args.routes) modules.set(route.virtualModuleId, `export { default } from ${moduleSpecifier(route.filePath)};`);
|
|
@@ -806,8 +942,12 @@ function buildVirtualModules(args) {
|
|
|
806
942
|
//#endregion
|
|
807
943
|
//#region source/plugins/openapi/virtual-modules.ts
|
|
808
944
|
var openApiRegistryModuleId = VIRTUAL_RUNTIME;
|
|
809
|
-
function generateOpenAPIRegistryModule(openApis) {
|
|
810
|
-
|
|
945
|
+
function generateOpenAPIRegistryModule(openApis, runtimeModule = "") {
|
|
946
|
+
const openApisExport = `export const openApis = ${JSON.stringify(openApis)};`;
|
|
947
|
+
const openApisPlaceholder = /export const openApis = \{\};?/;
|
|
948
|
+
if (!runtimeModule) return openApisExport;
|
|
949
|
+
if (openApisPlaceholder.test(runtimeModule)) return runtimeModule.replace(openApisPlaceholder, openApisExport);
|
|
950
|
+
return runtimeModule;
|
|
811
951
|
}
|
|
812
952
|
function generateOpenAPIModule(spec, tagFilter) {
|
|
813
953
|
return `import { createElement } from 'react';
|
|
@@ -935,7 +1075,7 @@ function createOpenAPIPlugin() {
|
|
|
935
1075
|
return nextRoutes;
|
|
936
1076
|
},
|
|
937
1077
|
"modules:before": (modules, ctx) => {
|
|
938
|
-
modules.set(openApiRegistryModuleId, generateOpenAPIRegistryModule(Object.fromEntries(Object.entries(specs).map(([moduleId, entry]) => [moduleId, entry.spec]))));
|
|
1078
|
+
modules.set(openApiRegistryModuleId, generateOpenAPIRegistryModule(Object.fromEntries(Object.entries(specs).map(([moduleId, entry]) => [moduleId, entry.spec])), modules.get(openApiRegistryModuleId)));
|
|
939
1079
|
for (const [moduleId, entry] of Object.entries(specs)) modules.set(moduleId, generateOpenAPIModule(entry.spec, entry.tagFilter));
|
|
940
1080
|
for (const route of ctx.routes.filter((route) => route.kind === "openapi" && route.diagnostic)) if (route.diagnostic) modules.set(route.virtualModuleId, generateOpenAPIErrorModule(route.diagnostic));
|
|
941
1081
|
return modules;
|
|
@@ -944,6 +1084,180 @@ function createOpenAPIPlugin() {
|
|
|
944
1084
|
};
|
|
945
1085
|
}
|
|
946
1086
|
//#endregion
|
|
1087
|
+
//#region source/core/search-language.ts
|
|
1088
|
+
function toPagefindLanguage(locale) {
|
|
1089
|
+
return locale?.trim().replace(/_/g, "-").split("-").filter(Boolean).join("-").toLowerCase() || "en";
|
|
1090
|
+
}
|
|
1091
|
+
//#endregion
|
|
1092
|
+
//#region source/core/temp-dir.ts
|
|
1093
|
+
function createClarifyTempDir(name) {
|
|
1094
|
+
return (0, node_fs.mkdtempSync)((0, node_path.join)((0, node_os.tmpdir)(), `clarify-${name}-`));
|
|
1095
|
+
}
|
|
1096
|
+
function removeClarifyTempDir(path) {
|
|
1097
|
+
if (!path) return;
|
|
1098
|
+
(0, node_fs.rmSync)(path, {
|
|
1099
|
+
recursive: true,
|
|
1100
|
+
force: true
|
|
1101
|
+
});
|
|
1102
|
+
}
|
|
1103
|
+
//#endregion
|
|
1104
|
+
//#region source/plugins/search-index/index.ts
|
|
1105
|
+
var pagefindContentTypes = {
|
|
1106
|
+
".css": "text/css; charset=utf-8",
|
|
1107
|
+
".js": "text/javascript; charset=utf-8",
|
|
1108
|
+
".json": "application/json; charset=utf-8",
|
|
1109
|
+
".wasm": "application/wasm"
|
|
1110
|
+
};
|
|
1111
|
+
function assertNoPagefindErrors(action, errors) {
|
|
1112
|
+
if (!errors?.length) return;
|
|
1113
|
+
throw new Error(`[clarify] Pagefind ${action} failed:\n${errors.join("\n")}`);
|
|
1114
|
+
}
|
|
1115
|
+
async function generatePagefindIndex(options) {
|
|
1116
|
+
const pagefind = await import("pagefind");
|
|
1117
|
+
const { errors, index } = await pagefind.createIndex({
|
|
1118
|
+
excludeSelectors: [
|
|
1119
|
+
"[data-pagefind-ignore]",
|
|
1120
|
+
"script",
|
|
1121
|
+
"style",
|
|
1122
|
+
"svg"
|
|
1123
|
+
],
|
|
1124
|
+
includeCharacters: "._-/#:@",
|
|
1125
|
+
keepIndexUrl: false,
|
|
1126
|
+
verbose: false,
|
|
1127
|
+
writePlayground: false
|
|
1128
|
+
});
|
|
1129
|
+
assertNoPagefindErrors("createIndex", errors);
|
|
1130
|
+
if (!index) throw new Error("[clarify] Pagefind did not create an index.");
|
|
1131
|
+
try {
|
|
1132
|
+
const addResult = await index.addDirectory({
|
|
1133
|
+
path: options.sourceRoot ?? options.outputRoot,
|
|
1134
|
+
glob: "**/*.html"
|
|
1135
|
+
});
|
|
1136
|
+
assertNoPagefindErrors("addDirectory", addResult.errors);
|
|
1137
|
+
assertNoPagefindErrors("writeFiles", (await index.writeFiles({ outputPath: (0, node_path.join)(options.outputRoot, "pagefind") })).errors);
|
|
1138
|
+
return addResult.page_count;
|
|
1139
|
+
} finally {
|
|
1140
|
+
await index.deleteIndex();
|
|
1141
|
+
await pagefind.close();
|
|
1142
|
+
}
|
|
1143
|
+
}
|
|
1144
|
+
function routeSearchContent(route) {
|
|
1145
|
+
return [
|
|
1146
|
+
route.title,
|
|
1147
|
+
route.description,
|
|
1148
|
+
route.keywords?.join(" "),
|
|
1149
|
+
route.sections?.map((section) => section.title).join(" "),
|
|
1150
|
+
route.content
|
|
1151
|
+
].filter(Boolean).join("\n\n");
|
|
1152
|
+
}
|
|
1153
|
+
async function generateDevSearchIndex(ctx, root) {
|
|
1154
|
+
const pagefind = await import("pagefind");
|
|
1155
|
+
const { errors, index } = await pagefind.createIndex({
|
|
1156
|
+
includeCharacters: "._-/#:@",
|
|
1157
|
+
keepIndexUrl: false,
|
|
1158
|
+
verbose: false,
|
|
1159
|
+
writePlayground: false
|
|
1160
|
+
});
|
|
1161
|
+
assertNoPagefindErrors("createIndex", errors);
|
|
1162
|
+
if (!index) throw new Error("[clarify] Pagefind did not create an index.");
|
|
1163
|
+
try {
|
|
1164
|
+
let pageCount = 0;
|
|
1165
|
+
for (const route of ctx.routes) {
|
|
1166
|
+
const content = routeSearchContent(route);
|
|
1167
|
+
if (!content.trim()) continue;
|
|
1168
|
+
const result = await index.addCustomRecord({
|
|
1169
|
+
url: route.path,
|
|
1170
|
+
content,
|
|
1171
|
+
language: toPagefindLanguage(route.locale ?? ctx.projectConfig.i18n?.defaultLocale),
|
|
1172
|
+
meta: { title: route.title }
|
|
1173
|
+
});
|
|
1174
|
+
assertNoPagefindErrors(`addCustomRecord ${route.path}`, result.errors);
|
|
1175
|
+
pageCount += 1;
|
|
1176
|
+
}
|
|
1177
|
+
assertNoPagefindErrors("writeFiles", (await index.writeFiles({ outputPath: (0, node_path.join)(root, "pagefind") })).errors);
|
|
1178
|
+
console.log(`[clarify] Dev search index generated for ${pageCount} pages.`);
|
|
1179
|
+
} finally {
|
|
1180
|
+
await index.deleteIndex();
|
|
1181
|
+
await pagefind.close();
|
|
1182
|
+
}
|
|
1183
|
+
}
|
|
1184
|
+
function normalizeDevPagefindPath(rawUrl, routePrefix) {
|
|
1185
|
+
const pathname = rawUrl?.split("?")[0];
|
|
1186
|
+
if (!pathname) return void 0;
|
|
1187
|
+
const normalizedPrefix = routePrefix && routePrefix !== "/" ? `/${routePrefix.replace(/^\/+|\/+$/g, "")}` : "";
|
|
1188
|
+
const pagefindPath = normalizedPrefix && pathname.startsWith(`${normalizedPrefix}/pagefind/`) ? pathname.slice(normalizedPrefix.length) : pathname;
|
|
1189
|
+
return pagefindPath.startsWith("/pagefind/") ? pagefindPath : void 0;
|
|
1190
|
+
}
|
|
1191
|
+
function serveDevPagefind(server, getRoot, ctx) {
|
|
1192
|
+
server.middlewares.use((req, res, next) => {
|
|
1193
|
+
const root = getRoot();
|
|
1194
|
+
const pagefindPath = normalizeDevPagefindPath(req.url, ctx.projectConfig.routePrefix);
|
|
1195
|
+
if (!root || !pagefindPath) {
|
|
1196
|
+
next();
|
|
1197
|
+
return;
|
|
1198
|
+
}
|
|
1199
|
+
const filePath = (0, node_path.join)(root, pagefindPath);
|
|
1200
|
+
const relativePath = (0, node_path.relative)(root, filePath);
|
|
1201
|
+
if (relativePath.startsWith("..") || relativePath === "" || !(0, node_fs.existsSync)(filePath)) {
|
|
1202
|
+
next();
|
|
1203
|
+
return;
|
|
1204
|
+
}
|
|
1205
|
+
const contentType = pagefindContentTypes[(0, node_path.extname)(filePath)] ?? "application/octet-stream";
|
|
1206
|
+
res.setHeader("Content-Type", contentType);
|
|
1207
|
+
(0, node_fs.createReadStream)(filePath).pipe(res);
|
|
1208
|
+
});
|
|
1209
|
+
}
|
|
1210
|
+
function createSearchIndexPlugin() {
|
|
1211
|
+
return {
|
|
1212
|
+
name: "clarify:search-index",
|
|
1213
|
+
hooks: {
|
|
1214
|
+
async "dev:configureServer"(server, ctx) {
|
|
1215
|
+
let currentRoot;
|
|
1216
|
+
const staleRoots = /* @__PURE__ */ new Set();
|
|
1217
|
+
const replaceDevIndex = async () => {
|
|
1218
|
+
const nextRoot = createClarifyTempDir("pagefind");
|
|
1219
|
+
await generateDevSearchIndex(ctx, nextRoot);
|
|
1220
|
+
const previousRoot = currentRoot;
|
|
1221
|
+
currentRoot = nextRoot;
|
|
1222
|
+
if (previousRoot) {
|
|
1223
|
+
staleRoots.add(previousRoot);
|
|
1224
|
+
setTimeout(() => {
|
|
1225
|
+
staleRoots.delete(previousRoot);
|
|
1226
|
+
removeClarifyTempDir(previousRoot);
|
|
1227
|
+
}, 3e4).unref?.();
|
|
1228
|
+
}
|
|
1229
|
+
};
|
|
1230
|
+
serveDevPagefind(server, () => currentRoot, ctx);
|
|
1231
|
+
await replaceDevIndex();
|
|
1232
|
+
let regenerateTimer;
|
|
1233
|
+
const regenerate = (filePath) => {
|
|
1234
|
+
if (!/\.(md|mdx|json|ya?ml)$/i.test(filePath)) return;
|
|
1235
|
+
if (regenerateTimer) clearTimeout(regenerateTimer);
|
|
1236
|
+
regenerateTimer = setTimeout(() => {
|
|
1237
|
+
replaceDevIndex().catch((err) => {
|
|
1238
|
+
console.error("[clarify] Failed to regenerate dev search index:", err);
|
|
1239
|
+
});
|
|
1240
|
+
}, 100);
|
|
1241
|
+
};
|
|
1242
|
+
server.watcher.on("add", regenerate);
|
|
1243
|
+
server.watcher.on("change", regenerate);
|
|
1244
|
+
server.watcher.on("unlink", regenerate);
|
|
1245
|
+
server.httpServer?.once("close", () => {
|
|
1246
|
+
if (regenerateTimer) clearTimeout(regenerateTimer);
|
|
1247
|
+
removeClarifyTempDir(currentRoot);
|
|
1248
|
+
for (const staleRoot of staleRoots) removeClarifyTempDir(staleRoot);
|
|
1249
|
+
});
|
|
1250
|
+
},
|
|
1251
|
+
async "build:done"(ctx) {
|
|
1252
|
+
const outputDirectory = ctx.generateOptions.outputDirectory;
|
|
1253
|
+
if (!outputDirectory) return;
|
|
1254
|
+
const pageCount = await generatePagefindIndex({ outputRoot: (0, node_path.resolve)(ctx.generateOptions.projectRoot, outputDirectory) });
|
|
1255
|
+
console.log(`[clarify] Search index generated for ${pageCount} pages.`);
|
|
1256
|
+
}
|
|
1257
|
+
}
|
|
1258
|
+
};
|
|
1259
|
+
}
|
|
1260
|
+
//#endregion
|
|
947
1261
|
//#region source/plugins/seo/artifacts.ts
|
|
948
1262
|
function trimTrailingSlash(value) {
|
|
949
1263
|
return value.replace(/\/+$/, "");
|
|
@@ -1039,7 +1353,8 @@ function createBuiltinPlugins(options = {}) {
|
|
|
1039
1353
|
createOpenAPIPlugin(),
|
|
1040
1354
|
createSourceLinksPlugin(),
|
|
1041
1355
|
createContentArtifactsPlugin(),
|
|
1042
|
-
createSeoPlugin()
|
|
1356
|
+
createSeoPlugin(),
|
|
1357
|
+
createSearchIndexPlugin()
|
|
1043
1358
|
];
|
|
1044
1359
|
if (options.htmlShell ?? true) plugins.push(createHtmlShellPlugin());
|
|
1045
1360
|
return plugins;
|
|
@@ -1097,11 +1412,12 @@ var clarifyBannerConfigSchema = zod.z.object({
|
|
|
1097
1412
|
content: clarifyLocalizedTextSchema,
|
|
1098
1413
|
dismissible: zod.z.boolean().optional()
|
|
1099
1414
|
});
|
|
1100
|
-
var
|
|
1415
|
+
var clarifyFooterLinksConfigSchema = zod.z.object({
|
|
1101
1416
|
links: zod.z.array(clarifyNavbarLinkSchema).optional(),
|
|
1102
1417
|
socials: zod.z.record(zod.z.string(), zod.z.string()).optional(),
|
|
1103
1418
|
copyright: clarifyLocalizedTextSchema.optional()
|
|
1104
|
-
});
|
|
1419
|
+
}).strict();
|
|
1420
|
+
var clarifyFooterConfigSchema = zod.z.union([clarifyFooterLinksConfigSchema, zod.z.string()]);
|
|
1105
1421
|
var clarifySourceConfigSchema = zod.z.object({
|
|
1106
1422
|
repository: zod.z.string(),
|
|
1107
1423
|
branch: zod.z.string().optional(),
|
|
@@ -1185,78 +1501,6 @@ var clarifyProjectConfigSchema = zod.z.object({
|
|
|
1185
1501
|
tabs: clarifyTabsConfigSchema.optional()
|
|
1186
1502
|
});
|
|
1187
1503
|
//#endregion
|
|
1188
|
-
//#region source/core/theme.ts
|
|
1189
|
-
var clarifyThemePresets = {
|
|
1190
|
-
default: {
|
|
1191
|
-
preset: "default",
|
|
1192
|
-
tokens: {
|
|
1193
|
-
colors: {
|
|
1194
|
-
primary: "#047857",
|
|
1195
|
-
accent: "#0D9488",
|
|
1196
|
-
background: "#ffffff",
|
|
1197
|
-
foreground: "#111827",
|
|
1198
|
-
surface: "#ffffff",
|
|
1199
|
-
muted: "#64748b",
|
|
1200
|
-
border: "rgb(15 23 42 / 0.12)",
|
|
1201
|
-
codeBackground: "#f6fbf8"
|
|
1202
|
-
},
|
|
1203
|
-
radius: {
|
|
1204
|
-
sm: "6px",
|
|
1205
|
-
md: "10px",
|
|
1206
|
-
lg: "14px",
|
|
1207
|
-
xl: "18px"
|
|
1208
|
-
}
|
|
1209
|
-
},
|
|
1210
|
-
layout: { maxWidth: "82rem" },
|
|
1211
|
-
editor: false
|
|
1212
|
-
},
|
|
1213
|
-
base: {
|
|
1214
|
-
preset: "base",
|
|
1215
|
-
tokens: {
|
|
1216
|
-
colors: {
|
|
1217
|
-
primary: "#18181b",
|
|
1218
|
-
accent: "#52525b",
|
|
1219
|
-
background: "#ffffff",
|
|
1220
|
-
foreground: "#18181b",
|
|
1221
|
-
surface: "#ffffff",
|
|
1222
|
-
muted: "#71717a",
|
|
1223
|
-
border: "rgb(24 24 27 / 0.12)",
|
|
1224
|
-
codeBackground: "#f4f4f5"
|
|
1225
|
-
},
|
|
1226
|
-
radius: {
|
|
1227
|
-
sm: "6px",
|
|
1228
|
-
md: "8px",
|
|
1229
|
-
lg: "12px",
|
|
1230
|
-
xl: "16px"
|
|
1231
|
-
}
|
|
1232
|
-
},
|
|
1233
|
-
layout: { maxWidth: "80rem" },
|
|
1234
|
-
editor: false
|
|
1235
|
-
}
|
|
1236
|
-
};
|
|
1237
|
-
function resolveThemeConfig(theme = {}) {
|
|
1238
|
-
const preset = theme.preset ?? "default";
|
|
1239
|
-
const presetTheme = clarifyThemePresets[preset];
|
|
1240
|
-
return {
|
|
1241
|
-
preset,
|
|
1242
|
-
tokens: {
|
|
1243
|
-
colors: {
|
|
1244
|
-
...presetTheme.tokens.colors,
|
|
1245
|
-
...theme.tokens?.colors
|
|
1246
|
-
},
|
|
1247
|
-
radius: {
|
|
1248
|
-
...presetTheme.tokens.radius,
|
|
1249
|
-
...theme.tokens?.radius
|
|
1250
|
-
}
|
|
1251
|
-
},
|
|
1252
|
-
layout: {
|
|
1253
|
-
...presetTheme.layout,
|
|
1254
|
-
...theme.layout
|
|
1255
|
-
},
|
|
1256
|
-
editor: theme.editor ?? presetTheme.editor
|
|
1257
|
-
};
|
|
1258
|
-
}
|
|
1259
|
-
//#endregion
|
|
1260
1504
|
//#region source/core/config.ts
|
|
1261
1505
|
function formatIssuePath(path) {
|
|
1262
1506
|
return path.reduce((result, segment) => {
|
|
@@ -1550,13 +1794,13 @@ function routeOutputFiles(outputDirectory, route) {
|
|
|
1550
1794
|
var SSR_ENTRY_CODE = `import { renderToHTML } from '@clarify-labs/renderer/server';
|
|
1551
1795
|
import { routes, navigation } from 'virtual:clarify-routes/server';
|
|
1552
1796
|
import { config } from 'virtual:clarify-config';
|
|
1553
|
-
import { openApis } from 'virtual:clarify-runtime';
|
|
1797
|
+
import { openApis, footerComponent } from 'virtual:clarify-runtime';
|
|
1554
1798
|
|
|
1555
1799
|
export function render(url) {
|
|
1556
|
-
return renderToHTML({ config, routes, navigation, openApis, url, themeEditor: config.theme.editor });
|
|
1800
|
+
return renderToHTML({ config, routes, navigation, openApis, footerComponent, url, themeEditor: config.theme.editor });
|
|
1557
1801
|
}`;
|
|
1558
1802
|
function createTempEntryFile(content) {
|
|
1559
|
-
const entryPath = (0, node_path.join)((
|
|
1803
|
+
const entryPath = (0, node_path.join)(createClarifyTempDir("ssr"), "entry-server.ts");
|
|
1560
1804
|
(0, node_fs.writeFileSync)(entryPath, content, "utf-8");
|
|
1561
1805
|
return entryPath;
|
|
1562
1806
|
}
|
|
@@ -1596,6 +1840,7 @@ async function renderSSGRoutes(routes, projectConfig, outputDirectory, ssrBundle
|
|
|
1596
1840
|
//#endregion
|
|
1597
1841
|
//#region source/core/user-config.ts
|
|
1598
1842
|
function defineConfig(config) {
|
|
1843
|
+
validateProjectConfig(config);
|
|
1599
1844
|
return config;
|
|
1600
1845
|
}
|
|
1601
1846
|
var CONFIG_FILENAMES = [
|
|
@@ -1858,6 +2103,12 @@ Object.defineProperty(exports, "createClarifyRuntimeAliases", {
|
|
|
1858
2103
|
return createClarifyRuntimeAliases;
|
|
1859
2104
|
}
|
|
1860
2105
|
});
|
|
2106
|
+
Object.defineProperty(exports, "createClarifyTempDir", {
|
|
2107
|
+
enumerable: true,
|
|
2108
|
+
get: function() {
|
|
2109
|
+
return createClarifyTempDir;
|
|
2110
|
+
}
|
|
2111
|
+
});
|
|
1861
2112
|
Object.defineProperty(exports, "defineConfig", {
|
|
1862
2113
|
enumerable: true,
|
|
1863
2114
|
get: function() {
|
|
@@ -1877,4 +2128,4 @@ Object.defineProperty(exports, "resolveClarifySite", {
|
|
|
1877
2128
|
}
|
|
1878
2129
|
});
|
|
1879
2130
|
|
|
1880
|
-
//# sourceMappingURL=plugin-
|
|
2131
|
+
//# sourceMappingURL=plugin-dzXRzjdX.cjs.map
|