@openelement/adapter-vite 0.41.0-alpha.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.
- package/LICENSE +21 -0
- package/README.md +87 -0
- package/package.json +87 -0
- package/src/alias-utils.js +39 -0
- package/src/build-context.d.ts +111 -0
- package/src/build-context.js +184 -0
- package/src/build-manifest.d.ts +38 -0
- package/src/build-manifest.js +198 -0
- package/src/build.js +97 -0
- package/src/cli/build-client.d.ts +3 -0
- package/src/cli/build-client.js +292 -0
- package/src/cli/build-ssg.d.ts +40 -0
- package/src/cli/build-ssg.js +377 -0
- package/src/cli/build.d.ts +0 -0
- package/src/cli/build.js +27 -0
- package/src/cli/ssg-render.js +32 -0
- package/src/generated-data-resolver.d.ts +12 -0
- package/src/generated-data-resolver.js +52 -0
- package/src/head-injection.d.ts +31 -0
- package/src/head-injection.js +248 -0
- package/src/index.d.ts +58 -0
- package/src/index.js +52 -0
- package/src/island-transform.js +27 -0
- package/src/nitro-mount.d.ts +24 -0
- package/src/nitro-mount.js +27 -0
- package/src/plugin-mdx.d.ts +7 -0
- package/src/plugin-mdx.js +15 -0
- package/src/plugin.d.ts +22 -0
- package/src/plugin.js +264 -0
- package/src/ssg-package-resolver.js +256 -0
- package/src/subpath-resolver.d.ts +26 -0
- package/src/subpath-resolver.js +153 -0
- package/src/workspace-alias.js +113 -0
|
@@ -0,0 +1,292 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @openelement/adapter-vite - CLI: Client Island Build
|
|
3
|
+
*
|
|
4
|
+
* Client build for Island components.
|
|
5
|
+
* Produces dist/client/islands/*.js + manifest for SSG post-processing.
|
|
6
|
+
*
|
|
7
|
+
* ADR 0011: This module exports buildClient() only - it is called from
|
|
8
|
+
* closeBundle() in open:build plugin. No longer a standalone CLI entry.
|
|
9
|
+
* ctx parameter is required (no globalThis fallback).
|
|
10
|
+
*
|
|
11
|
+
* Usage:
|
|
12
|
+
* deno task build (unified entry - runs all 3 phases)
|
|
13
|
+
*/ import { build as viteBuild } from 'vite';
|
|
14
|
+
import { existsSync, readFileSync } from 'node:fs';
|
|
15
|
+
import { join, resolve } from 'node:path';
|
|
16
|
+
import { fileURLToPath } from 'node:url';
|
|
17
|
+
import process from 'node:process';
|
|
18
|
+
import { generateClientEntry } from '@openelement/ssg';
|
|
19
|
+
import { createOpenJsrPackageResolverPlugin } from '../ssg-package-resolver.js';
|
|
20
|
+
import { formatError } from '@openelement/core/errors';
|
|
21
|
+
import { createLogger } from '@openelement/core/logger';
|
|
22
|
+
const log = createLogger('ssg');
|
|
23
|
+
const VIRTUAL_CLIENT_ENTRY_ID = 'virtual:open-client-entry';
|
|
24
|
+
const RESOLVED_CLIENT_ENTRY_ID = '\0' + VIRTUAL_CLIENT_ENTRY_ID;
|
|
25
|
+
const FALLBACK_openElement_VERSION = '0.23.0';
|
|
26
|
+
/** Workspace root derived from this module's location (packages/adapter-vite/src/cli/).
|
|
27
|
+
* Only valid in local workspace (file:// import.meta.url). In JSR consumers, returns null. */ const WORKSPACE_ROOT = (()=>{
|
|
28
|
+
if (!import.meta.url.startsWith('file:')) return null;
|
|
29
|
+
try {
|
|
30
|
+
return fileURLToPath(new URL('../../../..', import.meta.url)).replace(/\\/g, '/');
|
|
31
|
+
} catch {
|
|
32
|
+
return null;
|
|
33
|
+
}
|
|
34
|
+
})();
|
|
35
|
+
function getJsrPackageVersion(metaUrl) {
|
|
36
|
+
const match = metaUrl.match(/\/@openelement\/adapter-vite\/([^/]+)\//);
|
|
37
|
+
return match?.[1] ?? FALLBACK_openElement_VERSION;
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* Look up a bare specifier in a deno.json import map.
|
|
41
|
+
* Walks up directory tree to find workspace-level deno.json as fallback.
|
|
42
|
+
* Returns { target, denoJsonDir } so relative paths can be resolved correctly.
|
|
43
|
+
*/ function lookupInDenoJson(id, root) {
|
|
44
|
+
const denoJsonDirs = new Set();
|
|
45
|
+
let dir = resolve(root);
|
|
46
|
+
// Walk up from consumer root
|
|
47
|
+
while(!denoJsonDirs.has(dir)){
|
|
48
|
+
denoJsonDirs.add(dir);
|
|
49
|
+
const found = tryDenoJsonDir(id, dir);
|
|
50
|
+
if (found) return found;
|
|
51
|
+
const parent = resolve(dir, '..');
|
|
52
|
+
if (parent === dir) break;
|
|
53
|
+
dir = parent;
|
|
54
|
+
}
|
|
55
|
+
// Also try workspace root (module-relative, for monorepo dev / testing)
|
|
56
|
+
if (WORKSPACE_ROOT && !denoJsonDirs.has(WORKSPACE_ROOT)) {
|
|
57
|
+
const found = tryDenoJsonDir(id, WORKSPACE_ROOT);
|
|
58
|
+
if (found) return found;
|
|
59
|
+
}
|
|
60
|
+
return null;
|
|
61
|
+
}
|
|
62
|
+
/** Check a single directory for a deno.json with the given import. */ function tryDenoJsonDir(id, dir) {
|
|
63
|
+
const denoJsonPath = join(dir, 'deno.json');
|
|
64
|
+
if (!existsSync(denoJsonPath)) return null;
|
|
65
|
+
const raw = readFileSync(denoJsonPath, 'utf-8');
|
|
66
|
+
// Strip JSONC comments:
|
|
67
|
+
// - Line comments: // at start of line (after optional whitespace)
|
|
68
|
+
// - Block comments: /* ... */
|
|
69
|
+
// - Trailing commas (Deno JSONC allows them, JSON.parse does not)
|
|
70
|
+
const json = raw.replace(/^\s*\/\/.*$/gm, '').replace(/\/\*[\s\S]*?\*\//g, '').replace(/,\s*([}\]])/g, '$1');
|
|
71
|
+
let denoJson;
|
|
72
|
+
try {
|
|
73
|
+
denoJson = JSON.parse(json);
|
|
74
|
+
} catch {
|
|
75
|
+
return null; // Invalid JSON — skip this deno.json
|
|
76
|
+
}
|
|
77
|
+
const imports = denoJson.imports;
|
|
78
|
+
if (!imports) return null;
|
|
79
|
+
// Exact match
|
|
80
|
+
if (imports[id]) return {
|
|
81
|
+
target: imports[id],
|
|
82
|
+
denoJsonDir: dir
|
|
83
|
+
};
|
|
84
|
+
// Prefix/subpath matching (trailing slash)
|
|
85
|
+
for (const [key, value] of Object.entries(imports)){
|
|
86
|
+
if (key.endsWith('/') && id.startsWith(key)) {
|
|
87
|
+
return {
|
|
88
|
+
target: value + id.slice(key.length),
|
|
89
|
+
denoJsonDir: dir
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
return null;
|
|
94
|
+
}
|
|
95
|
+
/**
|
|
96
|
+
* Convert a Deno import map target to a resolvable Vite path.
|
|
97
|
+
* - file:// URLs → absolute filesystem path
|
|
98
|
+
* - Relative paths (./) → resolved relative to denoJsonDir
|
|
99
|
+
* - npm:, jsr: → null (handled by node_modules)
|
|
100
|
+
*/ function convertImportMapTarget(target, denoJsonDir) {
|
|
101
|
+
if (target.startsWith('file://')) {
|
|
102
|
+
try {
|
|
103
|
+
return fileURLToPath(target).replace(/\\/g, '/');
|
|
104
|
+
} catch {
|
|
105
|
+
return null;
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
// Relative path — resolve relative to the deno.json directory
|
|
109
|
+
if (target.startsWith('./') || target.startsWith('../')) {
|
|
110
|
+
return resolve(denoJsonDir, target).replace(/\\/g, '/');
|
|
111
|
+
}
|
|
112
|
+
// npm:, jsr: — let Vite/Rolldown handle these normally
|
|
113
|
+
return null;
|
|
114
|
+
}
|
|
115
|
+
async function buildClient(ctx) {
|
|
116
|
+
const root = ctx.phase3.root || process.cwd();
|
|
117
|
+
const outDir = ctx.phase3.outDir || 'dist';
|
|
118
|
+
const islandsDir = ctx.phase3.islandsDir || 'app/islands';
|
|
119
|
+
const localIslands = ctx.phase1.islandTagNames || [];
|
|
120
|
+
const localIslandFiles = ctx.phase1.islandFiles || [];
|
|
121
|
+
const packageIslandDecls = ctx.phase1.packageIslandDecls || [];
|
|
122
|
+
// Aliases pre-generated by createOpenPlugin() and stored in ctx
|
|
123
|
+
const resolveAlias = ctx.phase1.userResolveAlias;
|
|
124
|
+
const serializedAlias = resolveAlias ? Array.isArray(resolveAlias) ? resolveAlias.filter((a)=>typeof a.find === 'string').map((a)=>({
|
|
125
|
+
find: a.find,
|
|
126
|
+
replacement: a.replacement
|
|
127
|
+
})) : Object.entries(resolveAlias).map(([find, replacement])=>({
|
|
128
|
+
find,
|
|
129
|
+
replacement
|
|
130
|
+
})) : [];
|
|
131
|
+
// Always resolve @openelement/core/style-sheet from workspace (core re-exports it)
|
|
132
|
+
if (WORKSPACE_ROOT) {
|
|
133
|
+
serializedAlias.push({
|
|
134
|
+
find: '@openelement/core/style-sheet',
|
|
135
|
+
replacement: join(WORKSPACE_ROOT, 'packages', 'core', 'src', 'style-sheet.ts')
|
|
136
|
+
});
|
|
137
|
+
serializedAlias.push({
|
|
138
|
+
find: /^@openelement\/router/,
|
|
139
|
+
replacement: join(WORKSPACE_ROOT, 'packages', 'router', 'src')
|
|
140
|
+
});
|
|
141
|
+
}
|
|
142
|
+
serializedAlias.sort((a, b)=>{
|
|
143
|
+
const findA = typeof a.find === 'string' ? a.find.length : 0;
|
|
144
|
+
const findB = typeof b.find === 'string' ? b.find.length : 0;
|
|
145
|
+
return findB - findA;
|
|
146
|
+
});
|
|
147
|
+
if (localIslands.length === 0 && packageIslandDecls.length === 0) {
|
|
148
|
+
log.info('No islands found - zero client JS output');
|
|
149
|
+
return;
|
|
150
|
+
}
|
|
151
|
+
const totalIslands = localIslands.length + packageIslandDecls.length;
|
|
152
|
+
log.info(`Building client bundle for ${totalIslands} island(s)...`);
|
|
153
|
+
// Generate client entry code
|
|
154
|
+
const islandEntries = [
|
|
155
|
+
...localIslands.map((tagName, i)=>({
|
|
156
|
+
tagName,
|
|
157
|
+
modulePath: resolve(root, localIslandFiles[i] ? `${islandsDir}/${localIslandFiles[i]}` : `${islandsDir}/${tagName}.ts`).replace(/\\/g, '/'),
|
|
158
|
+
isPackage: false,
|
|
159
|
+
strategy: ctx.phase1.islandMeta[tagName]?.hydrate || ctx.phase3.upgradeStrategy || 'idle',
|
|
160
|
+
ssr: ctx.phase1.islandMeta[tagName]?.hydrate === 'only' ? false : ctx.phase1.islandMeta[tagName]?.ssr,
|
|
161
|
+
dsd: ctx.phase1.islandMeta[tagName]?.hydrate === 'only' ? false : ctx.phase1.islandMeta[tagName]?.dsd,
|
|
162
|
+
reason: ctx.phase1.islandMeta[tagName]?.reason
|
|
163
|
+
})),
|
|
164
|
+
...packageIslandDecls.map((island)=>({
|
|
165
|
+
tagName: island.tagName,
|
|
166
|
+
modulePath: island.modulePath,
|
|
167
|
+
isPackage: true,
|
|
168
|
+
strategy: island.hydrate || ctx.phase3.upgradeStrategy || 'idle',
|
|
169
|
+
ssr: island.hydrate === 'only' ? false : island.ssr,
|
|
170
|
+
dsd: island.hydrate === 'only' ? false : island.dsd,
|
|
171
|
+
reason: island.reason
|
|
172
|
+
}))
|
|
173
|
+
];
|
|
174
|
+
const clientEntryCode = generateClientEntry(islandEntries);
|
|
175
|
+
// Restore RegExp from serialized noExternal patterns
|
|
176
|
+
const noExternalPatterns = (ctx.phase3.ssrNoExternal || []).map((item)=>{
|
|
177
|
+
if (typeof item === 'string') return item;
|
|
178
|
+
if (item && typeof item === 'object' && item.__type === 'RegExp') {
|
|
179
|
+
return new RegExp(item.source, item.flags);
|
|
180
|
+
}
|
|
181
|
+
return item;
|
|
182
|
+
});
|
|
183
|
+
const clientOutDir = resolve(root, outDir, 'client');
|
|
184
|
+
const clientBase = ctx.phase3.base || '/';
|
|
185
|
+
const clientConfig = {
|
|
186
|
+
configFile: false,
|
|
187
|
+
root,
|
|
188
|
+
base: `${clientBase}client/`,
|
|
189
|
+
logLevel: 'warn',
|
|
190
|
+
// ADR-0057: JSX automatic runtime must be configured in the internal
|
|
191
|
+
// viteBuild() call — configFile:false means user's vite.config.ts is
|
|
192
|
+
// NOT read. Without this, esbuild defaults to classic React.createElement
|
|
193
|
+
// transform, producing {type, props, $$typeof} objects that DsdElement
|
|
194
|
+
// does not recognize (causes [object Object] rendering).
|
|
195
|
+
esbuild: {
|
|
196
|
+
jsx: 'automatic',
|
|
197
|
+
jsxImportSource: '@openelement/core'
|
|
198
|
+
},
|
|
199
|
+
build: {
|
|
200
|
+
outDir: clientOutDir,
|
|
201
|
+
emptyOutDir: true,
|
|
202
|
+
chunkSizeWarningLimit: 1500,
|
|
203
|
+
minify: 'oxc',
|
|
204
|
+
manifest: true,
|
|
205
|
+
rollupOptions: {
|
|
206
|
+
input: {
|
|
207
|
+
client: VIRTUAL_CLIENT_ENTRY_ID
|
|
208
|
+
},
|
|
209
|
+
output: {
|
|
210
|
+
format: 'esm',
|
|
211
|
+
entryFileNames: 'islands/[name].js',
|
|
212
|
+
chunkFileNames: 'islands/[name]-[hash].js',
|
|
213
|
+
manualChunks (id) {
|
|
214
|
+
if (id.includes(`/${islandsDir}/`)) {
|
|
215
|
+
const match = id.match(/\/([^/]+)\.(ts|js)$/);
|
|
216
|
+
if (match) return `island-${match[1]}`;
|
|
217
|
+
}
|
|
218
|
+
for (const island of packageIslandDecls){
|
|
219
|
+
if (id.includes(island.modulePath)) return `island-${island.tagName}`;
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
},
|
|
225
|
+
resolve: {
|
|
226
|
+
...serializedAlias.length > 0 ? {
|
|
227
|
+
alias: serializedAlias
|
|
228
|
+
} : {},
|
|
229
|
+
extensions: [
|
|
230
|
+
'.ts',
|
|
231
|
+
'.tsx',
|
|
232
|
+
'.js',
|
|
233
|
+
'.jsx',
|
|
234
|
+
'.json'
|
|
235
|
+
]
|
|
236
|
+
},
|
|
237
|
+
ssr: {
|
|
238
|
+
noExternal: noExternalPatterns.length > 0 ? noExternalPatterns : undefined
|
|
239
|
+
},
|
|
240
|
+
plugins: [
|
|
241
|
+
createOpenJsrPackageResolverPlugin({
|
|
242
|
+
workspaceRoot: WORKSPACE_ROOT,
|
|
243
|
+
version: getJsrPackageVersion(import.meta.url)
|
|
244
|
+
}),
|
|
245
|
+
{
|
|
246
|
+
name: 'open:virtual-client-entry',
|
|
247
|
+
resolveId (id) {
|
|
248
|
+
if (id === VIRTUAL_CLIENT_ENTRY_ID) return RESOLVED_CLIENT_ENTRY_ID;
|
|
249
|
+
},
|
|
250
|
+
load (id) {
|
|
251
|
+
if (id === RESOLVED_CLIENT_ENTRY_ID) return clientEntryCode;
|
|
252
|
+
}
|
|
253
|
+
},
|
|
254
|
+
{
|
|
255
|
+
name: 'open:deno-import-map-resolve',
|
|
256
|
+
enforce: 'pre',
|
|
257
|
+
async resolveId (id, importer) {
|
|
258
|
+
// Only handle bare specifiers (no relative imports, no absolute paths)
|
|
259
|
+
if (id.startsWith('.') || id.startsWith('/') || id.startsWith('file:')) {
|
|
260
|
+
return null;
|
|
261
|
+
}
|
|
262
|
+
// Try deno.json import map — walks up from root to find
|
|
263
|
+
// workspace-level deno.json as fallback for monorepo dev.
|
|
264
|
+
const result = lookupInDenoJson(id, root);
|
|
265
|
+
if (!result) return null;
|
|
266
|
+
// Only handle file:// and relative targets (workspace-local dev mappings).
|
|
267
|
+
// npm:, jsr: → return null, let node_modules handle them.
|
|
268
|
+
const resolved = convertImportMapTarget(result.target, result.denoJsonDir);
|
|
269
|
+
if (!resolved) return null;
|
|
270
|
+
return await this.resolve(resolved, importer, {
|
|
271
|
+
skipSelf: true
|
|
272
|
+
});
|
|
273
|
+
}
|
|
274
|
+
}
|
|
275
|
+
]
|
|
276
|
+
};
|
|
277
|
+
try {
|
|
278
|
+
await viteBuild(clientConfig);
|
|
279
|
+
log.info('Client bundle built -> ' + clientOutDir);
|
|
280
|
+
const { printBuildManifest } = await import('../build-manifest.js');
|
|
281
|
+
printBuildManifest({
|
|
282
|
+
root,
|
|
283
|
+
outDir,
|
|
284
|
+
phase: 2
|
|
285
|
+
});
|
|
286
|
+
} catch (error) {
|
|
287
|
+
log.error(`Client build failed: ${formatError(error)}`);
|
|
288
|
+
throw error;
|
|
289
|
+
}
|
|
290
|
+
}
|
|
291
|
+
export { buildClient };
|
|
292
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJzb3VyY2VzIjpbImZpbGU6Ly8vaG9tZS9ydW5uZXIvd29yay9vcGVuZWxlbWVudC9vcGVuZWxlbWVudC9wYWNrYWdlcy9hZGFwdGVyLXZpdGUvc3JjL2NsaS9idWlsZC1jbGllbnQudHMiXSwic291cmNlc0NvbnRlbnQiOlsiLyoqXG4gKiBAb3BlbmVsZW1lbnQvYWRhcHRlci12aXRlIC0gQ0xJOiBDbGllbnQgSXNsYW5kIEJ1aWxkXG4gKlxuICogQ2xpZW50IGJ1aWxkIGZvciBJc2xhbmQgY29tcG9uZW50cy5cbiAqIFByb2R1Y2VzIGRpc3QvY2xpZW50L2lzbGFuZHMvKi5qcyArIG1hbmlmZXN0IGZvciBTU0cgcG9zdC1wcm9jZXNzaW5nLlxuICpcbiAqIEFEUiAwMDExOiBUaGlzIG1vZHVsZSBleHBvcnRzIGJ1aWxkQ2xpZW50KCkgb25seSAtIGl0IGlzIGNhbGxlZCBmcm9tXG4gKiBjbG9zZUJ1bmRsZSgpIGluIG9wZW46YnVpbGQgcGx1Z2luLiBObyBsb25nZXIgYSBzdGFuZGFsb25lIENMSSBlbnRyeS5cbiAqIGN0eCBwYXJhbWV0ZXIgaXMgcmVxdWlyZWQgKG5vIGdsb2JhbFRoaXMgZmFsbGJhY2spLlxuICpcbiAqIFVzYWdlOlxuICogICBkZW5vIHRhc2sgYnVpbGQgICh1bmlmaWVkIGVudHJ5IC0gcnVucyBhbGwgMyBwaGFzZXMpXG4gKi9cblxuaW1wb3J0IHsgYnVpbGQgYXMgdml0ZUJ1aWxkLCB0eXBlIElubGluZUNvbmZpZyB9IGZyb20gJ3ZpdGUnO1xuaW1wb3J0IHsgZXhpc3RzU3luYywgcmVhZEZpbGVTeW5jIH0gZnJvbSAnbm9kZTpmcyc7XG5pbXBvcnQgeyBqb2luLCByZXNvbHZlIH0gZnJvbSAnbm9kZTpwYXRoJztcbmltcG9ydCB7IGZpbGVVUkxUb1BhdGggfSBmcm9tICdub2RlOnVybCc7XG5pbXBvcnQgcHJvY2VzcyBmcm9tICdub2RlOnByb2Nlc3MnO1xuaW1wb3J0IHsgZ2VuZXJhdGVDbGllbnRFbnRyeSB9IGZyb20gJ0BvcGVuZWxlbWVudC9zc2cnO1xuaW1wb3J0IHR5cGUgeyBDbGllbnRJc2xhbmRFbnRyeSB9IGZyb20gJ0BvcGVuZWxlbWVudC9wcm90b2NvbC9zc2cnO1xuaW1wb3J0IHR5cGUgeyBPcGVuRWxlbWVudEJ1aWxkQ29udGV4dCB9IGZyb20gJy4uL2J1aWxkLWNvbnRleHQuanMnO1xuaW1wb3J0IHsgY3JlYXRlT3BlbkpzclBhY2thZ2VSZXNvbHZlclBsdWdpbiB9IGZyb20gJy4uL3NzZy1wYWNrYWdlLXJlc29sdmVyLmpzJztcbmltcG9ydCB7IGZvcm1hdEVycm9yIH0gZnJvbSAnQG9wZW5lbGVtZW50L2NvcmUvZXJyb3JzJztcbmltcG9ydCB7IGNyZWF0ZUxvZ2dlciB9IGZyb20gJ0BvcGVuZWxlbWVudC9jb3JlL2xvZ2dlcic7XG5cbmNvbnN0IGxvZyA9IGNyZWF0ZUxvZ2dlcignc3NnJyk7XG5cbmNvbnN0IFZJUlRVQUxfQ0xJRU5UX0VOVFJZX0lEID0gJ3ZpcnR1YWw6b3Blbi1jbGllbnQtZW50cnknO1xuY29uc3QgUkVTT0xWRURfQ0xJRU5UX0VOVFJZX0lEID0gJ1xcMCcgKyBWSVJUVUFMX0NMSUVOVF9FTlRSWV9JRDtcbmNvbnN0IEZBTExCQUNLX29wZW5FbGVtZW50X1ZFUlNJT04gPSAnMC4yMy4wJztcblxudHlwZSBWaXRlQnVpbGRPcHRpb25zV2l0aE1hbmlmZXN0ID0gTm9uTnVsbGFibGU8SW5saW5lQ29uZmlnWydidWlsZCddPiAmIHtcbiAgbWFuaWZlc3Q/OiBib29sZWFuO1xufTtcblxudHlwZSBWaXRlSW5saW5lQ29uZmlnV2l0aE1hbmlmZXN0ID0gT21pdDxJbmxpbmVDb25maWcsICdidWlsZCc+ICYge1xuICBidWlsZD86IFZpdGVCdWlsZE9wdGlvbnNXaXRoTWFuaWZlc3Q7XG59O1xuXG4vKiogV29ya3NwYWNlIHJvb3QgZGVyaXZlZCBmcm9tIHRoaXMgbW9kdWxlJ3MgbG9jYXRpb24gKHBhY2thZ2VzL2FkYXB0ZXItdml0ZS9zcmMvY2xpLykuXG4gKiBPbmx5IHZhbGlkIGluIGxvY2FsIHdvcmtzcGFjZSAoZmlsZTovLyBpbXBvcnQubWV0YS51cmwpLiBJbiBKU1IgY29uc3VtZXJzLCByZXR1cm5zIG51bGwuICovXG5jb25zdCBXT1JLU1BBQ0VfUk9PVDogc3RyaW5nIHwgbnVsbCA9ICgoKSA9PiB7XG4gIGlmICghaW1wb3J0Lm1ldGEudXJsLnN0YXJ0c1dpdGgoJ2ZpbGU6JykpIHJldHVybiBudWxsO1xuICB0cnkge1xuICAgIHJldHVybiBmaWxlVVJMVG9QYXRoKG5ldyBVUkwoJy4uLy4uLy4uLy4uJywgaW1wb3J0Lm1ldGEudXJsKSkucmVwbGFjZSgvXFxcXC9nLCAnLycpO1xuICB9IGNhdGNoIHtcbiAgICByZXR1cm4gbnVsbDtcbiAgfVxufSkoKTtcblxuZnVuY3Rpb24gZ2V0SnNyUGFja2FnZVZlcnNpb24obWV0YVVybDogc3RyaW5nKTogc3RyaW5nIHtcbiAgY29uc3QgbWF0Y2ggPSBtZXRhVXJsLm1hdGNoKC9cXC9Ab3BlbmVsZW1lbnRcXC9hZGFwdGVyLXZpdGVcXC8oW14vXSspXFwvLyk7XG4gIHJldHVybiBtYXRjaD8uWzFdID8/IEZBTExCQUNLX29wZW5FbGVtZW50X1ZFUlNJT047XG59XG5cbi8qKlxuICogTG9vayB1cCBhIGJhcmUgc3BlY2lmaWVyIGluIGEgZGVuby5qc29uIGltcG9ydCBtYXAuXG4gKiBXYWxrcyB1cCBkaXJlY3RvcnkgdHJlZSB0byBmaW5kIHdvcmtzcGFjZS1sZXZlbCBkZW5vLmpzb24gYXMgZmFsbGJhY2suXG4gKiBSZXR1cm5zIHsgdGFyZ2V0LCBkZW5vSnNvbkRpciB9IHNvIHJlbGF0aXZlIHBhdGhzIGNhbiBiZSByZXNvbHZlZCBjb3JyZWN0bHkuXG4gKi9cbmZ1bmN0aW9uIGxvb2t1cEluRGVub0pzb24oXG4gIGlkOiBzdHJpbmcsXG4gIHJvb3Q6IHN0cmluZyxcbik6IHsgdGFyZ2V0OiBzdHJpbmc7IGRlbm9Kc29uRGlyOiBzdHJpbmcgfSB8IG51bGwge1xuICBjb25zdCBkZW5vSnNvbkRpcnMgPSBuZXcgU2V0PHN0cmluZz4oKTtcbiAgbGV0IGRpciA9IHJlc29sdmUocm9vdCk7XG5cbiAgLy8gV2FsayB1cCBmcm9tIGNvbnN1bWVyIHJvb3RcbiAgd2hpbGUgKCFkZW5vSnNvbkRpcnMuaGFzKGRpcikpIHtcbiAgICBkZW5vSnNvbkRpcnMuYWRkKGRpcik7XG4gICAgY29uc3QgZm91bmQgPSB0cnlEZW5vSnNvbkRpcihpZCwgZGlyKTtcbiAgICBpZiAoZm91bmQpIHJldHVybiBmb3VuZDtcbiAgICBjb25zdCBwYXJlbnQgPSByZXNvbHZlKGRpciwgJy4uJyk7XG4gICAgaWYgKHBhcmVudCA9PT0gZGlyKSBicmVhaztcbiAgICBkaXIgPSBwYXJlbnQ7XG4gIH1cblxuICAvLyBBbHNvIHRyeSB3b3Jrc3BhY2Ugcm9vdCAobW9kdWxlLXJlbGF0aXZlLCBmb3IgbW9ub3JlcG8gZGV2IC8gdGVzdGluZylcbiAgaWYgKFdPUktTUEFDRV9ST09UICYmICFkZW5vSnNvbkRpcnMuaGFzKFdPUktTUEFDRV9ST09UKSkge1xuICAgIGNvbnN0IGZvdW5kID0gdHJ5RGVub0pzb25EaXIoaWQsIFdPUktTUEFDRV9ST09UKTtcbiAgICBpZiAoZm91bmQpIHJldHVybiBmb3VuZDtcbiAgfVxuXG4gIHJldHVybiBudWxsO1xufVxuXG4vKiogQ2hlY2sgYSBzaW5nbGUgZGlyZWN0b3J5IGZvciBhIGRlbm8uanNvbiB3aXRoIHRoZSBnaXZlbiBpbXBvcnQuICovXG5mdW5jdGlvbiB0cnlEZW5vSnNvbkRpcihcbiAgaWQ6IHN0cmluZyxcbiAgZGlyOiBzdHJpbmcsXG4pOiB7IHRhcmdldDogc3RyaW5nOyBkZW5vSnNvbkRpcjogc3RyaW5nIH0gfCBudWxsIHtcbiAgY29uc3QgZGVub0pzb25QYXRoID0gam9pbihkaXIsICdkZW5vLmpzb24nKTtcbiAgaWYgKCFleGlzdHNTeW5jKGRlbm9Kc29uUGF0aCkpIHJldHVybiBudWxsO1xuICBjb25zdCByYXcgPSByZWFkRmlsZVN5bmMoZGVub0pzb25QYXRoLCAndXRmLTgnKTtcbiAgLy8gU3RyaXAgSlNPTkMgY29tbWVudHM6XG4gIC8vIC0gTGluZSBjb21tZW50czogLy8gYXQgc3RhcnQgb2YgbGluZSAoYWZ0ZXIgb3B0aW9uYWwgd2hpdGVzcGFjZSlcbiAgLy8gLSBCbG9jayBjb21tZW50czogLyogLi4uICovXG4gIC8vIC0gVHJhaWxpbmcgY29tbWFzIChEZW5vIEpTT05DIGFsbG93cyB0aGVtLCBKU09OLnBhcnNlIGRvZXMgbm90KVxuICBjb25zdCBqc29uID0gcmF3XG4gICAgLnJlcGxhY2UoL15cXHMqXFwvXFwvLiokL2dtLCAnJylcbiAgICAucmVwbGFjZSgvXFwvXFwqW1xcc1xcU10qP1xcKlxcLy9nLCAnJylcbiAgICAucmVwbGFjZSgvLFxccyooW31cXF1dKS9nLCAnJDEnKTtcbiAgbGV0IGRlbm9Kc29uOiBSZWNvcmQ8c3RyaW5nLCB1bmtub3duPjtcbiAgdHJ5IHtcbiAgICBkZW5vSnNvbiA9IEpTT04ucGFyc2UoanNvbik7XG4gIH0gY2F0Y2gge1xuICAgIHJldHVybiBudWxsOyAvLyBJbnZhbGlkIEpTT04g4oCUIHNraXAgdGhpcyBkZW5vLmpzb25cbiAgfVxuICBjb25zdCBpbXBvcnRzID0gZGVub0pzb24uaW1wb3J0cyBhcyBSZWNvcmQ8c3RyaW5nLCBzdHJpbmc+IHwgdW5kZWZpbmVkO1xuICBpZiAoIWltcG9ydHMpIHJldHVybiBudWxsO1xuICAvLyBFeGFjdCBtYXRjaFxuICBpZiAoaW1wb3J0c1tpZF0pIHJldHVybiB7IHRhcmdldDogaW1wb3J0c1tpZF0sIGRlbm9Kc29uRGlyOiBkaXIgfTtcbiAgLy8gUHJlZml4L3N1YnBhdGggbWF0Y2hpbmcgKHRyYWlsaW5nIHNsYXNoKVxuICBmb3IgKGNvbnN0IFtrZXksIHZhbHVlXSBvZiBPYmplY3QuZW50cmllcyhpbXBvcnRzKSkge1xuICAgIGlmIChrZXkuZW5kc1dpdGgoJy8nKSAmJiBpZC5zdGFydHNXaXRoKGtleSkpIHtcbiAgICAgIHJldHVybiB7IHRhcmdldDogdmFsdWUgKyBpZC5zbGljZShrZXkubGVuZ3RoKSwgZGVub0pzb25EaXI6IGRpciB9O1xuICAgIH1cbiAgfVxuICByZXR1cm4gbnVsbDtcbn1cblxuLyoqXG4gKiBDb252ZXJ0IGEgRGVubyBpbXBvcnQgbWFwIHRhcmdldCB0byBhIHJlc29sdmFibGUgVml0ZSBwYXRoLlxuICogLSBmaWxlOi8vIFVSTHMg4oaSIGFic29sdXRlIGZpbGVzeXN0ZW0gcGF0aFxuICogLSBSZWxhdGl2ZSBwYXRocyAoLi8pIOKGkiByZXNvbHZlZCByZWxhdGl2ZSB0byBkZW5vSnNvbkRpclxuICogLSBucG06LCBqc3I6IOKGkiBudWxsIChoYW5kbGVkIGJ5IG5vZGVfbW9kdWxlcylcbiAqL1xuZnVuY3Rpb24gY29udmVydEltcG9ydE1hcFRhcmdldCh0YXJnZXQ6IHN0cmluZywgZGVub0pzb25EaXI6IHN0cmluZyk6IHN0cmluZyB8IG51bGwge1xuICBpZiAodGFyZ2V0LnN0YXJ0c1dpdGgoJ2ZpbGU6Ly8nKSkge1xuICAgIHRyeSB7XG4gICAgICByZXR1cm4gZmlsZVVSTFRvUGF0aCh0YXJnZXQpLnJlcGxhY2UoL1xcXFwvZywgJy8nKTtcbiAgICB9IGNhdGNoIHtcbiAgICAgIHJldHVybiBudWxsO1xuICAgIH1cbiAgfVxuICAvLyBSZWxhdGl2ZSBwYXRoIOKAlCByZXNvbHZlIHJlbGF0aXZlIHRvIHRoZSBkZW5vLmpzb24gZGlyZWN0b3J5XG4gIGlmICh0YXJnZXQuc3RhcnRzV2l0aCgnLi8nKSB8fCB0YXJnZXQuc3RhcnRzV2l0aCgnLi4vJykpIHtcbiAgICByZXR1cm4gcmVzb2x2ZShkZW5vSnNvbkRpciwgdGFyZ2V0KS5yZXBsYWNlKC9cXFxcL2csICcvJyk7XG4gIH1cbiAgLy8gbnBtOiwganNyOiDigJQgbGV0IFZpdGUvUm9sbGRvd24gaGFuZGxlIHRoZXNlIG5vcm1hbGx5XG4gIHJldHVybiBudWxsO1xufVxuXG5hc3luYyBmdW5jdGlvbiBidWlsZENsaWVudChjdHg6IE9wZW5FbGVtZW50QnVpbGRDb250ZXh0KTogUHJvbWlzZTx2b2lkPiB7XG4gIGNvbnN0IHJvb3QgPSBjdHgucGhhc2UzLnJvb3QgfHwgcHJvY2Vzcy5jd2QoKTtcbiAgY29uc3Qgb3V0RGlyID0gY3R4LnBoYXNlMy5vdXREaXIgfHwgJ2Rpc3QnO1xuICBjb25zdCBpc2xhbmRzRGlyID0gY3R4LnBoYXNlMy5pc2xhbmRzRGlyIHx8ICdhcHAvaXNsYW5kcyc7XG4gIGNvbnN0IGxvY2FsSXNsYW5kcyA9IGN0eC5waGFzZTEuaXNsYW5kVGFnTmFtZXMgfHwgW107XG4gIGNvbnN0IGxvY2FsSXNsYW5kRmlsZXMgPSBjdHgucGhhc2UxLmlzbGFuZEZpbGVzIHx8IFtdO1xuICBjb25zdCBwYWNrYWdlSXNsYW5kRGVjbHMgPSBjdHgucGhhc2UxLnBhY2thZ2VJc2xhbmREZWNscyB8fCBbXTtcblxuICAvLyBBbGlhc2VzIHByZS1nZW5lcmF0ZWQgYnkgY3JlYXRlT3BlblBsdWdpbigpIGFuZCBzdG9yZWQgaW4gY3R4XG4gIGNvbnN0IHJlc29sdmVBbGlhcyA9IGN0eC5waGFzZTEudXNlclJlc29sdmVBbGlhcztcbiAgY29uc3Qgc2VyaWFsaXplZEFsaWFzID0gcmVzb2x2ZUFsaWFzXG4gICAgPyAoQXJyYXkuaXNBcnJheShyZXNvbHZlQWxpYXMpXG4gICAgICA/IHJlc29sdmVBbGlhcy5maWx0ZXIoKGEpID0+IHR5cGVvZiBhLmZpbmQgPT09ICdzdHJpbmcnKS5tYXAoKGEpID0+ICh7XG4gICAgICAgIGZpbmQ6IGEuZmluZCBhcyBzdHJpbmcsXG4gICAgICAgIHJlcGxhY2VtZW50OiBhLnJlcGxhY2VtZW50LFxuICAgICAgfSkpXG4gICAgICA6IE9iamVjdC5lbnRyaWVzKHJlc29sdmVBbGlhcykubWFwKChbZmluZCwgcmVwbGFjZW1lbnRdKSA9PiAoeyBmaW5kLCByZXBsYWNlbWVudCB9KSkpXG4gICAgOiBbXTtcblxuICAvLyBBbHdheXMgcmVzb2x2ZSBAb3BlbmVsZW1lbnQvY29yZS9zdHlsZS1zaGVldCBmcm9tIHdvcmtzcGFjZSAoY29yZSByZS1leHBvcnRzIGl0KVxuICBpZiAoV09SS1NQQUNFX1JPT1QpIHtcbiAgICBzZXJpYWxpemVkQWxpYXMucHVzaCh7XG4gICAgICBmaW5kOiAnQG9wZW5lbGVtZW50L2NvcmUvc3R5bGUtc2hlZXQnLFxuICAgICAgcmVwbGFjZW1lbnQ6IGpvaW4oV09SS1NQQUNFX1JPT1QsICdwYWNrYWdlcycsICdjb3JlJywgJ3NyYycsICdzdHlsZS1zaGVldC50cycpLFxuICAgIH0pO1xuICAgIChzZXJpYWxpemVkQWxpYXMgYXMgQXJyYXk8eyBmaW5kOiBzdHJpbmcgfCBSZWdFeHA7IHJlcGxhY2VtZW50OiBzdHJpbmcgfT4pLnB1c2goe1xuICAgICAgZmluZDogL15Ab3BlbmVsZW1lbnRcXC9yb3V0ZXIvLFxuICAgICAgcmVwbGFjZW1lbnQ6IGpvaW4oV09SS1NQQUNFX1JPT1QsICdwYWNrYWdlcycsICdyb3V0ZXInLCAnc3JjJyksXG4gICAgfSk7XG4gIH1cbiAgc2VyaWFsaXplZEFsaWFzLnNvcnQoKGEsIGIpID0+IHtcbiAgICBjb25zdCBmaW5kQSA9IHR5cGVvZiBhLmZpbmQgPT09ICdzdHJpbmcnID8gYS5maW5kLmxlbmd0aCA6IDA7XG4gICAgY29uc3QgZmluZEIgPSB0eXBlb2YgYi5maW5kID09PSAnc3RyaW5nJyA/IGIuZmluZC5sZW5ndGggOiAwO1xuICAgIHJldHVybiBmaW5kQiAtIGZpbmRBO1xuICB9KTtcblxuICBpZiAobG9jYWxJc2xhbmRzLmxlbmd0aCA9PT0gMCAmJiBwYWNrYWdlSXNsYW5kRGVjbHMubGVuZ3RoID09PSAwKSB7XG4gICAgbG9nLmluZm8oJ05vIGlzbGFuZHMgZm91bmQgLSB6ZXJvIGNsaWVudCBKUyBvdXRwdXQnKTtcbiAgICByZXR1cm47XG4gIH1cblxuICBjb25zdCB0b3RhbElzbGFuZHMgPSBsb2NhbElzbGFuZHMubGVuZ3RoICsgcGFja2FnZUlzbGFuZERlY2xzLmxlbmd0aDtcbiAgbG9nLmluZm8oYEJ1aWxkaW5nIGNsaWVudCBidW5kbGUgZm9yICR7dG90YWxJc2xhbmRzfSBpc2xhbmQocykuLi5gKTtcblxuICAvLyBHZW5lcmF0ZSBjbGllbnQgZW50cnkgY29kZVxuICBjb25zdCBpc2xhbmRFbnRyaWVzOiBDbGllbnRJc2xhbmRFbnRyeVtdID0gW1xuICAgIC4uLmxvY2FsSXNsYW5kcy5tYXAoKHRhZ05hbWU6IHN0cmluZywgaTogbnVtYmVyKSA9PiAoe1xuICAgICAgdGFnTmFtZSxcbiAgICAgIG1vZHVsZVBhdGg6IHJlc29sdmUoXG4gICAgICAgIHJvb3QsXG4gICAgICAgIGxvY2FsSXNsYW5kRmlsZXNbaV1cbiAgICAgICAgICA/IGAke2lzbGFuZHNEaXJ9LyR7bG9jYWxJc2xhbmRGaWxlc1tpXX1gXG4gICAgICAgICAgOiBgJHtpc2xhbmRzRGlyfS8ke3RhZ05hbWV9LnRzYCxcbiAgICAgICkucmVwbGFjZSgvXFxcXC9nLCAnLycpLFxuICAgICAgaXNQYWNrYWdlOiBmYWxzZSxcbiAgICAgIHN0cmF0ZWd5OiBjdHgucGhhc2UxLmlzbGFuZE1ldGFbdGFnTmFtZV0/Lmh5ZHJhdGUgfHwgY3R4LnBoYXNlMy51cGdyYWRlU3RyYXRlZ3kgfHwgJ2lkbGUnLFxuICAgICAgc3NyOiBjdHgucGhhc2UxLmlzbGFuZE1ldGFbdGFnTmFtZV0/Lmh5ZHJhdGUgPT09ICdvbmx5J1xuICAgICAgICA/IGZhbHNlXG4gICAgICAgIDogY3R4LnBoYXNlMS5pc2xhbmRNZXRhW3RhZ05hbWVdPy5zc3IsXG4gICAgICBkc2Q6IGN0eC5waGFzZTEuaXNsYW5kTWV0YVt0YWdOYW1lXT8uaHlkcmF0ZSA9PT0gJ29ubHknXG4gICAgICAgID8gZmFsc2VcbiAgICAgICAgOiBjdHgucGhhc2UxLmlzbGFuZE1ldGFbdGFnTmFtZV0/LmRzZCxcbiAgICAgIHJlYXNvbjogY3R4LnBoYXNlMS5pc2xhbmRNZXRhW3RhZ05hbWVdPy5yZWFzb24sXG4gICAgfSkpLFxuICAgIC4uLnBhY2thZ2VJc2xhbmREZWNscy5tYXAoXG4gICAgICAoaXNsYW5kKSA9PiAoe1xuICAgICAgICB0YWdOYW1lOiBpc2xhbmQudGFnTmFtZSxcbiAgICAgICAgbW9kdWxlUGF0aDogaXNsYW5kLm1vZHVsZVBhdGgsXG4gICAgICAgIGlzUGFja2FnZTogdHJ1ZSxcbiAgICAgICAgc3RyYXRlZ3k6IGlzbGFuZC5oeWRyYXRlIHx8IGN0eC5waGFzZTMudXBncmFkZVN0cmF0ZWd5IHx8ICdpZGxlJyxcbiAgICAgICAgc3NyOiBpc2xhbmQuaHlkcmF0ZSA9PT0gJ29ubHknID8gZmFsc2UgOiBpc2xhbmQuc3NyLFxuICAgICAgICBkc2Q6IGlzbGFuZC5oeWRyYXRlID09PSAnb25seScgPyBmYWxzZSA6IGlzbGFuZC5kc2QsXG4gICAgICAgIHJlYXNvbjogaXNsYW5kLnJlYXNvbixcbiAgICAgIH0pLFxuICAgICksXG4gIF07XG5cbiAgY29uc3QgY2xpZW50RW50cnlDb2RlID0gZ2VuZXJhdGVDbGllbnRFbnRyeShpc2xhbmRFbnRyaWVzKTtcblxuICAvLyBSZXN0b3JlIFJlZ0V4cCBmcm9tIHNlcmlhbGl6ZWQgbm9FeHRlcm5hbCBwYXR0ZXJuc1xuICBjb25zdCBub0V4dGVybmFsUGF0dGVybnMgPSAoY3R4LnBoYXNlMy5zc3JOb0V4dGVybmFsIHx8IFtdKS5tYXAoKGl0ZW0pID0+IHtcbiAgICBpZiAodHlwZW9mIGl0ZW0gPT09ICdzdHJpbmcnKSByZXR1cm4gaXRlbTtcbiAgICBpZiAoaXRlbSAmJiB0eXBlb2YgaXRlbSA9PT0gJ29iamVjdCcgJiYgKGl0ZW0gYXMgUmVjb3JkPHN0cmluZywgdW5rbm93bj4pLl9fdHlwZSA9PT0gJ1JlZ0V4cCcpIHtcbiAgICAgIHJldHVybiBuZXcgUmVnRXhwKFxuICAgICAgICAoaXRlbSBhcyB7IHNvdXJjZTogc3RyaW5nOyBmbGFnczogc3RyaW5nIH0pLnNvdXJjZSxcbiAgICAgICAgKGl0ZW0gYXMgeyBzb3VyY2U6IHN0cmluZzsgZmxhZ3M6IHN0cmluZyB9KS5mbGFncyxcbiAgICAgICk7XG4gICAgfVxuICAgIHJldHVybiBpdGVtO1xuICB9KTtcblxuICBjb25zdCBjbGllbnRPdXREaXIgPSByZXNvbHZlKHJvb3QsIG91dERpciwgJ2NsaWVudCcpO1xuICBjb25zdCBjbGllbnRCYXNlID0gY3R4LnBoYXNlMy5iYXNlIHx8ICcvJztcbiAgY29uc3QgY2xpZW50Q29uZmlnOiBWaXRlSW5saW5lQ29uZmlnV2l0aE1hbmlmZXN0ID0ge1xuICAgIGNvbmZpZ0ZpbGU6IGZhbHNlLFxuICAgIHJvb3QsXG4gICAgYmFzZTogYCR7Y2xpZW50QmFzZX1jbGllbnQvYCxcbiAgICBsb2dMZXZlbDogJ3dhcm4nLFxuICAgIC8vIEFEUi0wMDU3OiBKU1ggYXV0b21hdGljIHJ1bnRpbWUgbXVzdCBiZSBjb25maWd1cmVkIGluIHRoZSBpbnRlcm5hbFxuICAgIC8vIHZpdGVCdWlsZCgpIGNhbGwg4oCUIGNvbmZpZ0ZpbGU6ZmFsc2UgbWVhbnMgdXNlcidzIHZpdGUuY29uZmlnLnRzIGlzXG4gICAgLy8gTk9UIHJlYWQuIFdpdGhvdXQgdGhpcywgZXNidWlsZCBkZWZhdWx0cyB0byBjbGFzc2ljIFJlYWN0LmNyZWF0ZUVsZW1lbnRcbiAgICAvLyB0cmFuc2Zvcm0sIHByb2R1Y2luZyB7dHlwZSwgcHJvcHMsICQkdHlwZW9mfSBvYmplY3RzIHRoYXQgRHNkRWxlbWVudFxuICAgIC8vIGRvZXMgbm90IHJlY29nbml6ZSAoY2F1c2VzIFtvYmplY3QgT2JqZWN0XSByZW5kZXJpbmcpLlxuICAgIGVzYnVpbGQ6IHtcbiAgICAgIGpzeDogJ2F1dG9tYXRpYycsXG4gICAgICBqc3hJbXBvcnRTb3VyY2U6ICdAb3BlbmVsZW1lbnQvY29yZScsXG4gICAgfSxcbiAgICBidWlsZDoge1xuICAgICAgb3V0RGlyOiBjbGllbnRPdXREaXIsXG4gICAgICBlbXB0eU91dERpcjogdHJ1ZSxcbiAgICAgIGNodW5rU2l6ZVdhcm5pbmdMaW1pdDogMTUwMCxcbiAgICAgIG1pbmlmeTogJ294YycsXG4gICAgICBtYW5pZmVzdDogdHJ1ZSxcbiAgICAgIHJvbGx1cE9wdGlvbnM6IHtcbiAgICAgICAgaW5wdXQ6IHsgY2xpZW50OiBWSVJUVUFMX0NMSUVOVF9FTlRSWV9JRCB9LFxuICAgICAgICBvdXRwdXQ6IHtcbiAgICAgICAgICBmb3JtYXQ6ICdlc20nLFxuICAgICAgICAgIGVudHJ5RmlsZU5hbWVzOiAnaXNsYW5kcy9bbmFtZV0uanMnLFxuICAgICAgICAgIGNodW5rRmlsZU5hbWVzOiAnaXNsYW5kcy9bbmFtZV0tW2hhc2hdLmpzJyxcbiAgICAgICAgICBtYW51YWxDaHVua3MoaWQ6IHN0cmluZykge1xuICAgICAgICAgICAgaWYgKGlkLmluY2x1ZGVzKGAvJHtpc2xhbmRzRGlyfS9gKSkge1xuICAgICAgICAgICAgICBjb25zdCBtYXRjaCA9IGlkLm1hdGNoKC9cXC8oW14vXSspXFwuKHRzfGpzKSQvKTtcbiAgICAgICAgICAgICAgaWYgKG1hdGNoKSByZXR1cm4gYGlzbGFuZC0ke21hdGNoWzFdfWA7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgICBmb3IgKGNvbnN0IGlzbGFuZCBvZiBwYWNrYWdlSXNsYW5kRGVjbHMpIHtcbiAgICAgICAgICAgICAgaWYgKGlkLmluY2x1ZGVzKGlzbGFuZC5tb2R1bGVQYXRoKSkgcmV0dXJuIGBpc2xhbmQtJHtpc2xhbmQudGFnTmFtZX1gO1xuICAgICAgICAgICAgfVxuICAgICAgICAgIH0sXG4gICAgICAgIH0sXG4gICAgICB9LFxuICAgIH0sXG4gICAgcmVzb2x2ZToge1xuICAgICAgLi4uKHNlcmlhbGl6ZWRBbGlhcy5sZW5ndGggPiAwID8geyBhbGlhczogc2VyaWFsaXplZEFsaWFzIH0gOiB7fSksXG4gICAgICBleHRlbnNpb25zOiBbJy50cycsICcudHN4JywgJy5qcycsICcuanN4JywgJy5qc29uJ10sXG4gICAgfSxcbiAgICBzc3I6IHtcbiAgICAgIG5vRXh0ZXJuYWw6IChub0V4dGVybmFsUGF0dGVybnMubGVuZ3RoID4gMCA/IG5vRXh0ZXJuYWxQYXR0ZXJucyA6IHVuZGVmaW5lZCkgYXNcbiAgICAgICAgfCAoc3RyaW5nIHwgUmVnRXhwKVtdXG4gICAgICAgIHwgdW5kZWZpbmVkLFxuICAgIH0sXG4gICAgcGx1Z2luczogW1xuICAgICAgY3JlYXRlT3BlbkpzclBhY2thZ2VSZXNvbHZlclBsdWdpbih7XG4gICAgICAgIHdvcmtzcGFjZVJvb3Q6IFdPUktTUEFDRV9ST09ULFxuICAgICAgICB2ZXJzaW9uOiBnZXRKc3JQYWNrYWdlVmVyc2lvbihpbXBvcnQubWV0YS51cmwpLFxuICAgICAgfSksXG4gICAgICB7XG4gICAgICAgIG5hbWU6ICdvcGVuOnZpcnR1YWwtY2xpZW50LWVudHJ5JyxcbiAgICAgICAgcmVzb2x2ZUlkKGlkKSB7XG4gICAgICAgICAgaWYgKGlkID09PSBWSVJUVUFMX0NMSUVOVF9FTlRSWV9JRCkgcmV0dXJuIFJFU09MVkVEX0NMSUVOVF9FTlRSWV9JRDtcbiAgICAgICAgfSxcbiAgICAgICAgbG9hZChpZCkge1xuICAgICAgICAgIGlmIChpZCA9PT0gUkVTT0xWRURfQ0xJRU5UX0VOVFJZX0lEKSByZXR1cm4gY2xpZW50RW50cnlDb2RlO1xuICAgICAgICB9LFxuICAgICAgfSxcbiAgICAgIHtcbiAgICAgICAgbmFtZTogJ29wZW46ZGVuby1pbXBvcnQtbWFwLXJlc29sdmUnLFxuICAgICAgICBlbmZvcmNlOiAncHJlJyxcbiAgICAgICAgYXN5bmMgcmVzb2x2ZUlkKGlkLCBpbXBvcnRlcikge1xuICAgICAgICAgIC8vIE9ubHkgaGFuZGxlIGJhcmUgc3BlY2lmaWVycyAobm8gcmVsYXRpdmUgaW1wb3J0cywgbm8gYWJzb2x1dGUgcGF0aHMpXG4gICAgICAgICAgaWYgKGlkLnN0YXJ0c1dpdGgoJy4nKSB8fCBpZC5zdGFydHNXaXRoKCcvJykgfHwgaWQuc3RhcnRzV2l0aCgnZmlsZTonKSkge1xuICAgICAgICAgICAgcmV0dXJuIG51bGw7XG4gICAgICAgICAgfVxuXG4gICAgICAgICAgLy8gVHJ5IGRlbm8uanNvbiBpbXBvcnQgbWFwIOKAlCB3YWxrcyB1cCBmcm9tIHJvb3QgdG8gZmluZFxuICAgICAgICAgIC8vIHdvcmtzcGFjZS1sZXZlbCBkZW5vLmpzb24gYXMgZmFsbGJhY2sgZm9yIG1vbm9yZXBvIGRldi5cbiAgICAgICAgICBjb25zdCByZXN1bHQgPSBsb29rdXBJbkRlbm9Kc29uKGlkLCByb290KTtcbiAgICAgICAgICBpZiAoIXJlc3VsdCkgcmV0dXJuIG51bGw7XG5cbiAgICAgICAgICAvLyBPbmx5IGhhbmRsZSBmaWxlOi8vIGFuZCByZWxhdGl2ZSB0YXJnZXRzICh3b3Jrc3BhY2UtbG9jYWwgZGV2IG1hcHBpbmdzKS5cbiAgICAgICAgICAvLyBucG06LCBqc3I6IOKGkiByZXR1cm4gbnVsbCwgbGV0IG5vZGVfbW9kdWxlcyBoYW5kbGUgdGhlbS5cbiAgICAgICAgICBjb25zdCByZXNvbHZlZCA9IGNvbnZlcnRJbXBvcnRNYXBUYXJnZXQocmVzdWx0LnRhcmdldCwgcmVzdWx0LmRlbm9Kc29uRGlyKTtcbiAgICAgICAgICBpZiAoIXJlc29sdmVkKSByZXR1cm4gbnVsbDtcblxuICAgICAgICAgIHJldHVybiBhd2FpdCB0aGlzLnJlc29sdmUocmVzb2x2ZWQsIGltcG9ydGVyLCB7IHNraXBTZWxmOiB0cnVlIH0pO1xuICAgICAgICB9LFxuICAgICAgfSxcbiAgICBdLFxuICB9O1xuXG4gIHRyeSB7XG4gICAgYXdhaXQgdml0ZUJ1aWxkKGNsaWVudENvbmZpZyk7XG4gICAgbG9nLmluZm8oJ0NsaWVudCBidW5kbGUgYnVpbHQgLT4gJyArIGNsaWVudE91dERpcik7XG5cbiAgICBjb25zdCB7IHByaW50QnVpbGRNYW5pZmVzdCB9ID0gYXdhaXQgaW1wb3J0KCcuLi9idWlsZC1tYW5pZmVzdC5qcycpO1xuICAgIHByaW50QnVpbGRNYW5pZmVzdCh7IHJvb3QsIG91dERpciwgcGhhc2U6IDIgfSk7XG4gIH0gY2F0Y2ggKGVycm9yKSB7XG4gICAgbG9nLmVycm9yKGBDbGllbnQgYnVpbGQgZmFpbGVkOiAke2Zvcm1hdEVycm9yKGVycm9yKX1gKTtcbiAgICB0aHJvdyBlcnJvcjtcbiAgfVxufVxuXG5leHBvcnQgeyBidWlsZENsaWVudCB9O1xuIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOzs7Ozs7Ozs7Ozs7Q0FZQyxHQUVELFNBQVMs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
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import type { FrameworkOptions, HydrationStrategy } from '@openelement/protocol/framework';
|
|
2
|
+
import type { OpenElementPackageManifest } from '@openelement/protocol/manifest';
|
|
3
|
+
import type { OpenElementBuildContext } from "../build-context.js";
|
|
4
|
+
interface BuildSSGOptions {
|
|
5
|
+
root?: string;
|
|
6
|
+
outDir?: string;
|
|
7
|
+
routesDir?: string;
|
|
8
|
+
islandsDir?: string;
|
|
9
|
+
middleware?: FrameworkOptions['middleware'];
|
|
10
|
+
ssr?: FrameworkOptions['ssr'];
|
|
11
|
+
islandTagNames?: string[];
|
|
12
|
+
islandMeta?: Record<string, Partial<import('@openelement/protocol/ssg').IslandDecl>>;
|
|
13
|
+
packageManifests?: OpenElementPackageManifest[];
|
|
14
|
+
/** @security Injected as raw HTML without sanitization */ headExtras?: string;
|
|
15
|
+
allowHeadExtrasScripts?: boolean;
|
|
16
|
+
html?: {
|
|
17
|
+
lang?: string;
|
|
18
|
+
title?: string;
|
|
19
|
+
};
|
|
20
|
+
appShell?: FrameworkOptions['appShell'];
|
|
21
|
+
layouts?: FrameworkOptions['layouts'];
|
|
22
|
+
upgradeStrategy?: HydrationStrategy;
|
|
23
|
+
resolveAlias?: Record<string, string> | import('vite').Alias[];
|
|
24
|
+
base?: string;
|
|
25
|
+
/**
|
|
26
|
+
* View Transitions API configuration.
|
|
27
|
+
* When true (default), injects <meta name="view-transition" content="same-origin">
|
|
28
|
+
* into all HTML files for smooth cross-page animations in MPA navigation.
|
|
29
|
+
* Set to false to disable.
|
|
30
|
+
* @default true
|
|
31
|
+
*/ viewTransition?: boolean;
|
|
32
|
+
/**
|
|
33
|
+
* Speculation Rules API configuration.
|
|
34
|
+
* Enables browser prefetch/prerender of pages before the user navigates.
|
|
35
|
+
* Can be a boolean (true = auto-generate from routes) or explicit rules.
|
|
36
|
+
*/ speculation?: boolean | import('@openelement/protocol/ssg').SpeculationRulesOptions;
|
|
37
|
+
/** ADR-0047: Skip Deno pre-resolution, use regex fallback for external deps. */ skipPreResolution?: boolean;
|
|
38
|
+
}
|
|
39
|
+
declare function buildSSG(options: BuildSSGOptions | undefined, ctx: OpenElementBuildContext): Promise<void>;
|
|
40
|
+
export { buildSSG };
|