@hanzo/docs-mdx 14.1.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.
Files changed (83) hide show
  1. package/LICENSE +21 -0
  2. package/dist/bin.d.ts +1 -0
  3. package/dist/bin.js +16 -0
  4. package/dist/build-mdx-LN7FEKIP.js +8 -0
  5. package/dist/build-mdx-RXJZQXGA.js +8 -0
  6. package/dist/bun/index.d.ts +25 -0
  7. package/dist/bun/index.js +52 -0
  8. package/dist/chunk-4JSFLXXT.js +8 -0
  9. package/dist/chunk-5OBUOALK.js +141 -0
  10. package/dist/chunk-72JS4QVZ.js +17 -0
  11. package/dist/chunk-7I4W7XGI.js +179 -0
  12. package/dist/chunk-7W73RILB.js +173 -0
  13. package/dist/chunk-A3YIGE7S.js +334 -0
  14. package/dist/chunk-AOTZP2TV.js +152 -0
  15. package/dist/chunk-AXJB5MGS.js +173 -0
  16. package/dist/chunk-DMIIE3XZ.js +179 -0
  17. package/dist/chunk-DTFUANSF.js +40 -0
  18. package/dist/chunk-JWZR25CW.js +116 -0
  19. package/dist/chunk-K7N6GD4M.js +17 -0
  20. package/dist/chunk-LXB7WYAF.js +334 -0
  21. package/dist/chunk-MYAVS2LD.js +116 -0
  22. package/dist/chunk-OLD35ARB.js +116 -0
  23. package/dist/chunk-PW2AZGGD.js +125 -0
  24. package/dist/chunk-RGBNABKS.js +334 -0
  25. package/dist/chunk-RPUM7REY.js +40 -0
  26. package/dist/chunk-RR2X6AE6.js +274 -0
  27. package/dist/chunk-S7KOJHHO.js +89 -0
  28. package/dist/chunk-STUCUTJQ.js +334 -0
  29. package/dist/chunk-T6G5VOED.js +116 -0
  30. package/dist/chunk-U5YPLCO5.js +89 -0
  31. package/dist/chunk-UB55AMXC.js +274 -0
  32. package/dist/chunk-VITVHHR6.js +334 -0
  33. package/dist/chunk-VKSHE52K.js +274 -0
  34. package/dist/chunk-VWJKRQZR.js +19 -0
  35. package/dist/chunk-WAAWFNDX.js +179 -0
  36. package/dist/chunk-WGXYJGSZ.js +141 -0
  37. package/dist/chunk-WLJ6EKOZ.js +17 -0
  38. package/dist/chunk-WMYYALAS.js +334 -0
  39. package/dist/chunk-Y7ISNZ7X.js +216 -0
  40. package/dist/chunk-YKRCQ42E.js +216 -0
  41. package/dist/chunk-ZAYZWFWP.js +89 -0
  42. package/dist/config/index.d.ts +18 -0
  43. package/dist/config/index.js +63 -0
  44. package/dist/core-BQcKaqmC.d.ts +350 -0
  45. package/dist/core-BhWOtait.d.ts +350 -0
  46. package/dist/core-CV8uFMUa.d.ts +350 -0
  47. package/dist/core-DAQ64Hkq.d.ts +350 -0
  48. package/dist/core-DZtRjhds.d.ts +350 -0
  49. package/dist/core-De5K4ixv.d.ts +350 -0
  50. package/dist/core-X5ggQtBM.d.ts +350 -0
  51. package/dist/index-BqkSNsGO.d.ts +8 -0
  52. package/dist/index.d.ts +61 -0
  53. package/dist/index.js +0 -0
  54. package/dist/load-from-file-FHW724YY.js +8 -0
  55. package/dist/load-from-file-S5CQ4H6T.js +8 -0
  56. package/dist/next/index.cjs +1165 -0
  57. package/dist/next/index.d.ts +33 -0
  58. package/dist/next/index.js +181 -0
  59. package/dist/node/loader.d.ts +5 -0
  60. package/dist/node/loader.js +41 -0
  61. package/dist/plugins/index-file.d.ts +14 -0
  62. package/dist/plugins/index-file.js +8 -0
  63. package/dist/plugins/json-schema.d.ts +31 -0
  64. package/dist/plugins/json-schema.js +80 -0
  65. package/dist/plugins/last-modified.d.ts +40 -0
  66. package/dist/plugins/last-modified.js +89 -0
  67. package/dist/runtime/browser.d.ts +53 -0
  68. package/dist/runtime/browser.js +67 -0
  69. package/dist/runtime/dynamic.d.ts +27 -0
  70. package/dist/runtime/dynamic.js +79 -0
  71. package/dist/runtime/server.d.ts +14 -0
  72. package/dist/runtime/server.js +8 -0
  73. package/dist/runtime/types.d.ts +61 -0
  74. package/dist/runtime/types.js +0 -0
  75. package/dist/vite/index.d.ts +44 -0
  76. package/dist/vite/index.js +122 -0
  77. package/dist/webpack/mdx.d.ts +6 -0
  78. package/dist/webpack/mdx.js +37 -0
  79. package/dist/webpack/meta.d.ts +6 -0
  80. package/dist/webpack/meta.js +40 -0
  81. package/loader-mdx.cjs +7 -0
  82. package/loader-meta.cjs +7 -0
  83. package/package.json +137 -0
