@aerobuilt/core 0.3.0 → 0.3.2
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.
|
@@ -26,6 +26,65 @@ function isDirectiveAttr(attrName, config = defaultConfig) {
|
|
|
26
26
|
return prefixes.some((p) => attrName.startsWith(p));
|
|
27
27
|
}
|
|
28
28
|
|
|
29
|
+
//#endregion
|
|
30
|
+
//#region src/compiler/constants.ts
|
|
31
|
+
/**
|
|
32
|
+
* Shared constants for the Aero compiler (parser, codegen, helpers).
|
|
33
|
+
*
|
|
34
|
+
* @remarks
|
|
35
|
+
* Attribute names are used with optional `data-` prefix (e.g. `data-each`). Script taxonomy uses
|
|
36
|
+
* `is:build`, `is:inline`, `is:blocking`; default scripts are treated as client (virtual module).
|
|
37
|
+
*/
|
|
38
|
+
/** Prefix for data attributes (e.g. `data-each` → ATTR_PREFIX + ATTR_EACH). */
|
|
39
|
+
const ATTR_PREFIX = "data-";
|
|
40
|
+
/** Attribute for spreading props onto a component: `data-props` or `data-props="{ ... }"`. */
|
|
41
|
+
const ATTR_PROPS = "props";
|
|
42
|
+
/** Attribute for iteration: `data-each="{ item in items }"`. */
|
|
43
|
+
const ATTR_EACH = "each";
|
|
44
|
+
const ATTR_IF = "if";
|
|
45
|
+
const ATTR_ELSE_IF = "else-if";
|
|
46
|
+
const ATTR_ELSE = "else";
|
|
47
|
+
/** Slot name (on `<slot>` or content). */
|
|
48
|
+
const ATTR_NAME = "name";
|
|
49
|
+
const ATTR_SLOT = "slot";
|
|
50
|
+
/** Script runs at build time; extracted and becomes render function body. */
|
|
51
|
+
const ATTR_IS_BUILD = "is:build";
|
|
52
|
+
/** Script left in template in place; not extracted. */
|
|
53
|
+
const ATTR_IS_INLINE = "is:inline";
|
|
54
|
+
/** Script hoisted to head; extracted. */
|
|
55
|
+
const ATTR_IS_BLOCKING = "is:blocking";
|
|
56
|
+
/** Script/style receives data from template: `pass:data="{ config }"` or `pass:data="{ ...theme }"`. */
|
|
57
|
+
const ATTR_PASS_DATA = "pass:data";
|
|
58
|
+
/** Script external source (HTML attribute). */
|
|
59
|
+
const ATTR_SRC = "src";
|
|
60
|
+
const TAG_SLOT = "slot";
|
|
61
|
+
/** Default slot name when no name is given. */
|
|
62
|
+
const SLOT_NAME_DEFAULT = "default";
|
|
63
|
+
/** Matches `item in items` for data-each (captures: loop variable, iterable expression). */
|
|
64
|
+
const EACH_REGEX = /^(\w+)\s+in\s+(.+)$/;
|
|
65
|
+
/** Matches tag names ending with `-component` or `-layout`. */
|
|
66
|
+
const COMPONENT_SUFFIX_REGEX = /-(component|layout)$/;
|
|
67
|
+
/** Self-closing tag: `<tag ... />`. */
|
|
68
|
+
const SELF_CLOSING_TAG_REGEX = /<([a-z0-9-]+)([^>]*?)\/>/gi;
|
|
69
|
+
const SELF_CLOSING_TAIL_REGEX = /\/>$/;
|
|
70
|
+
/** HTML void elements that have no closing tag. */
|
|
71
|
+
const VOID_TAGS = new Set([
|
|
72
|
+
"area",
|
|
73
|
+
"base",
|
|
74
|
+
"br",
|
|
75
|
+
"col",
|
|
76
|
+
"embed",
|
|
77
|
+
"hr",
|
|
78
|
+
"img",
|
|
79
|
+
"input",
|
|
80
|
+
"link",
|
|
81
|
+
"meta",
|
|
82
|
+
"param",
|
|
83
|
+
"source",
|
|
84
|
+
"track",
|
|
85
|
+
"wbr"
|
|
86
|
+
]);
|
|
87
|
+
|
|
29
88
|
//#endregion
|
|
30
89
|
//#region src/compiler/build-script-analysis.ts
|
|
31
90
|
/**
|
|
@@ -190,4 +249,4 @@ function analyzeBuildScriptForEditor(script) {
|
|
|
190
249
|
}
|
|
191
250
|
|
|
192
251
|
//#endregion
|
|
193
|
-
export { compileInterpolationFromSegments as a,
|
|
252
|
+
export { DEFAULT_DIRECTIVE_PREFIXES as C, tokenizeCurlyInterpolation as E, VOID_TAGS as S, compileInterpolationFromSegments as T, EACH_REGEX as _, ATTR_ELSE_IF as a, SLOT_NAME_DEFAULT as b, ATTR_IS_BUILD as c, ATTR_PASS_DATA as d, ATTR_PREFIX as f, COMPONENT_SUFFIX_REGEX as g, ATTR_SRC as h, ATTR_ELSE as i, ATTR_IS_INLINE as l, ATTR_SLOT as m, analyzeBuildScriptForEditor as n, ATTR_IF as o, ATTR_PROPS as p, ATTR_EACH as r, ATTR_IS_BLOCKING as s, analyzeBuildScript as t, ATTR_NAME as u, SELF_CLOSING_TAG_REGEX as v, isDirectiveAttr as w, TAG_SLOT as x, SELF_CLOSING_TAIL_REGEX as y };
|
package/dist/entry-editor.d.mts
CHANGED
|
@@ -3,8 +3,7 @@ import { InterpolationSegment, LiteralSegment, Segment, TokenizeOptions, compile
|
|
|
3
3
|
//#region src/compiler/directive-attributes.d.ts
|
|
4
4
|
/**
|
|
5
5
|
* Classifier for directive attributes (Alpine.js, HTMX, Vue, etc.) that should
|
|
6
|
-
* skip { } interpolation in the compiler.
|
|
7
|
-
* declarative list for clearer semantics and easier extension.
|
|
6
|
+
* skip { } interpolation in the compiler.
|
|
8
7
|
*
|
|
9
8
|
* @packageDocumentation
|
|
10
9
|
*/
|
|
@@ -30,6 +29,10 @@ declare const DEFAULT_DIRECTIVE_PREFIXES: string[];
|
|
|
30
29
|
*/
|
|
31
30
|
declare function isDirectiveAttr(attrName: string, config?: DirectiveAttrConfig): boolean;
|
|
32
31
|
//#endregion
|
|
32
|
+
//#region src/compiler/constants.d.ts
|
|
33
|
+
/** Matches tag names ending with `-component` or `-layout`. */
|
|
34
|
+
declare const COMPONENT_SUFFIX_REGEX: RegExp;
|
|
35
|
+
//#endregion
|
|
33
36
|
//#region src/compiler/build-script-analysis.d.ts
|
|
34
37
|
/**
|
|
35
38
|
* AST-based analysis of Aero build scripts: extract imports and getStaticPaths export.
|
|
@@ -71,4 +74,4 @@ interface BuildScriptAnalysisForEditorResult {
|
|
|
71
74
|
*/
|
|
72
75
|
declare function analyzeBuildScriptForEditor(script: string): BuildScriptAnalysisForEditorResult;
|
|
73
76
|
//#endregion
|
|
74
|
-
export { type BuildScriptAnalysisForEditorResult, type BuildScriptImportForEditor, DEFAULT_DIRECTIVE_PREFIXES, type DirectiveAttrConfig, type InterpolationSegment, type LiteralSegment, type Segment, type TokenizeOptions, analyzeBuildScriptForEditor, compileInterpolationFromSegments, isDirectiveAttr, tokenizeCurlyInterpolation };
|
|
77
|
+
export { type BuildScriptAnalysisForEditorResult, type BuildScriptImportForEditor, COMPONENT_SUFFIX_REGEX, DEFAULT_DIRECTIVE_PREFIXES, type DirectiveAttrConfig, type InterpolationSegment, type LiteralSegment, type Segment, type TokenizeOptions, analyzeBuildScriptForEditor, compileInterpolationFromSegments, isDirectiveAttr, tokenizeCurlyInterpolation };
|
package/dist/entry-editor.mjs
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { C as DEFAULT_DIRECTIVE_PREFIXES, E as tokenizeCurlyInterpolation, T as compileInterpolationFromSegments, g as COMPONENT_SUFFIX_REGEX, n as analyzeBuildScriptForEditor, w as isDirectiveAttr } from "./build-script-analysis-Bll0Ujh4.mjs";
|
|
2
2
|
|
|
3
|
-
export { DEFAULT_DIRECTIVE_PREFIXES, analyzeBuildScriptForEditor, compileInterpolationFromSegments, isDirectiveAttr, tokenizeCurlyInterpolation };
|
|
3
|
+
export { COMPONENT_SUFFIX_REGEX, DEFAULT_DIRECTIVE_PREFIXES, analyzeBuildScriptForEditor, compileInterpolationFromSegments, isDirectiveAttr, tokenizeCurlyInterpolation };
|
|
@@ -31,10 +31,14 @@ const notify = () => {
|
|
|
31
31
|
};
|
|
32
32
|
if (!globalThis.__AERO_INSTANCE__) globalThis.__AERO_INSTANCE__ = instance;
|
|
33
33
|
if (!globalThis.__AERO_LISTENERS__) globalThis.__AERO_LISTENERS__ = listeners;
|
|
34
|
-
/**
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
34
|
+
/**
|
|
35
|
+
* Eager globs so pages, layouts, and components are available synchronously for SSR/build.
|
|
36
|
+
* Patterns use default client dir (./client/...) so Vite's import-glob accepts them; apps with
|
|
37
|
+
* custom dirs rely on path aliases mapping @components/@layouts/@pages to the same structure.
|
|
38
|
+
*/
|
|
39
|
+
const components = /* @__PURE__ */ Object.assign({});
|
|
40
|
+
const layouts = /* @__PURE__ */ Object.assign({});
|
|
41
|
+
const pages = /* @__PURE__ */ Object.assign({});
|
|
38
42
|
aero.registerPages(components);
|
|
39
43
|
aero.registerPages(layouts);
|
|
40
44
|
aero.registerPages(pages);
|
package/dist/vite/index.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { a as isDynamicRoutePattern, i as expandRoutePattern, n as resolvePageName, o as toPosix, s as toPosixRelative, t as pagePathToKey } from "../routing-Bai79LCq.mjs";
|
|
2
|
-
import {
|
|
2
|
+
import { E as tokenizeCurlyInterpolation, S as VOID_TAGS, T as compileInterpolationFromSegments, _ as EACH_REGEX, a as ATTR_ELSE_IF, b as SLOT_NAME_DEFAULT, c as ATTR_IS_BUILD, d as ATTR_PASS_DATA, f as ATTR_PREFIX, g as COMPONENT_SUFFIX_REGEX, h as ATTR_SRC, i as ATTR_ELSE, l as ATTR_IS_INLINE, m as ATTR_SLOT, o as ATTR_IF, p as ATTR_PROPS, r as ATTR_EACH, s as ATTR_IS_BLOCKING, t as analyzeBuildScript, u as ATTR_NAME, v as SELF_CLOSING_TAG_REGEX, w as isDirectiveAttr, x as TAG_SLOT, y as SELF_CLOSING_TAIL_REGEX } from "../build-script-analysis-Bll0Ujh4.mjs";
|
|
3
3
|
import { loadTsconfigAliases, mergeWithDefaultAliases } from "../utils/aliases.mjs";
|
|
4
4
|
import { redirectsToRouteRules } from "../utils/redirects.mjs";
|
|
5
5
|
import { createRequire } from "node:module";
|
|
@@ -117,65 +117,6 @@ function resolveDirs(dirs) {
|
|
|
117
117
|
};
|
|
118
118
|
}
|
|
119
119
|
|
|
120
|
-
//#endregion
|
|
121
|
-
//#region src/compiler/constants.ts
|
|
122
|
-
/**
|
|
123
|
-
* Shared constants for the Aero compiler (parser, codegen, helpers).
|
|
124
|
-
*
|
|
125
|
-
* @remarks
|
|
126
|
-
* Attribute names are used with optional `data-` prefix (e.g. `data-each`). Script taxonomy uses
|
|
127
|
-
* `is:build`, `is:inline`, `is:blocking`; default scripts are treated as client (virtual module).
|
|
128
|
-
*/
|
|
129
|
-
/** Prefix for data attributes (e.g. `data-each` → ATTR_PREFIX + ATTR_EACH). */
|
|
130
|
-
const ATTR_PREFIX = "data-";
|
|
131
|
-
/** Attribute for spreading props onto a component: `data-props` or `data-props="{ ... }"`. */
|
|
132
|
-
const ATTR_PROPS = "props";
|
|
133
|
-
/** Attribute for iteration: `data-each="{ item in items }"`. */
|
|
134
|
-
const ATTR_EACH = "each";
|
|
135
|
-
const ATTR_IF = "if";
|
|
136
|
-
const ATTR_ELSE_IF = "else-if";
|
|
137
|
-
const ATTR_ELSE = "else";
|
|
138
|
-
/** Slot name (on `<slot>` or content). */
|
|
139
|
-
const ATTR_NAME = "name";
|
|
140
|
-
const ATTR_SLOT = "slot";
|
|
141
|
-
/** Script runs at build time; extracted and becomes render function body. */
|
|
142
|
-
const ATTR_IS_BUILD = "is:build";
|
|
143
|
-
/** Script left in template in place; not extracted. */
|
|
144
|
-
const ATTR_IS_INLINE = "is:inline";
|
|
145
|
-
/** Script hoisted to head; extracted. */
|
|
146
|
-
const ATTR_IS_BLOCKING = "is:blocking";
|
|
147
|
-
/** Script/style receives data from template: `pass:data="{ config }"` or `pass:data="{ ...theme }"`. */
|
|
148
|
-
const ATTR_PASS_DATA = "pass:data";
|
|
149
|
-
/** Script external source (HTML attribute). */
|
|
150
|
-
const ATTR_SRC = "src";
|
|
151
|
-
const TAG_SLOT = "slot";
|
|
152
|
-
/** Default slot name when no name is given. */
|
|
153
|
-
const SLOT_NAME_DEFAULT = "default";
|
|
154
|
-
/** Matches `item in items` for data-each (captures: loop variable, iterable expression). */
|
|
155
|
-
const EACH_REGEX = /^(\w+)\s+in\s+(.+)$/;
|
|
156
|
-
/** Matches tag names ending with `-component` or `-layout`. */
|
|
157
|
-
const COMPONENT_SUFFIX_REGEX = /-(component|layout)$/;
|
|
158
|
-
/** Self-closing tag: `<tag ... />`. */
|
|
159
|
-
const SELF_CLOSING_TAG_REGEX = /<([a-z0-9-]+)([^>]*?)\/>/gi;
|
|
160
|
-
const SELF_CLOSING_TAIL_REGEX = /\/>$/;
|
|
161
|
-
/** HTML void elements that have no closing tag. */
|
|
162
|
-
const VOID_TAGS = new Set([
|
|
163
|
-
"area",
|
|
164
|
-
"base",
|
|
165
|
-
"br",
|
|
166
|
-
"col",
|
|
167
|
-
"embed",
|
|
168
|
-
"hr",
|
|
169
|
-
"img",
|
|
170
|
-
"input",
|
|
171
|
-
"link",
|
|
172
|
-
"meta",
|
|
173
|
-
"param",
|
|
174
|
-
"source",
|
|
175
|
-
"track",
|
|
176
|
-
"wbr"
|
|
177
|
-
]);
|
|
178
|
-
|
|
179
120
|
//#endregion
|
|
180
121
|
//#region src/compiler/parser.ts
|
|
181
122
|
/** Serialize element attributes to a string, excluding given names (case-insensitive). Values are XML-escaped. */
|
|
@@ -648,31 +589,20 @@ var Lowerer = class {
|
|
|
648
589
|
}
|
|
649
590
|
/** Gets the condition value from if/else-if attribute */
|
|
650
591
|
getCondition(node, attr) {
|
|
592
|
+
const tagName = node?.tagName?.toLowerCase?.() || "element";
|
|
651
593
|
const plainValue = node.getAttribute(attr);
|
|
652
|
-
if (plainValue !== null) return
|
|
594
|
+
if (plainValue !== null) return stripBraces(validateSingleBracedExpression(plainValue, {
|
|
595
|
+
directive: attr,
|
|
596
|
+
tagName
|
|
597
|
+
}));
|
|
653
598
|
const dataAttr = ATTR_PREFIX + attr;
|
|
654
599
|
const dataValue = node.getAttribute(dataAttr);
|
|
655
|
-
if (dataValue !== null) return
|
|
600
|
+
if (dataValue !== null) return stripBraces(validateSingleBracedExpression(dataValue, {
|
|
601
|
+
directive: dataAttr,
|
|
602
|
+
tagName
|
|
603
|
+
}));
|
|
656
604
|
return null;
|
|
657
605
|
}
|
|
658
|
-
/**
|
|
659
|
-
* Require directive value to be a braced expression; optionally strip outer braces.
|
|
660
|
-
*
|
|
661
|
-
* @param value - Raw attribute value.
|
|
662
|
-
* @param directive - Attribute name for error message (e.g. `each`, `pass:data`).
|
|
663
|
-
* @param node - DOM node for error message (tag name).
|
|
664
|
-
* @param options - `strip: true` (default) returns inner expression; `strip: false` returns trimmed value including braces (e.g. for pass:data).
|
|
665
|
-
* @returns Trimmed value, with or without outer braces per options.
|
|
666
|
-
*/
|
|
667
|
-
requireBracedExpression(value, directive, node, options) {
|
|
668
|
-
const strip = options?.strip !== false;
|
|
669
|
-
const trimmed = value.trim();
|
|
670
|
-
if (!trimmed.startsWith("{") || !trimmed.endsWith("}")) {
|
|
671
|
-
const tagName = node?.tagName?.toLowerCase?.() || "element";
|
|
672
|
-
throw new Error(`Directive \`${directive}\` on <${tagName}> must use a braced expression, e.g. ${directive}="{ expression }".`);
|
|
673
|
-
}
|
|
674
|
-
return strip ? stripBraces(trimmed) : trimmed;
|
|
675
|
-
}
|
|
676
606
|
isSingleWrappedExpression(value) {
|
|
677
607
|
const trimmed = value.trim();
|
|
678
608
|
if (!trimmed.startsWith("{") || !trimmed.endsWith("}")) return false;
|
|
@@ -702,7 +632,13 @@ var Lowerer = class {
|
|
|
702
632
|
if (isAttr(attr.name, ATTR_PROPS, ATTR_PREFIX)) {
|
|
703
633
|
const value = attr.value?.trim() || "";
|
|
704
634
|
if (!value) dataPropsExpression = "...props";
|
|
705
|
-
else
|
|
635
|
+
else {
|
|
636
|
+
const tagName = node?.tagName?.toLowerCase?.() || "element";
|
|
637
|
+
dataPropsExpression = stripBraces(validateSingleBracedExpression(value, {
|
|
638
|
+
directive: attr.name,
|
|
639
|
+
tagName
|
|
640
|
+
}));
|
|
641
|
+
}
|
|
706
642
|
continue;
|
|
707
643
|
}
|
|
708
644
|
const rawValue = attr.value ?? "";
|
|
@@ -725,7 +661,11 @@ var Lowerer = class {
|
|
|
725
661
|
if (node.attributes) for (let i = 0; i < node.attributes.length; i++) {
|
|
726
662
|
const attr = node.attributes[i];
|
|
727
663
|
if (isAttr(attr.name, ATTR_EACH, ATTR_PREFIX)) {
|
|
728
|
-
const
|
|
664
|
+
const tagName = node?.tagName?.toLowerCase?.() || "element";
|
|
665
|
+
const match = stripBraces(validateSingleBracedExpression(attr.value || "", {
|
|
666
|
+
directive: attr.name,
|
|
667
|
+
tagName
|
|
668
|
+
})).match(EACH_REGEX);
|
|
729
669
|
if (!match) {
|
|
730
670
|
const tagName = node?.tagName?.toLowerCase?.() || "element";
|
|
731
671
|
throw new Error(`Directive \`${attr.name}\` on <${tagName}> must match "{ item in items }".`);
|
|
@@ -1086,6 +1026,109 @@ function compile(parsed, options) {
|
|
|
1086
1026
|
});
|
|
1087
1027
|
return importsCode + "\n" + renderFn;
|
|
1088
1028
|
}
|
|
1029
|
+
/**
|
|
1030
|
+
* Compile an HTML template source into a JavaScript module string. Single entry for parse + compile.
|
|
1031
|
+
* When optional `parsed` is provided (e.g. after registering client scripts in the plugin), it is used to avoid parsing twice.
|
|
1032
|
+
*
|
|
1033
|
+
* @param htmlSource - Raw HTML template string.
|
|
1034
|
+
* @param options - CompileOptions (root, resolvePath, importer, optional script overrides).
|
|
1035
|
+
* @param parsed - Optional pre-parsed result; when provided, used instead of parsing htmlSource again.
|
|
1036
|
+
* @returns Module source (async render function + optional getStaticPaths).
|
|
1037
|
+
*/
|
|
1038
|
+
function compileTemplate(htmlSource, options, parsed) {
|
|
1039
|
+
const p = parsed ?? parse(htmlSource);
|
|
1040
|
+
return compile(p, {
|
|
1041
|
+
...options,
|
|
1042
|
+
clientScripts: options.clientScripts ?? p.clientScripts,
|
|
1043
|
+
inlineScripts: options.inlineScripts ?? p.inlineScripts,
|
|
1044
|
+
blockingScripts: options.blockingScripts ?? p.blockingScripts
|
|
1045
|
+
});
|
|
1046
|
+
}
|
|
1047
|
+
|
|
1048
|
+
//#endregion
|
|
1049
|
+
//#region src/vite/rewrite.ts
|
|
1050
|
+
/** Route path to output file path (e.g. '' → index.html, about → about/index.html). */
|
|
1051
|
+
function toOutputFile(routePath) {
|
|
1052
|
+
if (routePath === "") return "index.html";
|
|
1053
|
+
if (routePath === "404") return "404.html";
|
|
1054
|
+
return toPosix(path$1.join(routePath, "index.html"));
|
|
1055
|
+
}
|
|
1056
|
+
/** Relative path from fromDir to targetPath, always starting with ./ when non-empty. */
|
|
1057
|
+
function normalizeRelativeLink(fromDir, targetPath) {
|
|
1058
|
+
const rel = path$1.posix.relative(fromDir, targetPath);
|
|
1059
|
+
if (!rel) return "./";
|
|
1060
|
+
if (rel.startsWith(".")) return rel;
|
|
1061
|
+
return `./${rel}`;
|
|
1062
|
+
}
|
|
1063
|
+
/** Relative path to a route (directory index); appends trailing slash for non-root routes. */
|
|
1064
|
+
function normalizeRelativeRouteLink(fromDir, routePath) {
|
|
1065
|
+
const targetDir = routePath === "" ? "" : routePath;
|
|
1066
|
+
const rel = path$1.posix.relative(fromDir, targetDir);
|
|
1067
|
+
let res = !rel ? "./" : rel.startsWith(".") ? rel : `./${rel}`;
|
|
1068
|
+
if (routePath !== "" && routePath !== "404" && !res.endsWith("/")) res += "/";
|
|
1069
|
+
return res;
|
|
1070
|
+
}
|
|
1071
|
+
function normalizeRoutePathFromHref(value) {
|
|
1072
|
+
if (value === "/") return "";
|
|
1073
|
+
return value.replace(/^\/+/, "").replace(/\/+$/, "");
|
|
1074
|
+
}
|
|
1075
|
+
function isSkippableUrl$1(value) {
|
|
1076
|
+
if (!value) return true;
|
|
1077
|
+
return SKIP_PROTOCOL_REGEX.test(value);
|
|
1078
|
+
}
|
|
1079
|
+
const ASSET_IMAGE_EXT = /\.(jpg|jpeg|png|gif|webp|svg|ico)(\?|$)/i;
|
|
1080
|
+
/** Rewrite one absolute URL to dist-relative using manifest and route set; leaves API and external URLs unchanged. */
|
|
1081
|
+
function rewriteAbsoluteUrl(value, fromDir, manifest, routeSet, apiPrefix = DEFAULT_API_PREFIX) {
|
|
1082
|
+
if (value.startsWith(apiPrefix)) return value;
|
|
1083
|
+
const noQuery = value.split(/[?#]/)[0] || value;
|
|
1084
|
+
const suffix = value.slice(noQuery.length);
|
|
1085
|
+
const manifestKey = noQuery.replace(/^\//, "");
|
|
1086
|
+
let manifestEntry = manifest[noQuery] ?? manifest[manifestKey];
|
|
1087
|
+
if (!manifestEntry && noQuery.startsWith("assets/")) {
|
|
1088
|
+
const entry = Object.values(manifest).find((e) => e?.file === noQuery || e?.file === manifestKey);
|
|
1089
|
+
if (entry) manifestEntry = entry;
|
|
1090
|
+
}
|
|
1091
|
+
if (manifestEntry?.file) return normalizeRelativeLink(fromDir, manifestEntry.assets?.find((a) => ASSET_IMAGE_EXT.test(a)) ?? manifestEntry.file) + suffix;
|
|
1092
|
+
if (noQuery.startsWith("/assets/")) return normalizeRelativeLink(fromDir, noQuery.replace(/^\//, "")) + suffix;
|
|
1093
|
+
const route = normalizeRoutePathFromHref(noQuery);
|
|
1094
|
+
if (routeSet.has(route) || route === "") return (route === "404" ? normalizeRelativeLink(fromDir, toOutputFile(route)) : normalizeRelativeRouteLink(fromDir, route)) + suffix;
|
|
1095
|
+
return normalizeRelativeLink(fromDir, noQuery.replace(/^\//, "")) + suffix;
|
|
1096
|
+
}
|
|
1097
|
+
/** Rewrite script src (virtual client → hashed asset) and LINK_ATTRS in rendered HTML; add doctype. */
|
|
1098
|
+
function rewriteRenderedHtml(html, outputFile, manifest, routeSet, apiPrefix = DEFAULT_API_PREFIX) {
|
|
1099
|
+
const fromDir = path$1.posix.dirname(outputFile);
|
|
1100
|
+
const { document } = parseHTML(html);
|
|
1101
|
+
for (const script of Array.from(document.querySelectorAll("script[src]"))) {
|
|
1102
|
+
const src = script.getAttribute("src") || "";
|
|
1103
|
+
if (src.startsWith(CLIENT_SCRIPT_PREFIX)) {
|
|
1104
|
+
const newSrc = rewriteAbsoluteUrl(src, fromDir, manifest, routeSet, apiPrefix);
|
|
1105
|
+
script.setAttribute("src", newSrc);
|
|
1106
|
+
script.setAttribute("type", "module");
|
|
1107
|
+
script.removeAttribute("defer");
|
|
1108
|
+
continue;
|
|
1109
|
+
}
|
|
1110
|
+
if (script.getAttribute("type") === "module") script.removeAttribute("defer");
|
|
1111
|
+
}
|
|
1112
|
+
for (const el of Array.from(document.querySelectorAll("*"))) for (const attrName of LINK_ATTRS) {
|
|
1113
|
+
if (!el.hasAttribute(attrName)) continue;
|
|
1114
|
+
const current = (el.getAttribute(attrName) || "").trim();
|
|
1115
|
+
if (!current || isSkippableUrl$1(current)) continue;
|
|
1116
|
+
if (!current.startsWith("/")) continue;
|
|
1117
|
+
el.setAttribute(attrName, rewriteAbsoluteUrl(current, fromDir, manifest, routeSet, apiPrefix));
|
|
1118
|
+
}
|
|
1119
|
+
const htmlTag = document.documentElement;
|
|
1120
|
+
if (htmlTag) return addDoctype(htmlTag.outerHTML);
|
|
1121
|
+
return addDoctype(document.toString());
|
|
1122
|
+
}
|
|
1123
|
+
/** Prepend `<!doctype html>` if missing. */
|
|
1124
|
+
function addDoctype(html) {
|
|
1125
|
+
return /^\s*<!doctype\s+html/i.test(html) ? html : `<!doctype html>\n${html}`;
|
|
1126
|
+
}
|
|
1127
|
+
function readManifest(distDir) {
|
|
1128
|
+
const manifestPath = path$1.join(distDir, ".vite", "manifest.json");
|
|
1129
|
+
if (!fs.existsSync(manifestPath)) return {};
|
|
1130
|
+
return JSON.parse(fs.readFileSync(manifestPath, "utf-8"));
|
|
1131
|
+
}
|
|
1089
1132
|
|
|
1090
1133
|
//#endregion
|
|
1091
1134
|
//#region src/vite/build.ts
|
|
@@ -1133,12 +1176,6 @@ function toRouteFromPageName(pageName) {
|
|
|
1133
1176
|
if (pageName.endsWith("/index")) return pageName.slice(0, -6);
|
|
1134
1177
|
return pageName;
|
|
1135
1178
|
}
|
|
1136
|
-
/** Route path to output file path (e.g. '' → index.html, about → about/index.html). */
|
|
1137
|
-
function toOutputFile(routePath) {
|
|
1138
|
-
if (routePath === "") return "index.html";
|
|
1139
|
-
if (routePath === "404") return "404.html";
|
|
1140
|
-
return toPosix(path$1.join(routePath, "index.html"));
|
|
1141
|
-
}
|
|
1142
1179
|
/**
|
|
1143
1180
|
* Generate sitemap.xml from route paths. Only called when site URL is set.
|
|
1144
1181
|
* Excludes 404. Writes to distDir/sitemap.xml.
|
|
@@ -1153,34 +1190,15 @@ function writeSitemap(routePaths, site, distDir) {
|
|
|
1153
1190
|
function escapeXml(s) {
|
|
1154
1191
|
return s.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """).replace(/'/g, "'");
|
|
1155
1192
|
}
|
|
1156
|
-
/**
|
|
1157
|
-
function
|
|
1158
|
-
|
|
1159
|
-
if (!rel) return "./";
|
|
1160
|
-
if (rel.startsWith(".")) return rel;
|
|
1161
|
-
return `./${rel}`;
|
|
1162
|
-
}
|
|
1163
|
-
/** Relative path to a route (directory index); appends trailing slash for non-root routes. */
|
|
1164
|
-
function normalizeRelativeRouteLink(fromDir, routePath) {
|
|
1165
|
-
const targetDir = routePath === "" ? "" : routePath;
|
|
1166
|
-
const rel = path$1.posix.relative(fromDir, targetDir);
|
|
1167
|
-
let res = !rel ? "./" : rel.startsWith(".") ? rel : `./${rel}`;
|
|
1168
|
-
if (routePath !== "" && routePath !== "404" && !res.endsWith("/")) res += "/";
|
|
1169
|
-
return res;
|
|
1170
|
-
}
|
|
1171
|
-
function normalizeRoutePathFromHref(value) {
|
|
1172
|
-
if (value === "/") return "";
|
|
1173
|
-
return value.replace(/^\/+/, "").replace(/\/+$/, "");
|
|
1193
|
+
/** Root-relative path for manifest key (posix). */
|
|
1194
|
+
function toManifestKey(root, filePath) {
|
|
1195
|
+
return toPosixRelative(filePath, root);
|
|
1174
1196
|
}
|
|
1175
1197
|
/** True if URL is empty or matches SKIP_PROTOCOL_REGEX (external, hash, etc.). */
|
|
1176
1198
|
function isSkippableUrl(value) {
|
|
1177
1199
|
if (!value) return true;
|
|
1178
1200
|
return SKIP_PROTOCOL_REGEX.test(value);
|
|
1179
1201
|
}
|
|
1180
|
-
/** Root-relative path for manifest key (posix). */
|
|
1181
|
-
function toManifestKey(root, filePath) {
|
|
1182
|
-
return toPosixRelative(filePath, root);
|
|
1183
|
-
}
|
|
1184
1202
|
/** Resolve script/link src or href to absolute path; returns null for external/skippable or unresolvable. */
|
|
1185
1203
|
function resolveTemplateAssetPath(rawValue, templateFile, root, resolvePath) {
|
|
1186
1204
|
if (!rawValue || isSkippableUrl(rawValue)) return null;
|
|
@@ -1300,60 +1318,6 @@ function walkFiles(dir) {
|
|
|
1300
1318
|
}
|
|
1301
1319
|
return files;
|
|
1302
1320
|
}
|
|
1303
|
-
/** Prepend `<!doctype html>` if missing. */
|
|
1304
|
-
function addDoctype(html) {
|
|
1305
|
-
return /^\s*<!doctype\s+html/i.test(html) ? html : `<!doctype html>\n${html}`;
|
|
1306
|
-
}
|
|
1307
|
-
/** Image extensions: when a manifest entry's .file is a .js chunk but .assets lists the real image, use it. */
|
|
1308
|
-
const ASSET_IMAGE_EXT = /\.(jpg|jpeg|png|gif|webp|svg|ico)(\?|$)/i;
|
|
1309
|
-
/** Rewrite one absolute URL to dist-relative using manifest and route set; leaves API and external URLs unchanged. */
|
|
1310
|
-
function rewriteAbsoluteUrl(value, fromDir, manifest, routeSet, apiPrefix = DEFAULT_API_PREFIX) {
|
|
1311
|
-
if (value.startsWith(apiPrefix)) return value;
|
|
1312
|
-
const noQuery = value.split(/[?#]/)[0] || value;
|
|
1313
|
-
const suffix = value.slice(noQuery.length);
|
|
1314
|
-
const manifestKey = noQuery.replace(/^\//, "");
|
|
1315
|
-
let manifestEntry = manifest[noQuery] ?? manifest[manifestKey];
|
|
1316
|
-
if (!manifestEntry && noQuery.startsWith("assets/")) {
|
|
1317
|
-
const entry = Object.values(manifest).find((e) => e?.file === noQuery || e?.file === manifestKey);
|
|
1318
|
-
if (entry) manifestEntry = entry;
|
|
1319
|
-
}
|
|
1320
|
-
if (manifestEntry?.file) return normalizeRelativeLink(fromDir, manifestEntry.assets?.find((a) => ASSET_IMAGE_EXT.test(a)) ?? manifestEntry.file) + suffix;
|
|
1321
|
-
if (noQuery.startsWith("/assets/")) return normalizeRelativeLink(fromDir, noQuery.replace(/^\//, "")) + suffix;
|
|
1322
|
-
const route = normalizeRoutePathFromHref(noQuery);
|
|
1323
|
-
if (routeSet.has(route) || route === "") return (route === "404" ? normalizeRelativeLink(fromDir, toOutputFile(route)) : normalizeRelativeRouteLink(fromDir, route)) + suffix;
|
|
1324
|
-
return normalizeRelativeLink(fromDir, noQuery.replace(/^\//, "")) + suffix;
|
|
1325
|
-
}
|
|
1326
|
-
/** Rewrite script src (virtual client → hashed asset) and LINK_ATTRS in rendered HTML; add doctype. */
|
|
1327
|
-
function rewriteRenderedHtml(html, outputFile, manifest, routeSet, apiPrefix = DEFAULT_API_PREFIX) {
|
|
1328
|
-
const fromDir = path$1.posix.dirname(outputFile);
|
|
1329
|
-
const { document } = parseHTML(html);
|
|
1330
|
-
for (const script of Array.from(document.querySelectorAll("script[src]"))) {
|
|
1331
|
-
const src = script.getAttribute("src") || "";
|
|
1332
|
-
if (src.startsWith(CLIENT_SCRIPT_PREFIX)) {
|
|
1333
|
-
const newSrc = rewriteAbsoluteUrl(src, fromDir, manifest, routeSet, apiPrefix);
|
|
1334
|
-
script.setAttribute("src", newSrc);
|
|
1335
|
-
script.setAttribute("type", "module");
|
|
1336
|
-
script.removeAttribute("defer");
|
|
1337
|
-
continue;
|
|
1338
|
-
}
|
|
1339
|
-
if (script.getAttribute("type") === "module") script.removeAttribute("defer");
|
|
1340
|
-
}
|
|
1341
|
-
for (const el of Array.from(document.querySelectorAll("*"))) for (const attrName of LINK_ATTRS) {
|
|
1342
|
-
if (!el.hasAttribute(attrName)) continue;
|
|
1343
|
-
const current = (el.getAttribute(attrName) || "").trim();
|
|
1344
|
-
if (!current || isSkippableUrl(current)) continue;
|
|
1345
|
-
if (!current.startsWith("/")) continue;
|
|
1346
|
-
el.setAttribute(attrName, rewriteAbsoluteUrl(current, fromDir, manifest, routeSet, apiPrefix));
|
|
1347
|
-
}
|
|
1348
|
-
const htmlTag = document.documentElement;
|
|
1349
|
-
if (htmlTag) return addDoctype(htmlTag.outerHTML);
|
|
1350
|
-
return addDoctype(document.toString());
|
|
1351
|
-
}
|
|
1352
|
-
function readManifest(distDir) {
|
|
1353
|
-
const manifestPath = path$1.join(distDir, ".vite", "manifest.json");
|
|
1354
|
-
if (!fs.existsSync(manifestPath)) return {};
|
|
1355
|
-
return JSON.parse(fs.readFileSync(manifestPath, "utf-8"));
|
|
1356
|
-
}
|
|
1357
1321
|
/**
|
|
1358
1322
|
* Render all static pages into outDir: discover pages, expand dynamic routes via getStaticPaths, run Vite in middleware mode, rewrite URLs, optionally minify.
|
|
1359
1323
|
*
|
|
@@ -1493,12 +1457,15 @@ function createBuildConfig(options = {}, root = process.cwd()) {
|
|
|
1493
1457
|
const require = createRequire(import.meta.url);
|
|
1494
1458
|
const AERO_DIR = ".aero";
|
|
1495
1459
|
const NITRO_CONFIG_FILENAME = "nitro.config.mjs";
|
|
1460
|
+
/** Filename for the generated runtime instance (uses app dirs for globs); written under .aero so Vite treats it as a real module. */
|
|
1461
|
+
const RUNTIME_INSTANCE_FILENAME = "runtime-instance.mjs";
|
|
1496
1462
|
/**
|
|
1497
1463
|
* Generate Nitro config from Aero options and write to <projectRoot>/.aero/nitro.config.mjs.
|
|
1498
1464
|
* root is the app/site directory (Vite config.root), e.g. examples/kitchen-sink or a create-aerobuilt project folder.
|
|
1465
|
+
* distDir is the configured output dir (e.g. 'build') so the catch-all route serves from the same path at preview time.
|
|
1499
1466
|
* Returns the absolute path to .aero (Nitro cwd so it loads this file).
|
|
1500
1467
|
*/
|
|
1501
|
-
function writeGeneratedNitroConfig(root, serverDir, redirects) {
|
|
1468
|
+
function writeGeneratedNitroConfig(root, serverDir, redirects, distDir) {
|
|
1502
1469
|
const aeroDir = path.join(root, AERO_DIR);
|
|
1503
1470
|
mkdirSync(aeroDir, { recursive: true });
|
|
1504
1471
|
const routeRules = redirectsToRouteRules(redirects ?? []);
|
|
@@ -1507,7 +1474,8 @@ function writeGeneratedNitroConfig(root, serverDir, redirects) {
|
|
|
1507
1474
|
output: { dir: path.join(root, ".output") },
|
|
1508
1475
|
scanDirs: [path.join(root, serverDir)],
|
|
1509
1476
|
routeRules,
|
|
1510
|
-
noPublicDir: true
|
|
1477
|
+
noPublicDir: true,
|
|
1478
|
+
replace: { "process.env.AERO_DIST": JSON.stringify(distDir) }
|
|
1511
1479
|
};
|
|
1512
1480
|
const content = `// Generated by Aero — do not edit
|
|
1513
1481
|
export default ${JSON.stringify(nitroConfig, null, 2)}
|
|
@@ -1540,9 +1508,7 @@ function createAeroConfigPlugin(state) {
|
|
|
1540
1508
|
enforce: "pre",
|
|
1541
1509
|
config(userConfig, env) {
|
|
1542
1510
|
const root = userConfig.root || process.cwd();
|
|
1543
|
-
|
|
1544
|
-
state.aliasResult = mergeWithDefaultAliases(rawAliases, root, state.dirs);
|
|
1545
|
-
if (state.dirs.client !== DEFAULT_DIRS.client && rawAliases.projectRoot != null) console.warn("[aero] Custom dirs.client is set; ensure tsconfig paths for @pages, @layouts, @components match (e.g. @pages → \"" + state.dirs.client + "/pages\").");
|
|
1511
|
+
state.aliasResult = mergeWithDefaultAliases(loadTsconfigAliases(root), root, state.dirs);
|
|
1546
1512
|
const site = state.options.site ?? "";
|
|
1547
1513
|
return {
|
|
1548
1514
|
base: "./",
|
|
@@ -1559,6 +1525,13 @@ function createAeroConfigPlugin(state) {
|
|
|
1559
1525
|
},
|
|
1560
1526
|
configResolved(resolvedConfig) {
|
|
1561
1527
|
state.config = resolvedConfig;
|
|
1528
|
+
const dir = path.join(resolvedConfig.root, AERO_DIR);
|
|
1529
|
+
mkdirSync(dir, { recursive: true });
|
|
1530
|
+
const filePath = path.join(dir, RUNTIME_INSTANCE_FILENAME);
|
|
1531
|
+
const runtimeIndexPath = path.join(path.dirname(state.runtimeInstancePath), "index.mjs");
|
|
1532
|
+
const runtimeImportPath = path.relative(dir, runtimeIndexPath).replace(/\\/g, "/");
|
|
1533
|
+
writeFileSync(filePath, getRuntimeInstanceVirtualSource(state.dirs.client, runtimeImportPath.startsWith(".") ? runtimeImportPath : "./" + runtimeImportPath), "utf-8");
|
|
1534
|
+
state.generatedRuntimeInstancePath = filePath;
|
|
1562
1535
|
}
|
|
1563
1536
|
};
|
|
1564
1537
|
}
|
|
@@ -1570,6 +1543,56 @@ function isAeroTemplateHtml(filePath, root, dirs) {
|
|
|
1570
1543
|
const sep = path.sep;
|
|
1571
1544
|
return rel.startsWith("pages" + sep) || rel.startsWith("components" + sep) || rel.startsWith("layouts" + sep);
|
|
1572
1545
|
}
|
|
1546
|
+
/**
|
|
1547
|
+
* Prefix for import.meta.glob patterns. In virtual modules Vite requires globs to start with '/'
|
|
1548
|
+
* (absolute from project root). Uses app-configured client dir so custom dirs (e.g. frontend/) resolve correctly.
|
|
1549
|
+
*/
|
|
1550
|
+
function clientGlobPrefix(clientDir) {
|
|
1551
|
+
const normalized = clientDir.replace(/\\/g, "/").replace(/^\.\/+/, "");
|
|
1552
|
+
return normalized ? `/${normalized}` : "/client";
|
|
1553
|
+
}
|
|
1554
|
+
/**
|
|
1555
|
+
* Virtual module source for the runtime instance with glob patterns using the app's client dir.
|
|
1556
|
+
* Ensures template resolution works for custom dirs (e.g. dirs.client === 'frontend').
|
|
1557
|
+
* runtimeImportPath: path that resolves to @aerobuilt/core/runtime from the generated file (e.g. relative to .aero/ for SSR).
|
|
1558
|
+
*/
|
|
1559
|
+
function getRuntimeInstanceVirtualSource(clientDir, runtimeImportPath = "@aerobuilt/core/runtime") {
|
|
1560
|
+
const prefix = clientGlobPrefix(clientDir);
|
|
1561
|
+
const componentsPattern = `${prefix}/components/**/*.html`;
|
|
1562
|
+
const layoutsPattern = `${prefix}/layouts/*.html`;
|
|
1563
|
+
const pagesPattern = `${prefix}/pages/**/*.html`;
|
|
1564
|
+
return `import { Aero } from ${JSON.stringify(runtimeImportPath)}
|
|
1565
|
+
|
|
1566
|
+
const instance = globalThis.__AERO_INSTANCE__ || new Aero()
|
|
1567
|
+
const listeners = globalThis.__AERO_LISTENERS__ || new Set()
|
|
1568
|
+
const aero = instance
|
|
1569
|
+
|
|
1570
|
+
const onUpdate = (cb) => {
|
|
1571
|
+
listeners.add(cb)
|
|
1572
|
+
return () => listeners.delete(cb)
|
|
1573
|
+
}
|
|
1574
|
+
const notify = () => {
|
|
1575
|
+
listeners.forEach((cb) => cb())
|
|
1576
|
+
}
|
|
1577
|
+
|
|
1578
|
+
if (!globalThis.__AERO_INSTANCE__) globalThis.__AERO_INSTANCE__ = instance
|
|
1579
|
+
if (!globalThis.__AERO_LISTENERS__) globalThis.__AERO_LISTENERS__ = listeners
|
|
1580
|
+
|
|
1581
|
+
const components = import.meta.glob(${JSON.stringify(componentsPattern)}, { eager: true })
|
|
1582
|
+
const layouts = import.meta.glob(${JSON.stringify(layoutsPattern)}, { eager: true })
|
|
1583
|
+
const pages = import.meta.glob(${JSON.stringify(pagesPattern)}, { eager: true })
|
|
1584
|
+
|
|
1585
|
+
aero.registerPages(components)
|
|
1586
|
+
aero.registerPages(layouts)
|
|
1587
|
+
aero.registerPages(pages)
|
|
1588
|
+
|
|
1589
|
+
notify()
|
|
1590
|
+
|
|
1591
|
+
if (import.meta.hot) import.meta.hot.accept()
|
|
1592
|
+
|
|
1593
|
+
export { aero, onUpdate }
|
|
1594
|
+
`;
|
|
1595
|
+
}
|
|
1573
1596
|
function createAeroVirtualsPlugin(state) {
|
|
1574
1597
|
return {
|
|
1575
1598
|
name: "vite-plugin-aero-virtuals",
|
|
@@ -1579,7 +1602,7 @@ function createAeroVirtualsPlugin(state) {
|
|
|
1579
1602
|
discoverClientScriptContentMap(state.config.root, state.dirs.client).forEach((entry, url) => state.clientScripts.set(url, entry));
|
|
1580
1603
|
},
|
|
1581
1604
|
async resolveId(id, importer) {
|
|
1582
|
-
if (id === RUNTIME_INSTANCE_MODULE_ID) return RESOLVED_RUNTIME_INSTANCE_MODULE_ID;
|
|
1605
|
+
if (id === RUNTIME_INSTANCE_MODULE_ID) return state.generatedRuntimeInstancePath ?? RESOLVED_RUNTIME_INSTANCE_MODULE_ID;
|
|
1583
1606
|
if (id.startsWith(CLIENT_SCRIPT_PREFIX)) return "\0" + id;
|
|
1584
1607
|
if (id.startsWith("\0" + CLIENT_SCRIPT_PREFIX)) return id;
|
|
1585
1608
|
if (id.startsWith(AERO_HTML_VIRTUAL_PREFIX)) return id;
|
|
@@ -1600,26 +1623,27 @@ function createAeroVirtualsPlugin(state) {
|
|
|
1600
1623
|
return null;
|
|
1601
1624
|
},
|
|
1602
1625
|
load(id) {
|
|
1603
|
-
if (id === RESOLVED_RUNTIME_INSTANCE_MODULE_ID) return
|
|
1626
|
+
if (id === RESOLVED_RUNTIME_INSTANCE_MODULE_ID) return getRuntimeInstanceVirtualSource(state.dirs.client);
|
|
1604
1627
|
if (id.startsWith(AERO_EMPTY_INLINE_CSS_PREFIX)) return "/* aero: no inline styles */";
|
|
1605
1628
|
if (id.startsWith(AERO_HTML_VIRTUAL_PREFIX)) {
|
|
1606
1629
|
const filePath = id.slice(AERO_HTML_VIRTUAL_PREFIX.length).replace(/\.aero$/i, ".html");
|
|
1607
1630
|
if (!state.config || !state.aliasResult) return null;
|
|
1608
1631
|
this.addWatchFile(filePath);
|
|
1609
1632
|
try {
|
|
1610
|
-
const
|
|
1633
|
+
const code = readFileSync(filePath, "utf-8");
|
|
1634
|
+
const parsed = parse(code);
|
|
1611
1635
|
const baseName = toPosixRelative(filePath, state.config.root).replace(/\.html$/i, "");
|
|
1612
1636
|
registerClientScriptsToMap(parsed, baseName, state.clientScripts);
|
|
1613
1637
|
for (let i = 0; i < parsed.clientScripts.length; i++) parsed.clientScripts[i].content = getClientScriptVirtualUrl(baseName, i, parsed.clientScripts.length);
|
|
1614
1638
|
return {
|
|
1615
|
-
code:
|
|
1639
|
+
code: compileTemplate(code, {
|
|
1616
1640
|
root: state.config.root,
|
|
1617
1641
|
clientScripts: parsed.clientScripts,
|
|
1618
1642
|
blockingScripts: parsed.blockingScripts,
|
|
1619
1643
|
inlineScripts: parsed.inlineScripts,
|
|
1620
1644
|
resolvePath: state.aliasResult.resolve,
|
|
1621
1645
|
importer: filePath
|
|
1622
|
-
}),
|
|
1646
|
+
}, parsed),
|
|
1623
1647
|
map: null
|
|
1624
1648
|
};
|
|
1625
1649
|
} catch {
|
|
@@ -1656,14 +1680,14 @@ function createAeroTransformPlugin(state) {
|
|
|
1656
1680
|
for (let i = 0; i < parsed.clientScripts.length; i++) parsed.clientScripts[i].content = getClientScriptVirtualUrl(baseName, i, parsed.clientScripts.length);
|
|
1657
1681
|
}
|
|
1658
1682
|
return {
|
|
1659
|
-
code:
|
|
1683
|
+
code: compileTemplate(code, {
|
|
1660
1684
|
root: state.config.root,
|
|
1661
1685
|
clientScripts: parsed.clientScripts,
|
|
1662
1686
|
blockingScripts: parsed.blockingScripts,
|
|
1663
1687
|
inlineScripts: parsed.inlineScripts,
|
|
1664
1688
|
resolvePath: state.aliasResult.resolve,
|
|
1665
1689
|
importer: id
|
|
1666
|
-
}),
|
|
1690
|
+
}, parsed),
|
|
1667
1691
|
map: null
|
|
1668
1692
|
};
|
|
1669
1693
|
} catch (err) {
|
|
@@ -1796,6 +1820,7 @@ function aero(options = {}) {
|
|
|
1796
1820
|
aliasResult: null,
|
|
1797
1821
|
clientScripts: /* @__PURE__ */ new Map(),
|
|
1798
1822
|
runtimeInstancePath,
|
|
1823
|
+
generatedRuntimeInstancePath: null,
|
|
1799
1824
|
dirs,
|
|
1800
1825
|
apiPrefix,
|
|
1801
1826
|
options
|
|
@@ -1833,7 +1858,7 @@ function aero(options = {}) {
|
|
|
1833
1858
|
site: options.site,
|
|
1834
1859
|
redirects: options.redirects
|
|
1835
1860
|
}, outDir);
|
|
1836
|
-
if (enableNitro) await runNitroBuild(root, writeGeneratedNitroConfig(root, dirs.server, options.redirects));
|
|
1861
|
+
if (enableNitro) await runNitroBuild(root, writeGeneratedNitroConfig(root, dirs.server, options.redirects, dirs.dist));
|
|
1837
1862
|
}
|
|
1838
1863
|
},
|
|
1839
1864
|
ViteImageOptimizer({
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@aerobuilt/core",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.2",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": "Jamie Wilson",
|
|
@@ -60,7 +60,7 @@
|
|
|
60
60
|
"sharp": "^0.34.5",
|
|
61
61
|
"svgo": "^4.0.0",
|
|
62
62
|
"vite-plugin-image-optimizer": "^2.0.3",
|
|
63
|
-
"@aerobuilt/interpolation": "0.3.
|
|
63
|
+
"@aerobuilt/interpolation": "0.3.2"
|
|
64
64
|
},
|
|
65
65
|
"peerDependencies": {
|
|
66
66
|
"vite": "^8.0.0-0"
|
|
@@ -77,7 +77,7 @@
|
|
|
77
77
|
"vitest": "^4.0.18"
|
|
78
78
|
},
|
|
79
79
|
"scripts": {
|
|
80
|
-
"build": "tsdown
|
|
80
|
+
"build": "tsdown",
|
|
81
81
|
"typecheck": "tsc --noEmit",
|
|
82
82
|
"test": "vitest run"
|
|
83
83
|
}
|