@vmz/vmz 0.0.3 → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (52) hide show
  1. package/README.md +6 -4
  2. package/dist/build-assemble.d.ts +52 -0
  3. package/dist/build-assemble.js +191 -0
  4. package/dist/cdn-policy.d.ts +196 -0
  5. package/dist/cdn-policy.js +443 -0
  6. package/dist/cli.js +152 -11
  7. package/dist/content-addressed-assets.d.ts +69 -0
  8. package/dist/content-addressed-assets.js +206 -0
  9. package/dist/delivery-profile.d.ts +74 -0
  10. package/dist/delivery-profile.js +279 -0
  11. package/dist/dev-session.js +49 -13
  12. package/dist/document-build.js +9 -4
  13. package/dist/document-designs.js +30 -2
  14. package/dist/document-enrich.js +8 -0
  15. package/dist/embedded-packaging.d.ts +22 -0
  16. package/dist/embedded-packaging.js +113 -0
  17. package/dist/index.d.ts +19 -3
  18. package/dist/index.js +35 -15
  19. package/dist/invocation.d.ts +8 -31
  20. package/dist/invocation.js +12 -33
  21. package/dist/locale-check.d.ts +16 -0
  22. package/dist/locale-check.js +131 -3
  23. package/dist/locale-cmd.js +2 -2
  24. package/dist/locale-route-emit.d.ts +34 -0
  25. package/dist/locale-route-emit.js +134 -0
  26. package/dist/locale-router.d.ts +20 -0
  27. package/dist/locale-router.js +68 -0
  28. package/dist/log.d.ts +2 -2
  29. package/dist/log.js +11 -3
  30. package/dist/pack.d.ts +40 -0
  31. package/dist/pack.js +108 -0
  32. package/dist/plugin-host.d.ts +10 -1
  33. package/dist/plugin-host.js +19 -2
  34. package/dist/port.d.ts +10 -0
  35. package/dist/port.js +46 -0
  36. package/dist/production-observability.d.ts +286 -0
  37. package/dist/production-observability.js +469 -0
  38. package/dist/production-test-pack.d.ts +144 -0
  39. package/dist/production-test-pack.js +447 -0
  40. package/dist/release-cmd.d.ts +8 -0
  41. package/dist/release-cmd.js +126 -0
  42. package/dist/release-pack.d.ts +96 -0
  43. package/dist/release-pack.js +346 -0
  44. package/dist/server-artifact.d.ts +140 -0
  45. package/dist/server-artifact.js +205 -0
  46. package/dist/server-language-backend.d.ts +89 -0
  47. package/dist/server-language-backend.js +121 -0
  48. package/dist/site-delivery.d.ts +134 -0
  49. package/dist/site-delivery.js +345 -0
  50. package/dist/static-emit.d.ts +145 -0
  51. package/dist/static-emit.js +577 -0
  52. package/package.json +13 -13
package/README.md CHANGED
@@ -1,4 +1,7 @@
1
- # VMZ CLI
1
+ # `@vmz/vmz` (bin: `vmz`)
2
+
3
+ CLI / N-API toolchain host. Runtime mental entry is **`@vmz/core`**; optional official UI is **`@vmz/ui`**; plugins are
4
+ **`@vmz/plugin-*`**. Shelved umbrella name: `@vmz/vmz`.
2
5
 
3
6
  When a project reaches the point where it has a browser surface, SSR, server work, documents, tests, and several
4
7
  deployment concerns, the usual workflow becomes a chain of tools that each see a different version of the application. A
@@ -22,9 +25,8 @@ With VMZ, a normal workflow is expected to answer all of these from the same sou
22
25
  - **Test:** what did a user interaction actually cause?
23
26
  - **Explain:** why did the compiler make that decision?
24
27
 
25
- Use it when you are adopting VMZ as the application model. It is intentionally not a compatibility compiler for
26
- arbitrary Vue components, React hooks, or legacy VDOM applications; those ecosystems are better served by their native
27
- toolchains.
28
+ Use it when you are adopting VMZ as the application model. The CLI targets VMZ-native source and semantics; Vue, React,
29
+ and legacy VDOM ecosystems keep their own toolchains.
28
30
 
29
31
  ## One tool, several views of the same program
30
32
 