@@ -0,0 +1,179 @@
1
+ import {
2
+ ValidationError
3
+ } from "./chunk-RR2X6AE6.js";
4
+
5
+ // src/loaders/adapter.ts
6
+ import { fileURLToPath } from "url";
7
+ import fs from "fs/promises";
8
+ import { parse } from "querystring";
9
+ import path from "path";
10
+ import { readFileSync } from "fs";
11
+ function toNode(loader) {
12
+ return async (url, _context, nextLoad) => {
13
+ if (url.startsWith("file:///") && (!loader.test || loader.test.test(url))) {
14
+ const parsedUrl = new URL(url);
15
+ const filePath = fileURLToPath(parsedUrl);
16
+ const result = await loader.load({
17
+ filePath,
18
+ query: Object.fromEntries(parsedUrl.searchParams.entries()),
19
+ async getSource() {
20
+ return (await fs.readFile(filePath)).toString();
21
+ },
22
+ development: false,
23
+ compiler: {
24
+ addDependency() {
25
+ }
26
+ }
27
+ });
28
+ if (result) {
29
+ return {
30
+ source: result.code,
31
+ format: "module",
32
+ shortCircuit: true
33
+ };
34
+ }
35
+ }
36
+ return nextLoad(url);
37
+ };
38
+ }
39
+ function toVite(loader) {
40
+ return {
41
+ filter(id) {
42
+ return !loader.test || loader.test.test(id);
43
+ },
44
+ async transform(value, id) {
45
+ const [file, query = ""] = id.split("?", 2);
46
+ const result = await loader.load({
47
+ filePath: file,
48
+ query: parse(query),
49
+ getSource() {
50
+ return value;
51
+ },
52
+ development: this.environment.mode === "dev",
53
+ compiler: {
54
+ addDependency: (file2) => {
55
+ this.addWatchFile(file2);
56
+ }
57
+ }
58
+ });
59
+ if (result === null) return null;
60
+ return {
61
+ code: result.code,
62
+ map: result.map
63
+ };
64
+ }
65
+ };
66
+ }
67
+ function toWebpack(loader) {
68
+ return async function(source, callback) {
69
+ try {
70
+ const result = await loader.load({
71
+ filePath: this.resourcePath,
72
+ query: parse(this.resourceQuery.slice(1)),
73
+ getSource() {
74
+ return source;
75
+ },
76
+ development: this.mode === "development",
77
+ compiler: this
78
+ });
79
+ if (result === null) {
80
+ callback(void 0, source);
81
+ } else {
82
+ callback(void 0, result.code, result.map);
83
+ }
84
+ } catch (error) {
85
+ if (error instanceof ValidationError) {
86
+ return callback(new Error(await error.toStringFormatted()));
87
+ }
88
+ if (!(error instanceof Error)) throw error;
89
+ const fpath = path.relative(this.context, this.resourcePath);
90
+ error.message = `${fpath}:${error.name}: ${error.message}`;
91
+ callback(error);
92
+ }
93
+ };
94
+ }
95
+ function toBun(loader) {
96
+ function toResult(output) {
97
+ if (!output) return;
98
+ return {
99
+ contents: output.code,
100
+ loader: "js"
101
+ };
102
+ }
103
+ return (build) => {
104
+ build.onLoad({ filter: loader.test ?? /.+/ }, (args) => {
105
+ const [filePath, query = ""] = args.path.split("?", 2);
106
+ const input = {
107
+ async getSource() {
108
+ return Bun.file(filePath).text();
109
+ },
110
+ query: parse(query),
111
+ filePath,
112
+ development: false,
113
+ compiler: {
114
+ addDependency() {
115
+ }
116
+ }
117
+ };
118
+ if (loader.bun?.load) {
119
+ return loader.bun.load(readFileSync(filePath).toString(), input);
120
+ }
121
+ const result = loader.load(input);
122
+ if (result instanceof Promise) {
123
+ return result.then(toResult);
124
+ }
125
+ return toResult(result);
126
+ });
127
+ };
128
+ }
129
+
130
+ // src/loaders/config.ts
131
+ import fs2 from "fs/promises";
132
+ function createStandaloneConfigLoader({
133
+ core,
134
+ buildConfig,
135
+ mode
136
+ }) {
137
+ let prev;
138
+ async function getConfigHash() {
139
+ if (mode === "production") return "static";
140
+ const stats = await fs2.stat(core.getOptions().configPath).catch(() => {
141
+ throw new Error("Cannot find config file");
142
+ });
143
+ return stats.mtime.getTime().toString();
144
+ }
145
+ return {
146
+ async getCore() {
147
+ const hash = await getConfigHash();
148
+ if (!prev || hash !== prev.hash) {
149
+ prev = {
150
+ hash,
151
+ init: (async () => {
152
+ const { loadConfig } = await import("./load-from-file-S5CQ4H6T.js");
153
+ await core.init({
154
+ config: loadConfig(core, buildConfig)
155
+ });
156
+ })()
157
+ };
158
+ }
159
+ await prev.init;
160
+ return core;
161
+ }
162
+ };
163
+ }
164
+ function createIntegratedConfigLoader(core) {
165
+ return {
166
+ async getCore() {
167
+ return core;
168
+ }
169
+ };
170
+ }
171
+
172
+ export {
173
+ toNode,
174
+ toVite,
175
+ toWebpack,
176
+ toBun,
177
+ createStandaloneConfigLoader,
178
+ createIntegratedConfigLoader
179
+ };
@@ -0,0 +1,40 @@
1
+ import {
2
+ buildConfig
3
+ } from "./chunk-OLD35ARB.js";
4
+
5
+ // src/config/load-from-file.ts
6
+ import { pathToFileURL } from "url";
7
+ async function compileConfig(core) {
8
+ const { build } = await import("esbuild");
9
+ const { configPath, outDir } = core.getOptions();
10
+ const transformed = await build({
11
+ entryPoints: [{ in: configPath, out: "source.config" }],
12
+ bundle: true,
13
+ outdir: outDir,
14
+ target: "node20",
15
+ write: true,
16
+ platform: "node",
17
+ format: "esm",
18
+ packages: "external",
19
+ outExtension: {
20
+ ".js": ".mjs"
21
+ },
22
+ allowOverwrite: true
23
+ });
24
+ if (transformed.errors.length > 0) {
25
+ throw new Error("failed to compile configuration file");
26
+ }
27
+ }
28
+ async function loadConfig(core, build = false) {
29
+ if (build) await compileConfig(core);
30
+ const url = pathToFileURL(core.getCompiledConfigPath());
31
+ url.searchParams.set("hash", Date.now().toString());
32
+ const config = import(url.href).then(
33
+ (loaded) => buildConfig(loaded)
34
+ );
35
+ return await config;
36
+ }
37
+
38
+ export {
39
+ loadConfig
40
+ };
@@ -0,0 +1,116 @@
1
+ import {
2
+ mdxLoaderGlob
3
+ } from "./chunk-4JSFLXXT.js";
4
+ import {
5
+ fumaMatter
6
+ } from "./chunk-VWJKRQZR.js";
7
+
8
+ // src/loaders/mdx/index.ts
9
+ import { z } from "zod";
10
+ import fs from "fs/promises";
11
+ import path from "path";
12
+ import { createHash } from "crypto";
13
+ var querySchema = z.object({
14
+ only: z.literal(["frontmatter", "all"]).default("all"),
15
+ collection: z.string().optional(),
16
+ workspace: z.string().optional()
17
+ }).loose();
18
+ var cacheEntry = z.object({
19
+ code: z.string(),
20
+ map: z.any().optional(),
21
+ hash: z.string().optional()
22
+ });
23
+ function createMdxLoader({ getCore }) {
24
+ return {
25
+ test: mdxLoaderGlob,
26
+ async load({
27
+ getSource,
28
+ development: isDevelopment,
29
+ query,
30
+ compiler,
31
+ filePath
32
+ }) {
33
+ let core = await getCore();
34
+ const value = await getSource();
35
+ const matter = fumaMatter(value);
36
+ const {
37
+ collection: collectionName,
38
+ workspace,
39
+ only
40
+ } = querySchema.parse(query);
41
+ if (workspace) {
42
+ core = core.getWorkspaces().get(workspace) ?? core;
43
+ }
44
+ let after;
45
+ const { experimentalBuildCache = false } = core.getConfig().global;
46
+ if (!isDevelopment && experimentalBuildCache) {
47
+ const cacheDir = experimentalBuildCache;
48
+ const cacheKey = `${collectionName ?? "global"}_${generateCacheHash(filePath)}`;
49
+ const cached = await fs.readFile(path.join(cacheDir, cacheKey)).then((content) => cacheEntry.parse(JSON.parse(content.toString()))).catch(() => null);
50
+ if (cached && cached.hash === generateCacheHash(value)) return cached;
51
+ after = async () => {
52
+ await fs.mkdir(cacheDir, { recursive: true });
53
+ await fs.writeFile(
54
+ path.join(cacheDir, cacheKey),
55
+ JSON.stringify({
56
+ ...out,
57
+ hash: generateCacheHash(value)
58
+ })
59
+ );
60
+ };
61
+ }
62
+ const collection = collectionName ? core.getCollection(collectionName) : void 0;
63
+ let docCollection;
64
+ switch (collection?.type) {
65
+ case "doc":
66
+ docCollection = collection;
67
+ break;
68
+ case "docs":
69
+ docCollection = collection.docs;
70
+ break;
71
+ }
72
+ if (docCollection) {
73
+ matter.data = await core.transformFrontmatter(
74
+ { collection: docCollection, filePath, source: value },
75
+ matter.data
76
+ );
77
+ }
78
+ if (only === "frontmatter") {
79
+ return {
80
+ code: `export const frontmatter = ${JSON.stringify(matter.data)}`,
81
+ map: null
82
+ };
83
+ }
84
+ const lineOffset = isDevelopment ? countLines(matter.matter) : 0;
85
+ const { buildMDX } = await import("./build-mdx-LN7FEKIP.js");
86
+ const compiled = await buildMDX(core, docCollection, {
87
+ isDevelopment,
88
+ source: "\n".repeat(lineOffset) + matter.content,
89
+ filePath,
90
+ frontmatter: matter.data,
91
+ _compiler: compiler,
92
+ environment: "bundler"
93
+ });
94
+ const out = {
95
+ code: String(compiled.value),
96
+ map: compiled.map
97
+ };
98
+ await after?.();
99
+ return out;
100
+ }
101
+ };
102
+ }
103
+ function generateCacheHash(input) {
104
+ return createHash("md5").update(input).digest("hex");
105
+ }
106
+ function countLines(s) {
107
+ let num = 0;
108
+ for (const c of s) {
109
+ if (c === "\n") num++;
110
+ }
111
+ return num;
112
+ }
113
+
114
+ export {
115
+ createMdxLoader
116
+ };
@@ -0,0 +1,17 @@
1
+ import {
2
+ createCore
3
+ } from "./chunk-VKSHE52K.js";
4
+
5
+ // src/webpack/index.ts
6
+ var core;
7
+ function getCore(options) {
8
+ return core ??= createCore({
9
+ environment: "webpack",
10
+ outDir: options.outDir,
11
+ configPath: options.configPath
12
+ });
13
+ }
14
+
15
+ export {
16
+ getCore
17
+ };
@@ -0,0 +1,334 @@
1
+ import {
2
+ fumaMatter
3
+ } from "./chunk-VWJKRQZR.js";
4
+ import {
5
+ createCodegen,
6
+ ident
7
+ } from "./chunk-PW2AZGGD.js";
8
+
9
+ // src/plugins/index-file.ts
10
+ import path2 from "path";
11
+ import { glob } from "tinyglobby";
12
+
13
+ // src/utils/fs-cache.ts
14
+ import fs from "fs/promises";
15
+ import path from "path";
16
+ var map = /* @__PURE__ */ new Map();
17
+ function createFSCache() {
18
+ return {
19
+ read(file) {
20
+ const fullPath = toFullPath(file);
21
+ const cached = map.get(fullPath);
22
+ if (cached) return cached;
23
+ const read = fs.readFile(fullPath).then((s) => s.toString());
24
+ map.set(fullPath, read);
25
+ return read;
26
+ },
27
+ delete(file) {
28
+ map.delete(toFullPath(file));
29
+ }
30
+ };
31
+ }
32
+ function toFullPath(file) {
33
+ if (path.isAbsolute(file)) {
34
+ return path.relative(process.cwd(), file);
35
+ }
36
+ return file;
37
+ }
38
+
39
+ // src/plugins/index-file.ts
40
+ import { createHash } from "crypto";
41
+ var indexFileCache = createFSCache();
42
+ function indexFile(options = {}) {
43
+ const {
44
+ target = "default",
45
+ addJsExtension,
46
+ browser = true,
47
+ dynamic = true
48
+ } = options;
49
+ let dynamicCollections;
50
+ function isDynamic(collection) {
51
+ return collection.type === "docs" && collection.docs.dynamic || collection.type === "doc" && collection.dynamic;
52
+ }
53
+ function generateConfigs(core) {
54
+ const serverOptions = {};
55
+ const typeConfigs = [
56
+ 'import("@hanzo/docs-mdx/runtime/types").InternalTypeConfig'
57
+ ];
58
+ const ctx = core.getPluginContext();
59
+ for (const plugin of core.getPlugins()) {
60
+ const indexFilePlugin = plugin["index-file"];
61
+ if (!indexFilePlugin) continue;
62
+ indexFilePlugin.serverOptions?.call(ctx, serverOptions);
63
+ const config = indexFilePlugin.generateTypeConfig?.call(ctx);
64
+ if (config) typeConfigs.push(config);
65
+ }
66
+ return {
67
+ serverOptions,
68
+ tc: typeConfigs.join(" & ")
69
+ };
70
+ }
71
+ return {
72
+ name: "index-file",
73
+ config() {
74
+ dynamicCollections = this.core.getCollections().filter(isDynamic);
75
+ },
76
+ configureServer(server) {
77
+ if (!server.watcher) return;
78
+ server.watcher.on("all", async (event, file) => {
79
+ indexFileCache.delete(file);
80
+ if (dynamicCollections.length === 0) {
81
+ if (target === "vite") return;
82
+ if (target === "default" && event === "change") return;
83
+ }
84
+ const updatedCollection = this.core.getCollections().find((collection) => collection.hasFile(file));
85
+ if (!updatedCollection) return;
86
+ if (!isDynamic(updatedCollection)) {
87
+ if (target === "vite") return;
88
+ if (target === "default" && event === "change") return;
89
+ }
90
+ await this.core.emit({
91
+ filterPlugin: (plugin) => plugin.name === "index-file",
92
+ filterWorkspace: () => false,
93
+ write: true
94
+ });
95
+ });
96
+ },
97
+ async emit() {
98
+ const globCache = /* @__PURE__ */ new Map();
99
+ const { workspace, outDir } = this.core.getOptions();
100
+ const { serverOptions, tc } = generateConfigs(this.core);
101
+ const toEmitEntry = async (path3, content) => {
102
+ const codegen = createCodegen({
103
+ target,
104
+ outDir,
105
+ jsExtension: addJsExtension,
106
+ globCache
107
+ });
108
+ await content({
109
+ core: this.core,
110
+ codegen,
111
+ serverOptions,
112
+ tc,
113
+ workspace: workspace?.name
114
+ });
115
+ return {
116
+ path: path3,
117
+ content: codegen.toString()
118
+ };
119
+ };
120
+ const out = [
121
+ toEmitEntry("server.ts", generateServerIndexFile)
122
+ ];
123
+ if (dynamic)
124
+ out.push(toEmitEntry("dynamic.ts", generateDynamicIndexFile));
125
+ if (browser)
126
+ out.push(toEmitEntry("browser.ts", generateBrowserIndexFile));
127
+ return await Promise.all(out);
128
+ }
129
+ };
130
+ }
131
+ async function generateServerIndexFile(ctx) {
132
+ const { core, codegen, serverOptions, tc } = ctx;
133
+ codegen.lines.push(
134
+ `import { server } from '@hanzo/docs/mdx/runtime/server';`,
135
+ `import type * as Config from '${codegen.formatImportPath(core.getOptions().configPath)}';`,
136
+ "",
137
+ `const create = server<typeof Config, ${tc}>(${JSON.stringify(serverOptions)});`
138
+ );
139
+ async function generateCollectionObject(collection) {
140
+ const base = getBase(collection);
141
+ switch (collection.type) {
142
+ case "docs": {
143
+ if (collection.docs.dynamic) return;
144
+ if (collection.docs.async) {
145
+ const [metaGlob2, headGlob, bodyGlob] = await Promise.all([
146
+ generateMetaCollectionGlob(ctx, collection.meta, true),
147
+ generateDocCollectionFrontmatterGlob(ctx, collection.docs, true),
148
+ generateDocCollectionGlob(ctx, collection.docs)
149
+ ]);
150
+ return `await create.docsLazy("${collection.name}", "${base}", ${metaGlob2}, ${headGlob}, ${bodyGlob})`;
151
+ }
152
+ const [metaGlob, docGlob] = await Promise.all([
153
+ generateMetaCollectionGlob(ctx, collection.meta, true),
154
+ generateDocCollectionGlob(ctx, collection.docs, true)
155
+ ]);
156
+ return `await create.docs("${collection.name}", "${base}", ${metaGlob}, ${docGlob})`;
157
+ }
158
+ case "doc":
159
+ if (collection.dynamic) return;
160
+ if (collection.async) {
161
+ const [headGlob, bodyGlob] = await Promise.all([
162
+ generateDocCollectionFrontmatterGlob(ctx, collection, true),
163
+ generateDocCollectionGlob(ctx, collection)
164
+ ]);
165
+ return `await create.docLazy("${collection.name}", "${base}", ${headGlob}, ${bodyGlob})`;
166
+ }
167
+ return `await create.doc("${collection.name}", "${base}", ${await generateDocCollectionGlob(
168
+ ctx,
169
+ collection,
170
+ true
171
+ )})`;
172
+ case "meta":
173
+ return `await create.meta("${collection.name}", "${base}", ${await generateMetaCollectionGlob(
174
+ ctx,
175
+ collection,
176
+ true
177
+ )})`;
178
+ }
179
+ }
180
+ await codegen.pushAsync(
181
+ core.getCollections().map(async (collection) => {
182
+ const obj = await generateCollectionObject(collection);
183
+ if (!obj) return;
184
+ return `
185
+ export const ${collection.name} = ${obj};`;
186
+ })
187
+ );
188
+ }
189
+ async function generateDynamicIndexFile(ctx) {
190
+ const { core, codegen, serverOptions, tc } = ctx;
191
+ const { configPath, environment, outDir } = core.getOptions();
192
+ const partialOptions = {
193
+ configPath,
194
+ environment,
195
+ outDir
196
+ };
197
+ codegen.lines.push(
198
+ `import { dynamic } from '@hanzo/docs/mdx/runtime/dynamic';`,
199
+ `import * as Config from '${codegen.formatImportPath(configPath)}';`,
200
+ "",
201
+ `const create = await dynamic<typeof Config, ${tc}>(Config, ${JSON.stringify(partialOptions)}, ${JSON.stringify(serverOptions)});`
202
+ );
203
+ async function generateCollectionObjectEntry(collection, absolutePath) {
204
+ const fullPath = path2.relative(process.cwd(), absolutePath);
205
+ const content = await indexFileCache.read(fullPath).catch(() => "");
206
+ const parsed = fumaMatter(content);
207
+ const data = await core.transformFrontmatter(
208
+ {
209
+ collection,
210
+ filePath: fullPath,
211
+ source: content
212
+ },
213
+ parsed.data
214
+ );
215
+ const hash = createHash("md5").update(content).digest("hex");
216
+ const infoStr = [
217
+ // make sure it's included in vercel/nft
218
+ `absolutePath: path.resolve(${JSON.stringify(fullPath)})`
219
+ ];
220
+ for (const [k, v] of Object.entries({
221
+ info: {
222
+ fullPath,
223
+ path: path2.relative(collection.dir, absolutePath)
224
+ },
225
+ data,
226
+ hash
227
+ })) {
228
+ infoStr.push(`${k}: ${JSON.stringify(v)}`);
229
+ }
230
+ return `{ ${infoStr.join(", ")} }`;
231
+ }
232
+ async function generateCollectionObject(parent) {
233
+ let collection;
234
+ if (parent.type === "doc") collection = parent;
235
+ else if (parent.type === "docs") collection = parent.docs;
236
+ if (!collection || !collection.dynamic) return;
237
+ const files = await glob(collection.patterns, {
238
+ cwd: collection.dir,
239
+ absolute: true
240
+ });
241
+ const entries = await Promise.all(
242
+ files.map((file) => generateCollectionObjectEntry(collection, file))
243
+ );
244
+ switch (parent.type) {
245
+ case "docs": {
246
+ const metaGlob = await generateMetaCollectionGlob(
247
+ ctx,
248
+ parent.meta,
249
+ true
250
+ );
251
+ return `await create.docs("${parent.name}", "${getBase(parent)}", ${metaGlob}, ${entries.join(", ")})`;
252
+ }
253
+ case "doc":
254
+ return `await create.doc("${collection.name}", "${getBase(collection)}", ${entries.join(", ")})`;
255
+ }
256
+ }
257
+ await codegen.pushAsync(
258
+ core.getCollections().map(async (collection) => {
259
+ const obj = await generateCollectionObject(collection);
260
+ if (!obj) return;
261
+ return `
262
+ export const ${collection.name} = ${obj};`;
263
+ })
264
+ );
265
+ }
266
+ async function generateBrowserIndexFile(ctx) {
267
+ const { core, codegen, tc } = ctx;
268
+ codegen.lines.push(
269
+ `import { browser } from '@hanzo/docs/mdx/runtime/browser';`,
270
+ `import type * as Config from '${codegen.formatImportPath(core.getOptions().configPath)}';`,
271
+ "",
272
+ `const create = browser<typeof Config, ${tc}>();`
273
+ );
274
+ async function generateCollectionObject(collection) {
275
+ switch (collection.type) {
276
+ case "docs": {
277
+ if (collection.docs.dynamic) return;
278
+ return generateCollectionObject(collection.docs);
279
+ }
280
+ case "doc":
281
+ if (collection.dynamic) return;
282
+ return `create.doc("${collection.name}", ${await generateDocCollectionGlob(ctx, collection)})`;
283
+ }
284
+ }
285
+ codegen.lines.push("const browserCollections = {");
286
+ await codegen.pushAsync(
287
+ core.getCollections().map(async (collection) => {
288
+ const obj = await generateCollectionObject(collection);
289
+ if (!obj) return;
290
+ return ident(`${collection.name}: ${obj},`);
291
+ })
292
+ );
293
+ codegen.lines.push("};", "export default browserCollections;");
294
+ }
295
+ function getBase(collection) {
296
+ return path2.relative(process.cwd(), collection.dir);
297
+ }
298
+ function generateDocCollectionFrontmatterGlob({ codegen, workspace }, collection, eager = false) {
299
+ return codegen.generateGlobImport(collection.patterns, {
300
+ query: {
301
+ collection: collection.name,
302
+ only: "frontmatter",
303
+ workspace
304
+ },
305
+ import: "frontmatter",
306
+ base: collection.dir,
307
+ eager
308
+ });
309
+ }
310
+ function generateDocCollectionGlob({ codegen, workspace }, collection, eager = false) {
311
+ return codegen.generateGlobImport(collection.patterns, {
312
+ query: {
313
+ collection: collection.name,
314
+ workspace
315
+ },
316
+ base: collection.dir,
317
+ eager
318
+ });
319
+ }
320
+ function generateMetaCollectionGlob({ codegen, workspace }, collection, eager = false) {
321
+ return codegen.generateGlobImport(collection.patterns, {
322
+ query: {
323
+ collection: collection.name,
324
+ workspace
325
+ },
326
+ import: "default",
327
+ base: collection.dir,
328
+ eager
329
+ });
330
+ }
331
+
332
+ export {
333
+ indexFile
334
+ };