elegance-js 2.1.23 → 2.1.26

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (103) hide show
  1. package/dist/client/effect.d.ts +27 -0
  2. package/dist/client/effect.js +37 -0
  3. package/dist/client/eventListener.d.ts +39 -0
  4. package/dist/client/eventListener.js +52 -0
  5. package/dist/client/loadHook.d.ts +34 -0
  6. package/dist/client/loadHook.js +52 -0
  7. package/dist/client/observer.d.ts +36 -0
  8. package/dist/client/observer.js +66 -0
  9. package/dist/client/runtime.d.ts +105 -0
  10. package/dist/client/runtime.js +620 -0
  11. package/dist/client/state.d.ts +40 -0
  12. package/dist/client/state.js +110 -0
  13. package/dist/compilation/compiler.d.ts +155 -0
  14. package/dist/compilation/compiler.js +1153 -0
  15. package/dist/components/ClientComponent.d.ts +22 -0
  16. package/dist/components/ClientComponent.js +55 -0
  17. package/dist/components/Link.d.ts +16 -1
  18. package/dist/components/Link.js +22 -0
  19. package/dist/components/Portal.d.ts +2 -0
  20. package/dist/components/Portal.js +2 -0
  21. package/dist/elements/element.d.ts +87 -0
  22. package/dist/elements/element.js +33 -0
  23. package/dist/elements/element_list.d.ts +7 -0
  24. package/dist/elements/element_list.js +65 -0
  25. package/dist/elements/raw.d.ts +14 -0
  26. package/dist/elements/raw.js +78 -0
  27. package/dist/elements/specific_props.d.ts +750 -0
  28. package/dist/global.d.ts +221 -327
  29. package/dist/index.d.ts +15 -3
  30. package/dist/index.js +11 -0
  31. package/dist/server/layout.d.ts +34 -3
  32. package/dist/server/layout.js +6 -0
  33. package/dist/server/log.d.ts +12 -0
  34. package/dist/server/log.js +64 -0
  35. package/dist/server/page.d.ts +32 -0
  36. package/dist/server/page.js +6 -0
  37. package/dist/server/runtime.d.ts +6 -0
  38. package/dist/server/runtime.js +72 -0
  39. package/dist/server/server.d.ts +103 -11
  40. package/dist/server/server.js +709 -0
  41. package/package.json +13 -13
  42. package/scripts/bootstrap.js +37 -273
  43. package/scripts/bootstrap_files/elegance.txt +40 -0
  44. package/scripts/bootstrap_files/index.txt +3 -0
  45. package/scripts/bootstrap_files/layout.txt +46 -0
  46. package/scripts/bootstrap_files/middleware.txt +18 -0
  47. package/scripts/bootstrap_files/page.txt +123 -0
  48. package/scripts/bootstrap_files/route.txt +6 -0
  49. package/scripts/elegance_dev.ts +40 -0
  50. package/scripts/elegance_prod.ts +40 -0
  51. package/scripts/elegance_static.ts +24 -0
  52. package/scripts/prod.js +9 -26
  53. package/scripts/run.js +13 -0
  54. package/scripts/static.js +13 -0
  55. package/dist/build.d.ts +0 -2
  56. package/dist/build.mjs +0 -202
  57. package/dist/client/client.d.ts +0 -1
  58. package/dist/client/client.mjs +0 -574
  59. package/dist/client/processPageElements.d.ts +0 -1
  60. package/dist/client/processPageElements.mjs +0 -117
  61. package/dist/client/render.d.ts +0 -1
  62. package/dist/client/render.mjs +0 -40
  63. package/dist/client/watcher.d.ts +0 -1
  64. package/dist/client/watcher.mjs +0 -26
  65. package/dist/compilation/compilation.d.ts +0 -139
  66. package/dist/compilation/compilation.mjs +0 -751
  67. package/dist/compilation/compiler_process.d.ts +0 -3
  68. package/dist/compilation/compiler_process.mjs +0 -102
  69. package/dist/compilation/dynamic_compiler.d.ts +0 -10
  70. package/dist/compilation/dynamic_compiler.mjs +0 -93
  71. package/dist/compile_docs.mjs +0 -34
  72. package/dist/components/Link.mjs +0 -65
  73. package/dist/global.mjs +0 -0
  74. package/dist/helpers/ObjectAttributeType.d.ts +0 -7
  75. package/dist/helpers/ObjectAttributeType.mjs +0 -11
  76. package/dist/helpers/camelToKebab.d.ts +0 -1
  77. package/dist/helpers/camelToKebab.mjs +0 -6
  78. package/dist/index.mjs +0 -3
  79. package/dist/internal/deprecate.d.ts +0 -1
  80. package/dist/internal/deprecate.mjs +0 -7
  81. package/dist/log.d.ts +0 -10
  82. package/dist/log.mjs +0 -38
  83. package/dist/server/generateHTMLTemplate.d.ts +0 -12
  84. package/dist/server/generateHTMLTemplate.mjs +0 -41
  85. package/dist/server/layout.mjs +0 -19
  86. package/dist/server/loadHook.d.ts +0 -30
  87. package/dist/server/loadHook.mjs +0 -50
  88. package/dist/server/observe.d.ts +0 -19
  89. package/dist/server/observe.mjs +0 -16
  90. package/dist/server/render.d.ts +0 -5
  91. package/dist/server/render.mjs +0 -61
  92. package/dist/server/server.mjs +0 -429
  93. package/dist/server/state.d.ts +0 -61
  94. package/dist/server/state.mjs +0 -146
  95. package/dist/shared/bindServerElements.mjs +0 -3
  96. package/dist/shared/serverElements.d.ts +0 -11
  97. package/dist/shared/serverElements.mjs +0 -164
  98. package/scripts/dev.js +0 -33
  99. package/scripts/export.js +0 -20
  100. package/scripts/ts-arc-dev.js +0 -9
  101. package/scripts/ts-arc-prod.js +0 -9
  102. /package/dist/{compile_docs.d.ts → elements/specific_props.js} +0 -0
  103. /package/dist/{shared/bindServerElements.d.ts → global.js} +0 -0
