audrey 1.0.1 → 1.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +30 -0
- package/README.md +5 -3
- package/benchmarks/adapter-self-test.mjs +6 -2
- package/benchmarks/adapters/example-allow.mjs +5 -2
- package/benchmarks/adapters/mem0-platform.mjs +19 -12
- package/benchmarks/adapters/zep-cloud.mjs +51 -27
- package/benchmarks/baselines.js +11 -6
- package/benchmarks/build-leaderboard.mjs +36 -23
- package/benchmarks/cases.js +24 -12
- package/benchmarks/create-conformance-card.mjs +12 -3
- package/benchmarks/create-submission-bundle.mjs +22 -8
- package/benchmarks/dry-run-external-adapters.mjs +24 -12
- package/benchmarks/guardbench.js +263 -123
- package/benchmarks/output/adapter-self-test/guardbench-adapter-self-test.json +4 -4
- package/benchmarks/output/external/guardbench-external-dry-run.json +1 -1
- package/benchmarks/output/external/guardbench-external-evidence.json +1 -1
- package/benchmarks/output/guardbench-conformance-card.json +11 -11
- package/benchmarks/output/guardbench-raw.json +107 -108
- package/benchmarks/output/guardbench-summary.json +170 -172
- package/benchmarks/output/leaderboard/guardbench-leaderboard.json +5 -5
- package/benchmarks/output/leaderboard/guardbench-leaderboard.md +2 -2
- package/benchmarks/output/submission-bundle/guardbench-conformance-card.json +11 -11
- package/benchmarks/output/submission-bundle/guardbench-raw.json +107 -108
- package/benchmarks/output/submission-bundle/guardbench-summary.json +170 -172
- package/benchmarks/output/submission-bundle/submission-manifest.json +11 -11
- package/benchmarks/output/submission-bundle/validation-report.json +1 -1
- package/benchmarks/output/summary.json +57 -57
- package/benchmarks/perf-snapshot.js +12 -9
- package/benchmarks/perf.bench.js +14 -6
- package/benchmarks/public-paths.mjs +11 -5
- package/benchmarks/reference-results.js +10 -5
- package/benchmarks/report.js +48 -27
- package/benchmarks/run-external-guardbench.mjs +47 -25
- package/benchmarks/run.js +112 -59
- package/benchmarks/validate-adapter-module.mjs +13 -10
- package/benchmarks/validate-adapter-registry.mjs +16 -5
- package/benchmarks/validate-guardbench-artifacts.mjs +76 -19
- package/benchmarks/verify-external-evidence.mjs +86 -31
- package/benchmarks/verify-publication-artifacts.mjs +34 -11
- package/benchmarks/verify-submission-bundle.mjs +9 -4
- package/dist/mcp-server/config.d.ts +1 -1
- package/dist/mcp-server/config.d.ts.map +1 -1
- package/dist/mcp-server/config.js +5 -3
- package/dist/mcp-server/config.js.map +1 -1
- package/dist/mcp-server/index.d.ts +4 -3
- package/dist/mcp-server/index.d.ts.map +1 -1
- package/dist/mcp-server/index.js +479 -172
- package/dist/mcp-server/index.js.map +1 -1
- package/dist/src/action-key.d.ts.map +1 -1
- package/dist/src/action-key.js +6 -2
- package/dist/src/action-key.js.map +1 -1
- package/dist/src/adaptive.d.ts.map +1 -1
- package/dist/src/adaptive.js +4 -2
- package/dist/src/adaptive.js.map +1 -1
- package/dist/src/affect.d.ts.map +1 -1
- package/dist/src/affect.js +8 -5
- package/dist/src/affect.js.map +1 -1
- package/dist/src/audrey.d.ts +1 -1
- package/dist/src/audrey.d.ts.map +1 -1
- package/dist/src/audrey.js +93 -49
- package/dist/src/audrey.js.map +1 -1
- package/dist/src/capsule.d.ts.map +1 -1
- package/dist/src/capsule.js +37 -15
- package/dist/src/capsule.js.map +1 -1
- package/dist/src/causal.d.ts +1 -1
- package/dist/src/causal.d.ts.map +1 -1
- package/dist/src/causal.js +4 -2
- package/dist/src/causal.js.map +1 -1
- package/dist/src/confidence.d.ts.map +1 -1
- package/dist/src/confidence.js +5 -5
- package/dist/src/confidence.js.map +1 -1
- package/dist/src/consolidate.d.ts.map +1 -1
- package/dist/src/consolidate.js +17 -9
- package/dist/src/consolidate.js.map +1 -1
- package/dist/src/context.js +1 -1
- package/dist/src/context.js.map +1 -1
- package/dist/src/controller.d.ts.map +1 -1
- package/dist/src/controller.js +24 -13
- package/dist/src/controller.js.map +1 -1
- package/dist/src/db.d.ts.map +1 -1
- package/dist/src/db.js +78 -27
- package/dist/src/db.js.map +1 -1
- package/dist/src/decay.d.ts +1 -1
- package/dist/src/decay.d.ts.map +1 -1
- package/dist/src/decay.js +1 -1
- package/dist/src/decay.js.map +1 -1
- package/dist/src/embedding.d.ts +12 -4
- package/dist/src/embedding.d.ts.map +1 -1
- package/dist/src/embedding.js +18 -16
- package/dist/src/embedding.js.map +1 -1
- package/dist/src/encode.d.ts.map +1 -1
- package/dist/src/encode.js +5 -4
- package/dist/src/encode.js.map +1 -1
- package/dist/src/events.d.ts +3 -2
- package/dist/src/events.d.ts.map +1 -1
- package/dist/src/events.js +7 -3
- package/dist/src/events.js.map +1 -1
- package/dist/src/export.d.ts.map +1 -1
- package/dist/src/export.js +21 -7
- package/dist/src/export.js.map +1 -1
- package/dist/src/feedback.d.ts.map +1 -1
- package/dist/src/feedback.js +1 -1
- package/dist/src/feedback.js.map +1 -1
- package/dist/src/forget.d.ts.map +1 -1
- package/dist/src/forget.js +12 -6
- package/dist/src/forget.js.map +1 -1
- package/dist/src/fts.d.ts.map +1 -1
- package/dist/src/fts.js +20 -8
- package/dist/src/fts.js.map +1 -1
- package/dist/src/hybrid-recall.d.ts.map +1 -1
- package/dist/src/hybrid-recall.js +12 -6
- package/dist/src/hybrid-recall.js.map +1 -1
- package/dist/src/impact.d.ts.map +1 -1
- package/dist/src/impact.js +26 -10
- package/dist/src/impact.js.map +1 -1
- package/dist/src/import.d.ts.map +1 -1
- package/dist/src/import.js +11 -6
- package/dist/src/import.js.map +1 -1
- package/dist/src/index.d.ts +3 -3
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +3 -3
- package/dist/src/index.js.map +1 -1
- package/dist/src/interference.d.ts.map +1 -1
- package/dist/src/interference.js +10 -5
- package/dist/src/interference.js.map +1 -1
- package/dist/src/introspect.d.ts.map +1 -1
- package/dist/src/introspect.js +12 -6
- package/dist/src/introspect.js.map +1 -1
- package/dist/src/llm.d.ts +2 -2
- package/dist/src/llm.d.ts.map +1 -1
- package/dist/src/llm.js +6 -6
- package/dist/src/llm.js.map +1 -1
- package/dist/src/migrate.d.ts.map +1 -1
- package/dist/src/migrate.js +10 -4
- package/dist/src/migrate.js.map +1 -1
- package/dist/src/preflight.d.ts.map +1 -1
- package/dist/src/preflight.js +6 -8
- package/dist/src/preflight.js.map +1 -1
- package/dist/src/profile.d.ts.map +1 -1
- package/dist/src/profile.js.map +1 -1
- package/dist/src/promote.d.ts.map +1 -1
- package/dist/src/promote.js +16 -7
- package/dist/src/promote.js.map +1 -1
- package/dist/src/prompts.d.ts.map +1 -1
- package/dist/src/prompts.js +1 -2
- package/dist/src/prompts.js.map +1 -1
- package/dist/src/recall.d.ts.map +1 -1
- package/dist/src/recall.js +85 -18
- package/dist/src/recall.js.map +1 -1
- package/dist/src/redact.d.ts.map +1 -1
- package/dist/src/redact.js +9 -4
- package/dist/src/redact.js.map +1 -1
- package/dist/src/reflexes.d.ts.map +1 -1
- package/dist/src/reflexes.js +1 -7
- package/dist/src/reflexes.js.map +1 -1
- package/dist/src/rollback.d.ts.map +1 -1
- package/dist/src/rollback.js +4 -2
- package/dist/src/rollback.js.map +1 -1
- package/dist/src/routes.d.ts.map +1 -1
- package/dist/src/routes.js +33 -13
- package/dist/src/routes.js.map +1 -1
- package/dist/src/rules-compiler.d.ts.map +1 -1
- package/dist/src/rules-compiler.js +24 -2
- package/dist/src/rules-compiler.js.map +1 -1
- package/dist/src/server.js +2 -2
- package/dist/src/server.js.map +1 -1
- package/dist/src/tool-trace.d.ts +2 -2
- package/dist/src/tool-trace.d.ts.map +1 -1
- package/dist/src/tool-trace.js +12 -4
- package/dist/src/tool-trace.js.map +1 -1
- package/dist/src/types.d.ts.map +1 -1
- package/dist/src/ulid.js +1 -1
- package/dist/src/ulid.js.map +1 -1
- package/dist/src/utils.d.ts.map +1 -1
- package/dist/src/utils.js.map +1 -1
- package/dist/src/validate.d.ts.map +1 -1
- package/dist/src/validate.js +20 -10
- package/dist/src/validate.js.map +1 -1
- package/docs/paper/07-evaluation.md +5 -5
- package/docs/paper/audrey-paper-v1.md +5 -5
- package/docs/paper/evidence-ledger.md +1 -1
- package/docs/paper/output/arxiv/arxiv-manifest.json +4 -4
- package/docs/paper/output/arxiv/main.tex +5 -5
- package/docs/paper/output/arxiv-compile-report.json +3 -3
- package/docs/paper/output/submission-bundle/README.md +5 -3
- package/docs/paper/output/submission-bundle/benchmarks/output/adapter-self-test/guardbench-adapter-self-test.json +4 -4
- package/docs/paper/output/submission-bundle/benchmarks/output/external/guardbench-external-dry-run.json +1 -1
- package/docs/paper/output/submission-bundle/benchmarks/output/external/guardbench-external-evidence.json +1 -1
- package/docs/paper/output/submission-bundle/benchmarks/output/guardbench-conformance-card.json +11 -11
- package/docs/paper/output/submission-bundle/benchmarks/output/guardbench-raw.json +107 -108
- package/docs/paper/output/submission-bundle/benchmarks/output/guardbench-summary.json +170 -172
- package/docs/paper/output/submission-bundle/benchmarks/output/leaderboard/guardbench-leaderboard.json +5 -5
- package/docs/paper/output/submission-bundle/benchmarks/output/leaderboard/guardbench-leaderboard.md +2 -2
- package/docs/paper/output/submission-bundle/benchmarks/output/submission-bundle/submission-manifest.json +11 -11
- package/docs/paper/output/submission-bundle/benchmarks/output/submission-bundle/validation-report.json +1 -1
- package/docs/paper/output/submission-bundle/benchmarks/output/summary.json +58 -58
- package/docs/paper/output/submission-bundle/docs/paper/07-evaluation.md +5 -5
- package/docs/paper/output/submission-bundle/docs/paper/audrey-paper-v1.md +5 -5
- package/docs/paper/output/submission-bundle/docs/paper/evidence-ledger.md +1 -1
- package/docs/paper/output/submission-bundle/docs/paper/output/arxiv/arxiv-manifest.json +4 -4
- package/docs/paper/output/submission-bundle/docs/paper/output/arxiv/main.tex +5 -5
- package/docs/paper/output/submission-bundle/docs/paper/output/arxiv-compile-report.json +3 -3
- package/docs/paper/output/submission-bundle/package.json +17 -4
- package/docs/paper/output/submission-bundle/paper-submission-manifest.json +36 -36
- package/examples/fintech-ops-demo.js +12 -5
- package/examples/healthcare-ops-demo.js +8 -4
- package/examples/ollama-memory-agent.js +41 -13
- package/examples/stripe-demo.js +12 -5
- package/package.json +17 -4
- package/scripts/audit-release-completion.mjs +179 -101
- package/scripts/create-arxiv-source.mjs +20 -14
- package/scripts/create-paper-submission-bundle.mjs +6 -2
- package/scripts/finalize-release.mjs +111 -36
- package/scripts/prepare-release-cut.mjs +14 -6
- package/scripts/publish-release-bundle.mjs +62 -23
- package/scripts/publish-release-github-api.mjs +89 -24
- package/scripts/smoke-cli.js +9 -9
- package/scripts/sync-paper-artifacts.mjs +5 -1
- package/scripts/verify-arxiv-compile.mjs +52 -16
- package/scripts/verify-arxiv-source.mjs +45 -15
- package/scripts/verify-browser-launch-plan.mjs +28 -11
- package/scripts/verify-browser-launch-results.mjs +32 -14
- package/scripts/verify-paper-artifacts.mjs +539 -79
- package/scripts/verify-paper-claims.mjs +48 -20
- package/scripts/verify-paper-submission-bundle.mjs +22 -11
- package/scripts/verify-publication-pack.mjs +23 -9
- package/scripts/verify-release-readiness.mjs +211 -76
|
@@ -67,7 +67,8 @@ function safeRepoRelativePath(value, label) {
|
|
|
67
67
|
function normalizeArgs(args) {
|
|
68
68
|
args.version = safeVersion(args.version);
|
|
69
69
|
args.artifactDir = safeRepoRelativePath(args.artifactDir, '--artifact-dir');
|
|
70
|
-
if (args.commitMessage !== null)
|
|
70
|
+
if (args.commitMessage !== null)
|
|
71
|
+
args.commitMessage = safeString(args.commitMessage, '--commit-message');
|
|
71
72
|
if (args.npmOtp !== null) args.npmOtp = safeString(args.npmOtp, '--npm-otp');
|
|
72
73
|
return args;
|
|
73
74
|
}
|
|
@@ -109,7 +110,8 @@ function parseArgs(argv = process.argv.slice(2)) {
|
|
|
109
110
|
|
|
110
111
|
for (let i = 0; i < argv.length; i++) {
|
|
111
112
|
const token = argv[i];
|
|
112
|
-
if ((token === '--version' || token === '--target-version') && argv[i + 1])
|
|
113
|
+
if ((token === '--version' || token === '--target-version') && argv[i + 1])
|
|
114
|
+
args.version = argv[++i];
|
|
113
115
|
else if (token === '--artifact-dir' && argv[i + 1]) args.artifactDir = argv[++i];
|
|
114
116
|
else if (token === '--commit-message' && argv[i + 1]) args.commitMessage = argv[++i];
|
|
115
117
|
else if (token === '--npm-otp' && argv[i + 1]) args.npmOtp = argv[++i];
|
|
@@ -162,7 +164,9 @@ function commandFor(command, args) {
|
|
|
162
164
|
if (!RELEASE_COMMANDS.has(command)) {
|
|
163
165
|
throw new Error(`Unsupported release command: ${command}`);
|
|
164
166
|
}
|
|
165
|
-
const safeArgs = args.map((arg, index) =>
|
|
167
|
+
const safeArgs = args.map((arg, index) =>
|
|
168
|
+
safeString(String(arg), `${command} argument ${index + 1}`),
|
|
169
|
+
);
|
|
166
170
|
if (process.platform === 'win32' && command === 'npm') {
|
|
167
171
|
return { command: 'cmd.exe', args: ['/d', '/c', 'npm', ...safeArgs] };
|
|
168
172
|
}
|
|
@@ -218,7 +222,9 @@ function listArtifacts(artifactDir, version) {
|
|
|
218
222
|
}
|
|
219
223
|
|
|
220
224
|
return files.map(path => ({
|
|
221
|
-
path: path.startsWith(ROOT)
|
|
225
|
+
path: path.startsWith(ROOT)
|
|
226
|
+
? path.slice(ROOT.length + 1).replaceAll('\\', '/')
|
|
227
|
+
: path.replaceAll('\\', '/'),
|
|
222
228
|
sha256: sha256(path),
|
|
223
229
|
bytes: readFileSync(path).byteLength,
|
|
224
230
|
}));
|
|
@@ -280,15 +286,23 @@ function buildPlan(args) {
|
|
|
280
286
|
if (args.tag) commands.push(`git tag -a ${tagName} -m "Audrey ${args.version}"`);
|
|
281
287
|
if (args.push) commands.push(`git push origin HEAD:master --follow-tags`);
|
|
282
288
|
if (args.pack) commands.push(`npm pack --pack-destination ${args.artifactDir}`);
|
|
283
|
-
if (args.sourceBundle)
|
|
289
|
+
if (args.sourceBundle)
|
|
290
|
+
commands.push(
|
|
291
|
+
`git bundle create ${args.artifactDir}/audrey-${args.version}.git.bundle refs/heads/master refs/tags/v${args.version}`,
|
|
292
|
+
);
|
|
284
293
|
if (args.publishNpm) {
|
|
285
294
|
const otp = args.npmOtp ? ' --otp <provided>' : '';
|
|
286
|
-
commands.push(
|
|
295
|
+
commands.push(
|
|
296
|
+
`npm publish ${args.artifactDir}/audrey-${args.version}.tgz --access public --registry ${NPM_REGISTRY}${otp}`,
|
|
297
|
+
);
|
|
287
298
|
}
|
|
288
|
-
if (args.publishPypi)
|
|
299
|
+
if (args.publishPypi)
|
|
300
|
+
commands.push(`python -m twine upload python/dist/audrey_memory-${args.version}*`);
|
|
289
301
|
|
|
290
302
|
if (actions.length === 0) {
|
|
291
|
-
blockers.push(
|
|
303
|
+
blockers.push(
|
|
304
|
+
'Select at least one action such as --pack, --source-bundle, --commit, --tag, --push, --publish-npm, or --publish-pypi',
|
|
305
|
+
);
|
|
292
306
|
}
|
|
293
307
|
if (args.publishPypi && !pypiCredentialEnv()) {
|
|
294
308
|
blockers.push('Set TWINE_PASSWORD, PYPI_API_TOKEN, or UV_PUBLISH_TOKEN before --publish-pypi');
|
|
@@ -312,12 +326,18 @@ function buildPlan(args) {
|
|
|
312
326
|
}
|
|
313
327
|
|
|
314
328
|
function runReadiness(plan) {
|
|
315
|
-
const readiness = run(
|
|
329
|
+
const readiness = run(
|
|
330
|
+
'node',
|
|
331
|
+
['scripts/verify-release-readiness.mjs', '--allow-pending', '--json'],
|
|
332
|
+
{ timeout: 180_000 },
|
|
333
|
+
);
|
|
316
334
|
plan.results.push(readiness);
|
|
317
335
|
assertOk(readiness);
|
|
318
336
|
const report = JSON.parse(readiness.stdout);
|
|
319
337
|
if (!report.ok) {
|
|
320
|
-
throw new Error(
|
|
338
|
+
throw new Error(
|
|
339
|
+
`release readiness failed: ${report.failures?.join('; ') || 'unknown failure'}`,
|
|
340
|
+
);
|
|
321
341
|
}
|
|
322
342
|
plan.readiness = {
|
|
323
343
|
ok: report.ok,
|
|
@@ -367,7 +387,20 @@ function createSourceBundle(args, plan) {
|
|
|
367
387
|
}
|
|
368
388
|
|
|
369
389
|
const tree = assertOk(run('git', ['write-tree'], { env })).stdout;
|
|
370
|
-
const commit = assertOk(
|
|
390
|
+
const commit = assertOk(
|
|
391
|
+
run(
|
|
392
|
+
'git',
|
|
393
|
+
[
|
|
394
|
+
'commit-tree',
|
|
395
|
+
tree,
|
|
396
|
+
'-p',
|
|
397
|
+
'HEAD',
|
|
398
|
+
'-m',
|
|
399
|
+
args.commitMessage ?? `Release Audrey ${args.version}`,
|
|
400
|
+
],
|
|
401
|
+
{ env },
|
|
402
|
+
),
|
|
403
|
+
).stdout;
|
|
371
404
|
const tagContent = [
|
|
372
405
|
`object ${commit}`,
|
|
373
406
|
'type commit',
|
|
@@ -384,17 +417,33 @@ function createSourceBundle(args, plan) {
|
|
|
384
417
|
mkdirSync(join(gitDir, 'refs', 'heads'), { recursive: true });
|
|
385
418
|
mkdirSync(join(gitDir, 'refs', 'tags'), { recursive: true });
|
|
386
419
|
writeFileSync(join(gitDir, 'HEAD'), 'ref: refs/heads/master\n', 'utf-8');
|
|
387
|
-
writeFileSync(
|
|
420
|
+
writeFileSync(
|
|
421
|
+
join(gitDir, 'config'),
|
|
422
|
+
'[core]\n\trepositoryformatversion = 0\n\tfilemode = false\n\tbare = true\n',
|
|
423
|
+
'utf-8',
|
|
424
|
+
);
|
|
388
425
|
writeFileSync(join(gitDir, 'refs', 'heads', 'master'), `${commit}\n`, 'utf-8');
|
|
389
426
|
writeFileSync(join(gitDir, 'refs', 'tags', `v${args.version}`), `${tag}\n`, 'utf-8');
|
|
390
427
|
|
|
391
|
-
const bundle = run(
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
428
|
+
const bundle = run(
|
|
429
|
+
'git',
|
|
430
|
+
[
|
|
431
|
+
'--git-dir',
|
|
432
|
+
gitDir,
|
|
433
|
+
'bundle',
|
|
434
|
+
'create',
|
|
435
|
+
bundlePath,
|
|
436
|
+
'refs/heads/master',
|
|
437
|
+
`refs/tags/v${args.version}`,
|
|
438
|
+
],
|
|
439
|
+
{
|
|
440
|
+
env: {
|
|
441
|
+
GIT_OBJECT_DIRECTORY: objectDir,
|
|
442
|
+
GIT_ALTERNATE_OBJECT_DIRECTORIES: fromRoot('.git/objects'),
|
|
443
|
+
},
|
|
444
|
+
timeout: 180_000,
|
|
395
445
|
},
|
|
396
|
-
|
|
397
|
-
});
|
|
446
|
+
);
|
|
398
447
|
plan.results.push(bundle);
|
|
399
448
|
assertOk(bundle);
|
|
400
449
|
|
|
@@ -410,7 +459,11 @@ function createSourceBundle(args, plan) {
|
|
|
410
459
|
indexFile: '.tmp/release.index',
|
|
411
460
|
bundle: args.artifactDir.replaceAll('\\', '/') + `/audrey-${args.version}.git.bundle`,
|
|
412
461
|
};
|
|
413
|
-
writeFileSync(
|
|
462
|
+
writeFileSync(
|
|
463
|
+
fromRoot('.tmp/release-git-object-report.json'),
|
|
464
|
+
`${JSON.stringify(objectReport, null, 2)}\n`,
|
|
465
|
+
'utf-8',
|
|
466
|
+
);
|
|
414
467
|
plan.sourceControl = objectReport;
|
|
415
468
|
}
|
|
416
469
|
|
|
@@ -434,18 +487,22 @@ function execute(args, plan) {
|
|
|
434
487
|
}
|
|
435
488
|
|
|
436
489
|
if (args.push) {
|
|
437
|
-
const push = run(
|
|
438
|
-
'
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
490
|
+
const push = run(
|
|
491
|
+
'git',
|
|
492
|
+
[
|
|
493
|
+
'-c',
|
|
494
|
+
'http.sslBackend=openssl',
|
|
495
|
+
'-c',
|
|
496
|
+
'credential.helper=',
|
|
497
|
+
'-c',
|
|
498
|
+
'core.askPass=',
|
|
499
|
+
'push',
|
|
500
|
+
'origin',
|
|
501
|
+
'HEAD:master',
|
|
502
|
+
'--follow-tags',
|
|
503
|
+
],
|
|
504
|
+
{ timeout: 45_000 },
|
|
505
|
+
);
|
|
449
506
|
plan.results.push(push);
|
|
450
507
|
assertOk(push);
|
|
451
508
|
}
|
|
@@ -464,7 +521,14 @@ function execute(args, plan) {
|
|
|
464
521
|
const whoami = run('npm', ['whoami', '--registry', NPM_REGISTRY]);
|
|
465
522
|
plan.results.push(whoami);
|
|
466
523
|
assertOk(whoami);
|
|
467
|
-
const publishArgs = [
|
|
524
|
+
const publishArgs = [
|
|
525
|
+
'publish',
|
|
526
|
+
npmTarballPath(args.artifactDir, args.version),
|
|
527
|
+
'--access',
|
|
528
|
+
'public',
|
|
529
|
+
'--registry',
|
|
530
|
+
NPM_REGISTRY,
|
|
531
|
+
];
|
|
468
532
|
if (args.npmOtp) publishArgs.push('--otp', args.npmOtp);
|
|
469
533
|
const publish = run('npm', publishArgs, { timeout: 180_000 });
|
|
470
534
|
plan.results.push(publish);
|
|
@@ -473,19 +537,29 @@ function execute(args, plan) {
|
|
|
473
537
|
|
|
474
538
|
if (args.publishPypi) {
|
|
475
539
|
const uploadEnv = pypiCredentialEnv();
|
|
476
|
-
if (!uploadEnv)
|
|
540
|
+
if (!uploadEnv)
|
|
541
|
+
throw new Error(
|
|
542
|
+
'Missing PyPI credentials: set TWINE_PASSWORD, PYPI_API_TOKEN, or UV_PUBLISH_TOKEN',
|
|
543
|
+
);
|
|
477
544
|
const build = run('npm', ['run', 'python:release:check'], { timeout: 180_000 });
|
|
478
545
|
plan.results.push(build);
|
|
479
546
|
assertOk(build);
|
|
480
547
|
const artifacts = pythonArtifactPaths(args.version);
|
|
481
548
|
if (artifacts.length === 0) throw new Error(`No Python artifacts found for ${args.version}`);
|
|
482
|
-
const upload = run('python', ['-m', 'twine', 'upload', ...artifacts], {
|
|
549
|
+
const upload = run('python', ['-m', 'twine', 'upload', ...artifacts], {
|
|
550
|
+
timeout: 180_000,
|
|
551
|
+
env: uploadEnv,
|
|
552
|
+
});
|
|
483
553
|
plan.results.push(upload);
|
|
484
554
|
assertOk(upload);
|
|
485
555
|
}
|
|
486
556
|
|
|
487
557
|
plan.artifacts = listArtifacts(artifactDir, args.version);
|
|
488
|
-
writeFileSync(
|
|
558
|
+
writeFileSync(
|
|
559
|
+
join(artifactDir, 'release-finalize-report.json'),
|
|
560
|
+
`${JSON.stringify(plan, null, 2)}\n`,
|
|
561
|
+
'utf-8',
|
|
562
|
+
);
|
|
489
563
|
}
|
|
490
564
|
|
|
491
565
|
function printPlan(plan, json) {
|
|
@@ -503,7 +577,8 @@ function printPlan(plan, json) {
|
|
|
503
577
|
}
|
|
504
578
|
if (plan.artifacts.length) {
|
|
505
579
|
console.log('Artifacts:');
|
|
506
|
-
for (const artifact of plan.artifacts)
|
|
580
|
+
for (const artifact of plan.artifacts)
|
|
581
|
+
console.log(`- ${artifact.path} sha256=${artifact.sha256}`);
|
|
507
582
|
}
|
|
508
583
|
}
|
|
509
584
|
|
|
@@ -4,7 +4,8 @@ import { fileURLToPath } from 'node:url';
|
|
|
4
4
|
|
|
5
5
|
const ROOT = process.cwd();
|
|
6
6
|
const DEFAULT_TARGET_VERSION = '1.0.0';
|
|
7
|
-
const VERSION_RE =
|
|
7
|
+
const VERSION_RE =
|
|
8
|
+
/^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-[0-9A-Za-z.-]+)?(?:\+[0-9A-Za-z.-]+)?$/;
|
|
8
9
|
|
|
9
10
|
function fromRoot(path) {
|
|
10
11
|
return resolve(ROOT, path);
|
|
@@ -34,7 +35,8 @@ function parseArgs(argv = process.argv.slice(2)) {
|
|
|
34
35
|
|
|
35
36
|
for (let i = 0; i < argv.length; i++) {
|
|
36
37
|
const token = argv[i];
|
|
37
|
-
if ((token === '--target-version' || token === '--version') && argv[i + 1])
|
|
38
|
+
if ((token === '--target-version' || token === '--version') && argv[i + 1])
|
|
39
|
+
args.targetVersion = argv[++i];
|
|
38
40
|
else if (token === '--date' && argv[i + 1]) args.date = argv[++i];
|
|
39
41
|
else if (token === '--apply') args.apply = true;
|
|
40
42
|
else if (token === '--json') args.json = true;
|
|
@@ -203,10 +205,14 @@ export function prepareReleaseCut(options = {}) {
|
|
|
203
205
|
const versions = currentVersionSnapshot();
|
|
204
206
|
const versionValues = Object.values(versions);
|
|
205
207
|
const failures = [];
|
|
206
|
-
if (versionValues.some(value => !value))
|
|
207
|
-
|
|
208
|
+
if (versionValues.some(value => !value))
|
|
209
|
+
failures.push('One or more release version surfaces are missing');
|
|
210
|
+
if (new Set(versionValues).size !== 1)
|
|
211
|
+
failures.push(`Release version surfaces are not aligned: ${JSON.stringify(versions)}`);
|
|
208
212
|
if (versions.packageJson && compareCoreVersions(targetVersion, versions.packageJson) < 0) {
|
|
209
|
-
failures.push(
|
|
213
|
+
failures.push(
|
|
214
|
+
`Target version ${targetVersion} is lower than current package version ${versions.packageJson}`,
|
|
215
|
+
);
|
|
210
216
|
}
|
|
211
217
|
|
|
212
218
|
const files = plannedFiles(targetVersion, date).map(([path, after]) => {
|
|
@@ -251,7 +257,9 @@ async function main() {
|
|
|
251
257
|
console.log(JSON.stringify(report, null, 2));
|
|
252
258
|
} else if (report.ok) {
|
|
253
259
|
const changed = report.files.filter(file => file.changed).map(file => file.path);
|
|
254
|
-
console.log(
|
|
260
|
+
console.log(
|
|
261
|
+
`${report.apply ? 'Applied' : 'Planned'} Audrey ${report.targetVersion} release cut: ${changed.length} file(s)`,
|
|
262
|
+
);
|
|
255
263
|
for (const file of changed) console.log(`- ${file}`);
|
|
256
264
|
} else {
|
|
257
265
|
console.error('Release cut preparation failed:');
|
|
@@ -22,7 +22,8 @@ function parseArgs(argv = process.argv.slice(2)) {
|
|
|
22
22
|
|
|
23
23
|
for (let i = 0; i < argv.length; i++) {
|
|
24
24
|
const token = argv[i];
|
|
25
|
-
if ((token === '--version' || token === '--target-version') && argv[i + 1])
|
|
25
|
+
if ((token === '--version' || token === '--target-version') && argv[i + 1])
|
|
26
|
+
args.version = argv[++i];
|
|
26
27
|
else if (token === '--bundle' && argv[i + 1]) args.bundle = argv[++i];
|
|
27
28
|
else if (token === '--remote' && argv[i + 1]) args.remote = argv[++i];
|
|
28
29
|
else if (token === '--apply') args.apply = true;
|
|
@@ -72,7 +73,12 @@ function run(command, args, options = {}) {
|
|
|
72
73
|
}
|
|
73
74
|
|
|
74
75
|
function firstLine(result) {
|
|
75
|
-
return
|
|
76
|
+
return (
|
|
77
|
+
`${result.stderr}\n${result.stdout}`
|
|
78
|
+
.split(/\r?\n/)
|
|
79
|
+
.map(line => line.trim())
|
|
80
|
+
.find(Boolean) ?? ''
|
|
81
|
+
);
|
|
76
82
|
}
|
|
77
83
|
|
|
78
84
|
function parseBundleRefs(output, version) {
|
|
@@ -101,9 +107,27 @@ function parseRemoteRefs(output, version) {
|
|
|
101
107
|
}
|
|
102
108
|
|
|
103
109
|
function remoteHead(args) {
|
|
104
|
-
let result = run(
|
|
105
|
-
|
|
106
|
-
|
|
110
|
+
let result = run(
|
|
111
|
+
'git',
|
|
112
|
+
['ls-remote', args.remote, 'refs/heads/master', `refs/tags/v${args.version}`],
|
|
113
|
+
{ timeout: 60_000 },
|
|
114
|
+
);
|
|
115
|
+
if (
|
|
116
|
+
!result.ok &&
|
|
117
|
+
/schannel|AcquireCredentialsHandle|SEC_E_NO_CREDENTIALS/i.test(firstLine(result))
|
|
118
|
+
) {
|
|
119
|
+
result = run(
|
|
120
|
+
'git',
|
|
121
|
+
[
|
|
122
|
+
'-c',
|
|
123
|
+
'http.sslBackend=openssl',
|
|
124
|
+
'ls-remote',
|
|
125
|
+
args.remote,
|
|
126
|
+
'refs/heads/master',
|
|
127
|
+
`refs/tags/v${args.version}`,
|
|
128
|
+
],
|
|
129
|
+
{ timeout: 60_000 },
|
|
130
|
+
);
|
|
107
131
|
result.fallback = 'openssl';
|
|
108
132
|
}
|
|
109
133
|
return result;
|
|
@@ -112,20 +136,26 @@ function remoteHead(args) {
|
|
|
112
136
|
function publishFromBundle(args, refs) {
|
|
113
137
|
const temp = mkdtempSync(join(tmpdir(), 'audrey-release-push-'));
|
|
114
138
|
try {
|
|
115
|
-
const clone = run('git', ['clone', '--bare', resolve(ROOT, args.bundle), temp], {
|
|
139
|
+
const clone = run('git', ['clone', '--bare', resolve(ROOT, args.bundle), temp], {
|
|
140
|
+
timeout: 120_000,
|
|
141
|
+
});
|
|
116
142
|
if (!clone.ok) return [clone];
|
|
117
|
-
const push = run(
|
|
118
|
-
'
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
143
|
+
const push = run(
|
|
144
|
+
'git',
|
|
145
|
+
[
|
|
146
|
+
'-c',
|
|
147
|
+
'http.sslBackend=openssl',
|
|
148
|
+
'-c',
|
|
149
|
+
'credential.helper=',
|
|
150
|
+
'-c',
|
|
151
|
+
'core.askPass=',
|
|
152
|
+
'push',
|
|
153
|
+
args.remote,
|
|
154
|
+
`${refs.master}:refs/heads/master`,
|
|
155
|
+
`${refs.tag}:refs/tags/v${args.version}`,
|
|
156
|
+
],
|
|
157
|
+
{ cwd: temp, timeout: 45_000 },
|
|
158
|
+
);
|
|
129
159
|
return [clone, push];
|
|
130
160
|
} finally {
|
|
131
161
|
rmSync(temp, { recursive: true, force: true });
|
|
@@ -135,16 +165,22 @@ function publishFromBundle(args, refs) {
|
|
|
135
165
|
export function planPublish(args) {
|
|
136
166
|
const verify = run('git', ['bundle', 'verify', args.bundle], { timeout: 60_000 });
|
|
137
167
|
const remote = remoteHead(args);
|
|
138
|
-
const bundleRefs = verify.ok
|
|
139
|
-
|
|
168
|
+
const bundleRefs = verify.ok
|
|
169
|
+
? parseBundleRefs(verify.stdout, args.version)
|
|
170
|
+
: { master: null, tag: null };
|
|
171
|
+
const remoteRefs = remote.ok
|
|
172
|
+
? parseRemoteRefs(remote.stdout, args.version)
|
|
173
|
+
: { master: null, tag: null };
|
|
140
174
|
const blockers = [];
|
|
141
175
|
|
|
142
176
|
if (!verify.ok) blockers.push(`Bundle verification failed: ${firstLine(verify)}`);
|
|
143
177
|
if (!bundleRefs.master) blockers.push('Bundle is missing refs/heads/master');
|
|
144
178
|
if (!bundleRefs.tag) blockers.push(`Bundle is missing refs/tags/v${args.version}`);
|
|
145
179
|
if (!remote.ok) blockers.push(`Remote check failed: ${firstLine(remote)}`);
|
|
146
|
-
if (remoteRefs.tag && remoteRefs.tag !== bundleRefs.tag)
|
|
147
|
-
|
|
180
|
+
if (remoteRefs.tag && remoteRefs.tag !== bundleRefs.tag)
|
|
181
|
+
blockers.push(`Remote v${args.version} already points at ${remoteRefs.tag}`);
|
|
182
|
+
if (remoteRefs.master === bundleRefs.master && remoteRefs.tag === bundleRefs.tag)
|
|
183
|
+
blockers.push('Remote already matches the release bundle');
|
|
148
184
|
|
|
149
185
|
return {
|
|
150
186
|
schemaVersion: '1.0.0',
|
|
@@ -198,7 +234,10 @@ async function main() {
|
|
|
198
234
|
}
|
|
199
235
|
|
|
200
236
|
function isDirectRun() {
|
|
201
|
-
return
|
|
237
|
+
return (
|
|
238
|
+
Boolean(process.argv[1]) &&
|
|
239
|
+
resolve(process.argv[1]).toLowerCase() === fileURLToPath(import.meta.url).toLowerCase()
|
|
240
|
+
);
|
|
202
241
|
}
|
|
203
242
|
|
|
204
243
|
if (isDirectRun()) {
|
|
@@ -27,11 +27,14 @@ function parseArgs(argv = process.argv.slice(2)) {
|
|
|
27
27
|
|
|
28
28
|
for (let i = 0; i < argv.length; i++) {
|
|
29
29
|
const token = argv[i];
|
|
30
|
-
if ((token === '--repository' || token === '--repo') && argv[i + 1])
|
|
30
|
+
if ((token === '--repository' || token === '--repo') && argv[i + 1])
|
|
31
|
+
args.repository = argv[++i];
|
|
31
32
|
else if (token === '--branch' && argv[i + 1]) args.branch = argv[++i];
|
|
32
|
-
else if ((token === '--version' || token === '--target-version') && argv[i + 1])
|
|
33
|
+
else if ((token === '--version' || token === '--target-version') && argv[i + 1])
|
|
34
|
+
args.version = argv[++i];
|
|
33
35
|
else if (token === '--token-env' && argv[i + 1]) args.tokenEnv = argv[++i];
|
|
34
|
-
else if (token === '--concurrency' && argv[i + 1])
|
|
36
|
+
else if (token === '--concurrency' && argv[i + 1])
|
|
37
|
+
args.concurrency = Number.parseInt(argv[++i], 10);
|
|
35
38
|
else if (token === '--apply') args.apply = true;
|
|
36
39
|
else if (token === '--json') args.json = true;
|
|
37
40
|
else if (token === '--force') args.force = true;
|
|
@@ -84,7 +87,10 @@ function run(command, args, options = {}) {
|
|
|
84
87
|
}
|
|
85
88
|
|
|
86
89
|
function assertOk(result) {
|
|
87
|
-
if (!result.ok)
|
|
90
|
+
if (!result.ok)
|
|
91
|
+
throw new Error(
|
|
92
|
+
`${result.command} failed: ${result.stderr || result.stdout || result.error || result.status}`,
|
|
93
|
+
);
|
|
88
94
|
return result.stdout;
|
|
89
95
|
}
|
|
90
96
|
|
|
@@ -97,7 +103,9 @@ function normalized(path) {
|
|
|
97
103
|
}
|
|
98
104
|
|
|
99
105
|
function sha256(path) {
|
|
100
|
-
return createHash('sha256')
|
|
106
|
+
return createHash('sha256')
|
|
107
|
+
.update(readFileSync(resolve(ROOT, path)))
|
|
108
|
+
.digest('hex');
|
|
101
109
|
}
|
|
102
110
|
|
|
103
111
|
function readJsonIfExists(path) {
|
|
@@ -106,9 +114,24 @@ function readJsonIfExists(path) {
|
|
|
106
114
|
}
|
|
107
115
|
|
|
108
116
|
function collectChangedPaths() {
|
|
109
|
-
const changed = splitZ(
|
|
110
|
-
|
|
111
|
-
|
|
117
|
+
const changed = splitZ(
|
|
118
|
+
assertOk(run('git', ['-c', 'core.quotepath=false', 'diff', '--name-only', '-z', 'HEAD', '--'])),
|
|
119
|
+
);
|
|
120
|
+
const untracked = splitZ(
|
|
121
|
+
assertOk(
|
|
122
|
+
run('git', [
|
|
123
|
+
'-c',
|
|
124
|
+
'core.quotepath=false',
|
|
125
|
+
'ls-files',
|
|
126
|
+
'--others',
|
|
127
|
+
'--exclude-standard',
|
|
128
|
+
'-z',
|
|
129
|
+
]),
|
|
130
|
+
),
|
|
131
|
+
);
|
|
132
|
+
return [...new Set([...changed, ...untracked].map(normalized))].sort((a, b) =>
|
|
133
|
+
a.localeCompare(b),
|
|
134
|
+
);
|
|
112
135
|
}
|
|
113
136
|
|
|
114
137
|
function fileMode(path) {
|
|
@@ -136,9 +159,34 @@ function changedEntries() {
|
|
|
136
159
|
}
|
|
137
160
|
|
|
138
161
|
function remoteRefs(repository, branch, version) {
|
|
139
|
-
let result = run(
|
|
140
|
-
|
|
141
|
-
|
|
162
|
+
let result = run(
|
|
163
|
+
'git',
|
|
164
|
+
[
|
|
165
|
+
'ls-remote',
|
|
166
|
+
`https://github.com/${repository}.git`,
|
|
167
|
+
`refs/heads/${branch}`,
|
|
168
|
+
`refs/tags/v${version}`,
|
|
169
|
+
],
|
|
170
|
+
{ timeout: 60_000 },
|
|
171
|
+
);
|
|
172
|
+
if (
|
|
173
|
+
!result.ok &&
|
|
174
|
+
/schannel|AcquireCredentialsHandle|SEC_E_NO_CREDENTIALS/i.test(
|
|
175
|
+
`${result.stderr}\n${result.stdout}`,
|
|
176
|
+
)
|
|
177
|
+
) {
|
|
178
|
+
result = run(
|
|
179
|
+
'git',
|
|
180
|
+
[
|
|
181
|
+
'-c',
|
|
182
|
+
'http.sslBackend=openssl',
|
|
183
|
+
'ls-remote',
|
|
184
|
+
`https://github.com/${repository}.git`,
|
|
185
|
+
`refs/heads/${branch}`,
|
|
186
|
+
`refs/tags/v${version}`,
|
|
187
|
+
],
|
|
188
|
+
{ timeout: 60_000 },
|
|
189
|
+
);
|
|
142
190
|
result.fallback = 'openssl';
|
|
143
191
|
}
|
|
144
192
|
|
|
@@ -155,7 +203,10 @@ function remoteRefs(repository, branch, version) {
|
|
|
155
203
|
}
|
|
156
204
|
|
|
157
205
|
function releaseDates() {
|
|
158
|
-
const headTime = Number.parseInt(
|
|
206
|
+
const headTime = Number.parseInt(
|
|
207
|
+
assertOk(run('git', ['show', '-s', '--format=%ct', 'HEAD'])),
|
|
208
|
+
10,
|
|
209
|
+
);
|
|
159
210
|
const commitEpoch = headTime + 1;
|
|
160
211
|
return {
|
|
161
212
|
commitEpoch,
|
|
@@ -191,7 +242,9 @@ async function githubJson(token, repository, path, options = {}) {
|
|
|
191
242
|
const payload = text ? JSON.parse(text) : null;
|
|
192
243
|
if (!response.ok) {
|
|
193
244
|
const message = payload?.message ?? text.slice(0, 500) ?? response.statusText;
|
|
194
|
-
throw new Error(
|
|
245
|
+
throw new Error(
|
|
246
|
+
`GitHub API ${options.method ?? 'GET'} ${path} failed (${response.status}): ${message}`,
|
|
247
|
+
);
|
|
195
248
|
}
|
|
196
249
|
return payload;
|
|
197
250
|
}
|
|
@@ -238,12 +291,18 @@ function localState(args) {
|
|
|
238
291
|
const bytes = entries.reduce((total, entry) => total + entry.bytes, 0);
|
|
239
292
|
const blockers = [];
|
|
240
293
|
|
|
241
|
-
if (!refs.result.ok)
|
|
294
|
+
if (!refs.result.ok)
|
|
295
|
+
blockers.push(
|
|
296
|
+
`Remote ref check failed: ${refs.result.stderr || refs.result.stdout || refs.result.error}`,
|
|
297
|
+
);
|
|
242
298
|
if (refs.branch && refs.branch !== localHead && !args.force) {
|
|
243
299
|
blockers.push(`Remote ${args.branch} is ${refs.branch}, but local HEAD is ${localHead}`);
|
|
244
300
|
}
|
|
245
301
|
if (refs.tag) blockers.push(`Remote tag v${args.version} already exists at ${refs.tag}`);
|
|
246
|
-
if (!objectReport?.commit || !objectReport?.tree)
|
|
302
|
+
if (!objectReport?.commit || !objectReport?.tree)
|
|
303
|
+
blockers.push(
|
|
304
|
+
'Missing .tmp/release-git-object-report.json; run npm run release:artifacts first',
|
|
305
|
+
);
|
|
247
306
|
|
|
248
307
|
return {
|
|
249
308
|
localHead,
|
|
@@ -283,7 +342,9 @@ async function publishWithGitHubApi(args, state, token) {
|
|
|
283
342
|
});
|
|
284
343
|
|
|
285
344
|
if (state.expectedReleaseTree && tree.sha !== state.expectedReleaseTree) {
|
|
286
|
-
throw new Error(
|
|
345
|
+
throw new Error(
|
|
346
|
+
`GitHub release tree ${tree.sha} does not match local source-bundle tree ${state.expectedReleaseTree}`,
|
|
347
|
+
);
|
|
287
348
|
}
|
|
288
349
|
|
|
289
350
|
const dates = releaseDates();
|
|
@@ -300,7 +361,9 @@ async function publishWithGitHubApi(args, state, token) {
|
|
|
300
361
|
});
|
|
301
362
|
|
|
302
363
|
if (state.expectedReleaseCommit && commit.sha !== state.expectedReleaseCommit) {
|
|
303
|
-
throw new Error(
|
|
364
|
+
throw new Error(
|
|
365
|
+
`GitHub release commit ${commit.sha} does not match local source-bundle commit ${state.expectedReleaseCommit}`,
|
|
366
|
+
);
|
|
304
367
|
}
|
|
305
368
|
|
|
306
369
|
const branchUpdate = await githubJson(token, args.repository, `/git/refs/heads/${args.branch}`, {
|
|
@@ -398,12 +461,12 @@ async function main() {
|
|
|
398
461
|
})),
|
|
399
462
|
changedEntries: args.includeEntries
|
|
400
463
|
? state.entries.map(entry => ({
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
464
|
+
path: entry.path,
|
|
465
|
+
deleted: entry.deleted,
|
|
466
|
+
mode: entry.mode,
|
|
467
|
+
bytes: entry.bytes,
|
|
468
|
+
sha256: entry.sha256,
|
|
469
|
+
}))
|
|
407
470
|
: undefined,
|
|
408
471
|
finalizeArtifacts: state.finalizeArtifacts,
|
|
409
472
|
blockers: [...state.blockers],
|
|
@@ -413,7 +476,9 @@ async function main() {
|
|
|
413
476
|
if (args.apply) {
|
|
414
477
|
const token = process.env[args.tokenEnv];
|
|
415
478
|
if (!token) {
|
|
416
|
-
report.blockers.push(
|
|
479
|
+
report.blockers.push(
|
|
480
|
+
`Set ${args.tokenEnv} to a GitHub token with contents:write before applying`,
|
|
481
|
+
);
|
|
417
482
|
} else if (report.blockers.length === 0) {
|
|
418
483
|
report.publish = await publishWithGitHubApi(args, state, token);
|
|
419
484
|
}
|
package/scripts/smoke-cli.js
CHANGED
|
@@ -24,11 +24,9 @@ if (!existsSync(cli)) {
|
|
|
24
24
|
}
|
|
25
25
|
|
|
26
26
|
function createTempRoot() {
|
|
27
|
-
const candidates = [
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
join(root, '.tmp'),
|
|
31
|
-
].filter(Boolean);
|
|
27
|
+
const candidates = [process.env.AUDREY_SMOKE_TMPDIR, tmpdir(), join(root, '.tmp')].filter(
|
|
28
|
+
Boolean,
|
|
29
|
+
);
|
|
32
30
|
const failures = [];
|
|
33
31
|
|
|
34
32
|
for (const candidate of candidates) {
|
|
@@ -75,10 +73,12 @@ try {
|
|
|
75
73
|
|
|
76
74
|
const doctor = JSON.parse(run('doctor --json', ['doctor', '--json']));
|
|
77
75
|
if (doctor.version !== pkg.version || doctor.ok !== true) {
|
|
78
|
-
fail(
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
76
|
+
fail(
|
|
77
|
+
`doctor --json returned unexpected release status: ${JSON.stringify({
|
|
78
|
+
version: doctor.version,
|
|
79
|
+
ok: doctor.ok,
|
|
80
|
+
})}`,
|
|
81
|
+
);
|
|
82
82
|
}
|
|
83
83
|
|
|
84
84
|
const demo = run('demo', ['demo']);
|