@@ -0,0 +1,52 @@
1
+ /**
2
+ * B5 Assemble dispatch + B6 build-proof (per-build semantic id slots).
3
+ */
4
+ export declare const BUILD_PROOF_SCHEMA = "vmz.build.proof.v0";
5
+ export declare const ASSEMBLE_MANIFEST_SCHEMA = "vmz.assemble.manifest.v0";
6
+ /**
7
+ * @param {string} outDir
8
+ * @param {any} ctx
9
+ */
10
+ export declare function assembleDelivery(outDir: any, ctx: any): Promise<{
11
+ manifest: {
12
+ schema: string;
13
+ profileId: any;
14
+ assembly: any;
15
+ serverRuntime: any;
16
+ steps: any[];
17
+ };
18
+ path: string;
19
+ }>;
20
+ /**
21
+ * @param {string} outDir
22
+ * @param {any} ctx
23
+ */
24
+ export declare function emitBuildProof(outDir: any, ctx: any): {
25
+ proof: {
26
+ schema: string;
27
+ profileId: any;
28
+ assembly: any;
29
+ selectionDigest: any;
30
+ packDigest: any;
31
+ assembleDigest: any;
32
+ release: boolean;
33
+ semanticIds: string[];
34
+ slots: {
35
+ 'server-host': {
36
+ status: string;
37
+ };
38
+ 'static-delivery': {
39
+ status: string;
40
+ };
41
+ 'site-fallback': {
42
+ status: string;
43
+ };
44
+ 'asset-graph': {
45
+ status: string;
46
+ };
47
+ };
48
+ productionReadyClaim: boolean;
49
+ note: string;
50
+ };
51
+ path: string;
52
+ };
@@ -0,0 +1,191 @@
1
+ /**
2
+ * B5 Assemble dispatch + B6 build-proof (per-build semantic id slots).
3
+ */
4
+ // @ts-nocheck
5
+ import { mkdirSync, writeFileSync } from 'node:fs';
6
+ import path from 'node:path';
7
+ import { semanticIdsForAssembly, sha256Hex, canonicalJson } from './delivery-profile.js';
8
+ import { emitServerArtifact } from './server-artifact.js';
9
+ import { emitEmbeddedPackaging } from './embedded-packaging.js';
10
+ import { emitSiteDelivery } from './site-delivery.js';
11
+ import { emitWebStatic } from './static-emit.js';
12
+ export const BUILD_PROOF_SCHEMA = 'vmz.build.proof.v0';
13
+ export const ASSEMBLE_MANIFEST_SCHEMA = 'vmz.assemble.manifest.v0';
14
+ /**
15
+ * @param {string} outDir
16
+ * @param {any} ctx
17
+ */
18
+ export async function assembleDelivery(outDir, ctx) {
19
+ const { selection, profile } = ctx;
20
+ const assembly = selection.assembly;
21
+ const result = {
22
+ schema: ASSEMBLE_MANIFEST_SCHEMA,
23
+ profileId: selection.profileId,
24
+ assembly,
25
+ serverRuntime: selection.serverRuntime || null,
26
+ steps: [],
27
+ };
28
+ if (assembly === 'static-cdn' || assembly === 'cdn+server') {
29
+ const staticResult = await emitWebStatic(outDir, { origin: ctx.origin });
30
+ result.steps.push({
31
+ kind: 'static-cdn',
32
+ digest: staticResult.digest,
33
+ htmlFiles: staticResult.htmlFiles?.length ?? 0,
34
+ skipped: staticResult.skipped?.length ?? 0,
35
+ });
36
+ result.staticDelivery = {
37
+ digest: staticResult.digest,
38
+ htmlFiles: staticResult.htmlFiles,
39
+ skipped: staticResult.skipped,
40
+ };
41
+ }
42
+ if (assembly === 'local-static') {
43
+ result.steps.push({
44
+ kind: 'local-static',
45
+ status: 'modules-ready',
46
+ note: 'client modules packed; no ServerArtifact',
47
+ });
48
+ }
49
+ if (assembly === 'server-host' || assembly === 'cdn+server') {
50
+ const server = emitServerArtifact(outDir, {
51
+ profileId: selection.profileId,
52
+ assembly,
53
+ serverRuntime: selection.serverRuntime || 'node',
54
+ packDigest: ctx.pack?.packDigest || null,
55
+ });
56
+ result.steps.push({
57
+ kind: 'server-host',
58
+ status: 'emitted',
59
+ digest: server.artifact.artifactDigest,
60
+ publicRoutes: server.artifact.publicRoutes?.length ?? 0,
61
+ internalCapabilities: server.artifact.internalCapabilities?.length ?? 0,
62
+ httpContractDigest: server.httpContractDigest,
63
+ });
64
+ result.serverArtifact = {
65
+ digest: server.artifact.artifactDigest,
66
+ httpContractDigest: server.httpContractDigest,
67
+ schema: server.artifact.schema,
68
+ selectedRuntime: server.artifact.selectedRuntime,
69
+ };
70
+ }
71
+ const siteAuthoring = profile.sources || null;
72
+ if (siteAuthoring || assembly === 'rust-embedded') {
73
+ if (!siteAuthoring) {
74
+ throw new Error('rust-embedded requires delivery sources (SiteDeliveryContract); cannot assemble without embedded|filesystem|remote baselines');
75
+ }
76
+ const site = emitSiteDelivery(outDir, siteAuthoring, {
77
+ siteId: ctx.siteId,
78
+ });
79
+ result.steps.push({
80
+ kind: 'site-delivery',
81
+ digest: site.contract.contractDigest,
82
+ });
83
+ result.siteDelivery = {
84
+ digest: site.contract.contractDigest,
85
+ schema: site.contract.schema,
86
+ };
87
+ if (assembly === 'rust-embedded') {
88
+ const pack = emitEmbeddedPackaging(outDir, {
89
+ siteId: ctx.siteId,
90
+ contractDigest: site.contract.contractDigest,
91
+ });
92
+ result.steps.push({
93
+ kind: 'embedded-packaging',
94
+ digest: pack.index.indexDigest,
95
+ objectCount: pack.index.objectCount,
96
+ });
97
+ result.embeddedPackaging = {
98
+ digest: pack.index.indexDigest,
99
+ objectCount: pack.index.objectCount,
100
+ schema: pack.index.schema,
101
+ };
102
+ }
103
+ }
104
+ result.packDigest = ctx.pack?.packDigest || null;
105
+ result.assembleDigest = sha256Hex(canonicalJson({ ...result, assembleDigest: undefined }));
106
+ const vmzDir = path.join(outDir, '_vmz');
107
+ mkdirSync(vmzDir, { recursive: true });
108
+ const file = path.join(vmzDir, 'assemble-manifest.json');
109
+ writeFileSync(file, `${JSON.stringify(result, null, 2)}\n`, 'utf8');
110
+ return { manifest: result, path: file };
111
+ }
112
+ /**
113
+ * @param {string} outDir
114
+ * @param {any} ctx
115
+ */
116
+ export function emitBuildProof(outDir, ctx) {
117
+ const semanticIds = semanticIdsForAssembly(ctx.selection.assembly);
118
+ const slots = {
119
+ 'server-host': { status: 'not-applicable' },
120
+ 'static-delivery': { status: 'not-applicable' },
121
+ 'site-fallback': { status: 'not-applicable' },
122
+ 'asset-graph': { status: 'not-applicable' },
123
+ };
124
+ for (const id of semanticIds) {
125
+ if (id === 'static-delivery') {
126
+ const step = (ctx.assemble?.steps || []).find((s) => s.kind === 'static-cdn');
127
+ slots[id] = step
128
+ ? { status: 'emitted', detail: `digest=${String(step.digest).slice(0, 12)}` }
129
+ : { status: 'pending', detail: 'assembly requires static emit' };
130
+ }
131
+ else if (id === 'site-fallback') {
132
+ const siteStep = (ctx.assemble?.steps || []).find((s) => s.kind === 'site-delivery');
133
+ const packStep = (ctx.assemble?.steps || []).find((s) => s.kind === 'embedded-packaging');
134
+ if (siteStep && packStep) {
135
+ slots[id] = {
136
+ status: 'emitted',
137
+ detail: `contract=${String(siteStep.digest).slice(0, 12)}; pack=${String(packStep.digest).slice(0, 12)}; objects=${packStep.objectCount ?? '?'}`,
138
+ };
139
+ }
140
+ else if (siteStep && siteStep.status !== 'skipped') {
141
+ slots[id] = {
142
+ status: 'pending',
143
+ detail: 'site contract emitted; embedded packaging missing',
144
+ };
145
+ }
146
+ else {
147
+ slots[id] = { status: 'pending', detail: siteStep?.reason || 'no site sources' };
148
+ }
149
+ }
150
+ else if (id === 'server-host') {
151
+ const step = (ctx.assemble?.steps || []).find((s) => s.kind === 'server-host');
152
+ slots[id] =
153
+ step && step.status === 'emitted'
154
+ ? {
155
+ status: 'emitted',
156
+ detail: `digest=${String(step.digest).slice(0, 12)}; routes=${step.publicRoutes ?? 0}; internal=${step.internalCapabilities ?? 0}`,
157
+ }
158
+ : {
159
+ status: 'pending',
160
+ detail: step?.note || 'ServerArtifact not emitted',
161
+ };
162
+ }
163
+ else if (id === 'asset-graph') {
164
+ slots[id] = {
165
+ status: ctx.pack?.packDigest ? 'pack-digest' : 'pending',
166
+ detail: ctx.pack?.packDigest
167
+ ? `pack=${String(ctx.pack.packDigest).slice(0, 12)} units=${ctx.pack.unitCount ?? '?'}`
168
+ : 'pack missing',
169
+ };
170
+ }
171
+ }
172
+ const body = {
173
+ schema: BUILD_PROOF_SCHEMA,
174
+ profileId: ctx.selection.profileId,
175
+ assembly: ctx.selection.assembly,
176
+ selectionDigest: ctx.selection.digest || null,
177
+ packDigest: ctx.pack?.packDigest || null,
178
+ assembleDigest: ctx.assemble?.assembleDigest || null,
179
+ release: Boolean(ctx.release),
180
+ semanticIds,
181
+ slots,
182
+ productionReadyClaim: false,
183
+ note: 'Aggregate production-ready requires browser-production + cleared production-proof gaps (08)',
184
+ };
185
+ body.proofDigest = sha256Hex(canonicalJson({ ...body, proofDigest: undefined }));
186
+ const vmzDir = path.join(outDir, '_vmz');
187
+ mkdirSync(vmzDir, { recursive: true });
188
+ const file = path.join(vmzDir, 'build-proof.json');
189
+ writeFileSync(file, `${JSON.stringify(body, null, 2)}\n`, 'utf8');
190
+ return { proof: body, path: file };
191
+ }
@@ -0,0 +1,196 @@
1
+ /**
2
+ * A3-cdn: vendor-neutral CDN policy (cache / redirect / error) + local static host.
3
+ * Provider adapters only project the same contract — they must not change RouteId/canonical/CSP.
4
+ */
5
+ export declare const CDN_POLICY_MANIFEST_SCHEMA = "vmz.cdn.policy_manifest.v0";
6
+ export declare const CDN_ADAPTER_PROJECTION_SCHEMA = "vmz.cdn.adapter_projection.v0";
7
+ /** HTML: revalidate. Hashed/static assets: long immutable. */
8
+ export declare const CACHE_HTML = "public, max-age=0, must-revalidate";
9
+ export declare const CACHE_ASSET_IMMUTABLE = "public, max-age=31536000, immutable";
10
+ export declare const CACHE_META = "public, max-age=3600";
11
+ /**
12
+ * Build CDNPolicyManifest from StaticDeliveryManifest (+ optional redirects / locale artifact).
13
+ * Locale-prefixed HTML gets LocaleId-encoded cache keys; Accept-Language must not steal body.
14
+ * @param {Record<string, any>} staticManifest
15
+ * @param {{
16
+ * redirects?: Array<{ from: string, to: string, status?: number, reason?: string }>,
17
+ * localeArtifact?: Record<string, any> | null,
18
+ * }} [opts]
19
+ */
20
+ export declare function buildCdnPolicyManifest(staticManifest: any, opts?: {}): {
21
+ schema: string;
22
+ applicationId: any;
23
+ deliveryProfile: string;
24
+ origin: string;
25
+ spaFallback: boolean;
26
+ staticManifestDigest: any;
27
+ redirects: any[];
28
+ headers: ({
29
+ match: string;
30
+ headers: {
31
+ 'cache-control': string;
32
+ 'x-robots-tag'?: undefined;
33
+ };
34
+ } | {
35
+ match: string;
36
+ headers: {
37
+ 'cache-control': string;
38
+ 'x-robots-tag': string;
39
+ };
40
+ })[];
41
+ errorDocuments: any;
42
+ routes: any[];
43
+ localeCache: {
44
+ strategy: string;
45
+ varyAcceptLanguage: boolean;
46
+ defaultLocale: any;
47
+ routeCount: number;
48
+ locales: any[];
49
+ };
50
+ };
51
+ /**
52
+ * Write CDN policy + adapter projections under dist/_vmz.
53
+ * @param {string} distDir
54
+ * @param {Record<string, any>} staticManifest
55
+ * @param {{ redirects?: Array<{ from: string, to: string, status?: number, reason?: string }> }} [opts]
56
+ */
57
+ export declare function emitCdnPolicy(distDir: any, staticManifest: any, opts?: {}): {
58
+ policy: {
59
+ schema: string;
60
+ applicationId: any;
61
+ deliveryProfile: string;
62
+ origin: string;
63
+ spaFallback: boolean;
64
+ staticManifestDigest: any;
65
+ redirects: any[];
66
+ headers: ({
67
+ match: string;
68
+ headers: {
69
+ 'cache-control': string;
70
+ 'x-robots-tag'?: undefined;
71
+ };
72
+ } | {
73
+ match: string;
74
+ headers: {
75
+ 'cache-control': string;
76
+ 'x-robots-tag': string;
77
+ };
78
+ })[];
79
+ errorDocuments: any;
80
+ routes: any[];
81
+ localeCache: {
82
+ strategy: string;
83
+ varyAcceptLanguage: boolean;
84
+ defaultLocale: any;
85
+ routeCount: number;
86
+ locales: any[];
87
+ };
88
+ };
89
+ adapters: {
90
+ 'local-static': {
91
+ schema: string;
92
+ adapterId: string;
93
+ policyDigest: any;
94
+ host: string;
95
+ spaFallback: boolean;
96
+ redirects: any;
97
+ headers: any;
98
+ errorDocuments: any;
99
+ files: {
100
+ _headers?: undefined;
101
+ _redirects?: undefined;
102
+ };
103
+ } | {
104
+ schema: string;
105
+ adapterId: string;
106
+ policyDigest: any;
107
+ host: string;
108
+ spaFallback: boolean;
109
+ redirects: any;
110
+ headers: any;
111
+ errorDocuments: any;
112
+ files: {
113
+ _headers: string;
114
+ _redirects: string;
115
+ };
116
+ };
117
+ netlify: {
118
+ schema: string;
119
+ adapterId: string;
120
+ policyDigest: any;
121
+ host: string;
122
+ spaFallback: boolean;
123
+ redirects: any;
124
+ headers: any;
125
+ errorDocuments: any;
126
+ files: {
127
+ _headers?: undefined;
128
+ _redirects?: undefined;
129
+ };
130
+ } | {
131
+ schema: string;
132
+ adapterId: string;
133
+ policyDigest: any;
134
+ host: string;
135
+ spaFallback: boolean;
136
+ redirects: any;
137
+ headers: any;
138
+ errorDocuments: any;
139
+ files: {
140
+ _headers: string;
141
+ _redirects: string;
142
+ };
143
+ };
144
+ };
145
+ };
146
+ /**
147
+ * Project vendor-neutral policy to an adapter. Must preserve redirect targets and forbid SPA fallback.
148
+ * @param {Record<string, any>} policy
149
+ * @param {'local-static' | 'netlify'} adapterId
150
+ */
151
+ export declare function projectCdnAdapter(policy: any, adapterId: any): {
152
+ schema: string;
153
+ adapterId: string;
154
+ policyDigest: any;
155
+ host: string;
156
+ spaFallback: boolean;
157
+ redirects: any;
158
+ headers: any;
159
+ errorDocuments: any;
160
+ files: {
161
+ _headers?: undefined;
162
+ _redirects?: undefined;
163
+ };
164
+ } | {
165
+ schema: string;
166
+ adapterId: string;
167
+ policyDigest: any;
168
+ host: string;
169
+ spaFallback: boolean;
170
+ redirects: any;
171
+ headers: any;
172
+ errorDocuments: any;
173
+ files: {
174
+ _headers: string;
175
+ _redirects: string;
176
+ };
177
+ };
178
+ /**
179
+ * Local static host that applies CDNPolicyManifest (redirects, cache headers, 404 doc).
180
+ * @param {string} distDir
181
+ * @param {Record<string, any>} policy
182
+ * @param {{ host?: string, port?: number }} [opts]
183
+ * @returns {Promise<{ host: string, port: number, baseUrl: string, close: () => Promise<void> }>}
184
+ */
185
+ export declare function listenLocalStaticHost(distDir: any, policy: any, opts?: {}): Promise<unknown>;
186
+ /**
187
+ * @param {string} distDir
188
+ * @param {Record<string, any>} policy
189
+ */
190
+ export declare function createLocalStaticHandler(distDir: any, policy: any): (req: any, res: any) => void;
191
+ /**
192
+ * Minimal glob matcher for CDN header rules (html / js|css|mjs / exact / prefix).
193
+ * @param {string} pattern
194
+ * @param {string} pathname
195
+ */
196
+ export declare function matchGlob(pattern: any, pathname: any): any;