@@ -1,751 +0,0 @@
1
- import fs from "fs";
2
- import path from "path";
3
- const __filename = fileURLToPath(import.meta.url);
4
- const __dirname = path.dirname(__filename);
5
- import esbuild from "esbuild";
6
- import { fileURLToPath } from "url";
7
- import { generateHTMLTemplate } from "../server/generateHTMLTemplate";
8
- import crypto from "crypto";
9
- import { ObjectAttributeType } from "../helpers/ObjectAttributeType";
10
- import { serverSideRenderPage } from "../server/render";
11
- import { getState, initializeState, initializeObjectAttributes, getObjectAttributes } from "../server/state";
12
- import { getLoadHooks, resetLoadHooks } from "../server/loadHook";
13
- import { resetLayouts } from "../server/layout";
14
- import { renderRecursively } from "../server/render";
15
- let PAGE_MAP = /* @__PURE__ */ new Map();
16
- let LAYOUT_MAP = /* @__PURE__ */ new Map();
17
- function populateServerMaps(pageMap, layoutMap) {
18
- LAYOUT_MAP = layoutMap;
19
- PAGE_MAP = pageMap;
20
- }
21
- let options;
22
- let DIST_DIR;
23
- let elementKey = 0;
24
- const shippedModules = /* @__PURE__ */ new Map();
25
- let modulesToShip = [];
26
- let packageDir = process.env.PACKAGE_PATH;
27
- if (packageDir === void 0) {
28
- packageDir = path.resolve(__dirname, "..");
29
- }
30
- const clientPath = path.resolve(packageDir, "./dist/client/client.mjs");
31
- const watcherPath = path.resolve(packageDir, "./dist/client/watcher.mjs");
32
- function setCompilationOptions(newOptions, distDir) {
33
- options = newOptions;
34
- DIST_DIR = distDir;
35
- }
36
- function getAllSubdirectories(dir, baseDir = dir) {
37
- let directories = [];
38
- const items = fs.readdirSync(dir, { withFileTypes: true });
39
- for (const item of items) {
40
- if (item.isDirectory()) {
41
- const fullPath = path.join(dir, item.name);
42
- const relativePath = path.relative(baseDir, fullPath);
43
- directories.push(relativePath);
44
- directories = directories.concat(getAllSubdirectories(fullPath, baseDir));
45
- }
46
- }
47
- return directories;
48
- }
49
- ;
50
- async function buildClient(DIST_DIR2) {
51
- let clientString = "window.__name = (func) => func; ";
52
- clientString += fs.readFileSync(clientPath, "utf-8");
53
- if (options.hotReload !== void 0) {
54
- clientString += `const watchServerPort = ${options.hotReload.port};`;
55
- clientString += fs.readFileSync(watcherPath, "utf-8");
56
- }
57
- const transformedClient = await esbuild.transform(clientString, {
58
- minify: options.environment === "production",
59
- drop: options.environment === "production" ? ["console", "debugger"] : void 0,
60
- keepNames: false,
61
- format: "iife",
62
- platform: "node",
63
- loader: "ts"
64
- });
65
- fs.writeFileSync(
66
- path.join(DIST_DIR2, "/client.js"),
67
- transformedClient.code
68
- );
69
- }
70
- ;
71
- function processOptionAsObjectAttribute(element, optionName, optionValue, objectAttributes) {
72
- const lcOptionName = optionName.toLowerCase();
73
- const options2 = element.options;
74
- let key = options2.key;
75
- if (key == void 0) {
76
- key = elementKey += 1;
77
- options2.key = key;
78
- }
79
- if (!optionValue.type) {
80
- throw `ObjectAttributeType is missing from object attribute. ${element.tag}: ${optionName}/${optionValue}`;
81
- }
82
- let optionFinal = lcOptionName;
83
- switch (optionValue.type) {
84
- case ObjectAttributeType.STATE:
85
- const SOA = optionValue;
86
- if (typeof SOA.value === "function") {
87
- delete options2[optionName];
88
- break;
89
- }
90
- if (lcOptionName === "innertext" || lcOptionName === "innerhtml") {
91
- element.children = [SOA.value];
92
- delete options2[optionName];
93
- } else {
94
- delete options2[optionName];
95
- options2[lcOptionName] = SOA.value;
96
- }
97
- break;
98
- case ObjectAttributeType.OBSERVER:
99
- const OOA = optionValue;
100
- const firstValue = OOA.update(...OOA.initialValues);
101
- if (lcOptionName === "innertext" || lcOptionName === "innerhtml") {
102
- element.children = [firstValue];
103
- delete options2[optionName];
104
- } else {
105
- delete options2[optionName];
106
- options2[lcOptionName] = firstValue;
107
- }
108
- optionFinal = optionName;
109
- break;
110
- case ObjectAttributeType.REFERENCE:
111
- options2["ref"] = optionValue.value;
112
- break;
113
- }
114
- objectAttributes.push({ ...optionValue, key, attribute: optionFinal });
115
- }
116
- ;
117
- function buildTrace(stack, indent = 4) {
118
- try {
119
- if (!stack || stack.length === 0) return "[]";
120
- let traceObj = stack[stack.length - 1] && typeof stack[stack.length - 1] === "object" ? JSON.parse(JSON.stringify(stack[stack.length - 1])) : { value: stack[stack.length - 1] };
121
- traceObj._error = "This is the element where the error occurred";
122
- for (let i = stack.length - 2; i >= 0; i--) {
123
- const parent = stack[i];
124
- const child = stack[i + 1];
125
- if (!parent || typeof parent !== "object") {
126
- traceObj = { value: parent, _errorChild: traceObj };
127
- continue;
128
- }
129
- let parentClone;
130
- try {
131
- parentClone = JSON.parse(JSON.stringify(parent));
132
- } catch {
133
- parentClone = { value: parent };
134
- }
135
- let index = -1;
136
- if (Array.isArray(parentClone.children)) {
137
- index = parentClone.children.findIndex((c) => c === child);
138
- }
139
- if (index !== -1 && parentClone.children) {
140
- parentClone.children = parentClone.children.slice(0, index + 1);
141
- parentClone.children[index] = traceObj;
142
- } else {
143
- parentClone._errorChild = traceObj;
144
- }
145
- traceObj = parentClone;
146
- }
147
- return JSON.stringify(traceObj, null, indent).replace(/^/gm, " ".repeat(indent));
148
- } catch {
149
- return "Could not build stack-trace.";
150
- }
151
- }
152
- function processPageElements(element, objectAttributes, recursionLevel, stack = []) {
153
- stack.push(element);
154
- try {
155
- if (typeof element === "boolean" || typeof element === "number" || Array.isArray(element)) {
156
- stack.pop();
157
- return element;
158
- }
159
- if (typeof element === "string") {
160
- stack.pop();
161
- return element;
162
- }
163
- const processElementOptionsAsChildAndReturn = () => {
164
- try {
165
- const children = element.children;
166
- element.children = [
167
- element.options,
168
- ...children
169
- ];
170
- element.options = {};
171
- for (let i = 0; i < children.length + 1; i++) {
172
- const child = element.children[i];
173
- const processedChild = processPageElements(child, objectAttributes, recursionLevel + 1, stack);
174
- element.children[i] = processedChild;
175
- }
176
- return {
177
- ...element,
178
- options: {}
179
- };
180
- } catch (e) {
181
- const errorString = `Could not process element options as a child. ${e}.`;
182
- throw new Error(errorString);
183
- }
184
- };
185
- if (typeof element.options !== "object") {
186
- const result = processElementOptionsAsChildAndReturn();
187
- stack.pop();
188
- return result;
189
- }
190
- const {
191
- tag: elementTag,
192
- options: elementOptions,
193
- children: elementChildren
194
- } = element.options;
195
- if (elementTag && elementOptions && elementChildren) {
196
- const result = processElementOptionsAsChildAndReturn();
197
- stack.pop();
198
- return result;
199
- }
200
- const options2 = element.options;
201
- for (const [optionName, optionValue] of Object.entries(options2)) {
202
- const lcOptionName = optionName.toLowerCase();
203
- if (typeof optionValue !== "object") {
204
- if (lcOptionName === "innertext") {
205
- delete options2[optionName];
206
- if (element.children === null) {
207
- throw `Cannot use innerText or innerHTML on childrenless elements.`;
208
- }
209
- element.children = [optionValue, ...element.children];
210
- continue;
211
- } else if (lcOptionName === "innerhtml") {
212
- if (element.children === null) {
213
- throw `Cannot use innerText or innerHTML on childrenless elements.`;
214
- }
215
- delete options2[optionName];
216
- element.children = [optionValue];
217
- continue;
218
- }
219
- continue;
220
- }
221
- ;
222
- processOptionAsObjectAttribute(element, optionName, optionValue, objectAttributes);
223
- }
224
- if (element.children) {
225
- for (let i = 0; i < element.children.length; i++) {
226
- const child = element.children[i];
227
- const processedChild = processPageElements(child, objectAttributes, recursionLevel + 1, stack);
228
- element.children[i] = processedChild;
229
- }
230
- }
231
- stack.pop();
232
- return element;
233
- } catch (e) {
234
- const trace = buildTrace(stack);
235
- if (recursionLevel === 0) {
236
- throw new Error(`${e}
237
-
238
- Trace:
239
- ${trace}`);
240
- } else {
241
- throw e;
242
- }
243
- }
244
- }
245
- ;
246
- async function pageToHTML(pageLocation, pageElements, metadata, DIST_DIR2, pageName, doWrite = true, requiredClientModules = {}, layout, pathname = "") {
247
- if (typeof pageElements === "string" || typeof pageElements === "boolean" || typeof pageElements === "number" || Array.isArray(pageElements)) {
248
- throw new Error(`The root element of a page / layout must be a built element, not just a Child. Received: ${typeof pageElements}.`);
249
- }
250
- const objectAttributes = [];
251
- const stack = [];
252
- const processedPageElements = processPageElements(pageElements, objectAttributes, 0, stack);
253
- const renderedPage = await serverSideRenderPage(
254
- processedPageElements,
255
- pageLocation
256
- );
257
- const { internals, builtMetadata } = await generateHTMLTemplate({
258
- pageURL: pathname,
259
- head: metadata,
260
- addPageScriptTag: doWrite,
261
- name: pageName,
262
- requiredClientModules,
263
- environment: options.environment
264
- });
265
- let extraBodyHTML = "";
266
- if (doWrite === false) {
267
- const state = getState();
268
- const pageLoadHooks = getLoadHooks();
269
- const userObjectAttributes = getObjectAttributes();
270
- const {
271
- result
272
- } = await generateClientPageData(
273
- pathname,
274
- state || {},
275
- [...objectAttributes, ...userObjectAttributes],
276
- pageLoadHooks || [],
277
- DIST_DIR2,
278
- "page",
279
- "pd",
280
- false
281
- );
282
- const sanitized = pathname === "" ? "/" : `/${pathname}`;
283
- extraBodyHTML = `<script data-hook="true" data-pathname="${sanitized}" type="text/plain">${result}</script>`;
284
- extraBodyHTML += `<script>
285
- const text = document.querySelector('[data-hook="true"][data-pathname="${sanitized}"][type="text/plain"').textContent;
286
- const blob = new Blob([text], { type: 'text/javascript' });
287
- const url = URL.createObjectURL(blob);
288
-
289
- const script = document.createElement("script");
290
- script.src = url;
291
- script.type = "module";
292
- script.setAttribute("data-page", "true");
293
- script.setAttribute("data-pathname", "${sanitized}");
294
-
295
- document.head.appendChild(script);
296
-
297
- document.currentScript.remove();
298
- </script>`;
299
- extraBodyHTML = extraBodyHTML.replace(/\s+/g, " ").replace(/\s*([{}();,:])\s*/g, "$1").trim();
300
- }
301
- const headHTML = `<!DOCTYPE html>${layout.metadata.startHTML}${layout.scriptTag}${internals}${builtMetadata}${layout.metadata.endHTML}`;
302
- const bodyHTML = `${layout.pageContent.startHTML}${renderedPage.bodyHTML}${extraBodyHTML}${layout.pageContent.endHTML}`;
303
- const resultHTML = `${headHTML}${bodyHTML}`;
304
- const htmlLocation = path.join(pageLocation, (pageName === "page" ? "index" : pageName) + ".html");
305
- if (doWrite) {
306
- const dirname = path.dirname(htmlLocation);
307
- if (fs.existsSync(dirname) === false) {
308
- fs.mkdirSync(dirname, { recursive: true });
309
- }
310
- fs.writeFileSync(
311
- htmlLocation,
312
- resultHTML,
313
- {
314
- encoding: "utf-8",
315
- flag: "w"
316
- }
317
- );
318
- return objectAttributes;
319
- }
320
- return resultHTML;
321
- }
322
- ;
323
- async function generateClientPageData(pageLocation, state, objectAttributes, pageLoadHooks, DIST_DIR2, pageName, globalVariableName = "pd", write = true) {
324
- let clientPageJSText = "";
325
- {
326
- clientPageJSText += `${globalThis.__SERVER_PAGE_DATA_BANNER__}`;
327
- }
328
- {
329
- clientPageJSText += `export const data = {`;
330
- if (state) {
331
- clientPageJSText += `state:[`;
332
- for (const subject of state) {
333
- if (typeof subject.value === "string") {
334
- const stringified = JSON.stringify(subject.value);
335
- clientPageJSText += `{id:${subject.id},value:${stringified}},`;
336
- } else if (typeof subject.value === "function") {
337
- clientPageJSText += `{id:${subject.id},value:${subject.value.toString()}},`;
338
- } else {
339
- clientPageJSText += `{id:${subject.id},value:${JSON.stringify(subject.value)}},`;
340
- }
341
- }
342
- clientPageJSText += `],`;
343
- }
344
- const stateObjectAttributes = objectAttributes.filter((oa) => oa.type === ObjectAttributeType.STATE);
345
- if (stateObjectAttributes.length > 0) {
346
- const processed = [...stateObjectAttributes].map((soa) => {
347
- delete soa.type;
348
- return soa;
349
- });
350
- clientPageJSText += `soa:${JSON.stringify(processed)},`;
351
- }
352
- const observerObjectAttributes = objectAttributes.filter((oa) => oa.type === ObjectAttributeType.OBSERVER);
353
- if (observerObjectAttributes.length > 0) {
354
- let observerObjectAttributeString = "ooa:[";
355
- for (const observerObjectAttribute of observerObjectAttributes) {
356
- const ooa = observerObjectAttribute;
357
- observerObjectAttributeString += `{key:${ooa.key},attribute:"${ooa.attribute}",update:${ooa.update.toString()},`;
358
- observerObjectAttributeString += `refs:[`;
359
- for (const ref of ooa.refs) {
360
- observerObjectAttributeString += `{id:${ref.id}},`;
361
- }
362
- observerObjectAttributeString += "]},";
363
- }
364
- observerObjectAttributeString += "],";
365
- clientPageJSText += observerObjectAttributeString;
366
- }
367
- if (pageLoadHooks.length > 0) {
368
- clientPageJSText += "lh:[";
369
- for (const loadHook of pageLoadHooks) {
370
- clientPageJSText += `{fn:${loadHook.fn}},`;
371
- }
372
- clientPageJSText += "],";
373
- }
374
- clientPageJSText += `};`;
375
- }
376
- const pageDataPath = path.join(DIST_DIR2, pageLocation, `${pageName}_data.js`);
377
- let sendHardReloadInstruction = false;
378
- const transformedResult = await esbuild.transform(clientPageJSText, { minify: options.environment === "production" }).catch((error) => {
379
- console.error("Failed to transform client page js!", error);
380
- });
381
- if (!transformedResult) return { sendHardReloadInstruction };
382
- if (fs.existsSync(pageDataPath)) {
383
- const content = fs.readFileSync(pageDataPath).toString();
384
- if (content !== transformedResult.code) {
385
- sendHardReloadInstruction = true;
386
- }
387
- }
388
- if (write) fs.writeFileSync(pageDataPath, transformedResult.code, "utf-8");
389
- return { sendHardReloadInstruction, result: transformedResult.code };
390
- }
391
- ;
392
- async function generateLayout(DIST_DIR2, filePath, directory, childIndicator, generateDynamic = false) {
393
- initializeState();
394
- initializeObjectAttributes();
395
- resetLoadHooks();
396
- globalThis.__SERVER_PAGE_DATA_BANNER__ = "";
397
- let layoutElements;
398
- let metadataElements;
399
- let modules = [];
400
- let isDynamicLayout = false;
401
- try {
402
- const {
403
- layout,
404
- metadata,
405
- isDynamic,
406
- shippedModules: shippedModules2
407
- } = await import("file://" + filePath);
408
- if (shippedModules2 !== void 0) {
409
- modules = shippedModules2;
410
- }
411
- layoutElements = layout;
412
- metadataElements = metadata;
413
- if (isDynamic === true) {
414
- isDynamicLayout = isDynamic;
415
- }
416
- } catch (e) {
417
- throw new Error(`Error in Page: ${directory === "" ? "/" : directory}layout.ts - ${e}`);
418
- }
419
- LAYOUT_MAP.set(directory === "" ? "/" : `/${directory}`, {
420
- isDynamic: isDynamicLayout,
421
- filePath
422
- });
423
- if (isDynamicLayout === true && generateDynamic === false) return false;
424
- {
425
- if (!layoutElements) {
426
- throw new Error(`WARNING: ${filePath} should export a const layout, which is of type Layout: (child: Child) => AnyBuiltElement.`);
427
- }
428
- if (typeof layoutElements === "function") {
429
- if (layoutElements.constructor.name === "AsyncFunction") {
430
- layoutElements = await layoutElements(childIndicator);
431
- } else {
432
- layoutElements = layoutElements(childIndicator);
433
- }
434
- }
435
- }
436
- {
437
- if (!metadataElements) {
438
- throw new Error(`WARNING: ${filePath} should export a const metadata, which is of type LayoutMetadata: (child: Child) => AnyBuiltElement.`);
439
- }
440
- if (typeof metadataElements === "function") {
441
- if (metadataElements.constructor.name === "AsyncFunction") {
442
- metadataElements = await metadataElements(childIndicator);
443
- } else {
444
- metadataElements = metadataElements(childIndicator);
445
- }
446
- }
447
- }
448
- const state = getState();
449
- const pageLoadHooks = getLoadHooks();
450
- const objectAttributes = getObjectAttributes();
451
- if (typeof layoutElements === "string" || typeof layoutElements === "boolean" || typeof layoutElements === "number" || Array.isArray(layoutElements)) {
452
- throw new Error(`The root element of a page / layout must be a built element, not just a Child. Received: ${typeof layoutElements}.`);
453
- }
454
- const foundObjectAttributes = [];
455
- const stack = [];
456
- const processedPageElements = processPageElements(layoutElements, foundObjectAttributes, 0, stack);
457
- const renderedPage = await serverSideRenderPage(
458
- processedPageElements,
459
- directory
460
- );
461
- const metadataHTML = metadataElements ? renderRecursively(metadataElements) : "";
462
- await generateClientPageData(
463
- directory,
464
- state || {},
465
- [...objectAttributes, ...foundObjectAttributes],
466
- pageLoadHooks || [],
467
- DIST_DIR2,
468
- "layout",
469
- "ld"
470
- );
471
- return { pageContentHTML: renderedPage.bodyHTML, metadataHTML };
472
- }
473
- ;
474
- const builtLayouts = /* @__PURE__ */ new Map();
475
- async function buildLayouts() {
476
- const pagesDirectory = path.resolve(options.pagesDirectory);
477
- const subdirectories = [...getAllSubdirectories(pagesDirectory), ""];
478
- let shouldClientHardReload = false;
479
- for (const directory of subdirectories) {
480
- const abs = path.resolve(path.join(pagesDirectory, directory));
481
- const files = fs.readdirSync(abs, { withFileTypes: true }).filter((f) => f.name.endsWith(".ts"));
482
- for (const file of files) {
483
- const filePath = path.join(file.parentPath, file.name);
484
- const name = file.name.slice(0, file.name.length - 3);
485
- const isLayout = name === "layout";
486
- if (isLayout == false) {
487
- continue;
488
- }
489
- try {
490
- const builtLayout = await buildLayout(filePath, directory);
491
- if (!builtLayout) return { shouldClientHardReload: false };
492
- builtLayouts.set(filePath, builtLayout);
493
- } catch (e) {
494
- console.error(e);
495
- continue;
496
- }
497
- }
498
- }
499
- return { shouldClientHardReload };
500
- }
501
- function hashDirectory(directory) {
502
- return crypto.createHash("md5").update(directory).digest("hex");
503
- }
504
- async function buildLayout(filePath, directory, generateDynamic = false) {
505
- const id = hashDirectory(directory);
506
- const childIndicator = `<template layout-id="${id}"></template>`;
507
- const result = await generateLayout(
508
- DIST_DIR,
509
- filePath,
510
- directory,
511
- childIndicator,
512
- generateDynamic
513
- );
514
- if (result === false) return false;
515
- const { pageContentHTML, metadataHTML } = result;
516
- function splitAround(str, sub) {
517
- const i = str.indexOf(sub);
518
- if (i === -1) {
519
- throw new Error(`Whilst layout ${directory}, the splitter could not be found. Make sure to use the "child" prop passed into the layout.`);
520
- }
521
- return {
522
- startHTML: str.substring(0, i),
523
- endHTML: str.substring(i + sub.length)
524
- };
525
- }
526
- function splitAt(str, sub) {
527
- const i = str.indexOf(sub) + sub.length;
528
- if (i === -1) {
529
- throw new Error(`Whilst layout ${directory}, the splitter could not be found. Make sure to use the "child" prop passed into the layout's metadata.`);
530
- }
531
- return {
532
- startHTML: str.substring(0, i),
533
- endHTML: str.substring(i)
534
- };
535
- }
536
- const pathname = directory === "" ? "/" : directory;
537
- return {
538
- pageContent: splitAt(pageContentHTML, childIndicator),
539
- metadata: splitAround(metadataHTML, childIndicator),
540
- scriptTag: `<script data-layout="true" type="module" src="${pathname}layout_data.js" data-pathname="${pathname}" defer="true"></script>`
541
- };
542
- }
543
- ;
544
- async function fetchPageLayoutHTML(dirname) {
545
- const relative = path.relative(options.pagesDirectory, dirname);
546
- let split = relative.split(path.sep).filter(Boolean);
547
- split.push("/");
548
- split.reverse();
549
- let layouts = [];
550
- for (const dir of split) {
551
- if (!LAYOUT_MAP.has(dir)) {
552
- console.warn("A layout was not found within the layout map for a path:", dir, "This is normally not meant to be possible, so you might have royally screwed up.");
553
- continue;
554
- }
555
- const filePath = path.join(path.resolve(options.pagesDirectory), dir, "layout.ts");
556
- const layout = LAYOUT_MAP.get(dir);
557
- if (layout.isDynamic) {
558
- const builtLayout = await buildLayout(layout.filePath, dir, true);
559
- if (!builtLayout) continue;
560
- layouts.push(builtLayout);
561
- } else {
562
- if (!builtLayouts.has(filePath)) {
563
- const builtLayout = await buildLayout(layout.filePath, dir, true);
564
- if (!builtLayout) continue;
565
- builtLayouts.set(filePath, builtLayout);
566
- layouts.push(builtLayout);
567
- } else {
568
- layouts.push(builtLayouts.get(filePath));
569
- }
570
- }
571
- }
572
- const pageContent = {
573
- startHTML: "",
574
- endHTML: ""
575
- };
576
- const metadata = {
577
- startHTML: "",
578
- endHTML: ""
579
- };
580
- let scriptTags = "";
581
- for (const layout of layouts) {
582
- pageContent.startHTML += layout.pageContent.startHTML;
583
- metadata.startHTML += layout.metadata.startHTML;
584
- scriptTags += layout.scriptTag;
585
- pageContent.endHTML += layout.pageContent.endHTML;
586
- metadata.endHTML += layout.metadata.endHTML;
587
- }
588
- return { pageContent, metadata, scriptTag: scriptTags };
589
- }
590
- ;
591
- async function buildPages(DIST_DIR2) {
592
- resetLayouts();
593
- const pagesDirectory = path.resolve(options.pagesDirectory);
594
- const subdirectories = [...getAllSubdirectories(pagesDirectory), ""];
595
- let shouldClientHardReload = false;
596
- for (const directory of subdirectories) {
597
- const abs = path.resolve(path.join(pagesDirectory, directory));
598
- const files = fs.readdirSync(abs, { withFileTypes: true }).filter((f) => f.name.endsWith(".ts"));
599
- for (const file of files) {
600
- const filePath = path.join(file.parentPath, file.name);
601
- const name = file.name.slice(0, file.name.length - 3);
602
- const isPage = name === "page";
603
- if (isPage == false) {
604
- continue;
605
- }
606
- try {
607
- const hardReloadForPage = await buildPage(DIST_DIR2, directory, filePath, name);
608
- if (hardReloadForPage) {
609
- shouldClientHardReload = true;
610
- }
611
- } catch (e) {
612
- console.error(e);
613
- continue;
614
- }
615
- }
616
- }
617
- return {
618
- shouldClientHardReload
619
- };
620
- }
621
- ;
622
- async function buildPage(DIST_DIR2, directory, filePath, name) {
623
- initializeState();
624
- initializeObjectAttributes();
625
- resetLoadHooks();
626
- globalThis.__SERVER_PAGE_DATA_BANNER__ = "";
627
- let pageElements;
628
- let metadata;
629
- let modules = {};
630
- let pageIgnoresLayout = false;
631
- let isDynamicPage = false;
632
- try {
633
- const {
634
- page,
635
- metadata: pageMetadata,
636
- isDynamic,
637
- shippedModules: shippedModules2,
638
- ignoreLayout
639
- } = await import("file://" + filePath);
640
- if (shippedModules2 !== void 0) {
641
- modules = shippedModules2;
642
- }
643
- if (ignoreLayout) {
644
- pageIgnoresLayout = true;
645
- }
646
- pageElements = page;
647
- metadata = pageMetadata;
648
- if (isDynamic === true) {
649
- isDynamicPage = isDynamic;
650
- }
651
- } catch (e) {
652
- throw new Error(`Error in Page: ${directory}/${name}.ts - ${e}`);
653
- }
654
- PAGE_MAP.set(directory === "" ? "/" : `/${directory}`, {
655
- isDynamic: isDynamicPage,
656
- filePath
657
- });
658
- if (isDynamicPage) return false;
659
- if (modules !== void 0) {
660
- for (const [globalName, path2] of Object.entries(modules)) {
661
- modulesToShip.push({ globalName, path: path2 });
662
- }
663
- }
664
- if (!metadata || metadata && typeof metadata !== "function") {
665
- console.warn(`WARNING: ${filePath} does not export a metadata function.`);
666
- }
667
- if (!pageElements) {
668
- console.warn(`WARNING: ${filePath} should export a const page, which is of type () => BuiltElement<"body">.`);
669
- }
670
- const pageProps = {
671
- pageName: directory,
672
- middlewareData: {}
673
- };
674
- if (typeof pageElements === "function") {
675
- if (pageElements.constructor.name === "AsyncFunction") {
676
- pageElements = await pageElements(pageProps);
677
- } else {
678
- pageElements = pageElements(pageProps);
679
- }
680
- }
681
- const state = getState();
682
- const pageLoadHooks = getLoadHooks();
683
- const objectAttributes = getObjectAttributes();
684
- const layout = await fetchPageLayoutHTML(path.dirname(filePath));
685
- const foundObjectAttributes = await pageToHTML(
686
- path.join(DIST_DIR2, directory),
687
- pageElements || body(),
688
- metadata ?? (() => head()),
689
- DIST_DIR2,
690
- name,
691
- true,
692
- modules,
693
- layout,
694
- directory
695
- );
696
- const {
697
- sendHardReloadInstruction
698
- } = await generateClientPageData(
699
- directory,
700
- state || {},
701
- [...objectAttributes, ...foundObjectAttributes],
702
- pageLoadHooks || [],
703
- DIST_DIR2,
704
- name
705
- );
706
- return sendHardReloadInstruction === true;
707
- }
708
- ;
709
- async function shipModules() {
710
- for (const plugin of modulesToShip) {
711
- {
712
- if (shippedModules.has(plugin.globalName)) continue;
713
- shippedModules.set(plugin.globalName, true);
714
- }
715
- esbuild.build({
716
- entryPoints: [plugin.path],
717
- bundle: true,
718
- outfile: path.join(DIST_DIR, "shipped", plugin.globalName + ".js"),
719
- format: "iife",
720
- platform: "browser",
721
- globalName: plugin.globalName,
722
- minify: true,
723
- treeShaking: true
724
- });
725
- }
726
- modulesToShip = [];
727
- }
728
- ;
729
- function retrievePageAndLayoutMaps() {
730
- return { LAYOUT_MAP, PAGE_MAP };
731
- }
732
- export {
733
- LAYOUT_MAP,
734
- PAGE_MAP,
735
- buildClient,
736
- buildLayout,
737
- buildLayouts,
738
- buildPage,
739
- buildPages,
740
- fetchPageLayoutHTML,
741
- generateClientPageData,
742
- generateLayout,
743
- getAllSubdirectories,
744
- modulesToShip,
745
- pageToHTML,
746
- populateServerMaps,
747
- processPageElements,
748
- retrievePageAndLayoutMaps,
749
- setCompilationOptions,
750
- shipModules
751
- };