@vmz/vmz 0.0.4 → 0.1.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/dist/build-assemble.d.ts +52 -0
- package/dist/build-assemble.js +192 -0
- package/dist/cdn-policy.d.ts +22 -4
- package/dist/cdn-policy.js +109 -13
- package/dist/cli.js +122 -27
- package/dist/content-addressed-assets.js +2 -1
- package/dist/delivery-profile.d.ts +84 -0
- package/dist/delivery-profile.js +348 -0
- package/dist/dev-session.d.ts +6 -0
- package/dist/dev-session.js +167 -40
- package/dist/document-build.js +33 -32
- package/dist/document-cmd.js +2 -9
- package/dist/document-enrich.js +8 -0
- package/dist/document-integrate.js +10 -17
- package/dist/embedded-packaging.d.ts +22 -0
- package/dist/embedded-packaging.js +109 -0
- package/dist/index.d.ts +26 -1
- package/dist/index.js +69 -2
- package/dist/locale-check.js +39 -66
- package/dist/locale-cmd.js +12 -44
- package/dist/locale-route-emit.d.ts +37 -0
- package/dist/locale-route-emit.js +109 -0
- package/dist/locale-router.d.ts +20 -0
- package/dist/locale-router.js +68 -0
- package/dist/log.d.ts +2 -2
- package/dist/log.js +11 -3
- package/dist/mini-host.d.ts +47 -0
- package/dist/mini-host.js +202 -0
- package/dist/native-addon.d.ts +9 -0
- package/dist/native-addon.js +84 -0
- package/dist/pack-client-packages.d.ts +25 -0
- package/dist/pack-client-packages.js +399 -0
- package/dist/pack.d.ts +58 -0
- package/dist/pack.js +123 -0
- package/dist/plugin-host.d.ts +1 -1
- package/dist/plugin-host.js +2 -2
- package/dist/pretty-json.d.ts +19 -0
- package/dist/pretty-json.js +43 -0
- package/dist/production-observability.js +3 -2
- package/dist/production-test-pack.d.ts +0 -14
- package/dist/production-test-pack.js +27 -31
- package/dist/release-pack.js +17 -21
- package/dist/route-path.d.ts +35 -0
- package/dist/route-path.js +77 -0
- package/dist/server-artifact.d.ts +140 -0
- package/dist/server-artifact.js +204 -0
- package/dist/server-language-backend.d.ts +89 -0
- package/dist/server-language-backend.js +121 -0
- package/dist/site-delivery.js +3 -2
- package/dist/static-emit.d.ts +10 -1
- package/dist/static-emit.js +192 -97
- package/dist/test-cmd.js +2 -1
- package/dist/wechat-packaging.d.ts +22 -0
- package/dist/wechat-packaging.js +59 -0
- package/package.json +12 -12
package/dist/cli.js
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
import { spawn } from 'node:child_process';
|
|
6
6
|
import { copyFileSync, existsSync } from 'node:fs';
|
|
7
7
|
import path from 'node:path';
|
|
8
|
-
import { HOST_PROTOCOL, createWorkspace, getProtocolVersions, resolveCoreRuntimeDist } from './index.js';
|
|
8
|
+
import { HOST_PROTOCOL, createWorkspace, getProtocolVersions, resolveCoreRuntimeDist, resolveNativePath } from './index.js';
|
|
9
9
|
import { createDevSession } from './dev-session.js';
|
|
10
10
|
import { gateGlobalProjectCommand, getInvocationContext, isGlobalAllowedCommand } from './invocation.js';
|
|
11
11
|
import { log } from './log.js';
|
|
@@ -16,14 +16,16 @@ import { cmdDocument } from './document-cmd.js';
|
|
|
16
16
|
import { buildIntegratedDocuments, projectHasDocuments } from './document-integrate.js';
|
|
17
17
|
import { cmdLocale } from './locale-cmd.js';
|
|
18
18
|
import { emitLocaleRuntimeModules, localeHasErrors } from './locale-check.js';
|
|
19
|
+
import { emitLocaleRouteRealization } from './locale-route-emit.js';
|
|
19
20
|
import { cmdApplication } from './application-cmd.js';
|
|
20
21
|
import { cmdArtifact } from './release-cmd.js';
|
|
21
22
|
import { cmdRefactor } from './refactor-cmd.js';
|
|
22
23
|
import { cmdExplain } from './explain-cmd.js';
|
|
23
24
|
import { resolveNativeVmzCli } from './resolve-native-cli.js';
|
|
24
|
-
import { emitWebStatic } from './static-emit.js';
|
|
25
|
-
import { emitSiteDelivery } from './site-delivery.js';
|
|
26
25
|
import { loadVmzConfig } from './plugin-host.js';
|
|
26
|
+
import { normalizeDeliveryAuthoring, selectBuildProfile } from './delivery-profile.js';
|
|
27
|
+
import { packFromDeploymentIr } from './pack.js';
|
|
28
|
+
import { assembleDelivery, emitBuildProof } from './build-assemble.js';
|
|
27
29
|
/**
|
|
28
30
|
* @param {string[]} argv
|
|
29
31
|
*/
|
|
@@ -104,8 +106,8 @@ Usage:
|
|
|
104
106
|
vmz check [path] Check project via Workspace
|
|
105
107
|
vmz build [path] [options] Build project via Workspace
|
|
106
108
|
vmz serve [path] [options] Serve dist (optional --build)
|
|
107
|
-
vmz dev [path] [options]
|
|
108
|
-
vmz format [path] [--check] Format .vmz via N-API (oxc
|
|
109
|
+
vmz dev [path] [options] Rebuild session; --target mini-program-wechat packs dist/wechat
|
|
110
|
+
vmz format [path] [--check] Format .vmz via N-API (oxc formatter + EditorConfig)
|
|
109
111
|
vmz lint [path] [--deny-warnings] Lint (= check) via N-API
|
|
110
112
|
vmz test [path] [options] Native test discover / report
|
|
111
113
|
vmz document|docs <cmd> Project /documents domain
|
|
@@ -120,9 +122,10 @@ Usage:
|
|
|
120
122
|
|
|
121
123
|
Options:
|
|
122
124
|
--out-dir, -o <dir> Output directory (default: dist)
|
|
123
|
-
--release Release build (
|
|
124
|
-
--profile <name> Delivery profile
|
|
125
|
-
--
|
|
125
|
+
--release Release build (omit serve-host; pack minify slot; proof)
|
|
126
|
+
--profile <name> Delivery profile (default from config; builtins: web-ssr|web-static|web-client|web-hybrid)
|
|
127
|
+
--target <id> Dev preview: browser (default) | mini-program-wechat (pack dist/wechat; WeChat DevTools)
|
|
128
|
+
--origin <url> Site origin for static-cdn canonical/sitemap
|
|
126
129
|
--host <host> Listen host (default: 127.0.0.1)
|
|
127
130
|
--port <port> Listen port (dev: omit = auto from 5173; set = lock)
|
|
128
131
|
--poll-ms <ms> Dev watch poll interval (default: 300)
|
|
@@ -281,7 +284,11 @@ function cmdCheck(args) {
|
|
|
281
284
|
try {
|
|
282
285
|
return runWithPlugins(ws, project, outDir, async () => {
|
|
283
286
|
const report = ws.check();
|
|
284
|
-
const
|
|
287
|
+
const { checkLocales, localeHasErrors } = await import('./locale-check.js');
|
|
288
|
+
const localeReport = checkLocales({ projectRoot: project, checkUnused: false });
|
|
289
|
+
// Locale policy is first-class: missing /locales is warning (not silent), hard errors still fail.
|
|
290
|
+
const errors = log.diagnostics([...(report.diagnostics ?? []), ...(localeReport.diagnostics ?? [])]) ||
|
|
291
|
+
(localeHasErrors(localeReport) ? 1 : 0);
|
|
285
292
|
log.info(`checked ${report.filesChecked} file(s)`);
|
|
286
293
|
return errors ? 1 : 0;
|
|
287
294
|
});
|
|
@@ -290,6 +297,23 @@ function cmdCheck(args) {
|
|
|
290
297
|
ws.dispose();
|
|
291
298
|
}
|
|
292
299
|
}
|
|
300
|
+
/**
|
|
301
|
+
* Dedupe locale/build diagnostics by code+path+message (runtime + route emit both report missing manifest).
|
|
302
|
+
* @param {Array<{ code?: string, path?: string, message?: string, severity?: string }>} list
|
|
303
|
+
*/
|
|
304
|
+
function dedupeDiagnostics(list) {
|
|
305
|
+
const seen = new Set();
|
|
306
|
+
/** @type {typeof list} */
|
|
307
|
+
const out = [];
|
|
308
|
+
for (const d of list || []) {
|
|
309
|
+
const key = `${d.code || ''}\0${d.path || ''}\0${d.message || ''}\0${d.severity || ''}`;
|
|
310
|
+
if (seen.has(key))
|
|
311
|
+
continue;
|
|
312
|
+
seen.add(key);
|
|
313
|
+
out.push(d);
|
|
314
|
+
}
|
|
315
|
+
return out;
|
|
316
|
+
}
|
|
293
317
|
/**
|
|
294
318
|
* @param {import('./index.js').Workspace} ws
|
|
295
319
|
* @param {string} project
|
|
@@ -316,6 +340,21 @@ async function cmdBuild(args) {
|
|
|
316
340
|
log.info(`build ${project} → ${outDir}`);
|
|
317
341
|
const ws = createWorkspace({ root: project, outDir });
|
|
318
342
|
try {
|
|
343
|
+
const cfg = await loadVmzConfig(project);
|
|
344
|
+
const cliProfile = typeof args.profile === 'string' ? args.profile : '';
|
|
345
|
+
const norm = normalizeDeliveryAuthoring(cfg.delivery ?? null);
|
|
346
|
+
if (!norm.ok) {
|
|
347
|
+
log.diagnostics(norm.diagnostics ?? []);
|
|
348
|
+
log.error('delivery authoring invalid');
|
|
349
|
+
return 1;
|
|
350
|
+
}
|
|
351
|
+
const selected = selectBuildProfile(norm.table, cliProfile);
|
|
352
|
+
if (!selected.ok) {
|
|
353
|
+
log.diagnostics(selected.diagnostics ?? []);
|
|
354
|
+
log.error(`unknown build --profile ${cliProfile || norm.table.default}`);
|
|
355
|
+
return 1;
|
|
356
|
+
}
|
|
357
|
+
log.info(`delivery profile ${selected.selection.profileId} (assembly=${selected.selection.assembly})`);
|
|
319
358
|
const code = await runWithPlugins(ws, project, outDir, () => {
|
|
320
359
|
const report = ws.build(Boolean(args.release));
|
|
321
360
|
const errors = log.diagnostics(report.diagnostics ?? []);
|
|
@@ -330,47 +369,96 @@ async function cmdBuild(args) {
|
|
|
330
369
|
if (code !== 0)
|
|
331
370
|
return code;
|
|
332
371
|
const localeEmit = emitLocaleRuntimeModules(project, outDir);
|
|
372
|
+
const localeRoutes = emitLocaleRouteRealization(project, outDir, {
|
|
373
|
+
origin: typeof args.origin === 'string' ? args.origin : undefined,
|
|
374
|
+
});
|
|
375
|
+
// Always surface locale diagnostics (warnings included) — missing /locales must not be silent.
|
|
376
|
+
// Dedupe: runtime emit + route realization both report the same missing-manifest warning.
|
|
377
|
+
const localeDiags = dedupeDiagnostics([...(localeEmit.diagnostics ?? []), ...(localeRoutes.diagnostics ?? [])]);
|
|
378
|
+
log.diagnostics(localeDiags);
|
|
333
379
|
if (!localeEmit.ok || localeHasErrors({ diagnostics: localeEmit.diagnostics })) {
|
|
334
|
-
log.diagnostics(localeEmit.diagnostics ?? []);
|
|
335
380
|
log.error('locale runtime emit failed');
|
|
336
381
|
return 1;
|
|
337
382
|
}
|
|
338
383
|
if (localeEmit.written.length) {
|
|
339
384
|
log.info(`locale runtime emit (${localeEmit.written.length} module(s))`);
|
|
340
385
|
}
|
|
386
|
+
if (!localeRoutes.ok) {
|
|
387
|
+
log.error('locale route realization emit failed');
|
|
388
|
+
return 1;
|
|
389
|
+
}
|
|
390
|
+
if (localeRoutes.written.length) {
|
|
391
|
+
log.info(`locale route realization (${localeRoutes.written.length} artifact(s))`);
|
|
392
|
+
}
|
|
341
393
|
if (projectHasDocuments(project)) {
|
|
342
394
|
const docs = await buildIntegratedDocuments({ projectRoot: project, outDir });
|
|
343
395
|
if (!docs.ok)
|
|
344
396
|
return 1;
|
|
345
397
|
}
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
398
|
+
let pack = null;
|
|
399
|
+
try {
|
|
400
|
+
pack = packFromDeploymentIr(outDir, {
|
|
401
|
+
release: Boolean(args.release),
|
|
402
|
+
profileId: selected.selection.profileId,
|
|
403
|
+
assembly: selected.selection.assembly,
|
|
404
|
+
coreDist: resolveCoreRuntimeDist(),
|
|
405
|
+
projectRoot: project,
|
|
351
406
|
});
|
|
352
|
-
|
|
407
|
+
const lower = pack.manifest?.clientPackageLowering;
|
|
408
|
+
if (lower?.bareSpecs?.length) {
|
|
409
|
+
log.info(`pack client packages (${lower.bareSpecs.length} bare → vendor; rewritten=${lower.rewrittenFiles})`);
|
|
410
|
+
}
|
|
411
|
+
if (lower?.remainingBareSpecs?.length) {
|
|
412
|
+
log.warn(`pack client packages: ${lower.remainingBareSpecs.length} bare specifier(s) still unresolved for browser: ${lower.remainingBareSpecs.slice(0, 8).join(', ')}${lower.remainingBareSpecs.length > 8 ? '…' : ''}`);
|
|
413
|
+
}
|
|
414
|
+
log.info(`pack ok (units=${pack.manifest.unitCount}, digest=${String(pack.manifest.packDigest).slice(0, 12)}…)`);
|
|
353
415
|
}
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
416
|
+
catch (err) {
|
|
417
|
+
log.error(`pack failed: ${err instanceof Error ? err.message : String(err)}`);
|
|
418
|
+
return 1;
|
|
419
|
+
}
|
|
420
|
+
const origin = typeof args.origin === 'string' ? args.origin : undefined;
|
|
421
|
+
let assemble = null;
|
|
422
|
+
try {
|
|
423
|
+
if (selected.selection.assembly === 'static-cdn') {
|
|
424
|
+
log.info(`web-static emit ${outDir}`);
|
|
425
|
+
}
|
|
426
|
+
assemble = await assembleDelivery(outDir, {
|
|
427
|
+
selection: selected.selection,
|
|
428
|
+
profile: {
|
|
429
|
+
...selected.profile,
|
|
430
|
+
sources: selected.profile.sources || (norm.table.sugar ? norm.table.profiles[norm.table.default]?.sources : null),
|
|
431
|
+
},
|
|
432
|
+
siteId: cfg.application?.id || undefined,
|
|
433
|
+
origin,
|
|
434
|
+
pack: pack.manifest,
|
|
435
|
+
});
|
|
436
|
+
for (const step of assemble.manifest.steps || []) {
|
|
437
|
+
if (step.kind === 'static-cdn') {
|
|
438
|
+
log.info(`web-static ok (${step.htmlFiles} html, ${step.skipped} skipped, digest=${String(step.digest).slice(0, 12)}…)`);
|
|
439
|
+
}
|
|
440
|
+
else if (step.kind === 'site-delivery' && step.digest) {
|
|
441
|
+
log.info(`site-delivery ok (digest=${String(step.digest).slice(0, 12)}…)`);
|
|
442
|
+
}
|
|
443
|
+
}
|
|
360
444
|
}
|
|
361
|
-
|
|
362
|
-
log.error(`
|
|
445
|
+
catch (err) {
|
|
446
|
+
log.error(`assemble failed: ${err instanceof Error ? err.message : String(err)}`);
|
|
363
447
|
return 1;
|
|
364
448
|
}
|
|
449
|
+
const proof = emitBuildProof(outDir, {
|
|
450
|
+
selection: selected.selection,
|
|
451
|
+
pack: pack.manifest,
|
|
452
|
+
assemble: assemble.manifest,
|
|
453
|
+
release: Boolean(args.release),
|
|
454
|
+
});
|
|
455
|
+
log.info(`build-proof ok (profile=${proof.proof.profileId}, slots=${proof.proof.semanticIds.join(',')})`);
|
|
365
456
|
return 0;
|
|
366
457
|
}
|
|
367
458
|
finally {
|
|
368
459
|
ws.dispose();
|
|
369
460
|
}
|
|
370
461
|
}
|
|
371
|
-
/**
|
|
372
|
-
* @param {Record<string, string | boolean> & { _: string[] }} args
|
|
373
|
-
*/
|
|
374
462
|
async function cmdServe(args) {
|
|
375
463
|
const pathArg = args._[0] ?? '.';
|
|
376
464
|
if (args.build) {
|
|
@@ -406,6 +494,7 @@ async function cmdServe(args) {
|
|
|
406
494
|
VMZ_DIST: outDir,
|
|
407
495
|
VMZ_PORT: String(port),
|
|
408
496
|
VMZ_HOST: host,
|
|
497
|
+
VMZ_NATIVE_NODE: resolveNativePath(),
|
|
409
498
|
},
|
|
410
499
|
stdio: 'inherit',
|
|
411
500
|
});
|
|
@@ -452,6 +541,11 @@ async function cmdDev(args) {
|
|
|
452
541
|
}
|
|
453
542
|
}
|
|
454
543
|
const pollMs = Number(args['poll-ms'] ?? 300);
|
|
544
|
+
const targetRaw = typeof args.target === 'string' ? args.target : 'browser';
|
|
545
|
+
if (targetRaw !== 'browser' && targetRaw !== 'mini-program-wechat') {
|
|
546
|
+
log.error(`unknown --target ${targetRaw} (browser | mini-program-wechat)`);
|
|
547
|
+
return 1;
|
|
548
|
+
}
|
|
455
549
|
const ac = new AbortController();
|
|
456
550
|
const onSig = () => {
|
|
457
551
|
log.info('shutting down…');
|
|
@@ -465,6 +559,7 @@ async function cmdDev(args) {
|
|
|
465
559
|
host,
|
|
466
560
|
port,
|
|
467
561
|
pollMs,
|
|
562
|
+
target: targetRaw,
|
|
468
563
|
signal: ac.signal,
|
|
469
564
|
});
|
|
470
565
|
try {
|
|
@@ -8,6 +8,7 @@ import crypto from 'node:crypto';
|
|
|
8
8
|
import fs from 'node:fs';
|
|
9
9
|
import path from 'node:path';
|
|
10
10
|
import { canonicalJson, sha256Hex } from './release-pack.js';
|
|
11
|
+
import { writePrettyJsonFile } from './pretty-json.js';
|
|
11
12
|
export const CONTENT_ADDRESSED_ASSETS_SCHEMA = 'vmz.content_addressed_assets.v0';
|
|
12
13
|
/** Immutable delivery candidates (client-facing bytes). */
|
|
13
14
|
const DEFAULT_CANDIDATES = [
|
|
@@ -85,7 +86,7 @@ export function emitContentAddressedAssets(distDir, opts = {}) {
|
|
|
85
86
|
const vmzDir = path.join(abs, '_vmz');
|
|
86
87
|
fs.mkdirSync(vmzDir, { recursive: true });
|
|
87
88
|
const outPath = path.join(vmzDir, 'content-addressed-assets.json');
|
|
88
|
-
|
|
89
|
+
writePrettyJsonFile(outPath, manifest);
|
|
89
90
|
return { manifest, assetsDir, rewrites, manifestPath: outPath };
|
|
90
91
|
}
|
|
91
92
|
/**
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* B0 — Delivery profile authoring normalize + CLI --profile resolve.
|
|
3
|
+
* Pure data only; expands legacy site-delivery sugar into profiles[default].
|
|
4
|
+
*/
|
|
5
|
+
export declare const DELIVERY_PROFILE_AUTHORING_SCHEMA = "vmz.delivery.authoring.v0";
|
|
6
|
+
export declare const BUILD_PROFILE_SELECTION_SCHEMA = "vmz.build.profile_selection.v0";
|
|
7
|
+
/** Browser-era assembly kinds (04 B5). */
|
|
8
|
+
export declare const ASSEMBLIES: readonly string[];
|
|
9
|
+
export declare const SERVER_RUNTIMES: readonly string[];
|
|
10
|
+
/** Official built-in aliases when not overridden in config. */
|
|
11
|
+
export declare const BUILTIN_PROFILES: Readonly<{
|
|
12
|
+
'web-client': {
|
|
13
|
+
host: string;
|
|
14
|
+
assembly: string;
|
|
15
|
+
};
|
|
16
|
+
'web-static': {
|
|
17
|
+
host: string;
|
|
18
|
+
assembly: string;
|
|
19
|
+
};
|
|
20
|
+
'web-ssr': {
|
|
21
|
+
host: string;
|
|
22
|
+
assembly: string;
|
|
23
|
+
serverRuntime: string;
|
|
24
|
+
};
|
|
25
|
+
'web-hybrid': {
|
|
26
|
+
host: string;
|
|
27
|
+
assembly: string;
|
|
28
|
+
serverRuntime: string;
|
|
29
|
+
};
|
|
30
|
+
}>;
|
|
31
|
+
export declare function pickSiteAuthoring(raw: any): {
|
|
32
|
+
artifact: string;
|
|
33
|
+
sources: any;
|
|
34
|
+
};
|
|
35
|
+
/**
|
|
36
|
+
* `delivery.packaging.wechat` — vendor identity, not WeChat JSON / wx APIs.
|
|
37
|
+
* @param {unknown} raw
|
|
38
|
+
* @param {Array<{ code: string, message: string }>} diagnostics
|
|
39
|
+
*/
|
|
40
|
+
export declare function pickDeliveryPackaging(raw: any, diagnostics: any): {
|
|
41
|
+
wechat?: undefined;
|
|
42
|
+
} | {
|
|
43
|
+
wechat: {};
|
|
44
|
+
};
|
|
45
|
+
export declare function normalizeDeliveryAuthoring(raw: any): {
|
|
46
|
+
ok: boolean;
|
|
47
|
+
table: {
|
|
48
|
+
schema: string;
|
|
49
|
+
default: string;
|
|
50
|
+
profiles: {};
|
|
51
|
+
sugar: boolean;
|
|
52
|
+
};
|
|
53
|
+
diagnostics?: undefined;
|
|
54
|
+
} | {
|
|
55
|
+
ok: boolean;
|
|
56
|
+
diagnostics: any[];
|
|
57
|
+
table?: undefined;
|
|
58
|
+
};
|
|
59
|
+
export declare function selectBuildProfile(table: any, cliProfile?: string): {
|
|
60
|
+
ok: boolean;
|
|
61
|
+
diagnostics: {
|
|
62
|
+
code: string;
|
|
63
|
+
message: string;
|
|
64
|
+
}[];
|
|
65
|
+
selection?: undefined;
|
|
66
|
+
profile?: undefined;
|
|
67
|
+
} | {
|
|
68
|
+
ok: boolean;
|
|
69
|
+
selection: {
|
|
70
|
+
schema: string;
|
|
71
|
+
profileId: any;
|
|
72
|
+
host: any;
|
|
73
|
+
assembly: any;
|
|
74
|
+
serverRuntime: any;
|
|
75
|
+
hasSiteSources: boolean;
|
|
76
|
+
authoringDigest: any;
|
|
77
|
+
fromCli: boolean;
|
|
78
|
+
};
|
|
79
|
+
profile: any;
|
|
80
|
+
diagnostics?: undefined;
|
|
81
|
+
};
|
|
82
|
+
export declare function semanticIdsForAssembly(assembly: any): string[];
|
|
83
|
+
export declare function canonicalJson(value: any): string;
|
|
84
|
+
export declare function sha256Hex(text: any): string;
|