@pwfabric/cli 0.0.0-stage → 1.0.0-rc.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 +202 -0
- package/README.md +122 -2
- package/dist/args.d.ts +11 -0
- package/dist/args.js +43 -0
- package/dist/args.js.map +1 -0
- package/dist/bin.d.ts +2 -0
- package/dist/bin.js +10 -0
- package/dist/bin.js.map +1 -0
- package/dist/commands/add.d.ts +3 -0
- package/dist/commands/add.js +56 -0
- package/dist/commands/add.js.map +1 -0
- package/dist/commands/build.d.ts +3 -0
- package/dist/commands/build.js +55 -0
- package/dist/commands/build.js.map +1 -0
- package/dist/commands/create.d.ts +9 -0
- package/dist/commands/create.js +119 -0
- package/dist/commands/create.js.map +1 -0
- package/dist/commands/dev.d.ts +12 -0
- package/dist/commands/dev.js +107 -0
- package/dist/commands/dev.js.map +1 -0
- package/dist/commands/lib/flags.d.ts +10 -0
- package/dist/commands/lib/flags.js +33 -0
- package/dist/commands/lib/flags.js.map +1 -0
- package/dist/commands/lib/identity.d.ts +38 -0
- package/dist/commands/lib/identity.js +120 -0
- package/dist/commands/lib/identity.js.map +1 -0
- package/dist/commands/lib/project.d.ts +34 -0
- package/dist/commands/lib/project.js +78 -0
- package/dist/commands/lib/project.js.map +1 -0
- package/dist/commands/lib/report.d.ts +15 -0
- package/dist/commands/lib/report.js +75 -0
- package/dist/commands/lib/report.js.map +1 -0
- package/dist/commands/lib/starter.d.ts +41 -0
- package/dist/commands/lib/starter.js +136 -0
- package/dist/commands/lib/starter.js.map +1 -0
- package/dist/commands/lib/static-server.d.ts +45 -0
- package/dist/commands/lib/static-server.js +176 -0
- package/dist/commands/lib/static-server.js.map +1 -0
- package/dist/commands/pack.d.ts +5 -0
- package/dist/commands/pack.js +56 -0
- package/dist/commands/pack.js.map +1 -0
- package/dist/commands/registry.d.ts +7 -0
- package/dist/commands/registry.js +16 -0
- package/dist/commands/registry.js.map +1 -0
- package/dist/commands/run.d.ts +14 -0
- package/dist/commands/run.js +79 -0
- package/dist/commands/run.js.map +1 -0
- package/dist/commands/types.d.ts +34 -0
- package/dist/commands/types.js +10 -0
- package/dist/commands/types.js.map +1 -0
- package/dist/commands/validate.d.ts +6 -0
- package/dist/commands/validate.js +33 -0
- package/dist/commands/validate.js.map +1 -0
- package/dist/dev/assemble.d.ts +47 -0
- package/dist/dev/assemble.js +339 -0
- package/dist/dev/assemble.js.map +1 -0
- package/dist/dev/compile.d.ts +54 -0
- package/dist/dev/compile.js +215 -0
- package/dist/dev/compile.js.map +1 -0
- package/dist/dev/csp.d.ts +67 -0
- package/dist/dev/csp.js +260 -0
- package/dist/dev/csp.js.map +1 -0
- package/dist/dev/diagnostics.d.ts +21 -0
- package/dist/dev/diagnostics.js +22 -0
- package/dist/dev/diagnostics.js.map +1 -0
- package/dist/dev/envelope.d.ts +92 -0
- package/dist/dev/envelope.js +154 -0
- package/dist/dev/envelope.js.map +1 -0
- package/dist/dev/media.d.ts +53 -0
- package/dist/dev/media.js +128 -0
- package/dist/dev/media.js.map +1 -0
- package/dist/dev/needs-host.d.ts +2 -0
- package/dist/dev/needs-host.js +32 -0
- package/dist/dev/needs-host.js.map +1 -0
- package/dist/dev/output.d.ts +9 -0
- package/dist/dev/output.js +32 -0
- package/dist/dev/output.js.map +1 -0
- package/dist/dev/overlay.d.ts +21 -0
- package/dist/dev/overlay.js +59 -0
- package/dist/dev/overlay.js.map +1 -0
- package/dist/dev/server.d.ts +27 -0
- package/dist/dev/server.js +268 -0
- package/dist/dev/server.js.map +1 -0
- package/dist/dev/shell.d.ts +94 -0
- package/dist/dev/shell.js +267 -0
- package/dist/dev/shell.js.map +1 -0
- package/dist/dev/sources.d.ts +45 -0
- package/dist/dev/sources.js +165 -0
- package/dist/dev/sources.js.map +1 -0
- package/dist/dev/theme.d.ts +51 -0
- package/dist/dev/theme.js +185 -0
- package/dist/dev/theme.js.map +1 -0
- package/dist/dev/types.d.ts +40 -0
- package/dist/dev/types.js +11 -0
- package/dist/dev/types.js.map +1 -0
- package/dist/dev/watcher.d.ts +29 -0
- package/dist/dev/watcher.js +150 -0
- package/dist/dev/watcher.js.map +1 -0
- package/dist/host/definitions.d.ts +61 -0
- package/dist/host/definitions.js +136 -0
- package/dist/host/definitions.js.map +1 -0
- package/dist/host/http.d.ts +39 -0
- package/dist/host/http.js +156 -0
- package/dist/host/http.js.map +1 -0
- package/dist/host/local-host.d.ts +59 -0
- package/dist/host/local-host.js +420 -0
- package/dist/host/local-host.js.map +1 -0
- package/dist/host/oidc.d.ts +46 -0
- package/dist/host/oidc.js +192 -0
- package/dist/host/oidc.js.map +1 -0
- package/dist/host/query.d.ts +35 -0
- package/dist/host/query.js +158 -0
- package/dist/host/query.js.map +1 -0
- package/dist/host/receipts.d.ts +25 -0
- package/dist/host/receipts.js +72 -0
- package/dist/host/receipts.js.map +1 -0
- package/dist/host/records.d.ts +73 -0
- package/dist/host/records.js +229 -0
- package/dist/host/records.js.map +1 -0
- package/dist/host/tokens.d.ts +28 -0
- package/dist/host/tokens.js +52 -0
- package/dist/host/tokens.js.map +1 -0
- package/dist/host/types.d.ts +32 -0
- package/dist/host/types.js +11 -0
- package/dist/host/types.js.map +1 -0
- package/dist/index.d.ts +18 -0
- package/dist/index.js +51 -0
- package/dist/index.js.map +1 -0
- package/package.json +66 -3
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `pwf pack [dir]` — the deterministic `.pwpack` archive of a valid folder.
|
|
3
|
+
*/
|
|
4
|
+
import { mkdir, writeFile } from 'node:fs/promises';
|
|
5
|
+
import { dirname, join } from 'node:path';
|
|
6
|
+
import { hashPack, packContent, writePwpack } from '@pwfabric/pack';
|
|
7
|
+
import { guard, stringFlag } from './lib/flags.js';
|
|
8
|
+
import { readProject, resolveFrom } from './lib/project.js';
|
|
9
|
+
import { countLine, printIssues, validateProject } from './lib/report.js';
|
|
10
|
+
/** `<name>-<version>.pwpack`, where name is the last segment of the pack id. */
|
|
11
|
+
export function archiveName(id, version) {
|
|
12
|
+
const name = id.split('/').pop()?.replace(/^@/, '') || 'pack';
|
|
13
|
+
return `${name}-${version}.pwpack`;
|
|
14
|
+
}
|
|
15
|
+
export async function runPack(args, io) {
|
|
16
|
+
const root = resolveFrom(io.cwd, args.positionals[0]);
|
|
17
|
+
const pack = await readProject(root);
|
|
18
|
+
const result = await validateProject(root, pack);
|
|
19
|
+
if (!result.ok || !result.identity) {
|
|
20
|
+
printIssues(io, result.issues);
|
|
21
|
+
io.err(`pwf pack: ${root} is not valid (${countLine(result.issues)}); nothing written`);
|
|
22
|
+
return 1;
|
|
23
|
+
}
|
|
24
|
+
printIssues(io, result.issues.filter((i) => i.severity === 'warning'));
|
|
25
|
+
const { id, version } = result.identity;
|
|
26
|
+
const outFlag = stringFlag(args, 'out');
|
|
27
|
+
const out = outFlag ? resolveFrom(io.cwd, outFlag) : join(root, archiveName(id, version));
|
|
28
|
+
// The archive carries the pack content only: an author's tooling never
|
|
29
|
+
// ships, and the archive hashes the same as the folder it came from.
|
|
30
|
+
const content = packContent(pack);
|
|
31
|
+
const bytes = await writePwpack(content);
|
|
32
|
+
await mkdir(dirname(out), { recursive: true });
|
|
33
|
+
await writeFile(out, bytes);
|
|
34
|
+
const left = pack.files.size - content.files.size;
|
|
35
|
+
io.out(`Packed ${id}@${version}`);
|
|
36
|
+
io.out(` file ${out}`);
|
|
37
|
+
io.out(` size ${bytes.byteLength} bytes, ${content.files.size} files${left > 0 ? ` (${left} outside the pack content left out)` : ''}`);
|
|
38
|
+
io.out(` hash ${hashPack(content)}`);
|
|
39
|
+
return 0;
|
|
40
|
+
}
|
|
41
|
+
export const pack = {
|
|
42
|
+
name: 'pack',
|
|
43
|
+
summary: 'Write the deterministic .pwpack archive of a folder',
|
|
44
|
+
usage: `pwf pack [dir] [--out <file>]
|
|
45
|
+
|
|
46
|
+
dir the pwpack folder (default: the current folder)
|
|
47
|
+
--out <file> where to write (default <dir>/<name>-<version>.pwpack)
|
|
48
|
+
|
|
49
|
+
Validates first and refuses on errors. The archive holds the pack content
|
|
50
|
+
only — pwpack.json, LICENSE, NOTICE, README.md, app/, atoms/ and media/ —
|
|
51
|
+
never .pwf/, .gitignore or the author's tooling (package.json, scripts/, …).
|
|
52
|
+
The same folder always gives the same bytes; the printed hash is the
|
|
53
|
+
content hash pins use.`,
|
|
54
|
+
run: (args, io) => guard('pack', io, () => runPack(args, io)),
|
|
55
|
+
};
|
|
56
|
+
//# sourceMappingURL=pack.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"pack.js","sourceRoot":"","sources":["../../src/commands/pack.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * `pwf pack [dir]` — the deterministic `.pwpack` archive of a valid folder.\n */\nimport { mkdir, writeFile } from 'node:fs/promises'\nimport { dirname, join } from 'node:path'\nimport { hashPack, packContent, writePwpack } from '@pwfabric/pack'\nimport type { Command, CommandIO, ParsedArgs } from './types.js'\nimport { guard, stringFlag } from './lib/flags.js'\nimport { readProject, resolveFrom } from './lib/project.js'\nimport { countLine, printIssues, validateProject } from './lib/report.js'\n\n/** `<name>-<version>.pwpack`, where name is the last segment of the pack id. */\nexport function archiveName(id: string, version: string): string {\n const name = id.split('/').pop()?.replace(/^@/, '') || 'pack'\n return `${name}-${version}.pwpack`\n}\n\nexport async function runPack(args: ParsedArgs, io: CommandIO): Promise<number> {\n const root = resolveFrom(io.cwd, args.positionals[0])\n const pack = await readProject(root)\n const result = await validateProject(root, pack)\n if (!result.ok || !result.identity) {\n printIssues(io, result.issues)\n io.err(`pwf pack: ${root} is not valid (${countLine(result.issues)}); nothing written`)\n return 1\n }\n printIssues(\n io,\n result.issues.filter((i) => i.severity === 'warning')\n )\n const { id, version } = result.identity\n const outFlag = stringFlag(args, 'out')\n const out = outFlag ? resolveFrom(io.cwd, outFlag) : join(root, archiveName(id, version))\n // The archive carries the pack content only: an author's tooling never\n // ships, and the archive hashes the same as the folder it came from.\n const content = packContent(pack)\n const bytes = await writePwpack(content)\n await mkdir(dirname(out), { recursive: true })\n await writeFile(out, bytes)\n const left = pack.files.size - content.files.size\n io.out(`Packed ${id}@${version}`)\n io.out(` file ${out}`)\n io.out(` size ${bytes.byteLength} bytes, ${content.files.size} files${left > 0 ? ` (${left} outside the pack content left out)` : ''}`)\n io.out(` hash ${hashPack(content)}`)\n return 0\n}\n\nexport const pack: Command = {\n name: 'pack',\n summary: 'Write the deterministic .pwpack archive of a folder',\n usage: `pwf pack [dir] [--out <file>]\n\n dir the pwpack folder (default: the current folder)\n --out <file> where to write (default <dir>/<name>-<version>.pwpack)\n\nValidates first and refuses on errors. The archive holds the pack content\nonly — pwpack.json, LICENSE, NOTICE, README.md, app/, atoms/ and media/ —\nnever .pwf/, .gitignore or the author's tooling (package.json, scripts/, …).\nThe same folder always gives the same bytes; the printed hash is the\ncontent hash pins use.`,\n run: (args, io) => guard('pack', io, () => runPack(args, io)),\n}\n"]}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import type { Command } from './types.js';
|
|
2
|
+
/**
|
|
3
|
+
* Every `pwf` command. Lanes add their command module here and nowhere else.
|
|
4
|
+
* Order is the order `pwf help` prints.
|
|
5
|
+
*/
|
|
6
|
+
export declare const COMMANDS: Command[];
|
|
7
|
+
export declare function findCommand(name: string): Command | undefined;
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { create } from './create.js';
|
|
2
|
+
import { devCommand } from './dev.js';
|
|
3
|
+
import { buildCommand } from './build.js';
|
|
4
|
+
import { validate } from './validate.js';
|
|
5
|
+
import { pack } from './pack.js';
|
|
6
|
+
import { add } from './add.js';
|
|
7
|
+
import { run } from './run.js';
|
|
8
|
+
/**
|
|
9
|
+
* Every `pwf` command. Lanes add their command module here and nowhere else.
|
|
10
|
+
* Order is the order `pwf help` prints.
|
|
11
|
+
*/
|
|
12
|
+
export const COMMANDS = [create, devCommand, buildCommand, validate, pack, add, run];
|
|
13
|
+
export function findCommand(name) {
|
|
14
|
+
return COMMANDS.find((c) => c.name === name);
|
|
15
|
+
}
|
|
16
|
+
//# sourceMappingURL=registry.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"registry.js","sourceRoot":"","sources":["../../src/commands/registry.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,MAAM,EAAE,MAAM,aAAa,CAAA;AACpC,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAA;AACrC,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AACzC,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAA;AACxC,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAA;AAChC,OAAO,EAAE,GAAG,EAAE,MAAM,UAAU,CAAA;AAC9B,OAAO,EAAE,GAAG,EAAE,MAAM,UAAU,CAAA;AAE9B;;;GAGG;AACH,MAAM,CAAC,MAAM,QAAQ,GAAc,CAAC,MAAM,EAAE,UAAU,EAAE,YAAY,EAAE,QAAQ,EAAE,IAAI,EAAE,GAAG,EAAE,GAAG,CAAC,CAAA;AAE/F,MAAM,UAAU,WAAW,CAAC,IAAY;IACtC,OAAO,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,KAAK,IAAI,CAAC,CAAA;AAC9C,CAAC","sourcesContent":["import type { Command } from './types.js'\nimport { create } from './create.js'\nimport { devCommand } from './dev.js'\nimport { buildCommand } from './build.js'\nimport { validate } from './validate.js'\nimport { pack } from './pack.js'\nimport { add } from './add.js'\nimport { run } from './run.js'\n\n/**\n * Every `pwf` command. Lanes add their command module here and nowhere else.\n * Order is the order `pwf help` prints.\n */\nexport const COMMANDS: Command[] = [create, devCommand, buildCommand, validate, pack, add, run]\n\nexport function findCommand(name: string): Command | undefined {\n return COMMANDS.find((c) => c.name === name)\n}\n"]}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { Command, CommandIO, ParsedArgs } from './types.js';
|
|
2
|
+
import { type StaticServer, type StaticSource } from './lib/static-server.js';
|
|
3
|
+
export declare const DEFAULT_RUN_PORT = 4700;
|
|
4
|
+
/** Resolves when the process is asked to stop (Ctrl-C or SIGTERM). */
|
|
5
|
+
export declare function untilSignal(): Promise<void>;
|
|
6
|
+
export declare function parsePort(value: string | undefined): number;
|
|
7
|
+
/** The source to serve: a folder with an `index.html`, or a `.pwapp` archive opened in memory. */
|
|
8
|
+
export declare function openRunSource(path: string): Promise<StaticSource>;
|
|
9
|
+
export interface RunOptions {
|
|
10
|
+
/** Resolves when the server should stop. Default: SIGINT or SIGTERM. */
|
|
11
|
+
readonly until?: (server: StaticServer) => Promise<void>;
|
|
12
|
+
}
|
|
13
|
+
export declare function runRun(args: ParsedArgs, io: CommandIO, options?: RunOptions): Promise<number>;
|
|
14
|
+
export declare const run: Command;
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `pwf run <dir|file.pwapp>` — serve a built pwapp locally.
|
|
3
|
+
*/
|
|
4
|
+
import { readFile, stat } from 'node:fs/promises';
|
|
5
|
+
import { join } from 'node:path';
|
|
6
|
+
import { readPwpack } from '@pwfabric/pack';
|
|
7
|
+
import { guard, stringFlag, UsageError } from './lib/flags.js';
|
|
8
|
+
import { resolveFrom } from './lib/project.js';
|
|
9
|
+
import { startStaticServer } from './lib/static-server.js';
|
|
10
|
+
export const DEFAULT_RUN_PORT = 4700;
|
|
11
|
+
/** Resolves when the process is asked to stop (Ctrl-C or SIGTERM). */
|
|
12
|
+
export function untilSignal() {
|
|
13
|
+
return new Promise((done) => {
|
|
14
|
+
const stop = () => {
|
|
15
|
+
process.off('SIGINT', stop);
|
|
16
|
+
process.off('SIGTERM', stop);
|
|
17
|
+
done();
|
|
18
|
+
};
|
|
19
|
+
process.on('SIGINT', stop);
|
|
20
|
+
process.on('SIGTERM', stop);
|
|
21
|
+
});
|
|
22
|
+
}
|
|
23
|
+
export function parsePort(value) {
|
|
24
|
+
if (value === undefined)
|
|
25
|
+
return DEFAULT_RUN_PORT;
|
|
26
|
+
const port = Number(value);
|
|
27
|
+
if (!/^\d+$/.test(value) || port > 65535)
|
|
28
|
+
throw new UsageError(`--port "${value}" is not a port number`);
|
|
29
|
+
return port;
|
|
30
|
+
}
|
|
31
|
+
/** The source to serve: a folder with an `index.html`, or a `.pwapp` archive opened in memory. */
|
|
32
|
+
export async function openRunSource(path) {
|
|
33
|
+
const st = await stat(path).catch(() => null);
|
|
34
|
+
if (!st)
|
|
35
|
+
throw new Error(`no such file or folder: ${path}`);
|
|
36
|
+
if (st.isDirectory()) {
|
|
37
|
+
const index = await stat(join(path, 'index.html')).catch(() => null);
|
|
38
|
+
if (!index?.isFile())
|
|
39
|
+
throw new Error(`${path} has no index.html; build the app first (pwf build)`);
|
|
40
|
+
return { dir: path };
|
|
41
|
+
}
|
|
42
|
+
const { files } = await readPwpack(new Uint8Array(await readFile(path)));
|
|
43
|
+
if (!files.has('index.html'))
|
|
44
|
+
throw new Error(`${path} has no index.html at its root; it is not a built pwapp`);
|
|
45
|
+
return { files };
|
|
46
|
+
}
|
|
47
|
+
export async function runRun(args, io, options = {}) {
|
|
48
|
+
const target = args.positionals[0];
|
|
49
|
+
if (target === undefined)
|
|
50
|
+
throw new UsageError('missing <dir|file.pwapp>');
|
|
51
|
+
const port = parsePort(stringFlag(args, 'port'));
|
|
52
|
+
const hostname = stringFlag(args, 'host') ?? '127.0.0.1';
|
|
53
|
+
const source = await openRunSource(resolveFrom(io.cwd, target));
|
|
54
|
+
const server = await startStaticServer({ source, port, hostname });
|
|
55
|
+
io.out(`Serving ${target} at ${server.url}`);
|
|
56
|
+
io.out('Press Ctrl-C to stop.');
|
|
57
|
+
try {
|
|
58
|
+
await (options.until ?? untilSignal)(server);
|
|
59
|
+
}
|
|
60
|
+
finally {
|
|
61
|
+
await server.close();
|
|
62
|
+
}
|
|
63
|
+
return 0;
|
|
64
|
+
}
|
|
65
|
+
export const run = {
|
|
66
|
+
name: 'run',
|
|
67
|
+
summary: 'Serve a built pwapp (folder or .pwapp) on a local port',
|
|
68
|
+
usage: `pwf run <dir|file.pwapp> [--port <n>] [--host <name>]
|
|
69
|
+
|
|
70
|
+
<dir> a built pwapp folder with an index.html (see pwf build)
|
|
71
|
+
<file.pwapp> a packaged pwapp (gzipped tar, read like a .pwpack), served from memory
|
|
72
|
+
--port <n> port to listen on (default ${DEFAULT_RUN_PORT}; 0 picks a free one)
|
|
73
|
+
--host <name> interface to bind (default 127.0.0.1)
|
|
74
|
+
|
|
75
|
+
Page paths without a file extension are answered with index.html and a
|
|
76
|
+
<base href="/">, so path-routed apps work at any depth; a missing asset is a 404.`,
|
|
77
|
+
run: (args, io) => guard('run', io, () => runRun(args, io)),
|
|
78
|
+
};
|
|
79
|
+
//# sourceMappingURL=run.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"run.js","sourceRoot":"","sources":["../../src/commands/run.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * `pwf run <dir|file.pwapp>` — serve a built pwapp locally.\n */\nimport { readFile, stat } from 'node:fs/promises'\nimport { join } from 'node:path'\nimport { readPwpack } from '@pwfabric/pack'\nimport type { Command, CommandIO, ParsedArgs } from './types.js'\nimport { guard, stringFlag, UsageError } from './lib/flags.js'\nimport { resolveFrom } from './lib/project.js'\nimport { startStaticServer, type StaticServer, type StaticSource } from './lib/static-server.js'\n\nexport const DEFAULT_RUN_PORT = 4700\n\n/** Resolves when the process is asked to stop (Ctrl-C or SIGTERM). */\nexport function untilSignal(): Promise<void> {\n return new Promise((done) => {\n const stop = (): void => {\n process.off('SIGINT', stop)\n process.off('SIGTERM', stop)\n done()\n }\n process.on('SIGINT', stop)\n process.on('SIGTERM', stop)\n })\n}\n\nexport function parsePort(value: string | undefined): number {\n if (value === undefined) return DEFAULT_RUN_PORT\n const port = Number(value)\n if (!/^\\d+$/.test(value) || port > 65535) throw new UsageError(`--port \"${value}\" is not a port number`)\n return port\n}\n\n/** The source to serve: a folder with an `index.html`, or a `.pwapp` archive opened in memory. */\nexport async function openRunSource(path: string): Promise<StaticSource> {\n const st = await stat(path).catch(() => null)\n if (!st) throw new Error(`no such file or folder: ${path}`)\n if (st.isDirectory()) {\n const index = await stat(join(path, 'index.html')).catch(() => null)\n if (!index?.isFile()) throw new Error(`${path} has no index.html; build the app first (pwf build)`)\n return { dir: path }\n }\n const { files } = await readPwpack(new Uint8Array(await readFile(path)))\n if (!files.has('index.html')) throw new Error(`${path} has no index.html at its root; it is not a built pwapp`)\n return { files }\n}\n\nexport interface RunOptions {\n /** Resolves when the server should stop. Default: SIGINT or SIGTERM. */\n readonly until?: (server: StaticServer) => Promise<void>\n}\n\nexport async function runRun(args: ParsedArgs, io: CommandIO, options: RunOptions = {}): Promise<number> {\n const target = args.positionals[0]\n if (target === undefined) throw new UsageError('missing <dir|file.pwapp>')\n const port = parsePort(stringFlag(args, 'port'))\n const hostname = stringFlag(args, 'host') ?? '127.0.0.1'\n const source = await openRunSource(resolveFrom(io.cwd, target))\n const server = await startStaticServer({ source, port, hostname })\n io.out(`Serving ${target} at ${server.url}`)\n io.out('Press Ctrl-C to stop.')\n try {\n await (options.until ?? untilSignal)(server)\n } finally {\n await server.close()\n }\n return 0\n}\n\nexport const run: Command = {\n name: 'run',\n summary: 'Serve a built pwapp (folder or .pwapp) on a local port',\n usage: `pwf run <dir|file.pwapp> [--port <n>] [--host <name>]\n\n <dir> a built pwapp folder with an index.html (see pwf build)\n <file.pwapp> a packaged pwapp (gzipped tar, read like a .pwpack), served from memory\n --port <n> port to listen on (default ${DEFAULT_RUN_PORT}; 0 picks a free one)\n --host <name> interface to bind (default 127.0.0.1)\n\nPage paths without a file extension are answered with index.html and a\n<base href=\"/\">, so path-routed apps work at any depth; a missing asset is a 404.`,\n run: (args, io) => guard('run', io, () => runRun(args, io)),\n}\n"]}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The contract every `pwf` command implements.
|
|
3
|
+
*
|
|
4
|
+
* A command is a plain object registered in ./registry.ts. It never calls
|
|
5
|
+
* `process.exit` and never writes to `process.stdout` directly: it writes
|
|
6
|
+
* through the `io` it is given and returns an exit code. That keeps every
|
|
7
|
+
* command testable in-process.
|
|
8
|
+
*/
|
|
9
|
+
export interface CommandIO {
|
|
10
|
+
/** Working directory the command runs in (absolute). */
|
|
11
|
+
readonly cwd: string;
|
|
12
|
+
/** Normal output. */
|
|
13
|
+
out(line: string): void;
|
|
14
|
+
/** Diagnostics and errors. */
|
|
15
|
+
err(line: string): void;
|
|
16
|
+
/** Environment variables visible to the command. */
|
|
17
|
+
readonly env: Readonly<Record<string, string | undefined>>;
|
|
18
|
+
}
|
|
19
|
+
export interface ParsedArgs {
|
|
20
|
+
/** Positional arguments after the command name. */
|
|
21
|
+
readonly positionals: readonly string[];
|
|
22
|
+
/** `--flag value` and `--flag=value` become strings; bare `--flag` becomes true. */
|
|
23
|
+
readonly flags: Readonly<Record<string, string | boolean>>;
|
|
24
|
+
}
|
|
25
|
+
export interface Command {
|
|
26
|
+
/** The word after `pwf`, e.g. `create`. */
|
|
27
|
+
readonly name: string;
|
|
28
|
+
/** One line shown by `pwf help`. */
|
|
29
|
+
readonly summary: string;
|
|
30
|
+
/** Usage line, e.g. `pwf create <name> [--dir <path>]`. */
|
|
31
|
+
readonly usage: string;
|
|
32
|
+
/** Runs the command. Resolves to the process exit code (0 = success). */
|
|
33
|
+
run(args: ParsedArgs, io: CommandIO): Promise<number>;
|
|
34
|
+
}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The contract every `pwf` command implements.
|
|
3
|
+
*
|
|
4
|
+
* A command is a plain object registered in ./registry.ts. It never calls
|
|
5
|
+
* `process.exit` and never writes to `process.stdout` directly: it writes
|
|
6
|
+
* through the `io` it is given and returns an exit code. That keeps every
|
|
7
|
+
* command testable in-process.
|
|
8
|
+
*/
|
|
9
|
+
export {};
|
|
10
|
+
//# sourceMappingURL=types.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.js","sourceRoot":"","sources":["../../src/commands/types.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG","sourcesContent":["/**\n * The contract every `pwf` command implements.\n *\n * A command is a plain object registered in ./registry.ts. It never calls\n * `process.exit` and never writes to `process.stdout` directly: it writes\n * through the `io` it is given and returns an exit code. That keeps every\n * command testable in-process.\n */\n\nexport interface CommandIO {\n /** Working directory the command runs in (absolute). */\n readonly cwd: string\n /** Normal output. */\n out(line: string): void\n /** Diagnostics and errors. */\n err(line: string): void\n /** Environment variables visible to the command. */\n readonly env: Readonly<Record<string, string | undefined>>\n}\n\nexport interface ParsedArgs {\n /** Positional arguments after the command name. */\n readonly positionals: readonly string[]\n /** `--flag value` and `--flag=value` become strings; bare `--flag` becomes true. */\n readonly flags: Readonly<Record<string, string | boolean>>\n}\n\nexport interface Command {\n /** The word after `pwf`, e.g. `create`. */\n readonly name: string\n /** One line shown by `pwf help`. */\n readonly summary: string\n /** Usage line, e.g. `pwf create <name> [--dir <path>]`. */\n readonly usage: string\n /** Runs the command. Resolves to the process exit code (0 = success). */\n run(args: ParsedArgs, io: CommandIO): Promise<number>\n}\n"]}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `pwf validate [dir]` — checks a pwpack folder and its pinned packs.
|
|
3
|
+
*/
|
|
4
|
+
import type { Command, CommandIO, ParsedArgs } from './types.js';
|
|
5
|
+
export declare function runValidate(args: ParsedArgs, io: CommandIO): Promise<number>;
|
|
6
|
+
export declare const validate: Command;
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { boolFlag, guard } from './lib/flags.js';
|
|
2
|
+
import { readProject, resolveFrom } from './lib/project.js';
|
|
3
|
+
import { countLine, printIssues, validateProject } from './lib/report.js';
|
|
4
|
+
export async function runValidate(args, io) {
|
|
5
|
+
const root = resolveFrom(io.cwd, args.positionals[0]);
|
|
6
|
+
const result = await validateProject(root, await readProject(root));
|
|
7
|
+
if (boolFlag(args, 'json')) {
|
|
8
|
+
io.out(JSON.stringify(result, null, 2));
|
|
9
|
+
return result.ok ? 0 : 1;
|
|
10
|
+
}
|
|
11
|
+
const who = result.identity ? `${result.identity.id}@${result.identity.version}` : root;
|
|
12
|
+
printIssues(io, result.issues);
|
|
13
|
+
const summary = `${who}: ${result.ok ? 'valid' : 'invalid'} (${countLine(result.issues)}; layout ${result.layout}; ${result.atoms.length} atoms)`;
|
|
14
|
+
if (result.ok)
|
|
15
|
+
io.out(summary);
|
|
16
|
+
else
|
|
17
|
+
io.err(summary);
|
|
18
|
+
return result.ok ? 0 : 1;
|
|
19
|
+
}
|
|
20
|
+
export const validate = {
|
|
21
|
+
name: 'validate',
|
|
22
|
+
summary: 'Check a pwpack folder and the packs it pins',
|
|
23
|
+
usage: `pwf validate [dir] [--json]
|
|
24
|
+
|
|
25
|
+
dir the pwpack folder (default: the current folder)
|
|
26
|
+
--json print the raw result (ok, issues, identity, layout, atoms)
|
|
27
|
+
|
|
28
|
+
Every packs[] pin is looked up in .pwf/packs/<id>@<version>/: a build that is
|
|
29
|
+
not there is a warning, one whose content hash differs from the pin is an
|
|
30
|
+
error. Exit code 1 when there is any error, 0 otherwise.`,
|
|
31
|
+
run: (args, io) => guard('validate', io, () => runValidate(args, io)),
|
|
32
|
+
};
|
|
33
|
+
//# sourceMappingURL=validate.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"validate.js","sourceRoot":"","sources":["../../src/commands/validate.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,QAAQ,EAAE,KAAK,EAAE,MAAM,gBAAgB,CAAA;AAChD,OAAO,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA;AAC3D,OAAO,EAAE,SAAS,EAAE,WAAW,EAAE,eAAe,EAAE,MAAM,iBAAiB,CAAA;AAEzE,MAAM,CAAC,KAAK,UAAU,WAAW,CAAC,IAAgB,EAAE,EAAa;IAC/D,MAAM,IAAI,GAAG,WAAW,CAAC,EAAE,CAAC,GAAG,EAAE,IAAI,CAAC,WAAW,CAAC,CAAC,CAAC,CAAC,CAAA;IACrD,MAAM,MAAM,GAAG,MAAM,eAAe,CAAC,IAAI,EAAE,MAAM,WAAW,CAAC,IAAI,CAAC,CAAC,CAAA;IACnE,IAAI,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC,EAAE,CAAC;QAC3B,EAAE,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,CAAA;QACvC,OAAO,MAAM,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAA;IAC1B,CAAC;IACD,MAAM,GAAG,GAAG,MAAM,CAAC,QAAQ,CAAC,CAAC,CAAC,GAAG,MAAM,CAAC,QAAQ,CAAC,EAAE,IAAI,MAAM,CAAC,QAAQ,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,IAAI,CAAA;IACvF,WAAW,CAAC,EAAE,EAAE,MAAM,CAAC,MAAM,CAAC,CAAA;IAC9B,MAAM,OAAO,GAAG,GAAG,GAAG,KAAK,MAAM,CAAC,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,SAAS,KAAK,SAAS,CAAC,MAAM,CAAC,MAAM,CAAC,YAAY,MAAM,CAAC,MAAM,KAAK,MAAM,CAAC,KAAK,CAAC,MAAM,SAAS,CAAA;IACjJ,IAAI,MAAM,CAAC,EAAE;QAAE,EAAE,CAAC,GAAG,CAAC,OAAO,CAAC,CAAA;;QACzB,EAAE,CAAC,GAAG,CAAC,OAAO,CAAC,CAAA;IACpB,OAAO,MAAM,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAA;AAC1B,CAAC;AAED,MAAM,CAAC,MAAM,QAAQ,GAAY;IAC/B,IAAI,EAAE,UAAU;IAChB,OAAO,EAAE,6CAA6C;IACtD,KAAK,EAAE;;;;;;;yDAOgD;IACvD,GAAG,EAAE,CAAC,IAAI,EAAE,EAAE,EAAE,EAAE,CAAC,KAAK,CAAC,UAAU,EAAE,EAAE,EAAE,GAAG,EAAE,CAAC,WAAW,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;CACtE,CAAA","sourcesContent":["/**\n * `pwf validate [dir]` — checks a pwpack folder and its pinned packs.\n */\nimport type { Command, CommandIO, ParsedArgs } from './types.js'\nimport { boolFlag, guard } from './lib/flags.js'\nimport { readProject, resolveFrom } from './lib/project.js'\nimport { countLine, printIssues, validateProject } from './lib/report.js'\n\nexport async function runValidate(args: ParsedArgs, io: CommandIO): Promise<number> {\n const root = resolveFrom(io.cwd, args.positionals[0])\n const result = await validateProject(root, await readProject(root))\n if (boolFlag(args, 'json')) {\n io.out(JSON.stringify(result, null, 2))\n return result.ok ? 0 : 1\n }\n const who = result.identity ? `${result.identity.id}@${result.identity.version}` : root\n printIssues(io, result.issues)\n const summary = `${who}: ${result.ok ? 'valid' : 'invalid'} (${countLine(result.issues)}; layout ${result.layout}; ${result.atoms.length} atoms)`\n if (result.ok) io.out(summary)\n else io.err(summary)\n return result.ok ? 0 : 1\n}\n\nexport const validate: Command = {\n name: 'validate',\n summary: 'Check a pwpack folder and the packs it pins',\n usage: `pwf validate [dir] [--json]\n\n dir the pwpack folder (default: the current folder)\n --json print the raw result (ok, issues, identity, layout, atoms)\n\nEvery packs[] pin is looked up in .pwf/packs/<id>@<version>/: a build that is\nnot there is a warning, one whose content hash differs from the pin is an\nerror. Exit code 1 when there is any error, 0 otherwise.`,\n run: (args, io) => guard('validate', io, () => runValidate(args, io)),\n}\n"]}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import { type CompileCache, type CompiledAtom } from './compile.js';
|
|
2
|
+
import { type AssembleDiagnostic } from './diagnostics.js';
|
|
3
|
+
import { type RuntimeAssets } from './shell.js';
|
|
4
|
+
import { type PackMemo } from './sources.js';
|
|
5
|
+
export interface AssembleOptions {
|
|
6
|
+
/** Markup appended to the shell's `<body>` — the dev server's reload client. Absent in a build. */
|
|
7
|
+
readonly shellExtra?: string;
|
|
8
|
+
/** Envelope files a local host adds (see `LocalHost.envelopeEntries`). */
|
|
9
|
+
readonly envelopeEntries?: Readonly<Record<string, unknown>>;
|
|
10
|
+
/** A compile cache to reuse across builds; default: one on disk under `.pwf/build-cache/`. */
|
|
11
|
+
readonly cache?: CompileCache;
|
|
12
|
+
/** Folder of the on-disk compile cache; `null` keeps it in memory only. */
|
|
13
|
+
readonly cacheDir?: string | null;
|
|
14
|
+
/** `publish.json`'s `publishedAt`; default now. */
|
|
15
|
+
readonly publishedAt?: string;
|
|
16
|
+
/** Runner and renderer bundles; default: the installed engine packages. */
|
|
17
|
+
readonly runtime?: RuntimeAssets;
|
|
18
|
+
/** Pack builds read by an earlier build of the same session. */
|
|
19
|
+
readonly packMemo?: PackMemo;
|
|
20
|
+
}
|
|
21
|
+
export interface AssembleStats {
|
|
22
|
+
readonly pages: number;
|
|
23
|
+
/** Entries in `blocks/manifest.json`. */
|
|
24
|
+
readonly blocks: number;
|
|
25
|
+
/** Entries in `engines/manifest.json`. */
|
|
26
|
+
readonly engines: number;
|
|
27
|
+
/** Atoms of a compiled kind across the app and its packs. */
|
|
28
|
+
readonly atoms: number;
|
|
29
|
+
/** Of those, how many have a module (compiled or shipped precompiled). */
|
|
30
|
+
readonly compiled: number;
|
|
31
|
+
/** Of the compiled, how many came from the cache. */
|
|
32
|
+
readonly fromCache: number;
|
|
33
|
+
readonly failed: number;
|
|
34
|
+
}
|
|
35
|
+
export interface AssembleResult {
|
|
36
|
+
/** No diagnostic is an error. */
|
|
37
|
+
readonly ok: boolean;
|
|
38
|
+
/** The served folder: POSIX path → bytes. Filled as far as the build got, even when not `ok`. */
|
|
39
|
+
readonly files: Map<string, Uint8Array>;
|
|
40
|
+
readonly diagnostics: readonly AssembleDiagnostic[];
|
|
41
|
+
readonly stats: AssembleStats;
|
|
42
|
+
readonly ms: number;
|
|
43
|
+
}
|
|
44
|
+
/** Every name a block atom answers to in a receipt: its id, its manifest name, and its short forms. */
|
|
45
|
+
export declare function blockNames(atom: Pick<CompiledAtom, 'id' | 'manifest'>): string[];
|
|
46
|
+
/** Assembles the pwapp for the app folder at `root`. */
|
|
47
|
+
export declare function assemblePwapp(root: string, options?: AssembleOptions): Promise<AssembleResult>;
|