diff --git a/examples/hooks-and-scripts/README.md b/examples/hooks-and-scripts/README.md index ea77731c8..49b4ed312 100644 --- a/examples/hooks-and-scripts/README.md +++ b/examples/hooks-and-scripts/README.md @@ -9,7 +9,9 @@ pnpm example:hooks The example is credential-free. It models a release preparation session with a session-start Hook, a manifest-backed packaging check, and a risk-register check so the Workbench can show canonical Hook simulation, successful and -blocking script traces, and live Logs. +blocking script traces, and live Logs. Both scripts export `main` and return +their exit codes; the build generates the process envelope that owns argv, +awaiting, and exit-code adoption. ## Workbench walkthrough diff --git a/examples/hooks-and-scripts/src/scripts/detect-risk.ts b/examples/hooks-and-scripts/src/scripts/detect-risk.ts index 05369d5ee..ba595a133 100644 --- a/examples/hooks-and-scripts/src/scripts/detect-risk.ts +++ b/examples/hooks-and-scripts/src/scripts/detect-risk.ts @@ -13,20 +13,22 @@ interface RiskRegister { const registerPath = new URL('../assets/release/risk-register.json', import.meta.url); -try { - const register = JSON.parse(await readFile(registerPath, 'utf8')) as RiskRegister; - if (!Array.isArray(register.risks)) throw new Error('risk register must contain a risks array'); +export const main = async (): Promise => { + try { + const register = JSON.parse(await readFile(registerPath, 'utf8')) as RiskRegister; + if (!Array.isArray(register.risks)) throw new Error('risk register must contain a risks array'); - const blockers = register.risks.filter((risk) => risk.status === 'open' && risk.severity === 'high'); - if (blockers.length === 0) { - process.stdout.write('No open high-severity release risks found.\n'); - } else { + const blockers = register.risks.filter((risk) => risk.status === 'open' && risk.severity === 'high'); + if (blockers.length === 0) { + process.stdout.write('No open high-severity release risks found.\n'); + return 0; + } for (const risk of blockers) { process.stderr.write(`${typeof risk.id === 'string' ? risk.id : 'UNIDENTIFIED'}: ${typeof risk.summary === 'string' ? risk.summary : 'Open high-severity release risk'}\n`); } - process.exitCode = 2; + return 2; + } catch (error) { + process.stderr.write(`Unable to detect release risks: ${error instanceof Error ? error.message : String(error)}\n`); + return 1; } -} catch (error) { - process.stderr.write(`Unable to detect release risks: ${error instanceof Error ? error.message : String(error)}\n`); - process.exitCode = 1; -} +}; diff --git a/examples/hooks-and-scripts/src/scripts/verify-release.ts b/examples/hooks-and-scripts/src/scripts/verify-release.ts index 85b99f3c5..1d6510e56 100644 --- a/examples/hooks-and-scripts/src/scripts/verify-release.ts +++ b/examples/hooks-and-scripts/src/scripts/verify-release.ts @@ -35,16 +35,18 @@ const validationErrors = (manifest: ReleaseManifest): readonly string[] => { return errors; }; -try { - const manifest = await readManifest(); - const errors = validationErrors(manifest); - if (errors.length > 0) { - process.stderr.write(`Release manifest is incomplete:\n${errors.map((error) => `- ${error}`).join('\n')}\n`); - process.exitCode = 1; - } else { +export const main = async (): Promise => { + try { + const manifest = await readManifest(); + const errors = validationErrors(manifest); + if (errors.length > 0) { + process.stderr.write(`Release manifest is incomplete:\n${errors.map((error) => `- ${error}`).join('\n')}\n`); + return 1; + } process.stdout.write(`Release ${manifest.version} is ready for packaging.\n`); + return 0; + } catch (error) { + process.stderr.write(`Unable to verify release manifest: ${error instanceof Error ? error.message : String(error)}\n`); + return 1; } -} catch (error) { - process.stderr.write(`Unable to verify release manifest: ${error instanceof Error ? error.message : String(error)}\n`); - process.exitCode = 1; -} +};