@blinkk/root 2.0.0-rc.1 → 2.0.1

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.
@@ -45,19 +45,12 @@ interface ConfigureServerOptions {
45
45
  rootConfig: RootConfig;
46
46
  }
47
47
  interface PluginHooks {
48
- /**
49
- * Startup hook called when root is initialized.
50
- */
51
- startup?: (options: {
52
- command: string;
53
- rootConfig: RootConfig;
54
- }) => void | Promise<void>;
55
48
  /**
56
49
  * Post-render hook that's called before the HTML is rendered to the response
57
50
  * object. If a string is returned from this hook, it will replace the
58
51
  * rendered HTML.
59
52
  */
60
- preRender?: (html: string) => void | string | Promise<string>;
53
+ preRender: (html: string) => void | string | Promise<string>;
61
54
  }
62
55
  interface Plugin {
63
56
  [key: string]: any;
@@ -101,10 +94,6 @@ interface Plugin {
101
94
  declare function configureServerPlugins(server: Server, callback: () => Promise<void>, plugins: Plugin[], options: ConfigureServerOptions): Promise<void>;
102
95
  declare function getVitePlugins(plugins: Plugin[]): PluginOption[];
103
96
 
104
- interface RootExperimentsConfig {
105
- [name: string]: boolean | undefined;
106
- enableScriptAsync?: boolean;
107
- }
108
97
  interface RootUserConfig {
109
98
  /**
110
99
  * Canonical domain the website will serve on. Useful for things like the
@@ -138,6 +127,10 @@ interface RootUserConfig {
138
127
  * Config options for the Root.js express server.
139
128
  */
140
129
  server?: RootServerConfig;
130
+ /**
131
+ * Build options for the `root build` command.
132
+ */
133
+ build?: RootBuildConfig;
141
134
  /**
142
135
  * Vite config.
143
136
  * @see {@link https://vitejs.dev/config/} for more information.
@@ -171,7 +164,10 @@ interface RootUserConfig {
171
164
  /**
172
165
  * Experimental config options. Note: these are subject to change at any time.
173
166
  */
174
- experiments?: RootExperimentsConfig;
167
+ experiments?: {
168
+ /** Whether to render `<script>` tags with `async`. */
169
+ enableScriptAsync?: boolean;
170
+ };
175
171
  }
176
172
  type RootConfig = RootUserConfig & {
177
173
  rootDir: string;
@@ -198,23 +194,33 @@ interface RootI18nConfig {
198
194
  * locales.
199
195
  */
200
196
  groups?: Record<string, LocaleGroup>;
197
+ }
198
+ interface RootBuildConfig {
201
199
  /**
202
- * Fallback locales. When a translation doesn't exist for the requested
203
- * locale, it will fall back to the locales as configured, e.g.:
204
- *
205
- * ```
206
- * {
207
- * "en-CA": ["en-GB", "en"],
208
- * "es-MX": ["es-419", "es"]
209
- * }
210
- * ```
200
+ * Excludes the `/intl/{defaultLocale}/...` path from the SSG build.
211
201
  */
212
- fallbacks?: Record<string, string[]>;
202
+ excludeDefaultLocaleFromIntlPaths?: boolean;
213
203
  }
214
204
  interface RootRedirectConfig {
205
+ /**
206
+ * The source path to redirect. Accepts placeholders in the format
207
+ * `[key]` or `[...key]`. Use `[key]` for single segments and
208
+ * `[...key]` for multi-segment wildcards.
209
+ * @example "/old-path/[id]" or "/old-path/[...wildcard]"
210
+ */
215
211
  source: string;
212
+ /**
213
+ * The destination to redirect to. Placeholders from the source can
214
+ * optionally be inserted into the destination using the same
215
+ * placeholder format.
216
+ * @example "/new-path/[id]" or "/new-path/[...wildcard]"
217
+ */
216
218
  destination: string;
217
- type?: number;
219
+ /**
220
+ * The redirect type (`301` = permanent, `302` = temporary). If unspecified,
221
+ * defaults to `302` (temporary).
222
+ */
223
+ type?: 301 | 302;
218
224
  }
219
225
  interface RootHeaderConfig {
220
226
  /** A glob pattern match (regex not supported yet). */
@@ -284,7 +290,22 @@ interface RootServerConfig {
284
290
  */
285
291
  sessionCookieSecret?: string | string[];
286
292
  /**
287
- * List of redirects.
293
+ * List of redirects. Supports optional wildcards.
294
+ *
295
+ * @example
296
+ * ```ts
297
+ * redirects: [
298
+ * {
299
+ * source: '/old-path/[id]',
300
+ * destination: '/new-path/[id]',
301
+ * type: 301,
302
+ * },
303
+ * {
304
+ * source: '/old-path/[...wildcard]',
305
+ * destination: '/new-path/[...wildcard]',
306
+ * },
307
+ * ]
308
+ * ```
288
309
  */
289
310
  redirects?: RootRedirectConfig[];
290
311
  /**
@@ -296,6 +317,10 @@ interface RootServerConfig {
296
317
  * commonly used default values.
297
318
  */
298
319
  security?: RootSecurityConfig;
320
+ /**
321
+ * Home page URL path, which is printed when the dev server starts.
322
+ */
323
+ homePagePath?: string;
299
324
  }
300
325
  declare function defineConfig(config: RootUserConfig): RootUserConfig;
301
326
 
@@ -384,6 +409,14 @@ declare class Renderer {
384
409
  html?: string;
385
410
  notFound?: boolean;
386
411
  }>;
412
+ /**
413
+ * Constructs and returns the project's sitemap.
414
+ *
415
+ * The sitemap is used to:
416
+ * - determine all paths to build in SSG mode
417
+ * - display links on the dev server's 404 page
418
+ * - construct alternates for localized URL paths
419
+ */
387
420
  getSitemap(): Promise<Sitemap>;
388
421
  private renderHtml;
389
422
  render404(options?: {
@@ -538,8 +571,13 @@ interface HandlerContext<Props = any> {
538
571
  getPreferredLocale: (availableLocales: string[]) => string;
539
572
  /** Renders the default exported component from the route. */
540
573
  render: HandlerRenderFn<Props>;
541
- /** Renders a 404 page. */
542
- render404: () => Promise<void>;
574
+ /**
575
+ * Renders a 404 page. When `nextRoute` is true, the next matching route
576
+ * handler will be invoked instead of rendering the default 404 page.
577
+ */
578
+ render404: (options?: {
579
+ nextRoute?: boolean;
580
+ }) => Promise<void>;
543
581
  }
544
582
  /**
545
583
  * The `handle()` function can be exported by a route to define a custom express
@@ -548,11 +586,25 @@ interface HandlerContext<Props = any> {
548
586
  * used to render the route's default component.
549
587
  */
550
588
  type Handler = (req: Request, res: Response, next: NextFunction) => void | Promise<void>;
589
+ interface StaticContentResult {
590
+ body: string;
591
+ contentType?: string;
592
+ }
593
+ /**
594
+ * The `getStaticContent()` function is a SSG handler function for non-HTML
595
+ * routes, e.g. `routes/sitemap.xml.ts`.
596
+ *
597
+ * If the route exports a `getStaticProps()` function, the props returned from
598
+ * that function is passed to `getStaticContent()`. Otherwise a default props
599
+ * value is passed which includes the `rootConfig` and route param values.
600
+ */
601
+ type GetStaticContent = (props: any) => Promise<StaticContentResult | string> | StaticContentResult | string;
551
602
  interface RouteModule {
552
603
  default?: ComponentType<unknown>;
553
604
  getStaticPaths?: GetStaticPaths;
554
605
  getStaticProps?: GetStaticProps;
555
606
  handle?: Handler;
607
+ getStaticContent?: GetStaticContent;
556
608
  }
557
609
  interface Route {
558
610
  /** The relative path to the route file, e.g. `routes/index.tsx`. */
@@ -618,4 +670,4 @@ interface SitemapItem {
618
670
  }>;
619
671
  }
620
672
 
621
- export { type SessionMiddlewareOptions as A, type SaveSessionOptions as B, type ContentSecurityPolicyConfig as C, sessionMiddleware as D, Session as E, Renderer as F, type GetStaticProps as G, type HandlerContext as H, type LocaleGroup as L, type MultipartFile as M, type NextFunction as N, type PluginHooks as P, type Route as R, type Server as S, type XFrameOptionsConfig as X, type RootExperimentsConfig as a, type RootUserConfig as b, type RootConfig as c, type RootI18nConfig as d, type RootRedirectConfig as e, type RootHeaderConfig as f, type RootSecurityConfig as g, type RootServerConfig as h, defineConfig as i, type ConfigureServerHook as j, type ConfigureServerOptions as k, type Plugin as l, configureServerPlugins as m, getVitePlugins as n, type RouteParams as o, type GetStaticPaths as p, type RequestMiddleware as q, type Request as r, type Response as s, type Handler as t, type RouteModule as u, type HandlerRenderOptions as v, type HandlerRenderFn as w, type Sitemap as x, type SitemapItem as y, SESSION_COOKIE as z };
673
+ export { type SitemapItem as A, SESSION_COOKIE as B, type ContentSecurityPolicyConfig as C, type SessionMiddlewareOptions as D, type SaveSessionOptions as E, sessionMiddleware as F, type GetStaticProps as G, type HandlerContext as H, Session as I, Renderer as J, type LocaleGroup as L, type MultipartFile as M, type NextFunction as N, type PluginHooks as P, type Route as R, type Server as S, type XFrameOptionsConfig as X, type RootUserConfig as a, type RootConfig as b, type RootI18nConfig as c, type RootBuildConfig as d, type RootRedirectConfig as e, type RootHeaderConfig as f, type RootSecurityConfig as g, type RootServerConfig as h, defineConfig as i, type ConfigureServerHook as j, type ConfigureServerOptions as k, type Plugin as l, configureServerPlugins as m, getVitePlugins as n, type RouteParams as o, type GetStaticPaths as p, type RequestMiddleware as q, type Request as r, type Response as s, type Handler as t, type StaticContentResult as u, type GetStaticContent as v, type RouteModule as w, type HandlerRenderOptions as x, type HandlerRenderFn as y, type Sitemap as z };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@blinkk/root",
3
- "version": "2.0.0-rc.1",
3
+ "version": "2.0.1",
4
4
  "author": "s@blinkk.com",
5
5
  "license": "MIT",
6
6
  "engines": {
@@ -54,6 +54,7 @@
54
54
  }
55
55
  },
56
56
  "dependencies": {
57
+ "@types/js-yaml": "4.0.9",
57
58
  "@types/micromatch": "4.0.6",
58
59
  "bundle-require": "4.0.2",
59
60
  "busboy": "1.6.0",
@@ -66,13 +67,15 @@
66
67
  "fs-extra": "11.1.1",
67
68
  "html-minifier-terser": "7.2.0",
68
69
  "js-beautify": "1.14.9",
70
+ "js-yaml": "4.1.0",
69
71
  "kleur": "4.1.5",
70
72
  "micromatch": "4.0.5",
71
73
  "sass": "1.69.3",
72
74
  "sirv": "2.0.3",
73
75
  "source-map-support": "0.5.21",
74
76
  "tiny-glob": "0.2.9",
75
- "vite": "5.0.8"
77
+ "vite": "5.0.8",
78
+ "workspace-tools": "0.37.0"
76
79
  },
77
80
  "peerDependencies": {
78
81
  "firebase-admin": ">=11",
@@ -111,7 +114,7 @@
111
114
  "scripts": {
112
115
  "build": "rm -rf dist && tsup-node",
113
116
  "dev": "nodemon --watch src -e ts,tsx --exec pnpm build",
114
- "test": "pnpm build && vitest run",
117
+ "test": "pnpm build && vitest run --test-timeout=30000",
115
118
  "test:watch": "pnpm build && vitest"
116
119
  }
117
120
  }
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/utils/elements.ts","../src/render/html-minify.ts","../src/render/html-pretty.ts","../src/render/route-trie.ts"],"sourcesContent":["export const ELEMENT_RE = /^[a-z][\\w-]*-[\\w-]*$/;\nexport const HTML_ELEMENTS_REGEX = /<([a-z][\\w-]*-[\\w-]*)/g;\n\n/**\n * Returns true if the tagName is a valid custom element tag.\n */\nexport function isValidTagName(tagName: string) {\n return ELEMENT_RE.test(tagName);\n}\n\n/**\n * Returns a list of custom elements used in a src string (e.g. HTML, jsx, lit).\n * NOTE: the impl uses a simple regex, so tagNames used in comments and attr\n * values may be included.\n */\nexport function parseTagNames(src: string): string[] {\n if (!src) {\n return [];\n }\n const tagNames = new Set<string>();\n const matches = Array.from(String(src).matchAll(HTML_ELEMENTS_REGEX));\n for (const match of matches) {\n const tagName = match[1];\n tagNames.add(tagName);\n }\n return Array.from(tagNames);\n}\n","import {createRequire} from 'module';\n\nconst require = createRequire(import.meta.url);\nimport type {Options} from 'html-minifier-terser';\n\nconst {minify} = require('html-minifier-terser');\n\nexport type HtmlMinifyOptions = Options;\n\nexport async function htmlMinify(\n html: string,\n options?: HtmlMinifyOptions\n): Promise<string> {\n const minifyOptions = options || {\n collapseWhitespace: true,\n removeComments: true,\n preserveLineBreaks: true,\n };\n try {\n const min = await minify(html, minifyOptions);\n return min.trimStart();\n } catch (e) {\n console.error('failed to minify html:', e);\n return html;\n }\n}\n","import {createRequire} from 'module';\n\nconst require = createRequire(import.meta.url);\nimport type {HTMLBeautifyOptions} from 'js-beautify';\n\nconst beautify = require('js-beautify');\n\nexport type HtmlPrettyOptions = HTMLBeautifyOptions;\n\nexport async function htmlPretty(\n html: string,\n options?: HtmlPrettyOptions\n): Promise<string> {\n const prettyOptions = options || {\n indent_size: 0,\n end_with_newline: true,\n extra_liners: [],\n };\n try {\n const output = beautify.html(html, prettyOptions);\n return output.trimStart();\n } catch (e) {\n console.error('failed to pretty html:', e);\n return html;\n }\n}\n","/**\n * A trie data structure that stores routes. Supports Next-style routing using\n * [param], [...catchall], and [[...optcatchall]] placeholders.\n */\nexport class RouteTrie<T> {\n private children: Record<string, RouteTrie<T>> = {};\n private paramNodes?: {[param: string]: ParamNode<T>};\n private catchAllNodes?: CatchAllNode<T>;\n private optCatchAllNodes?: CatchAllNode<T>;\n private route?: T;\n\n /**\n * Adds a route to the trie.\n */\n add(path: string, route: T) {\n path = this.normalizePath(path);\n\n // If the end was reached, save the value to the node.\n if (path === '') {\n this.route = route;\n return;\n }\n\n const [head, tail] = this.splitPath(path);\n\n if (head.startsWith('[[...') && head.endsWith(']]')) {\n const paramName = head.slice(5, -2);\n this.optCatchAllNodes = new CatchAllNode(paramName, route);\n return;\n }\n if (head.startsWith('[...') && head.endsWith(']')) {\n const paramName = head.slice(4, -1);\n this.catchAllNodes = new CatchAllNode(paramName, route);\n return;\n }\n\n let nextNode: RouteTrie<T>;\n if (head.startsWith('[') && head.endsWith(']')) {\n if (!this.paramNodes) {\n this.paramNodes = {};\n }\n const paramName = head.slice(1, -1);\n if (!this.paramNodes[paramName]) {\n this.paramNodes[paramName] = new ParamNode(paramName);\n }\n nextNode = this.paramNodes[paramName].trie;\n } else {\n nextNode = this.children[head];\n if (!nextNode) {\n nextNode = new RouteTrie();\n this.children[head] = nextNode;\n }\n }\n nextNode.add(tail, route);\n }\n\n /**\n * Returns a route mapped to the given path and any parameter values from the\n * URL.\n */\n get(path: string): [T | undefined, Record<string, string>] {\n const params = {};\n const route = this.getRoute(path, params);\n return [route, params];\n }\n\n /**\n * Walks the route trie and calls a callback function for each route.\n */\n walk(cb: (urlPath: string, route: T) => Promise<void> | void): Promise<void> {\n const promises: Array<Promise<void>> = [];\n const addPromise = (promise: Promise<void> | void) => {\n if (promise) {\n promises.push(promise);\n }\n };\n if (this.route) {\n addPromise(cb('/', this.route));\n }\n if (this.paramNodes) {\n Object.values(this.paramNodes).forEach((paramChild) => {\n const param = `[${paramChild.name}]`;\n paramChild.trie.walk((childPath: string, route: T) => {\n const paramUrlPath = `/${param}${childPath}`;\n addPromise(cb(paramUrlPath, route));\n });\n });\n }\n if (this.catchAllNodes) {\n const wildcardUrlPath = `/[...${this.catchAllNodes.name}]`;\n addPromise(cb(wildcardUrlPath, this.catchAllNodes.route));\n }\n if (this.optCatchAllNodes) {\n const wildcardUrlPath = `/[[...${this.optCatchAllNodes.name}]]`;\n addPromise(cb(wildcardUrlPath, this.optCatchAllNodes.route));\n }\n for (const subpath of Object.keys(this.children)) {\n const childTrie = this.children[subpath];\n childTrie.walk((childPath: string, childRoute: T) => {\n addPromise(cb(`/${subpath}${childPath}`, childRoute));\n });\n }\n return Promise.all(promises).then(() => {});\n }\n\n /**\n * Removes all routes from the trie.\n */\n clear() {\n this.children = {};\n this.paramNodes = undefined;\n this.catchAllNodes = undefined;\n this.optCatchAllNodes = undefined;\n this.route = undefined;\n }\n\n private getRoute(\n urlPath: string,\n params: Record<string, string>\n ): T | undefined {\n urlPath = this.normalizePath(urlPath);\n if (urlPath === '') {\n if (this.route) {\n return this.route;\n }\n if (this.optCatchAllNodes) {\n if (urlPath) {\n params[this.optCatchAllNodes.name] = urlPath;\n }\n return this.optCatchAllNodes.route;\n }\n return undefined;\n }\n\n const [head, tail] = this.splitPath(urlPath);\n\n const child = this.children[head];\n if (child) {\n const route = child.getRoute(tail, params);\n if (route) {\n return route;\n }\n }\n\n if (this.paramNodes) {\n for (const paramChild of Object.values(this.paramNodes)) {\n const route = paramChild.trie.getRoute(tail, params);\n if (route) {\n params[paramChild.name] = head;\n return route;\n }\n }\n }\n\n if (this.catchAllNodes) {\n params[this.catchAllNodes.name] = urlPath;\n return this.catchAllNodes.route;\n }\n\n if (this.optCatchAllNodes) {\n params[this.optCatchAllNodes.name] = urlPath;\n return this.optCatchAllNodes.route;\n }\n\n return undefined;\n }\n\n /**\n * Normalizes a path for inclusion into the route trie.\n */\n private normalizePath(path: string) {\n // Remove leading/trailing slashes.\n return path.replace(/^\\/+/g, '').replace(/\\/+$/g, '');\n }\n\n /**\n * Splits the parent directory from its children, e.g.:\n *\n * splitPath(\"foo/bar/baz\") -> [\"foo\", \"bar/baz\"]\n */\n private splitPath(path: string): [string, string] {\n const i = path.indexOf('/');\n if (i === -1) {\n return [path, ''];\n }\n return [path.slice(0, i), path.slice(i + 1)];\n }\n}\n\n/**\n * A node in the RouteTrie for a :param child.\n */\nclass ParamNode<T> {\n readonly name: string;\n readonly trie: RouteTrie<T> = new RouteTrie();\n\n constructor(name: string) {\n this.name = name;\n }\n}\n\n/**\n * A node in the RouteTrie for a *wildcard child.\n */\nclass CatchAllNode<T> {\n readonly name: string;\n readonly route: T;\n\n constructor(name: string, route: T) {\n this.name = name;\n this.route = route;\n }\n}\n"],"mappings":"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","names":["require","createRequire","require"]}
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/cli/cli.ts","../src/cli/build.ts","../src/node/element-graph.ts","../src/render/asset-map/build-asset-map.ts","../src/utils/batch.ts","../src/cli/codegen.ts","../src/cli/create-package.ts","../src/cli/dev.ts","../src/middleware/hooks.ts","../src/middleware/redirects.ts","../src/render/asset-map/dev-asset-map.ts","../src/utils/ports.ts","../src/utils/rand.ts","../src/cli/preview.ts","../src/cli/start.ts"],"sourcesContent":["import {Command} from 'commander';\nimport {bgGreen, black} from 'kleur/colors';\nimport {build} from './build.js';\nimport {codegen} from './codegen.js';\nimport {createPackage} from './create-package.js';\nimport {dev, createDevServer} from './dev.js';\nimport {preview, createPreviewServer} from './preview.js';\nimport {start, createProdServer} from './start.js';\n\nclass CliRunner {\n private name: string;\n private version: string;\n\n constructor(name: string, version: string) {\n this.name = name;\n this.version = version;\n }\n\n async run(argv: string[]) {\n const program = new Command('root');\n program.version(this.version);\n program.option('-q, --quiet', 'quiet');\n program.hook('preAction', (cmd) => {\n if (!cmd.opts().quiet) {\n console.log(\n `🥕 ${bgGreen(black(` ${this.name} `))} v${this.version}\\n`\n );\n }\n });\n program\n .command('build [path]')\n .description('generates a static build')\n .option('--ssr-only', 'produce a ssr-only build')\n .option(\n '--mode <mode>',\n 'see: https://vitejs.dev/guide/env-and-mode.html#modes',\n 'production'\n )\n .option(\n '-c, --concurrency <num>',\n 'number of files to build concurrently',\n '10'\n )\n .action(build);\n program\n .command('codegen [type] [name]')\n .description('generates boilerplate code')\n .option('--out <outdir>', 'output dir')\n .action(codegen);\n program\n .command('create-package [path]')\n .alias('package')\n .description(\n 'creates a standalone npm package for deployment to various hosting services'\n )\n .option('--target <target>', 'hosting target, i.e. appengine or firebase')\n .option('--out <outdir>', 'output dir')\n .option('--mode <mode>', 'deployment mode, i.e. production or preview')\n .action((rootPackageDir, options) => {\n options.version = this.version;\n createPackage(rootPackageDir, options);\n });\n program\n .command('dev [path]')\n .description('starts the server in development mode')\n .option(\n '--host <host>',\n 'network address the server should listen on, e.g. 127.0.0.1'\n )\n .action(dev);\n program\n .command('preview [path]')\n .description('starts the server in preview mode')\n .option(\n '--host <host>',\n 'network address the server should listen on, e.g. 127.0.0.1'\n )\n .action(preview);\n program\n .command('start [path]')\n .description('starts the server in production mode')\n .option(\n '--host <host>',\n 'network address the server should listen on, e.g. 127.0.0.1'\n )\n .action(start);\n await program.parseAsync(argv);\n }\n}\n\nexport {\n CliRunner,\n build,\n createPackage,\n dev,\n createDevServer,\n preview,\n createPreviewServer,\n start,\n createProdServer,\n};\n","/* eslint-disable no-control-regex */\nimport path from 'node:path';\nimport {fileURLToPath} from 'node:url';\n\nimport fsExtra from 'fs-extra';\nimport {dim, cyan} from 'kleur/colors';\nimport glob from 'tiny-glob';\nimport {build as viteBuild, Manifest, ManifestChunk, UserConfig} from 'vite';\n\nimport {getVitePlugins} from '../core/plugin.js';\nimport {Route} from '../core/types.js';\nimport {getElements} from '../node/element-graph.js';\nimport {bundleRootConfig, loadRootConfig} from '../node/load-config.js';\nimport {BuildAssetMap} from '../render/asset-map/build-asset-map.js';\nimport {htmlMinify} from '../render/html-minify.js';\nimport {htmlPretty} from '../render/html-pretty.js';\nimport {batchAsyncCalls} from '../utils/batch.js';\nimport {\n copyGlob,\n fileExists,\n isDirectory,\n isJsFile,\n loadJson,\n makeDir,\n rmDir,\n writeFile,\n} from '../utils/fsutils.js';\n\nconst __dirname = path.dirname(fileURLToPath(import.meta.url));\n\ntype RenderModule = typeof import('../render/render.js');\n\ninterface BuildOptions {\n ssrOnly?: boolean;\n mode?: string;\n concurrency?: string | number;\n}\n\nexport async function build(rootProjectDir?: string, options?: BuildOptions) {\n const mode = options?.mode || 'production';\n process.env.NODE_ENV = mode;\n\n const rootDir = path.resolve(rootProjectDir || process.cwd());\n const rootConfig = await loadRootConfig(rootDir, {command: 'build'});\n const distDir = path.join(rootDir, 'dist');\n const ssrOnly = options?.ssrOnly || false;\n\n console.log();\n console.log(`${dim('┃')} project: ${rootDir}`);\n console.log(`${dim('┃')} output: ${distDir}/html`);\n console.log(`${dim('┃')} mode: ${mode}`);\n console.log();\n\n await rmDir(distDir);\n await makeDir(distDir);\n\n const routeFiles: string[] = [];\n if (await isDirectory(path.join(rootDir, 'routes'))) {\n const pageFiles = await glob('routes/**/*', {cwd: rootDir});\n pageFiles.forEach((file) => {\n const parts = path.parse(file);\n if (!parts.name.startsWith('_') && isJsFile(parts.base)) {\n routeFiles.push(path.resolve(rootDir, file));\n }\n });\n }\n\n const elementGraph = await getElements(rootConfig);\n const elements = Object.values(elementGraph.sourceFiles).map((sourceFile) => {\n return sourceFile.filePath;\n });\n\n const bundleScripts: string[] = [];\n if (await isDirectory(path.join(rootDir, 'bundles'))) {\n const bundleFiles = await glob('bundles/*', {cwd: rootDir});\n bundleFiles.forEach((file) => {\n const parts = path.parse(file);\n if (isJsFile(parts.base)) {\n bundleScripts.push(path.resolve(rootDir, file));\n }\n });\n }\n\n const rootPlugins = rootConfig.plugins || [];\n\n // Run any \"startup\" hooks.\n for (const plugin of rootPlugins) {\n if (typeof plugin.hooks?.startup === 'function') {\n await plugin.hooks.startup({command: 'build', rootConfig});\n }\n }\n\n const viteConfig = rootConfig.vite || {};\n const vitePlugins = [\n ...(viteConfig.plugins || []),\n ...getVitePlugins(rootPlugins),\n ];\n\n const baseConfig: UserConfig = {\n ...viteConfig,\n root: rootDir,\n mode: mode,\n esbuild: {\n ...viteConfig.esbuild,\n jsx: 'automatic',\n jsxImportSource: 'preact',\n treeShaking: true,\n },\n plugins: vitePlugins,\n };\n\n // Bundle the render.js file with vite along with any plugins `ssrInput()`\n // config values. These inputs are bundled through vite and support things\n // like `input.meta.glob()`.\n const ssrInput = {\n render: path.resolve(__dirname, './render.js'),\n };\n rootPlugins.forEach((plugin) => {\n if (plugin.ssrInput) {\n Object.assign(ssrInput, plugin.ssrInput());\n }\n });\n const noExternalConfig = viteConfig.ssr?.noExternal;\n const noExternal: Array<string | RegExp> = [];\n if (noExternalConfig) {\n if (Array.isArray(noExternalConfig)) {\n noExternal.push(...noExternalConfig);\n } else {\n noExternal.push(noExternalConfig as string | RegExp);\n }\n }\n await viteBuild({\n ...baseConfig,\n publicDir: false,\n build: {\n ...viteConfig?.build,\n rollupOptions: {\n ...viteConfig?.build?.rollupOptions,\n input: ssrInput,\n output: {\n format: 'esm',\n chunkFileNames: 'chunks/[hash].min.js',\n assetFileNames: 'assets/[hash][extname]',\n sanitizeFileName: sanitizeFileName,\n },\n },\n outDir: path.join(distDir, 'server'),\n ssr: true,\n ssrManifest: false,\n cssCodeSplit: true,\n target: 'esnext',\n minify: false,\n modulePreload: {polyfill: false},\n reportCompressedSize: false,\n sourcemap: 'inline',\n },\n ssr: {\n ...viteConfig.ssr,\n target: 'node',\n noExternal: ['@blinkk/root', '@blinkk/root-cms/richtext', ...noExternal],\n },\n });\n\n // Pre-render CSS deps from /routes/.\n await viteBuild({\n ...baseConfig,\n publicDir: false,\n build: {\n ...viteConfig?.build,\n rollupOptions: {\n ...viteConfig?.build?.rollupOptions,\n input: [...routeFiles],\n output: {\n format: 'esm',\n entryFileNames: 'assets/[hash].min.js',\n assetFileNames: 'assets/[hash][extname]',\n chunkFileNames: 'chunks/[hash].min.js',\n sanitizeFileName: sanitizeFileName,\n ...viteConfig?.build?.rollupOptions?.output,\n },\n },\n outDir: path.join(distDir, '.build/routes'),\n ssr: true,\n ssrManifest: false,\n ssrEmitAssets: true,\n manifest: true,\n cssCodeSplit: true,\n target: 'esnext',\n minify: true,\n modulePreload: {polyfill: false},\n reportCompressedSize: false,\n },\n });\n\n // Pre-render /elements/ and /bundles/.\n const clientInput = [...elements, ...bundleScripts];\n if (clientInput.length > 0) {\n await viteBuild({\n ...baseConfig,\n publicDir: false,\n build: {\n ...viteConfig?.build,\n rollupOptions: {\n ...viteConfig?.build?.rollupOptions,\n input: [...elements, ...bundleScripts],\n output: {\n format: 'esm',\n entryFileNames: 'assets/[hash].min.js',\n assetFileNames: 'assets/[hash][extname]',\n chunkFileNames: 'chunks/[hash].min.js',\n sanitizeFileName: sanitizeFileName,\n ...viteConfig?.build?.rollupOptions?.output,\n },\n },\n outDir: path.join(distDir, '.build/client'),\n ssr: false,\n ssrManifest: false,\n manifest: true,\n cssCodeSplit: true,\n target: 'esnext',\n minify: true,\n modulePreload: {polyfill: false},\n reportCompressedSize: false,\n },\n });\n } else {\n await writeFile(\n path.join(distDir, '.build/client/.vite/manifest.json'),\n '{}'\n );\n }\n\n // Bundle the root.config.ts file to dist/root.config.js.\n await bundleRootConfig(rootDir, path.join(distDir, 'root.config.js'));\n\n // Copy CSS files from `dist/.build/routes/**/*.css` to\n // `dist/.build/client/` and flatten the routes manifest to ignore any\n // imported modules. Then add the route assets to the client manifest.\n await copyGlob(\n '**/*.css',\n path.join(distDir, '.build/routes'),\n path.join(distDir, '.build/client')\n );\n const routesManifest = await loadJson<Manifest>(\n path.join(distDir, '.build/routes/.vite/manifest.json')\n );\n const clientManifest = await loadJson<Manifest>(\n path.join(distDir, '.build/client/.vite/manifest.json')\n );\n function collectRouteCss(\n asset: ManifestChunk,\n cssDeps: Set<string>,\n visited: Set<string>\n ) {\n if (!asset || !asset.file || visited.has(asset.file)) {\n return;\n }\n visited.add(asset.file);\n if (asset.css) {\n asset.css.forEach((dep) => cssDeps.add(dep));\n }\n if (asset.imports) {\n asset.imports.forEach((manifestKey) => {\n collectRouteCss(routesManifest[manifestKey], cssDeps, visited);\n });\n }\n }\n Object.keys(routesManifest).forEach((manifestKey) => {\n const asset = routesManifest[manifestKey];\n if (asset.isEntry) {\n const visited = new Set<string>();\n const cssDeps = new Set<string>();\n collectRouteCss(asset, cssDeps, visited);\n asset.css = Array.from(cssDeps);\n asset.imports = [];\n clientManifest[manifestKey] = asset;\n } else if (asset.file.endsWith('.css')) {\n clientManifest[manifestKey] = asset;\n }\n });\n\n // Use the output of the client build to generate an asset map, which is used\n // by the renderer for automatically injecting dependencies for a page.\n const assetMap = BuildAssetMap.fromViteManifest(\n rootConfig,\n clientManifest,\n elementGraph\n );\n\n // Save the root's asset map to `dist/.root/manifest.json` for use by the prod\n // SSR server.\n const rootManifest = assetMap.toJson();\n await writeFile(\n path.join(distDir, '.root/manifest.json'),\n JSON.stringify(rootManifest, null, 2)\n );\n\n // Save the element graph to `dist/.root/elements.json` for use by the prod\n // SSR server.\n const elementGraphJson = elementGraph.toJson();\n await writeFile(\n path.join(distDir, '.root/elements.json'),\n JSON.stringify(elementGraphJson, null, 2)\n );\n\n // Write SSG output to `dist/html`.\n const buildDir = path.join(distDir, 'html');\n\n // Recursively copy files from `public` to `dist/html`.\n const publicDir = path.join(rootDir, 'public');\n if (fsExtra.existsSync(path.join(rootDir, 'public'))) {\n fsExtra.copySync(publicDir, buildDir, {dereference: true});\n } else {\n await makeDir(buildDir);\n }\n\n const seenAssets = new Set<string>();\n async function copyAssetToDistHtml(assetUrl: string) {\n if (seenAssets.has(assetUrl)) {\n return;\n }\n seenAssets.add(assetUrl);\n const assetRelPath = assetUrl.slice(1);\n const assetFrom = path.join(distDir, '.build/client', assetRelPath);\n const assetTo = path.join(buildDir, assetRelPath);\n // Ignore assets that don't exist. This is because build artifacts from\n // the routes/ folder are not copied to dist/client (only css deps are).\n if (!(await fileExists(assetFrom))) {\n console.log(`${assetFrom} does not exist`);\n return;\n }\n await fsExtra.copy(assetFrom, assetTo);\n printFileOutput(fileSize(assetTo), 'dist/html/', assetRelPath);\n }\n\n // Copy files from `dist/client/{assets,chunks}` to `dist/html` using the\n // root manifest. Ignore route files.\n console.log('\\njs/css output:');\n await Promise.all(\n Object.keys(rootManifest).map(async (src) => {\n const assetData = rootManifest[src];\n // Only imported css from routes files should be included in build output.\n // Don't expose route files in the final output. If any client-side code\n // relies on route dependencies, it should probably be broken out into a\n // shared component instead.\n if (isRouteFile(src)) {\n const importedCss = assetData.importedCss || [];\n for (const cssAssetUrl of importedCss) {\n await copyAssetToDistHtml(cssAssetUrl);\n }\n return;\n }\n\n // Ignore files with no assetUrl, which can sometimes occur if a source\n // file is empty.\n if (!assetData.assetUrl) {\n return;\n }\n\n // Copy assets and any imported css files.\n await copyAssetToDistHtml(assetData.assetUrl);\n const importedCss = assetData.importedCss || [];\n for (const cssAssetUrl of importedCss) {\n await copyAssetToDistHtml(cssAssetUrl);\n }\n })\n );\n\n // Pre-render HTML pages (SSG).\n if (!ssrOnly) {\n const render: RenderModule = await import(\n path.join(distDir, 'server/render.js')\n );\n const renderer = new render.Renderer(rootConfig, {assetMap, elementGraph});\n const sitemap = await renderer.getSitemap();\n\n const sitemapXmlItems: Array<{\n url: string;\n locale: string;\n alts: Array<{locale: string; hreflang: string; url: string}>;\n }> = [];\n if (rootConfig.sitemap && !rootConfig.domain) {\n throw new Error(\n 'missing \"domain\" in root.config.ts, required when using {sitemap: true}'\n );\n }\n const domain = rootConfig.domain!;\n\n console.log('\\nhtml output:');\n const batchSize = Number(options?.concurrency || 10);\n await batchAsyncCalls(Object.keys(sitemap), batchSize, async (urlPath) => {\n const sitemapItem = sitemap[urlPath];\n try {\n const data = await renderer.renderRoute(sitemapItem.route, {\n routeParams: sitemapItem.params,\n });\n if (data.notFound) {\n return;\n }\n\n // The renderer currently assumes that all paths serve HTML.\n // TODO(stevenle): support non-HTML routes using `routes/[name].[ext].ts`.\n let outFilePath = path.join(urlPath.slice(1), 'index.html');\n if (outFilePath.endsWith('404/index.html')) {\n outFilePath = outFilePath.replace('404/index.html', '404.html');\n }\n const outPath = path.join(buildDir, outFilePath);\n\n // Save the url to sitemap.xml. Ignore error files (e.g. 404.html).\n if (rootConfig.sitemap && outFilePath.endsWith('index.html')) {\n const sitemapXmlItem: {\n url: string;\n locale: string;\n alts: Array<{locale: string; hreflang: string; url: string}>;\n } = {\n url: `${domain}${urlPath}`,\n locale: sitemapItem.locale,\n alts: [],\n };\n sitemapXmlItems.push(sitemapXmlItem);\n if (sitemapItem.alts) {\n Object.entries(sitemapItem.alts).forEach(([altLocale, item]) => {\n sitemapXmlItem.alts.push({\n url: `${domain}${item.urlPath}`,\n locale: altLocale,\n hreflang: item.hrefLang,\n });\n });\n }\n }\n\n // Render html and save the file to dist/html.\n let html = data.html || '';\n if (rootConfig.prettyHtml !== false) {\n html = await htmlPretty(html, rootConfig.prettyHtmlOptions);\n }\n // HTML minification is `true` by default. Set to `false` to disable.\n if (rootConfig.minifyHtml !== false) {\n html = await htmlMinify(html, rootConfig.minifyHtmlOptions);\n }\n await writeFile(outPath, html);\n\n printFileOutput(fileSize(outPath), 'dist/html/', outFilePath);\n } catch (e) {\n logBuildError(\n {route: sitemapItem.route, params: sitemapItem.params, urlPath},\n e\n );\n throw new Error(\n `BuildError: ${urlPath} (${sitemapItem.route.src}) failed to build.`\n );\n }\n });\n\n // Generate sitemap.xml.\n if (rootConfig.sitemap) {\n const sitemapXmlBuilder: string[] = [];\n sitemapXmlItems.sort((a, b) => a.url.localeCompare(b.url));\n sitemapXmlItems.forEach((item) => {\n sitemapXmlBuilder.push('<url>');\n sitemapXmlBuilder.push(` <loc>${item.url}</loc>`);\n if (item.alts.length > 0) {\n item.alts.sort((a, b) => a.hreflang.localeCompare(b.hreflang));\n item.alts.forEach((alt) => {\n if (item.locale !== alt.locale) {\n sitemapXmlBuilder.push(\n ` <xhtml:link rel=\"alternate\" hreflang=\"${alt.hreflang}\" href=\"${alt.url}\" />`\n );\n }\n });\n }\n sitemapXmlBuilder.push('</url>');\n });\n\n const sitemapXmlLines = [\n '<?xml version=\"1.0\" encoding=\"UTF-8\"?>',\n '<urlset xmlns=\"http://www.sitemaps.org/schemas/sitemap/0.9\" xmlns:xhtml=\"http://www.w3.org/1999/xhtml\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:schemaLocation=\"http://www.sitemaps.org/schemas/sitemap/0.9 http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd\">',\n ...sitemapXmlBuilder,\n '</urlset>',\n ];\n const sitemapXml = sitemapXmlLines.join('\\n');\n const outPath = path.join(buildDir, 'sitemap.xml');\n await writeFile(outPath, sitemapXml);\n printFileOutput(fileSize(outPath), 'dist/html/', 'sitemap.xml');\n }\n }\n}\n\nfunction isRouteFile(filepath: string) {\n return filepath.startsWith('routes') && isJsFile(filepath);\n}\n\nfunction fileSize(filepath: string) {\n const stats = fsExtra.statSync(filepath);\n const bytes = stats.size;\n\n const k = 1024;\n if (bytes < k) {\n return (bytes / k).toFixed(2) + ' kB';\n }\n const units = ['B', 'kB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];\n const i = Math.floor(Math.log(bytes) / Math.log(k));\n return parseFloat((bytes / Math.pow(k, i)).toFixed(2)) + ' ' + units[i];\n}\n\nfunction printFileOutput(\n fileSize: string,\n outputDir: string,\n outputFile: string\n) {\n const indent = ' '.repeat(2);\n const paddedSize = fileSize.padStart(9, ' ');\n console.log(\n `${indent}${dim(paddedSize)} ${dim(outputDir)}${cyan(outputFile)}`\n );\n}\n\nfunction sanitizeFileName(name: string): string {\n return (\n name\n // Remove placeholder vars from paths like routes/[...var].tsx.\n .replaceAll('...', '')\n .replaceAll('_', '')\n .replaceAll('[', '')\n .replaceAll(']', '')\n // Remove non-ascii chars and null bytes.\n .replace(/[^\\x00-\\x7F]/g, '')\n .replace(/\\x00/g, '')\n .toLowerCase()\n );\n}\n\ninterface BuildContext {\n route: Route;\n params: Record<string, string>;\n urlPath: string;\n}\n\nfunction logBuildError(ctx: BuildContext, e: Error) {\n const {route, params, urlPath} = ctx;\n const errorString = String(e.stack || e);\n console.error();\n if (Object.keys(params).length > 0) {\n console.error(\n `An error occurred building ${urlPath} (${route.src}) with params:\n${formatParams(params)}\n\nThe error was:\n ${errorString}\n `.trim()\n );\n } else {\n console.error(\n `An error occurred building ${urlPath} (${route.src})\n\nThe error was:\n ${errorString}`\n );\n }\n}\n\nfunction formatParams(params: Record<string, string>) {\n return Object.entries(params)\n .map(([key, value]) => {\n return ` ${key}: ${value}`;\n })\n .join('\\n');\n}\n","import fs from 'node:fs';\nimport path from 'node:path';\nimport glob from 'tiny-glob';\nimport {searchForWorkspaceRoot} from 'vite';\nimport {RootConfig} from '../core/config.js';\nimport {isValidTagName, parseTagNames} from '../utils/elements.js';\nimport {directoryContains, isDirectory, isJsFile} from '../utils/fsutils.js';\n\ninterface ElementSourceFile {\n /** Full file path. */\n filePath: string;\n /** Path relative to the root project directory. */\n relPath: string;\n}\n\n/**\n * Dependency graph for element files to capture which other elements are used\n * by any particular element.\n */\nexport class ElementGraph {\n /**\n * Element tagName => sourceFile.\n */\n readonly sourceFiles: {[tagName: string]: ElementSourceFile} = {};\n\n /**\n * Element tagName => set of element tagName dependencies.\n */\n private deps: Record<string, string[]> = {};\n\n constructor(sourceFiles: {[tagName: string]: ElementSourceFile}) {\n this.sourceFiles = sourceFiles;\n }\n\n toJson() {\n for (const tagName in this.sourceFiles) {\n this.deps[tagName] ??= this.parseDepsFromSource(tagName);\n }\n return {\n sourceFiles: this.sourceFiles,\n deps: this.deps,\n };\n }\n\n static fromJson(data: {deps: any; sourceFiles: any}) {\n const graph = new ElementGraph(data.sourceFiles);\n graph.deps = data.deps;\n return graph;\n }\n\n getDeps(tagName: string, visited?: Set<string>): string[] {\n visited ??= new Set();\n if (visited.has(tagName)) {\n return [];\n }\n\n visited.add(tagName);\n this.deps[tagName] ??= this.parseDepsFromSource(tagName);\n\n const deps = new Set(this.deps[tagName]);\n for (const depTagName of this.deps[tagName]) {\n for (const childDep of this.getDeps(depTagName, visited)) {\n deps.add(childDep);\n }\n }\n return Array.from(deps);\n }\n\n /**\n * Parses an element's source file for usage of other custom elements.\n */\n private parseDepsFromSource(tagName: string): string[] {\n const srcFile = this.sourceFiles[tagName];\n if (!srcFile) {\n throw new Error(`could not find file path for tagName <${tagName}>`);\n }\n const src = fs.readFileSync(srcFile.filePath, 'utf-8');\n const tagNames = parseTagNames(src);\n const deps = new Set<string>();\n for (const depTagName of tagNames) {\n if (depTagName !== tagName && depTagName in this.sourceFiles) {\n deps.add(depTagName);\n }\n }\n return Array.from(deps);\n }\n}\n\n/**\n * Returns a map of all the element file definitions in the project.\n */\nexport async function getElements(\n rootConfig: RootConfig\n): Promise<ElementGraph> {\n const rootDir = rootConfig.rootDir;\n\n const elementsDirs = getElementsDirs(rootConfig);\n const excludePatterns = rootConfig.elements?.exclude || [];\n const excludeElement = (moduleId: string) => {\n return excludePatterns.some((pattern) => Boolean(moduleId.match(pattern)));\n };\n\n const elementFilePaths: {[tagName: string]: ElementSourceFile} = {};\n for (const dirPath of elementsDirs) {\n if (await isDirectory(dirPath)) {\n const files = await glob('**/*', {cwd: dirPath});\n files.forEach((file) => {\n const parts = path.parse(file);\n if (isJsFile(parts.base) && isValidTagName(parts.name)) {\n const tagName = parts.name;\n const filePath = path.join(dirPath, file);\n const relPath = path.relative(rootDir, filePath);\n if (!excludeElement(relPath)) {\n elementFilePaths[tagName] = {filePath, relPath};\n }\n }\n });\n }\n }\n\n const graph = new ElementGraph(elementFilePaths);\n return graph;\n}\n\n/**\n * Get all element dirs.\n */\nexport function getElementsDirs(rootConfig: RootConfig) {\n const rootDir = rootConfig.rootDir;\n const workspaceRoot = searchForWorkspaceRoot(rootDir);\n\n const elementsDirs = [path.join(rootDir, 'elements')];\n const elementsInclude = rootConfig.elements?.include || [];\n\n for (const dirPath of elementsInclude) {\n const elementsDir = path.resolve(rootDir, dirPath);\n if (!directoryContains(rootDir, elementsDir)) {\n throw new Error(\n `the elements dir (${dirPath}) should be within the project's workspace (${workspaceRoot})`\n );\n }\n elementsDirs.push(elementsDir);\n }\n\n return elementsDirs;\n}\n","import fs from 'node:fs';\nimport path from 'node:path';\nimport {Manifest} from 'vite';\nimport {RootConfig} from '../../core/config.js';\nimport {ElementGraph} from '../../node/element-graph.js';\nimport {isJsFile} from '../../utils/fsutils.js';\nimport {Asset, AssetMap} from './asset-map.js';\n\nexport type BuildAssetManifest = Record<\n string,\n {\n src: string;\n assetUrl: string;\n importedModules: string[];\n importedCss: string[];\n isElement: boolean;\n }\n>;\n\nexport class BuildAssetMap implements AssetMap {\n private rootConfig: RootConfig;\n private srcToAsset: Map<string, BuildAsset>;\n\n constructor(rootConfig: RootConfig) {\n this.rootConfig = rootConfig;\n this.srcToAsset = new Map();\n }\n\n async get(src: string): Promise<Asset | null> {\n const asset = this.srcToAsset.get(src);\n if (asset) {\n return asset;\n }\n // Try resolving the realpath of the asset, following symlinks.\n const realSrc = realPathRelativeTo(this.rootConfig.rootDir, src);\n if (realSrc !== src) {\n const asset = this.srcToAsset.get(realSrc);\n if (asset) {\n return asset;\n }\n }\n console.log(`could not find build asset: ${src}`);\n return null;\n }\n\n private add(asset: BuildAsset) {\n this.srcToAsset.set(asset.src, asset);\n }\n\n toJson(): BuildAssetManifest {\n const result: BuildAssetManifest = {};\n for (const src of this.srcToAsset.keys()) {\n result[src] = this.srcToAsset.get(src)!.toJson();\n }\n return result;\n }\n\n static fromViteManifest(\n rootConfig: RootConfig,\n clientManifest: Manifest,\n elementsGraph: ElementGraph\n ) {\n const assetMap = new BuildAssetMap(rootConfig);\n\n const elementFiles = new Set();\n Object.values(elementsGraph.sourceFiles).forEach((elementSource) => {\n elementFiles.add(elementSource.relPath);\n // Vite will resolve symlinks, so we need to follow the src and add the\n // realpath to the element files.\n const realSrc = realPathRelativeTo(\n rootConfig.rootDir,\n elementSource.relPath\n );\n if (realSrc !== elementSource.filePath) {\n elementFiles.add(realSrc);\n }\n });\n\n Object.keys(clientManifest).forEach((manifestKey) => {\n const src = manifestKey;\n const manifestChunk = clientManifest[manifestKey];\n const isElement = elementFiles.has(src);\n // NOTES(stevenle): routes/ files are included in the manifest for\n // their CSS deps, but do not have an asset URL.\n const assetUrl =\n src.startsWith('routes/') && isJsFile(src)\n ? ''\n : `/${manifestChunk.file}`;\n const assetData = {\n src: src,\n assetUrl: assetUrl,\n importedModules: manifestChunk.imports || [],\n importedCss: (manifestChunk.css || []).map((relPath) => `/${relPath}`),\n isElement: isElement,\n };\n assetMap.add(new BuildAsset(assetMap, assetData));\n });\n\n return assetMap;\n }\n\n static fromRootManifest(\n rootConfig: RootConfig,\n rootManifest: BuildAssetManifest\n ) {\n const assetMap = new BuildAssetMap(rootConfig);\n Object.keys(rootManifest).forEach((moduleId) => {\n const assetData = rootManifest[moduleId];\n assetMap.add(new BuildAsset(assetMap, assetData));\n });\n return assetMap;\n }\n}\n\n/**\n * Returns the realpath of a src file, relative to the rootDir.\n */\nfunction realPathRelativeTo(rootDir: string, src: string) {\n const fullPath = path.resolve(rootDir, src);\n if (!fs.existsSync(fullPath)) {\n return src;\n }\n const realpath = fs.realpathSync(path.resolve(rootDir, src));\n return path.relative(rootDir, realpath);\n}\n\nexport class BuildAsset {\n src: string;\n assetUrl: string;\n private assetMap: BuildAssetMap;\n private importedModules: string[];\n private importedCss: string[];\n isElement: boolean;\n\n constructor(\n assetMap: BuildAssetMap,\n assetData: {\n src: string;\n assetUrl: string;\n importedModules: string[];\n importedCss: string[];\n isElement: boolean;\n }\n ) {\n this.assetMap = assetMap;\n this.src = assetData.src;\n this.assetUrl = assetData.assetUrl;\n this.importedModules = assetData.importedModules;\n this.importedCss = assetData.importedCss;\n this.isElement = assetData.isElement;\n }\n\n async getCssDeps(): Promise<string[]> {\n const visited = new Set<string>();\n const deps = new Set<string>();\n await this.collectCss(this, deps, visited);\n return Array.from(deps);\n }\n\n async getJsDeps(): Promise<string[]> {\n const visited = new Set<string>();\n const deps = new Set<string>();\n await this.collectJs(this, deps, visited);\n return Array.from(deps);\n }\n\n private async collectJs(\n asset: BuildAsset | null,\n urls: Set<string>,\n visited: Set<string>\n ) {\n if (!asset) {\n return;\n }\n if (!asset.src) {\n return;\n }\n if (visited.has(asset.src)) {\n return;\n }\n visited.add(asset.src);\n if (asset.isElement) {\n urls.add(asset.assetUrl);\n }\n await Promise.all(\n asset.importedModules.map(async (src) => {\n const importedAsset = (await this.assetMap.get(src)) as BuildAsset;\n this.collectJs(importedAsset, urls, visited);\n })\n );\n }\n\n private async collectCss(\n asset: BuildAsset | null,\n urls: Set<string>,\n visited: Set<string>\n ) {\n if (!asset) {\n return;\n }\n if (!asset.src) {\n return;\n }\n if (visited.has(asset.src)) {\n return;\n }\n visited.add(asset.src);\n if (asset.importedCss) {\n asset.importedCss.forEach((cssUrl) => urls.add(cssUrl));\n }\n await Promise.all(\n asset.importedModules.map(async (moduleId) => {\n const importedAsset = (await this.assetMap.get(moduleId)) as BuildAsset;\n this.collectCss(importedAsset, urls, visited);\n })\n );\n }\n\n toJson() {\n return {\n src: this.src,\n assetUrl: this.assetUrl,\n importedModules: this.importedModules,\n importedCss: this.importedCss,\n isElement: this.isElement,\n };\n }\n}\n","export async function batchAsyncCalls<T, U>(\n data: T[],\n batchSize: number,\n asyncFunction: (item: T) => Promise<U>\n): Promise<U[]> {\n const result: U[] = [];\n const batches = Math.ceil(data.length / batchSize);\n for (let i = 0; i < batches; i++) {\n const batch = data.slice(i * batchSize, (i + 1) * batchSize);\n const batchResults = await Promise.all(batch.map(asyncFunction));\n result.push(...batchResults);\n }\n return result;\n}\n","import {promises as fs} from 'node:fs';\nimport path from 'node:path';\nimport {fileURLToPath} from 'node:url';\nimport glob from 'tiny-glob';\nimport {dirExists, makeDir, rmDir, writeFile} from '../utils/fsutils.js';\n\nconst __dirname = path.dirname(fileURLToPath(import.meta.url));\n\ninterface CodegenOptions {\n out?: string;\n}\n\ninterface Template {\n read: () => Promise<string>;\n}\n\ntype TemplateMap = Record<string, Template>;\n\nexport async function codegen(\n type: string,\n name: string,\n options?: CodegenOptions\n) {\n const rootDir = path.resolve(process.cwd());\n const project = new Project(rootDir);\n await project.generateCode(type, name, options);\n}\n\nclass Project {\n rootDir: string;\n tplDirs: string[];\n\n constructor(rootDir: string) {\n this.rootDir = rootDir;\n this.tplDirs = [\n path.join(rootDir, 'codegen'),\n path.join(__dirname, '../codegen'),\n ];\n }\n\n async generateCode(type: string, name: string, options?: CodegenOptions) {\n const files = await this.loadFiles(type);\n if (Object.keys(files).length === 0) {\n console.log(`no files in codegen/${type}/*.tpl`);\n return;\n }\n\n // By default, running `root codegen template Foo` outputs to\n // `<rootDir>/templates/Foo`.\n const outname = options?.out || `${type}s`;\n const outdir = path.join(this.rootDir, outname, name);\n if (await dirExists(outdir)) {\n await rmDir(outdir);\n }\n await makeDir(outdir);\n\n for (const tplName in files) {\n const tpl = await files[tplName].read();\n const content = tpl\n .replaceAll('[[name]]', name)\n .replaceAll('[[name:camel_upper]]', toCamelCaseUpper(name));\n const filename = tplName.replace('[name]', name);\n const filepath = path.join(outdir, filename);\n await writeFile(filepath, content);\n console.log(`saved ${filepath}`);\n }\n }\n\n /**\n * Searches the project's \"codegen\" dir (or fallsback to root's \"codegen\" dir)\n * and returns a `TemplateMap` for all files in `codgen/<type>/*.tpl`.\n */\n async loadFiles(type: string): Promise<TemplateMap> {\n for (const tplDir of this.tplDirs) {\n const typeDir = path.join(tplDir, type);\n if (await dirExists(typeDir)) {\n return this.loadTplFiles(typeDir);\n }\n }\n return {};\n }\n\n /**\n * Reads files matching `*.tpl` in a given directory.\n */\n private async loadTplFiles(dirpath: string): Promise<TemplateMap> {\n const tplFiles: TemplateMap = {};\n const files = await glob('*.tpl', {cwd: dirpath});\n for (const filename of files) {\n const filepath = path.join(dirpath, filename);\n // Remove `.tpl`.\n const name = filename.slice(0, -4);\n tplFiles[name] = {\n read: () => fs.readFile(filepath, 'utf-8'),\n };\n }\n return tplFiles;\n }\n}\n\nfunction toCamelCaseUpper(str: string) {\n const segments = str.split('-');\n return segments.map((part) => toTitleCase(part)).join('');\n}\n\nfunction toTitleCase(str: string) {\n const ch = String(str).charAt(0).toUpperCase();\n return `${ch}${str.slice(1)}`;\n}\n","import {promises as fs} from 'node:fs';\nimport path from 'node:path';\nimport {build as esbuild} from 'esbuild';\nimport {\n copyDir,\n dirExists,\n fileExists,\n loadJson,\n makeDir,\n rmDir,\n writeJson,\n} from '../utils/fsutils.js';\nimport {build as rootBuild} from './build.js';\n\ntype DeployTarget = 'appengine' | 'firebase';\n\ninterface CreatePackageOptions {\n mode?: string;\n out?: string;\n target?: DeployTarget;\n version?: string;\n}\n\ninterface PeerDependencyMeta {\n optional?: boolean;\n}\n\ninterface PackageJson {\n [key: string]: any;\n scripts?: Record<string, string>;\n dependencies?: Record<string, string>;\n peerDependencies?: Record<string, string>;\n peerDependenciesMeta?: Record<string, PeerDependencyMeta>;\n workspaces?: string[];\n}\n\nexport async function createPackage(\n rootProjectDir?: string,\n options?: CreatePackageOptions\n) {\n const mode = options?.mode || 'production';\n process.env.NODE_ENV = mode;\n\n const rootDir = path.resolve(rootProjectDir || process.cwd());\n // const rootConfig = await loadRootConfig(rootDir, {command: 'build'});\n const distDir = path.join(rootDir, 'dist');\n const target = options?.target || (await getDefaultTarget(rootDir));\n const outDir = path.resolve(options?.out || target || 'out');\n\n // Build the site in ssr-only mode.\n await rootBuild(rootProjectDir, {ssrOnly: true, mode: mode});\n\n // Create `outDir` and copy the generated `distDir` files to it.\n await rmDir(outDir);\n await makeDir(outDir);\n await copyDir(distDir, path.resolve(outDir, 'dist'));\n\n // Copy the \"collections\" dir if it exists.\n const collectionsDir = path.resolve(rootDir, 'collections');\n if (await dirExists(collectionsDir)) {\n await copyDir(collectionsDir, path.join(outDir, 'collections'));\n }\n\n // Create package.json.\n const packageJson = await generatePackageJson(rootDir);\n\n // Set root.js versions.\n if (options?.version && packageJson.dependencies) {\n if (packageJson.dependencies['@blinkk/root']) {\n packageJson.dependencies['@blinkk/root'] = options.version;\n }\n if (packageJson.dependencies['@blinkk/root-cms']) {\n packageJson.dependencies['@blinkk/root-cms'] = options.version;\n }\n if (packageJson.dependencies['@blinkk/root-password-protect']) {\n packageJson.dependencies['@blinkk/root-password-protect'] =\n options.version;\n }\n }\n\n // Run target-specific updates to the output.\n if (target === 'appengine') {\n await onAppEngine({rootDir, packageJson, outDir});\n } else if (target === 'firebase') {\n await onFirebase({rootDir, packageJson, outDir});\n }\n\n // Save `outDir/package.json`.\n await writeJson(path.resolve(outDir, 'package.json'), packageJson);\n\n console.log('done!');\n console.log(`saved package to ${outDir}`);\n}\n\nasync function getDefaultTarget(rootDir: string): Promise<DeployTarget | null> {\n // Default to firebase if a firebase.json file exists in the root dir.\n const firebaseConfigPath = path.resolve(rootDir, 'firebase.json');\n if (await fileExists(firebaseConfigPath)) {\n return 'firebase';\n }\n\n // Default to appengine.\n const appEngineConfigPath = path.resolve(rootDir, 'app.yaml');\n if (await fileExists(appEngineConfigPath)) {\n return 'appengine';\n }\n\n return null;\n}\n\nasync function generatePackageJson(rootDir: string): Promise<PackageJson> {\n // Read the package.json.\n const packageJson = await loadJson<any>(\n path.resolve(rootDir, 'package.json')\n );\n\n // If the package.json has any peer deps, check the workspace root for any\n // matching versions and move the peer deps to prod deps.\n if (packageJson.peerDependencies) {\n await updatePeerDepsFromWorkspace(rootDir, packageJson);\n }\n\n return packageJson;\n}\n\nasync function updatePeerDepsFromWorkspace(\n rootDir: string,\n packageJson: PackageJson\n) {\n const requiredPeerDeps = getRequiredPeerDeps(packageJson);\n if (requiredPeerDeps.length === 0) {\n return;\n }\n\n const workspaceRoot = await findWorkspaceRoot(rootDir);\n if (!workspaceRoot) {\n return;\n }\n\n const workspacePackageJsonPath = path.resolve(workspaceRoot, 'package.json');\n const workspacePackageJson = await loadJson<PackageJson>(\n workspacePackageJsonPath\n );\n const workspaceDeps = workspacePackageJson.dependencies || {};\n\n function setDep(name: string, value: string) {\n if (!packageJson.dependencies) {\n packageJson.dependencies = {};\n }\n packageJson.dependencies[name] = value;\n }\n\n for (const peerDep of requiredPeerDeps) {\n const workspaceDepVersion = workspaceDeps[peerDep];\n if (workspaceDepVersion) {\n setDep(peerDep, workspaceDepVersion);\n } else {\n console.warn(\n `could not find peer dep \"${peerDep}\" in workspace \"${workspacePackageJsonPath}\"`\n );\n }\n }\n}\n\nasync function findWorkspaceRoot(rootDir: string): Promise<string | null> {\n const parentDir = path.dirname(rootDir);\n\n if (parentDir === '/') {\n return null;\n }\n\n // PNPM uses `pnpm-workspace.yaml` for its workspace root.\n const pnpmWorkspaceFile = path.resolve(parentDir, 'pnpm-workspace.yaml');\n if (await fileExists(pnpmWorkspaceFile)) {\n return parentDir;\n }\n\n // YARN uses the \"workspaces\" key in package.json.\n const packageJsonPath = path.resolve(parentDir, 'package.json');\n if (await fileExists(packageJsonPath)) {\n const parentPackageJson = await loadJson<PackageJson>(packageJsonPath);\n if (parentPackageJson && parentPackageJson.workspaces) {\n return parentDir;\n }\n }\n\n return findWorkspaceRoot(parentDir);\n}\n\n/**\n * Returns all the `peerDependencies` that are not marked as\n * `{\"optional\": true}` in `peerDependenciesMeta`.\n */\nfunction getRequiredPeerDeps(packageJson: PackageJson) {\n const requiredPeerDeps: string[] = [];\n const peerDeps = packageJson.peerDependencies || {};\n const peerDepsMeta = packageJson.peerDependenciesMeta || {};\n for (const key in peerDeps) {\n const meta = peerDepsMeta[key];\n if (!meta?.optional) {\n requiredPeerDeps.push(key);\n }\n }\n return requiredPeerDeps;\n}\n\n/**\n * Called for App Engine targets.\n */\nasync function onAppEngine(options: {\n rootDir: string;\n packageJson: PackageJson;\n outDir: string;\n}) {\n const {rootDir, outDir, packageJson} = options;\n const configPath = path.resolve(rootDir, 'app.yaml');\n if (await fileExists(configPath)) {\n await fs.copyFile(configPath, path.resolve(outDir, 'app.yaml'));\n }\n\n // Only include the \"start\" script.\n if (packageJson.scripts?.start) {\n packageJson.scripts = {start: packageJson.scripts.start};\n } else {\n packageJson.scripts = {start: 'root start --host=0.0.0.0'};\n }\n}\n\n/**\n * Called for Firebase Hosting targets.\n */\nasync function onFirebase(options: {\n rootDir: string;\n packageJson: PackageJson;\n outDir: string;\n}) {\n const {rootDir, outDir, packageJson} = options;\n\n // If the outDir is called `functions/` and an index.ts file exists in the\n // root project dir, automatically compile it through esbuild.\n const outBasename = path.basename(outDir);\n if (outBasename === 'functions') {\n const indexTsFile = path.resolve(rootDir, 'index.ts');\n if (await fileExists(indexTsFile)) {\n await bundleTsFile(indexTsFile, path.resolve(outDir, 'index.js'));\n }\n }\n\n // Only include the \"start\" script.\n if (packageJson.scripts?.start) {\n packageJson.scripts = {start: packageJson.scripts.start};\n } else {\n packageJson.scripts = {start: 'root start --host=0.0.0.0'};\n }\n}\n\n/**\n * Compiles a `.ts` file to `.js`.\n */\nexport async function bundleTsFile(srcPath: string, outPath: string) {\n await esbuild({\n entryPoints: [srcPath],\n bundle: true,\n minify: true,\n platform: 'node',\n outfile: outPath,\n sourcemap: 'inline',\n metafile: true,\n format: 'esm',\n plugins: [\n {\n name: 'externalize-deps',\n setup(build: any) {\n build.onResolve({filter: /.*/}, (args: any) => {\n const id = args.path;\n if (id[0] !== '.' && !path.isAbsolute(id)) {\n return {\n external: true,\n };\n }\n return null;\n });\n },\n },\n ],\n });\n}\n","import path from 'node:path';\nimport {fileURLToPath} from 'node:url';\n\nimport cookieParser from 'cookie-parser';\nimport {default as express} from 'express';\nimport {dim} from 'kleur/colors';\nimport sirv from 'sirv';\nimport glob from 'tiny-glob';\n\nimport {ViteDevServer} from 'vite';\nimport {RootConfig} from '../core/config.js';\nimport {configureServerPlugins} from '../core/plugin.js';\nimport {Server, Request, Response, NextFunction} from '../core/types.js';\nimport {hooksMiddleware} from '../middleware/hooks.js';\nimport {\n headersMiddleware,\n rootProjectMiddleware,\n trailingSlashMiddleware,\n} from '../middleware/middleware.js';\nimport {redirectsMiddleware} from '../middleware/redirects.js';\nimport {sessionMiddleware} from '../middleware/session.js';\nimport {getElements, getElementsDirs} from '../node/element-graph.js';\nimport {loadRootConfig} from '../node/load-config.js';\nimport {createViteServer} from '../node/vite.js';\nimport {DevServerAssetMap} from '../render/asset-map/dev-asset-map.js';\nimport {dirExists, isDirectory, isJsFile} from '../utils/fsutils.js';\nimport {findOpenPort} from '../utils/ports.js';\nimport {randString} from '../utils/rand.js';\n\nconst __dirname = path.dirname(fileURLToPath(import.meta.url));\n\ntype RenderModule = typeof import('../render/render.js');\n\nexport interface DevOptions {\n host?: string;\n}\n\nexport async function dev(rootProjectDir?: string, options?: DevOptions) {\n process.env.NODE_ENV = 'development';\n const rootDir = path.resolve(rootProjectDir || process.cwd());\n const defaultPort = parseInt(process.env.PORT || '4007');\n const host = options?.host || 'localhost';\n const port = await findOpenPort(defaultPort, defaultPort + 10);\n const server = await createDevServer({rootDir, port});\n const rootConfig: RootConfig = server.get('rootConfig');\n const basePath = rootConfig.base || '';\n console.log();\n console.log(`${dim('┃')} project: ${rootDir}`);\n console.log(`${dim('┃')} server: http://${host}:${port}${basePath}`);\n if (testCmsEnabled(rootConfig)) {\n console.log(`${dim('┃')} cms: http://${host}:${port}/cms/`);\n }\n console.log(`${dim('┃')} mode: development`);\n console.log();\n server.listen(port, host);\n}\n\nexport async function createDevServer(options?: {\n rootDir?: string;\n port?: number;\n}): Promise<Server> {\n const rootDir = path.resolve(options?.rootDir || process.cwd());\n const rootConfig = await loadRootConfig(rootDir, {command: 'dev'});\n const port = options?.port;\n\n const server: Server = express();\n server.set('rootConfig', rootConfig);\n server.disable('x-powered-by');\n\n // Create viteServer.\n const {viteServer, viteMiddleware} = await createViteMiddleware({\n rootConfig,\n port,\n });\n server.set('viteServer', viteServer);\n\n // Inject req context vars.\n server.use(rootProjectMiddleware({rootConfig}));\n server.use(viteMiddleware);\n server.use(hooksMiddleware());\n\n // Session middleware for handling session cookies.\n const sessionCookieSecret =\n rootConfig.server?.sessionCookieSecret || randString(36);\n server.use(cookieParser(sessionCookieSecret));\n server.use(sessionMiddleware());\n\n const plugins = rootConfig.plugins || [];\n await configureServerPlugins(\n server,\n async () => {\n // Add user-configured middlewares from `root.config.ts`.\n const userMiddlewares = rootConfig.server?.middlewares || [];\n for (const middleware of userMiddlewares) {\n server.use(middleware);\n }\n\n // Add redirects middlewares.\n if (rootConfig.server?.redirects) {\n server.use(\n redirectsMiddleware({redirects: rootConfig.server.redirects})\n );\n }\n\n // Add http headers middleware.\n if (rootConfig.server?.headers) {\n server.use(headersMiddleware({rootConfig: rootConfig}));\n }\n\n // Add static file middleware.\n const publicDir = path.join(rootDir, 'public');\n if (await dirExists(publicDir)) {\n server.use(rootPublicDirMiddleware({publicDir, viteServer}));\n }\n\n // NOTE: The trailing slash middleware needs to come after public files so\n // that slashes are not appended to public file routes.\n server.use(trailingSlashMiddleware({rootConfig}));\n\n // Add the root.js dev server middlewares.\n server.use(rootDevServerMiddleware());\n\n // Add any custom plugin 404 handlers.\n plugins.forEach((plugin) => {\n if (plugin.handle404) {\n server.use(plugin.handle404);\n }\n });\n\n // Add error handlers.\n server.use(rootDevServer404Middleware());\n server.use(rootDevServer500Middleware());\n },\n plugins,\n {type: 'dev', rootConfig}\n );\n\n // Run any \"startup\" hooks.\n for (const plugin of plugins) {\n if (typeof plugin.hooks?.startup === 'function') {\n await plugin.hooks.startup({command: 'dev', rootConfig});\n }\n }\n\n return server;\n}\n\n/**\n * Middleware that initializes a vite server and injects it into the request\n * context.\n */\nasync function createViteMiddleware(options: {\n rootConfig: RootConfig;\n port?: number;\n}) {\n const rootConfig = options.rootConfig;\n const rootDir = rootConfig.rootDir;\n\n let elementGraph = await getElements(rootConfig);\n const elements = Object.values(elementGraph.sourceFiles).map((sourceFile) => {\n return sourceFile.relPath;\n });\n\n const bundleScripts: string[] = [];\n if (await isDirectory(path.join(rootDir, 'bundles'))) {\n const bundleFiles = await glob('bundles/*', {cwd: rootDir});\n bundleFiles.forEach((file) => {\n const parts = path.parse(file);\n if (isJsFile(parts.base)) {\n bundleScripts.push(file);\n }\n });\n }\n\n const optimizeDeps = [...elements, ...bundleScripts];\n const viteServer = await createViteServer(rootConfig, {\n port: options.port,\n optimizeDeps: optimizeDeps,\n });\n\n // Watch for file changes and re-generate the elements graph if any elements\n // are added or deleted.\n function isInElementsDir(changedFilePath: string) {\n const filePath = path.resolve(changedFilePath);\n const elementsDirs = getElementsDirs(rootConfig);\n return elementsDirs.some((dirPath) => filePath.startsWith(dirPath));\n }\n viteServer.watcher.on('add', async (filePath: string) => {\n if (isInElementsDir(filePath)) {\n // Re-generate the elements graph.\n elementGraph = await getElements(rootConfig);\n console.log(`element added: ${filePath}`);\n }\n });\n viteServer.watcher.on('unlink', async (filePath: string) => {\n if (isInElementsDir(filePath)) {\n // Re-generate the elements graph.\n elementGraph = await getElements(rootConfig);\n console.log(`element deleted: ${filePath}`);\n }\n });\n\n const viteMiddleware = async (\n req: Request,\n res: Response,\n next: NextFunction\n ) => {\n try {\n // Add the viteServer to the req.\n req.viteServer = viteServer;\n // Dynamically import the render.js module using vite's SSR import loader.\n const renderModulePath = path.resolve(__dirname, './render.js');\n const render = (await viteServer.ssrLoadModule(\n renderModulePath\n )) as RenderModule;\n // Create a dev asset map using Vite dev server's module graph.\n const assetMap = new DevServerAssetMap(\n rootConfig,\n viteServer.moduleGraph\n );\n // Add a renderer object to the req for plugins and other middleware to\n // use.\n req.renderer = new render.Renderer(rootConfig, {assetMap, elementGraph});\n // Run the viteServer middlewares to handle vite-specific endpoints.\n viteServer.middlewares(req, res, next);\n } catch (e) {\n next(e);\n }\n };\n\n return {viteServer, viteMiddleware};\n}\n\nfunction rootPublicDirMiddleware(options: {\n publicDir: string;\n viteServer: ViteDevServer;\n}) {\n const publicDir = options.publicDir;\n\n // The `{dev: false}` option is used for performance reasons. When dev is set\n // to `true`, every request will traverse the filesystem to check if a\n // matching file exists. Setting it to `false` uses a cache, which can be\n // reloaded whenever a file change is detected in the `public` directory.\n const sirvOptions = {dev: false};\n let handler = sirv(publicDir, sirvOptions);\n\n const reloadPublicDirCache = debounce(() => {\n handler = sirv(publicDir, sirvOptions);\n }, 1000);\n\n function isInPublicDir(changedFilePath: string) {\n const filePath = path.resolve(changedFilePath);\n return filePath.startsWith(publicDir);\n }\n\n const watcher = options.viteServer.watcher;\n watcher.on('all', (event, filepath) => {\n if (isInPublicDir(filepath)) {\n reloadPublicDirCache();\n }\n });\n\n return (req: Request, res: Response, next: NextFunction) => {\n handler(req, res, next);\n };\n}\n\nfunction rootDevServerMiddleware() {\n return async (req: Request, res: Response, next: NextFunction) => {\n const renderer = req.renderer!;\n const viteServer = req.viteServer!;\n try {\n await renderer.handle(req, res, next);\n } catch (err) {\n // If an error is caught, let Vite fix the stack trace so it maps back to\n // your actual source code.\n viteServer.ssrFixStacktrace(err);\n next(err);\n }\n };\n}\n\nfunction rootDevServer404Middleware() {\n return async (req: Request, res: Response) => {\n console.error(`❓ 404 ${req.originalUrl}`);\n if (req.renderer) {\n const url = req.path;\n const ext = path.extname(url);\n if (!ext) {\n const renderer = req.renderer;\n const data = await renderer.renderDevServer404(req);\n const html = data.html || '';\n res.status(404).set({'Content-Type': 'text/html'}).end(html);\n return;\n }\n }\n res.status(404).set({'Content-Type': 'text/plain'}).end('404');\n };\n}\n\nfunction rootDevServer500Middleware() {\n return async (err: any, req: Request, res: Response, next: NextFunction) => {\n console.error(`❗ 500 ${req.originalUrl}`);\n console.error(String(err.stack || err));\n if (req.renderer) {\n const url = req.path;\n const ext = path.extname(url);\n if (!ext) {\n const renderer = req.renderer;\n const data = await renderer.renderDevServer500(req, err);\n const html = data.html || '';\n res.status(500).set({'Content-Type': 'text/html'}).end(html);\n return;\n }\n }\n next(err);\n };\n}\n\nfunction testCmsEnabled(rootConfig: RootConfig) {\n const plugins = rootConfig.plugins || [];\n return Boolean(plugins.find((plugin) => plugin.name === 'root-cms'));\n}\n\nfunction debounce(fn: (...args: any[]) => any, timeout: number) {\n let timer: NodeJS.Timeout;\n return (...args: any[]) => {\n clearTimeout(timer);\n timer = setTimeout(() => fn(...args), timeout);\n };\n}\n","import {Request, Response, NextFunction} from '../core/types.js';\n\nexport function hooksMiddleware() {\n return (req: Request, res: Response, next: NextFunction) => {\n req.hooks = new Hooks();\n next();\n };\n}\n\nexport type HooksCallbackFn = (...args: any[]) => any;\n\nexport class Hooks {\n private callbacks: {[name: string]: HooksCallbackFn[]} = {};\n\n add(name: string, cb: (...args: any[]) => any) {\n this.callbacks[name] ??= [];\n this.callbacks[name].push(cb);\n }\n\n trigger(name: string, ...args: any[]) {\n const callbacks = this.callbacks[name] || [];\n callbacks.forEach((cb) => {\n cb(...args);\n });\n }\n}\n","import {RootRedirectConfig} from '../core/config.js';\nimport {NextFunction, Request, Response} from '../core/types.js';\nimport {RouteTrie} from '../render/route-trie.js';\n\nexport interface RedirectsMiddlewareOptions {\n redirects: RootRedirectConfig[];\n}\n\n/**\n * Middleware for handling server-side redirects from the `server.redirects`\n * config in `root.config.ts`.\n */\nexport function redirectsMiddleware(options: RedirectsMiddlewareOptions) {\n const routeTrie = new RouteTrie<RootRedirectConfig>();\n const redirects = options.redirects || [];\n redirects.forEach((redirect) => {\n if (!verifyRedirectConfig(redirect)) {\n console.warn('ignoring invalid redirect config:', redirect);\n return;\n }\n routeTrie.add(redirect.source!, redirect);\n });\n\n return (req: Request, res: Response, next: NextFunction) => {\n const [redirect, params] = routeTrie.get(req.path);\n if (redirect) {\n const destination = replaceParams(redirect.destination!, params);\n const code = redirect.type || 302;\n res.redirect(code, destination);\n return;\n }\n next();\n };\n}\n\nfunction verifyRedirectConfig(redirect: RootRedirectConfig) {\n if (!redirect.source) {\n return false;\n }\n if (!redirect.destination) {\n return false;\n }\n // TODO(stevenle): verify all destination params exist within source.\n return true;\n}\n\nfunction replaceParams(urlPathFormat: string, params: Record<string, string>) {\n const urlPath = urlPathFormat.replaceAll(\n /\\[\\[?(\\.\\.\\.)?([\\w\\-_]*)\\]?\\]/g,\n (match: string, _wildcard: string, key: string) => {\n const val = params[key];\n if (!val) {\n throw new Error(`unreplaced param ${match} in url: ${urlPathFormat}`);\n }\n return val;\n }\n );\n return urlPath;\n}\n","import path from 'node:path';\nimport {ModuleGraph, ModuleNode, searchForWorkspaceRoot} from 'vite';\nimport {RootConfig} from '../../core/config.js';\nimport {directoryContains} from '../../utils/fsutils.js';\nimport {Asset, AssetMap} from './asset-map.js';\n\nexport class DevServerAssetMap implements AssetMap {\n private rootConfig: RootConfig;\n private moduleGraph: ModuleGraph;\n\n constructor(rootConfig: RootConfig, moduleGraph: ModuleGraph) {\n this.rootConfig = rootConfig;\n this.moduleGraph = moduleGraph;\n }\n\n async get(src: string): Promise<Asset | null> {\n const file = path.resolve(this.rootConfig.rootDir, src);\n\n const viteModules = this.moduleGraph.getModulesByFile(file);\n if (viteModules && viteModules.size > 0) {\n const [viteModule] = viteModules;\n return new DevServerAsset(src, {\n assetMap: this,\n viteModule: viteModule,\n });\n }\n\n // On dev, in some cases the module doesn't make it into the module graph\n // so return a generic asset.\n if (file.startsWith(this.rootConfig.rootDir)) {\n const assetUrl = file.slice(this.rootConfig.rootDir.length);\n return {\n src: src,\n assetUrl: assetUrl,\n getCssDeps: async () => [],\n getJsDeps: async () => [assetUrl],\n };\n }\n const workspaceRoot = searchForWorkspaceRoot(this.rootConfig.rootDir);\n if (await directoryContains(workspaceRoot, file)) {\n const assetUrl = `/@fs/${file}`;\n return {\n src: src,\n assetUrl: assetUrl,\n getCssDeps: async () => [],\n getJsDeps: async () => [assetUrl],\n };\n }\n\n console.log(`could not find asset in asset map: ${src}`);\n return null;\n }\n\n filePathToSrc(file: string) {\n return path.relative(this.rootConfig.rootDir, file);\n }\n}\n\nexport class DevServerAsset implements Asset {\n src: string;\n moduleId: string;\n assetUrl: string;\n private assetMap: DevServerAssetMap;\n private viteModule: ModuleNode;\n\n constructor(\n src: string,\n options: {\n assetMap: DevServerAssetMap;\n viteModule: ModuleNode;\n }\n ) {\n this.src = src;\n this.assetMap = options.assetMap;\n this.viteModule = options.viteModule;\n this.moduleId = this.viteModule.id!;\n this.assetUrl = this.viteModule.url;\n }\n\n async getCssDeps(): Promise<string[]> {\n const visited = new Set<string>();\n const deps = new Set<string>();\n this.collectCss(this, deps, visited);\n return Array.from(deps);\n }\n\n async getJsDeps(): Promise<string[]> {\n const visited = new Set<string>();\n const deps = new Set<string>();\n this.collectJs(this, deps, visited);\n return Array.from(deps);\n }\n\n getImportedModules() {\n return this.viteModule.importedModules;\n }\n\n private collectJs(\n asset: DevServerAsset | null,\n urls: Set<string>,\n visited: Set<string>\n ) {\n if (!asset) {\n return;\n }\n if (!asset.moduleId) {\n return;\n }\n if (visited.has(asset.moduleId)) {\n return;\n }\n visited.add(asset.moduleId);\n const parts = path.parse(asset.assetUrl);\n if (\n ['.js', '.jsx', '.ts', '.tsx'].includes(parts.ext) &&\n asset.moduleId.includes('/elements/')\n ) {\n urls.add(asset.assetUrl);\n }\n asset.getImportedModules().forEach((viteModule) => {\n if (viteModule.file) {\n const src = this.assetMap.filePathToSrc(viteModule.file);\n const importedAsset = new DevServerAsset(src, {\n assetMap: this.assetMap,\n viteModule: viteModule,\n });\n this.collectJs(importedAsset, urls, visited);\n }\n });\n }\n\n private collectCss(\n asset: DevServerAsset | null,\n urls: Set<string>,\n visited: Set<string>\n ) {\n if (!asset) {\n return;\n }\n if (!asset.assetUrl) {\n return;\n }\n if (visited.has(asset.assetUrl)) {\n return;\n }\n visited.add(asset.assetUrl);\n if (asset.src.endsWith('.scss')) {\n const parts = path.parse(asset.src);\n if (!parts.name.startsWith('_')) {\n urls.add(asset.assetUrl);\n }\n }\n asset.getImportedModules().forEach((viteModule) => {\n if (viteModule.file) {\n const src = this.assetMap.filePathToSrc(viteModule.file);\n const importedAsset = new DevServerAsset(src, {\n assetMap: this.assetMap,\n viteModule: viteModule,\n });\n this.collectCss(importedAsset, urls, visited);\n }\n });\n }\n}\n","import {createServer} from 'node:net';\n\n/**\n * Checks whether a port is open.\n */\nexport function isPortOpen(port: number): Promise<boolean> {\n return new Promise((resolve, reject) => {\n const server = createServer();\n server.on('error', (err: NodeJS.ErrnoException) => {\n if (err.code === 'EADDRINUSE') {\n resolve(false);\n return;\n }\n reject(err);\n });\n server.on('close', () => {\n resolve(true);\n });\n server.listen(port, () => {\n server.close((err) => {\n if (err) {\n console.log(`error closing server: ${err}`);\n reject(err);\n }\n });\n });\n });\n}\n\n/**\n * Finds the first open port between two values.\n */\nexport async function findOpenPort(min: number, max: number): Promise<number> {\n let port = min;\n while (port <= max) {\n const isOpen = await isPortOpen(port);\n if (isOpen) {\n return port;\n }\n port += 1;\n }\n throw new Error(`no ports open between ${min} and ${max}`);\n}\n","export function randString(len: number): string {\n const result = [];\n const chars =\n 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789';\n for (let i = 0; i < len; i++) {\n const rand = Math.floor(Math.random() * chars.length);\n result.push(chars.charAt(rand));\n }\n return result.join('');\n}\n","import path from 'node:path';\n\nimport compression from 'compression';\nimport cookieParser from 'cookie-parser';\nimport {default as express} from 'express';\nimport {dim} from 'kleur/colors';\nimport sirv from 'sirv';\n\nimport {RootConfig} from '../core/config.js';\nimport {configureServerPlugins} from '../core/plugin.js';\nimport {Request, Response, NextFunction, Server} from '../core/types.js';\nimport {hooksMiddleware} from '../middleware/hooks.js';\nimport {\n headersMiddleware,\n rootProjectMiddleware,\n trailingSlashMiddleware,\n} from '../middleware/middleware.js';\nimport {redirectsMiddleware} from '../middleware/redirects.js';\nimport {sessionMiddleware} from '../middleware/session.js';\nimport {ElementGraph} from '../node/element-graph.js';\nimport {loadBundledConfig} from '../node/load-config.js';\nimport {\n BuildAssetManifest,\n BuildAssetMap,\n} from '../render/asset-map/build-asset-map.js';\nimport {fileExists, loadJson} from '../utils/fsutils.js';\nimport {randString} from '../utils/rand.js';\n\ntype RenderModule = typeof import('../render/render.js');\n\nexport interface PreviewOptions {\n host?: string;\n}\n\nexport async function preview(\n rootProjectDir?: string,\n options?: PreviewOptions\n) {\n // TODO(stevenle): figure out standard practice for NODE_ENV when using the\n // preview command.\n process.env.NODE_ENV = 'development';\n const rootDir = path.resolve(rootProjectDir || process.cwd());\n const server = await createPreviewServer({rootDir});\n const port = parseInt(process.env.PORT || '4007');\n const host = options?.host || 'localhost';\n console.log();\n console.log(`${dim('┃')} project: ${rootDir}`);\n console.log(`${dim('┃')} server: http://${host}:${port}`);\n console.log(`${dim('┃')} mode: preview`);\n console.log();\n server.listen(port, host);\n}\n\nexport async function createPreviewServer(options: {\n rootDir: string;\n}): Promise<Server> {\n const rootDir = options.rootDir;\n const rootConfig = await loadBundledConfig(rootDir, {command: 'preview'});\n const distDir = path.join(rootDir, 'dist');\n\n const server: Server = express();\n server.disable('x-powered-by');\n server.use(compression());\n\n // Inject request context vars.\n server.use(rootProjectMiddleware({rootConfig}));\n server.use(await rootPreviewRendererMiddleware({rootConfig, distDir}));\n server.use(hooksMiddleware());\n\n // Session middleware for handling session cookies.\n const sessionCookieSecret =\n rootConfig.server?.sessionCookieSecret || randString(36);\n server.use(cookieParser(sessionCookieSecret));\n server.use(sessionMiddleware());\n\n const plugins = rootConfig.plugins || [];\n configureServerPlugins(\n server,\n async () => {\n // Add user-configured middlewares from `root.config.ts`.\n const userMiddlewares = rootConfig.server?.middlewares || [];\n userMiddlewares.forEach((middleware) => {\n server.use(middleware);\n });\n\n // Add redirects middleware.\n if (rootConfig.server?.redirects) {\n server.use(\n redirectsMiddleware({redirects: rootConfig.server.redirects})\n );\n }\n\n // Add http headers middleware.\n if (rootConfig.server?.headers) {\n server.use(headersMiddleware({rootConfig: rootConfig}));\n }\n\n // Add static file middleware.\n const publicDir = path.join(distDir, 'html');\n server.use(sirv(publicDir, {dev: false}));\n\n // NOTE: The trailing slash middleware needs to come after public files so\n // that slashes are not appended to public file routes.\n server.use(trailingSlashMiddleware({rootConfig}));\n\n // Add the root.js preview server middlewares.\n server.use(rootPreviewServerMiddleware());\n\n // Add any custom plugin 404 handlers.\n plugins.forEach((plugin) => {\n if (plugin.handle404) {\n server.use(plugin.handle404);\n }\n });\n\n // Add error handlers.\n server.use(rootPreviewServer404Middleware());\n server.use(rootPreviewServer500Middleware());\n },\n plugins,\n {type: 'preview', rootConfig}\n );\n\n // Run any \"startup\" hooks.\n for (const plugin of plugins) {\n if (typeof plugin.hooks?.startup === 'function') {\n await plugin.hooks.startup({command: 'preview', rootConfig});\n }\n }\n\n return server;\n}\n\n/**\n * Injects a renderer into the request.\n */\nasync function rootPreviewRendererMiddleware(options: {\n rootConfig: RootConfig;\n distDir: string;\n}) {\n const {distDir, rootConfig} = options;\n const render: RenderModule = await import(\n path.join(distDir, 'server/render.js')\n );\n const manifestPath = path.join(distDir, '.root/manifest.json');\n if (!(await fileExists(manifestPath))) {\n throw new Error(\n `could not find ${manifestPath}. run \\`root build\\` before \\`root preview\\`.`\n );\n }\n const elementGraphJsonPath = path.join(distDir, '.root/elements.json');\n if (!(await fileExists(elementGraphJsonPath))) {\n throw new Error(\n `could not find ${elementGraphJsonPath}. run \\`root build\\` before \\`root preview\\`.`\n );\n }\n const rootManifest = await loadJson<BuildAssetManifest>(manifestPath);\n const assetMap = BuildAssetMap.fromRootManifest(rootConfig, rootManifest);\n const elementGraphJson = await loadJson<any>(elementGraphJsonPath);\n const elementGraph = ElementGraph.fromJson(elementGraphJson);\n const renderer = new render.Renderer(rootConfig, {assetMap, elementGraph});\n return async (req: Request, _: Response, next: NextFunction) => {\n req.renderer = renderer;\n next();\n };\n}\n\n/**\n * Preview server request handler.\n */\nfunction rootPreviewServerMiddleware() {\n return async (req: Request, res: Response, next: NextFunction) => {\n const renderer = req.renderer!;\n try {\n await renderer.handle(req, res, next);\n } catch (e) {\n try {\n console.error(`error rendering ${req.originalUrl}`);\n console.error(e.stack || e);\n const {html} = await renderer.renderDevServer500(req, e);\n res.status(500).set({'Content-Type': 'text/html'}).end(html);\n } catch (e2) {\n console.error('failed to render custom error');\n console.error(e2);\n next(e);\n }\n }\n };\n}\n\nfunction rootPreviewServer404Middleware() {\n return async (req: Request, res: Response) => {\n console.error(`❓ 404 ${req.originalUrl}`);\n if (req.renderer) {\n const url = req.path;\n const ext = path.extname(url);\n if (!ext) {\n const renderer = req.renderer;\n const data = await renderer.render404({currentPath: url});\n const html = data.html || '';\n res.status(404).set({'Content-Type': 'text/html'}).end(html);\n return;\n }\n }\n res.status(404).set({'Content-Type': 'text/plain'}).end('404');\n };\n}\n\nfunction rootPreviewServer500Middleware() {\n return async (err: any, req: Request, res: Response, next: NextFunction) => {\n console.error(`❗ 500 ${req.originalUrl}`);\n console.error(String(err.stack || err));\n if (req.renderer) {\n const url = req.path;\n const ext = path.extname(url);\n if (!ext) {\n const renderer = req.renderer;\n const data = await renderer.renderDevServer500(req, err);\n const html = data.html || '';\n res.status(500).set({'Content-Type': 'text/html'}).end(html);\n return;\n }\n }\n next(err);\n };\n}\n","import path from 'node:path';\n\nimport compression from 'compression';\nimport cookieParser from 'cookie-parser';\nimport {default as express} from 'express';\nimport {dim} from 'kleur/colors';\nimport sirv from 'sirv';\n\nimport {RootConfig} from '../core/config.js';\nimport {configureServerPlugins} from '../core/plugin.js';\nimport {Request, Response, NextFunction, Server} from '../core/types.js';\nimport {hooksMiddleware} from '../middleware/hooks.js';\nimport {\n headersMiddleware,\n rootProjectMiddleware,\n trailingSlashMiddleware,\n} from '../middleware/middleware.js';\nimport {redirectsMiddleware} from '../middleware/redirects.js';\nimport {sessionMiddleware} from '../middleware/session.js';\nimport {ElementGraph} from '../node/element-graph.js';\nimport {loadBundledConfig} from '../node/load-config.js';\nimport {\n BuildAssetManifest,\n BuildAssetMap,\n} from '../render/asset-map/build-asset-map.js';\nimport {fileExists, loadJson} from '../utils/fsutils.js';\nimport {randString} from '../utils/rand.js';\n\ntype RenderModule = typeof import('../render/render.js');\n\nexport interface StartOptions {\n host?: string;\n}\n\nexport async function start(rootProjectDir?: string, options?: StartOptions) {\n process.env.NODE_ENV = 'production';\n const rootDir = path.resolve(rootProjectDir || process.cwd());\n const server = await createProdServer({rootDir});\n const port = parseInt(process.env.PORT || '4007');\n const host = options?.host || 'localhost';\n console.log();\n console.log(`${dim('┃')} project: ${rootDir}`);\n console.log(`${dim('┃')} server: http://${host}:${port}`);\n console.log(`${dim('┃')} mode: production`);\n console.log();\n server.listen(port, host);\n}\n\nexport async function createProdServer(options: {\n rootDir: string;\n}): Promise<Server> {\n const rootDir = options.rootDir;\n const rootConfig = await loadBundledConfig(rootDir, {command: 'start'});\n const distDir = path.join(rootDir, 'dist');\n\n const server: Server = express();\n server.disable('x-powered-by');\n server.use(compression());\n\n // Inject request context vars.\n server.use(rootProjectMiddleware({rootConfig}));\n server.use(await rootProdRendererMiddleware({rootConfig, distDir}));\n server.use(hooksMiddleware());\n\n // Session middleware for handling session cookies.\n const sessionCookieSecret =\n rootConfig.server?.sessionCookieSecret || randString(36);\n server.use(cookieParser(sessionCookieSecret));\n server.use(sessionMiddleware());\n\n const plugins = rootConfig.plugins || [];\n configureServerPlugins(\n server,\n async () => {\n // Add user-configured middlewares from `root.config.ts`.\n const userMiddlewares = rootConfig.server?.middlewares || [];\n userMiddlewares.forEach((middleware) => {\n server.use(middleware);\n });\n\n // Add redirects middleware.\n if (rootConfig.server?.redirects) {\n server.use(\n redirectsMiddleware({redirects: rootConfig.server.redirects})\n );\n }\n\n // Add http headers middleware.\n if (rootConfig.server?.headers) {\n server.use(headersMiddleware({rootConfig: rootConfig}));\n }\n\n // Add static file middleware.\n const publicDir = path.join(distDir, 'html');\n server.use(sirv(publicDir, {dev: false}));\n\n // NOTE: The trailing slash middleware needs to come after public files so\n // that slashes are not appended to public file routes.\n server.use(trailingSlashMiddleware({rootConfig}));\n\n // Add the root.js preview server middlewares.\n server.use(rootProdServerMiddleware());\n\n // Add any custom plugin 404 handlers.\n plugins.forEach((plugin) => {\n if (plugin.handle404) {\n server.use(plugin.handle404);\n }\n });\n\n // Add error handlers.\n server.use(rootProdServer404Middleware());\n server.use(rootProdServer500Middleware());\n },\n plugins,\n {type: 'prod', rootConfig}\n );\n\n // Run any \"startup\" hooks.\n for (const plugin of plugins) {\n if (typeof plugin.hooks?.startup === 'function') {\n await plugin.hooks.startup({command: 'start', rootConfig});\n }\n }\n\n return server;\n}\n\n/**\n * Injects a renderer into the request.\n */\nasync function rootProdRendererMiddleware(options: {\n rootConfig: RootConfig;\n distDir: string;\n}) {\n const {distDir, rootConfig} = options;\n const render: RenderModule = await import(\n path.join(distDir, 'server/render.js')\n );\n const manifestPath = path.join(distDir, '.root/manifest.json');\n if (!(await fileExists(manifestPath))) {\n throw new Error(\n `could not find ${manifestPath}. run \\`root build\\` before \\`root start\\`.`\n );\n }\n const elementGraphJsonPath = path.join(distDir, '.root/elements.json');\n if (!(await fileExists(elementGraphJsonPath))) {\n throw new Error(\n `could not find ${elementGraphJsonPath}. run \\`root build\\` before \\`root start\\`.`\n );\n }\n const rootManifest = await loadJson<BuildAssetManifest>(manifestPath);\n const assetMap = BuildAssetMap.fromRootManifest(rootConfig, rootManifest);\n const elementGraphJson = await loadJson<any>(elementGraphJsonPath);\n const elementGraph = ElementGraph.fromJson(elementGraphJson);\n const renderer = new render.Renderer(rootConfig, {assetMap, elementGraph});\n return async (req: Request, _: Response, next: NextFunction) => {\n req.renderer = renderer;\n next();\n };\n}\n\n/**\n * Prod server request handler.\n */\nfunction rootProdServerMiddleware() {\n return async (req: Request, res: Response, next: NextFunction) => {\n const renderer = req.renderer!;\n try {\n await renderer.handle(req, res, next);\n } catch (e) {\n try {\n console.error(`error rendering ${req.originalUrl}`);\n console.error(e.stack || e);\n const {html} = await renderer.renderError(e);\n res.status(500).set({'Content-Type': 'text/html'}).end(html);\n } catch (e2) {\n console.error('failed to render custom error');\n console.error(e2);\n next(e);\n }\n }\n };\n}\n\nfunction rootProdServer404Middleware() {\n return async (req: Request, res: Response) => {\n console.error(`❓ 404 ${req.originalUrl}`);\n if (req.renderer) {\n const url = req.path;\n const ext = path.extname(url);\n if (!ext) {\n const renderer = req.renderer;\n const data = await renderer.render404({currentPath: url});\n const html = data.html || '';\n res.status(404).set({'Content-Type': 'text/html'}).end(html);\n return;\n }\n }\n res.status(404).set({'Content-Type': 'text/plain'}).end('404');\n };\n}\n\nfunction rootProdServer500Middleware() {\n return async (err: any, req: Request, res: Response, next: NextFunction) => {\n console.error(`❗ 500 ${req.originalUrl}`);\n console.error(String(err.stack || err));\n if (req.renderer) {\n const url = req.path;\n const ext = path.extname(url);\n if (!ext) {\n const renderer = req.renderer;\n const data = await renderer.renderError(err);\n const html = data.html || '';\n res.status(500).set({'Content-Type': 'text/html'}).end(html);\n return;\n }\n }\n next(err);\n };\n}\n"],"mappings":"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","names":["path","glob","fs","path","asset","path","fs","path","glob","importedCss","fileSize","fs","path","fileURLToPath","glob","__dirname","path","fileURLToPath","glob","fs","fs","path","path","fs","build","path","fileURLToPath","dim","glob","path","searchForWorkspaceRoot","path","searchForWorkspaceRoot","__dirname","path","fileURLToPath","dim","glob","path","cookieParser","express","dim","sirv","path","dim","express","cookieParser","sirv","path","compression","cookieParser","express","dim","sirv","path","dim","express","compression","cookieParser","sirv"]}
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/node/load-config.ts","../src/utils/fsutils.ts","../src/node/vite.ts"],"sourcesContent":["import path from 'node:path';\nimport {bundleRequire} from 'bundle-require';\nimport {build} from 'esbuild';\nimport {RootConfig} from '../core/config.js';\nimport {fileExists, loadJson} from '../utils/fsutils.js';\n\nexport interface ConfigOptions {\n command: string;\n}\n\nexport async function loadRootConfig(\n rootDir: string,\n options: ConfigOptions\n): Promise<RootConfig> {\n const configPath = path.resolve(rootDir, 'root.config.ts');\n const exists = await fileExists(configPath);\n if (!exists) {\n throw new Error(`${configPath} does not exist`);\n }\n const configBundle = await bundleRequire({\n filepath: configPath,\n });\n let config = configBundle.mod.default || {};\n if (typeof config === 'function') {\n config = (await config(options)) || {};\n }\n return Object.assign({}, config, {rootDir});\n}\n\n/**\n * Compiles a root.config.ts file to root.config.js.\n */\nexport async function bundleRootConfig(rootDir: string, outPath: string) {\n const configPath = path.resolve(rootDir, 'root.config.ts');\n const configExists = await fileExists(configPath);\n if (!configExists) {\n throw new Error(`${configPath} does not exist`);\n }\n\n const packageJsonPath = path.resolve(rootDir, 'package.json');\n const packageJson = await loadPackageJson(packageJsonPath);\n const allDeps = {\n ...packageJson.peerDependencies,\n ...packageJson.dependencies,\n };\n\n function getPackageName(id: string): string {\n const segments = id.split('/');\n if (segments.length > 1) {\n // Check if package is an org path like `@blinkk/root`.\n if (segments[0].startsWith('@') && segments[0].length > 1) {\n return `${segments[0]}/${segments[1]}`;\n }\n // For imports like `my-package/subpackage`, return `my-package`.\n return segments[0];\n }\n return id;\n }\n\n await build({\n entryPoints: [configPath],\n bundle: true,\n minify: true,\n platform: 'node',\n outfile: outPath,\n sourcemap: 'inline',\n metafile: true,\n format: 'esm',\n plugins: [\n // Externalizes deps that are in package.json.\n {\n name: 'externalize-package-json-deps',\n setup(build) {\n build.onResolve({filter: /.*/}, (args) => {\n const id = args.path;\n if (id[0] !== '.' && !id.startsWith('@/')) {\n const packageName = getPackageName(id);\n if (packageName in allDeps) {\n return {\n external: true,\n };\n }\n }\n return null;\n });\n },\n },\n ],\n });\n}\n\n/**\n * Loads a pre-bundled config file from dist/root.config.js.\n */\nexport async function loadBundledConfig(\n rootDir: string,\n options: ConfigOptions\n): Promise<RootConfig> {\n const configPath = path.resolve(rootDir, 'dist/root.config.js');\n const exists = await fileExists(configPath);\n if (!exists) {\n throw new Error(`${configPath} does not exist`);\n }\n const module = await import(configPath);\n let config = module.default || {};\n if (typeof config === 'function') {\n config = (await config(options)) || {};\n }\n return Object.assign({}, config, {rootDir});\n}\n\nexport async function loadPackageJson(filepath: string): Promise<any> {\n try {\n const packageJson = await loadJson(filepath);\n return packageJson || {};\n } catch (err) {\n return {};\n }\n}\n","import {promises as fs} from 'node:fs';\nimport path from 'node:path';\n\nimport fsExtra from 'fs-extra';\nimport glob from 'tiny-glob';\n\nexport function isJsFile(filename: string) {\n return !!filename.match(/\\.(j|t)sx?$/);\n}\n\nexport async function writeFile(filepath: string, content: string) {\n const dirPath = path.dirname(filepath);\n await makeDir(dirPath);\n await fs.writeFile(filepath, content);\n}\n\nexport async function makeDir(dirpath: string) {\n try {\n await fs.access(dirpath);\n } catch (e) {\n await fs.mkdir(dirpath, {recursive: true});\n }\n}\n\nexport async function copyDir(srcdir: string, dstdir: string) {\n if (!fsExtra.existsSync(srcdir)) {\n return;\n }\n fsExtra.copySync(srcdir, dstdir, {overwrite: true});\n}\n\n/**\n * Copies a glob of files from one directory to another.\n *\n * Example:\n *\n * ```\n * await copyGlob('*.css', 'src/styles', 'dist/html/styles');\n * ```\n */\nexport async function copyGlob(\n pattern: string,\n srcdir: string,\n dstdir: string\n) {\n const files = await glob(pattern, {cwd: srcdir});\n if (files.length > 0) {\n await makeDir(dstdir);\n }\n files.forEach((file) => {\n fsExtra.copySync(path.resolve(srcdir, file), path.resolve(dstdir, file));\n });\n}\n\nexport async function rmDir(dirpath: string) {\n await fs.rm(dirpath, {recursive: true, force: true});\n}\n\nexport async function loadJson<T = unknown>(filepath: string): Promise<T> {\n const content = await fs.readFile(filepath, 'utf-8');\n return JSON.parse(content);\n}\n\nexport async function writeJson(filepath: string, data: any) {\n const content = JSON.stringify(data, null, 2);\n await writeFile(filepath, content);\n}\n\nexport async function isDirectory(dirpath: string) {\n return fs\n .stat(dirpath)\n .then((fsStat) => {\n return fsStat.isDirectory();\n })\n .catch((err) => {\n if (err.code === 'ENOENT') {\n return false;\n }\n throw err;\n });\n}\n\nexport function fileExists(filepath: string): Promise<boolean> {\n return fs\n .access(filepath)\n .then(() => true)\n .catch(() => false);\n}\n\nexport async function dirExists(dirpath: string): Promise<boolean> {\n try {\n const stat = await fs.stat(dirpath);\n return stat.isDirectory();\n } catch (error) {\n if (error.code === 'ENOENT') {\n return false;\n }\n throw error;\n }\n}\n\nexport async function directoryContains(\n dirpath: string,\n subpath: string\n): Promise<boolean> {\n const outer = await fs.realpath(dirpath);\n const inner = await fs.realpath(subpath);\n const rel = path.relative(outer, inner);\n return !rel.startsWith('..');\n}\n\nexport async function listFilesRecursive(dirPath: string): Promise<string[]> {\n const files: string[] = [];\n const entries = await fs.readdir(dirPath, {withFileTypes: true});\n for (const entry of entries) {\n const fullPath = path.join(dirPath, entry.name);\n if (entry.isDirectory()) {\n const subFiles = await listFilesRecursive(fullPath);\n files.push(...subFiles);\n } else {\n files.push(fullPath);\n }\n }\n return files;\n}\n","import {createServer, ViteDevServer} from 'vite';\nimport {RootConfig} from '../core/config.js';\nimport {getVitePlugins} from '../core/plugin.js';\n\nexport interface CreateViteServerOptions {\n /** Override HMR settings. */\n hmr?: boolean;\n /** The port the server will run on. */\n port?: number;\n /** List of files to include in the optimizeDeps.include config. */\n optimizeDeps?: string[];\n}\n\n/**\n * Returns a vite dev server.\n */\nexport async function createViteServer(\n rootConfig: RootConfig,\n options?: CreateViteServerOptions\n): Promise<ViteDevServer> {\n const rootDir = rootConfig.rootDir;\n const viteConfig = rootConfig.vite || {};\n\n let hmrOptions = viteConfig.server?.hmr;\n if (options?.hmr === false) {\n hmrOptions = false;\n } else if (typeof hmrOptions === 'undefined' && options?.port) {\n // Automatically set the HMR port to `port + 10`. This allows multiple\n // root.js dev servers to run without conflicts.\n hmrOptions = {port: options.port + 10};\n }\n\n const viteServer = await createServer({\n ...viteConfig,\n mode: 'development',\n root: rootDir,\n // publicDir is disabled from the vite dev server since it's handled by the\n // root dev server directly, which allows user middlewares to override\n // files in the public dir.\n publicDir: false,\n server: {\n ...(viteConfig.server || {}),\n middlewareMode: true,\n hmr: hmrOptions,\n },\n appType: 'custom',\n optimizeDeps: {\n // As of vite v5 / esbuild v19, experimentalDecorators need to be\n // explicitly set, and for some reason this option isn't read from the\n // project's tsconfig.json file by default.\n // See: https://vitejs.dev/blog/announcing-vite5\n esbuildOptions: {\n tsconfigRaw: {\n compilerOptions: {\n target: 'esnext',\n experimentalDecorators: true,\n useDefineForClassFields: false,\n },\n },\n },\n ...(viteConfig.optimizeDeps || {}),\n include: [\n ...(options?.optimizeDeps || []),\n ...(viteConfig.optimizeDeps?.include || []),\n ],\n extensions: [...(viteConfig.optimizeDeps?.extensions || []), '.tsx'],\n },\n ssr: {\n ...(viteConfig.ssr || {}),\n noExternal: ['@blinkk/root', '@blinkk/root-cms/richtext'],\n },\n esbuild: {\n ...(viteConfig.esbuild || {}),\n jsx: 'automatic',\n jsxImportSource: 'preact',\n },\n plugins: [\n ...(viteConfig.plugins || []),\n ...getVitePlugins(rootConfig.plugins || []),\n ],\n });\n return viteServer;\n}\n\n/**\n * Shortcut `viteServer.ssrLoadModule()` without starting an actual dev server.\n */\nexport async function viteSsrLoadModule(\n rootConfig: RootConfig,\n file: string\n): Promise<Record<string, any>> {\n const viteServer = await createViteServer(rootConfig, {hmr: false});\n const module = await viteServer.ssrLoadModule(file);\n await viteServer.close();\n return module;\n}\n"],"mappings":"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","names":["path","path","build"]}
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/core/plugin.ts"],"sourcesContent":["import {ViteDevServer, PluginOption as VitePlugin} from 'vite';\nimport {RootConfig} from './config.js';\nimport {NextFunction, Request, Response, Server} from './types.js';\n\ntype MaybePromise<T> = T | Promise<T>;\n\nexport type ConfigureServerHook = (\n server: Server,\n options: ConfigureServerOptions\n) => MaybePromise<void> | MaybePromise<() => void>;\n\nexport interface ConfigureServerOptions {\n type: 'dev' | 'preview' | 'prod';\n rootConfig: RootConfig;\n}\n\nexport interface PluginHooks {\n /**\n * Startup hook called when root is initialized.\n */\n startup?: (options: {\n command: string;\n rootConfig: RootConfig;\n }) => void | Promise<void>;\n\n /**\n * Post-render hook that's called before the HTML is rendered to the response\n * object. If a string is returned from this hook, it will replace the\n * rendered HTML.\n */\n preRender?: (html: string) => void | string | Promise<string>;\n}\n\nexport interface Plugin {\n [key: string]: any;\n /** The name of the plugin. */\n name?: string;\n /**\n * Configures the root.js express server. Any middleware defined by the plugin\n * will be added to the server first. If a callback fn is returned, it will\n * be called after the root.js middlewares are added.\n */\n configureServer?: ConfigureServerHook;\n /**\n * Hook for file changes.\n */\n onFileChange?: (\n eventName: 'add' | 'addDir' | 'change' | 'unlink' | 'unlinkDir',\n path: string\n ) => void;\n /**\n * Returns a list of deps to bundle for ssr. The files will be bundled and\n * output to `dist/server/`. The return value should be a map of\n * `{output filename => input filepath}`.\n *\n * E.g. a value of `{foo: 'path/to/bar.js'}` will output `dist/server/foo.js`.\n *\n * @experimental This config is subject to change to be incorporated into a\n * broader config option called \"ssr\" or \"ssrOptions\".\n */\n ssrInput?: () => {[entryAlias: string]: string};\n /** Adds vite plugins. */\n vitePlugins?: VitePlugin[];\n /** Plugin lifecycle callback hooks. */\n hooks?: PluginHooks;\n /** Custom 404 handler. */\n handle404?: (\n req: Request,\n res: Response,\n next: NextFunction\n ) => void | Promise<void>;\n}\n\n/**\n * Runs the pre-hook configureServer method of every plugin, calls a callback\n * function, and then runs the configureServer's post-hook if provided. Plugins\n * provide a post-hook by returning a callback function from configureServer.\n */\nexport async function configureServerPlugins(\n server: Server,\n callback: () => Promise<void>,\n plugins: Plugin[],\n options: ConfigureServerOptions\n) {\n const postHooks: Array<() => void> = [];\n const viteServer = server.get('viteServer') as ViteDevServer;\n\n // Call the `configureServer()` method for each plugin.\n for (const plugin of plugins) {\n if (plugin.configureServer) {\n const postHook = await plugin.configureServer(server, options);\n if (postHook) {\n postHooks.push(postHook);\n }\n }\n\n if (viteServer && plugin.onFileChange) {\n viteServer.watcher.on('all', plugin.onFileChange);\n }\n }\n\n // Register any built-in middleware.\n callback();\n\n // Run any post hooks returned by `plugin.configureServer()`.\n for (const postHook of postHooks) {\n await postHook();\n }\n}\n\nexport function getVitePlugins(plugins: Plugin[]): VitePlugin[] {\n const vitePlugins: VitePlugin[] = [];\n for (const plugin of plugins) {\n if (plugin.vitePlugins) {\n vitePlugins.push(...plugin.vitePlugins);\n }\n }\n return vitePlugins;\n}\n"],"mappings":";AA8EA,eAAsB,uBACpB,QACA,UACA,SACA,SACA;AACA,QAAM,YAA+B,CAAC;AACtC,QAAM,aAAa,OAAO,IAAI,YAAY;AAG1C,aAAW,UAAU,SAAS;AAC5B,QAAI,OAAO,iBAAiB;AAC1B,YAAM,WAAW,MAAM,OAAO,gBAAgB,QAAQ,OAAO;AAC7D,UAAI,UAAU;AACZ,kBAAU,KAAK,QAAQ;AAAA,MACzB;AAAA,IACF;AAEA,QAAI,cAAc,OAAO,cAAc;AACrC,iBAAW,QAAQ,GAAG,OAAO,OAAO,YAAY;AAAA,IAClD;AAAA,EACF;AAGA,WAAS;AAGT,aAAW,YAAY,WAAW;AAChC,UAAM,SAAS;AAAA,EACjB;AACF;AAEO,SAAS,eAAe,SAAiC;AAC9D,QAAM,cAA4B,CAAC;AACnC,aAAW,UAAU,SAAS;AAC5B,QAAI,OAAO,aAAa;AACtB,kBAAY,KAAK,GAAG,OAAO,WAAW;AAAA,IACxC;AAAA,EACF;AACA,SAAO;AACT;","names":[]}