@guilz-dev/belay 0.9.3 → 0.10.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.
- package/README.md +38 -3
- package/dist/adapters/codex/hooks.d.ts +1 -0
- package/dist/adapters/codex/hooks.js +3 -0
- package/dist/adapters/cursor/dispatcher-generation.d.ts +3 -0
- package/dist/adapters/cursor/dispatcher-generation.js +5 -0
- package/dist/adapters/cursor/hook-dispatch-entry.d.ts +10 -0
- package/dist/adapters/cursor/hook-dispatch-entry.js +137 -0
- package/dist/adapters/cursor/hook-router.d.ts +23 -0
- package/dist/adapters/cursor/hook-router.js +273 -0
- package/dist/adapters/cursor/hooks.d.ts +5 -1
- package/dist/adapters/cursor/hooks.js +112 -10
- package/dist/adapters/cursor/routing-config-trust.d.ts +1 -0
- package/dist/adapters/cursor/routing-config-trust.js +67 -0
- package/dist/adapters/cursor/routing-layout.d.ts +5 -0
- package/dist/adapters/cursor/routing-layout.js +29 -0
- package/dist/adapters/cursor/runtime-entry.d.ts +17 -0
- package/dist/adapters/cursor/runtime-entry.js +74 -49
- package/dist/adapters/layouts/scope.d.ts +5 -0
- package/dist/adapters/layouts/scope.js +71 -0
- package/dist/adapters/shared/gate-runtime.js +29 -17
- package/dist/bundle/claude-runtime.mjs +2428 -2072
- package/dist/bundle/codex-runtime.mjs +2440 -2084
- package/dist/bundle/cursor-dispatcher.mjs +517 -0
- package/dist/bundle/cursor-runtime.mjs +2521 -2133
- package/dist/cli.js +53 -4
- package/dist/commands/approval-token.d.ts +10 -0
- package/dist/commands/approval-token.js +26 -0
- package/dist/commands/audit.d.ts +2 -1
- package/dist/commands/audit.js +2 -2
- package/dist/commands/config.d.ts +1 -1
- package/dist/commands/config.js +28 -2
- package/dist/commands/doctor.js +149 -17
- package/dist/commands/dogfood-check.d.ts +3 -0
- package/dist/commands/dogfood-check.js +116 -0
- package/dist/commands/dogfood.d.ts +1 -0
- package/dist/commands/dogfood.js +4 -3
- package/dist/commands/health-snapshot.js +9 -4
- package/dist/commands/judge.js +2 -2
- package/dist/commands/recovery-checkpoints.d.ts +3 -3
- package/dist/commands/recovery-checkpoints.js +2 -11
- package/dist/config-io.d.ts +1 -0
- package/dist/config-io.js +19 -3
- package/dist/core/audit-legacy-archive.js +43 -25
- package/dist/core/classify-tool.js +16 -8
- package/dist/core/dogfood-environment.d.ts +8 -0
- package/dist/core/dogfood-environment.js +55 -0
- package/dist/core/effect-ir/argv-delegate.d.ts +9 -0
- package/dist/core/effect-ir/argv-delegate.js +42 -0
- package/dist/core/effect-ir/shell-lower/argv-delegate-gate.d.ts +3 -0
- package/dist/core/effect-ir/shell-lower/argv-delegate-gate.js +40 -0
- package/dist/core/effect-ir/shell-lower/augment.d.ts +4 -0
- package/dist/core/effect-ir/shell-lower/augment.js +97 -0
- package/dist/core/effect-ir/shell-lower/context.d.ts +10 -0
- package/dist/core/effect-ir/shell-lower/context.js +1 -0
- package/dist/core/effect-ir/shell-lower/decode-process.d.ts +9 -0
- package/dist/core/effect-ir/shell-lower/decode-process.js +201 -0
- package/dist/core/effect-ir/shell-lower/decoders/belay.d.ts +2 -0
- package/dist/core/effect-ir/shell-lower/decoders/belay.js +41 -0
- package/dist/core/effect-ir/shell-lower/decoders/builtins.d.ts +7 -0
- package/dist/core/effect-ir/shell-lower/decoders/builtins.js +194 -0
- package/dist/core/effect-ir/shell-lower/decoders/decode-package-exec.d.ts +4 -0
- package/dist/core/effect-ir/shell-lower/decoders/decode-package-exec.js +68 -0
- package/dist/core/effect-ir/shell-lower/decoders/docker.d.ts +3 -0
- package/dist/core/effect-ir/shell-lower/decoders/docker.js +43 -0
- package/dist/core/effect-ir/shell-lower/decoders/filesystem.d.ts +9 -0
- package/dist/core/effect-ir/shell-lower/decoders/filesystem.js +217 -0
- package/dist/core/effect-ir/shell-lower/decoders/prisma.d.ts +2 -0
- package/dist/core/effect-ir/shell-lower/decoders/prisma.js +54 -0
- package/dist/core/effect-ir/shell-lower/decoders/ruby.d.ts +11 -0
- package/dist/core/effect-ir/shell-lower/decoders/ruby.js +147 -0
- package/dist/core/effect-ir/shell-lower/decoders/toolchain.d.ts +7 -0
- package/dist/core/effect-ir/shell-lower/decoders/toolchain.js +155 -0
- package/dist/core/effect-ir/shell-lower/requirement.d.ts +12 -0
- package/dist/core/effect-ir/shell-lower/requirement.js +65 -0
- package/dist/core/effect-ir/shell-lower/segment.d.ts +11 -0
- package/dist/core/effect-ir/shell-lower/segment.js +82 -0
- package/dist/core/effect-ir/shell-lower/tokens.d.ts +26 -0
- package/dist/core/effect-ir/shell-lower/tokens.js +183 -0
- package/dist/core/effect-ir/shell-lower.d.ts +2 -7
- package/dist/core/effect-ir/shell-lower.js +60 -1502
- package/dist/core/egress-approval.js +0 -18
- package/dist/core/glob.js +32 -16
- package/dist/core/integrity.d.ts +2 -2
- package/dist/core/integrity.js +52 -12
- package/dist/core/notify.d.ts +8 -2
- package/dist/core/notify.js +63 -7
- package/dist/core/recovery/operator-guidance.js +4 -4
- package/dist/core/replay-scrub.d.ts +2 -0
- package/dist/core/replay-scrub.js +8 -0
- package/dist/core/repo-config-trust.d.ts +31 -0
- package/dist/core/repo-config-trust.js +152 -0
- package/dist/core/shell-substitution.js +2 -2
- package/dist/core/shell-unparseable.js +3 -1
- package/dist/corpus/benign-probe-cores.d.ts +1 -1
- package/dist/corpus/benign-probe-cores.js +0 -1
- package/dist/defaults.d.ts +7 -3
- package/dist/defaults.js +29 -47
- package/dist/installer/bootstrap.d.ts +1 -0
- package/dist/installer/bootstrap.js +2 -2
- package/dist/installer/runtime-artifacts.js +43 -13
- package/dist/installer/scope-config.js +2 -2
- package/dist/installer.js +48 -13
- package/dist/node-resolution.d.ts +1 -0
- package/dist/node-resolution.js +61 -0
- package/dist/templates.d.ts +7 -4
- package/dist/templates.js +42 -4
- package/dist/types.d.ts +20 -0
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/package.json +5 -1
package/dist/defaults.js
CHANGED
|
@@ -1,62 +1,42 @@
|
|
|
1
1
|
import path from 'node:path';
|
|
2
2
|
import { cursorLayout } from './adapters/layouts/cursor.js';
|
|
3
|
-
import { buildRunnerInvocation } from './adapters/layouts/scope.js';
|
|
3
|
+
import { buildAbsoluteRunnerInvocation, buildLegacyAbsoluteRunnerInvocation, buildLegacyBarePowerShellRunnerInvocation, buildLegacyQuotedAbsoluteRunnerInvocation, buildRunnerInvocation, } from './adapters/layouts/scope.js';
|
|
4
4
|
import { DEFAULT_CONFIG_V3 } from './core/config.js';
|
|
5
5
|
export { PACKAGE_NAME } from './branding.js';
|
|
6
6
|
export const DEFAULT_CONFIG = DEFAULT_CONFIG_V3;
|
|
7
|
-
function runnerCommand(platform, hooksDir,
|
|
8
|
-
|
|
7
|
+
function runnerCommand(platform, hooksDir, _repoRoot, hookScript, runnerPathMode, ...args) {
|
|
8
|
+
if (runnerPathMode === 'absolute') {
|
|
9
|
+
return buildAbsoluteRunnerInvocation(platform, hooksDir, hookScript, ...args);
|
|
10
|
+
}
|
|
11
|
+
if (runnerPathMode === 'legacy-absolute') {
|
|
12
|
+
return buildLegacyAbsoluteRunnerInvocation(platform, hooksDir, hookScript, ...args);
|
|
13
|
+
}
|
|
14
|
+
if (runnerPathMode === 'legacy-quoted-absolute') {
|
|
15
|
+
return buildLegacyQuotedAbsoluteRunnerInvocation(platform, hooksDir, hookScript, ...args);
|
|
16
|
+
}
|
|
17
|
+
if (runnerPathMode === 'legacy-bare-powershell-absolute') {
|
|
18
|
+
return buildLegacyBarePowerShellRunnerInvocation(platform, hooksDir, hookScript, ...args);
|
|
19
|
+
}
|
|
20
|
+
return buildRunnerInvocation(platform, hooksDir, _repoRoot, hookScript, ...args);
|
|
9
21
|
}
|
|
10
|
-
export function getManagedHookEntries(platform = process.platform, hooksDir, repoRoot) {
|
|
22
|
+
export function getManagedHookEntries(platform = process.platform, hooksDir, repoRoot, runnerPathMode = 'absolute') {
|
|
11
23
|
const resolvedRepo = path.resolve(repoRoot ?? process.cwd());
|
|
12
24
|
const resolvedHooksDir = hooksDir ?? cursorLayout.hooksDir(resolvedRepo);
|
|
13
|
-
const toolGate = runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-tool-gate', 'preToolUse');
|
|
14
|
-
const subagentGate = runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-tool-gate', 'subagentStart');
|
|
15
|
-
|
|
25
|
+
const toolGate = runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-tool-gate', runnerPathMode, 'preToolUse');
|
|
26
|
+
const subagentGate = runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-tool-gate', runnerPathMode, 'subagentStart');
|
|
27
|
+
const entries = [
|
|
16
28
|
{
|
|
17
29
|
event: 'beforeSubmitPrompt',
|
|
18
30
|
definition: {
|
|
19
|
-
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-before-submit'),
|
|
31
|
+
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-before-submit', runnerPathMode),
|
|
20
32
|
placement: 'prepend',
|
|
21
33
|
},
|
|
22
34
|
},
|
|
23
35
|
{
|
|
24
36
|
event: 'beforeShellExecution',
|
|
25
37
|
definition: {
|
|
26
|
-
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-shell-gate'),
|
|
27
|
-
placement: 'prepend',
|
|
28
|
-
},
|
|
29
|
-
},
|
|
30
|
-
{
|
|
31
|
-
event: 'preToolUse',
|
|
32
|
-
definition: {
|
|
33
|
-
command: toolGate,
|
|
34
|
-
placement: 'prepend',
|
|
35
|
-
matcher: 'Task',
|
|
36
|
-
},
|
|
37
|
-
},
|
|
38
|
-
{
|
|
39
|
-
event: 'preToolUse',
|
|
40
|
-
definition: {
|
|
41
|
-
command: toolGate,
|
|
42
|
-
placement: 'prepend',
|
|
43
|
-
matcher: 'Write',
|
|
44
|
-
},
|
|
45
|
-
},
|
|
46
|
-
{
|
|
47
|
-
event: 'preToolUse',
|
|
48
|
-
definition: {
|
|
49
|
-
command: toolGate,
|
|
50
|
-
placement: 'prepend',
|
|
51
|
-
matcher: 'StrReplace',
|
|
52
|
-
},
|
|
53
|
-
},
|
|
54
|
-
{
|
|
55
|
-
event: 'preToolUse',
|
|
56
|
-
definition: {
|
|
57
|
-
command: toolGate,
|
|
38
|
+
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-shell-gate', runnerPathMode),
|
|
58
39
|
placement: 'prepend',
|
|
59
|
-
matcher: 'Delete',
|
|
60
40
|
},
|
|
61
41
|
},
|
|
62
42
|
{
|
|
@@ -64,8 +44,6 @@ export function getManagedHookEntries(platform = process.platform, hooksDir, rep
|
|
|
64
44
|
definition: {
|
|
65
45
|
command: toolGate,
|
|
66
46
|
placement: 'prepend',
|
|
67
|
-
// Agent Shell tool (preToolUse) — distinct from terminal beforeShellExecution.
|
|
68
|
-
matcher: 'Shell',
|
|
69
47
|
},
|
|
70
48
|
},
|
|
71
49
|
{
|
|
@@ -119,32 +97,36 @@ export function getManagedHookEntries(platform = process.platform, hooksDir, rep
|
|
|
119
97
|
{
|
|
120
98
|
event: 'postToolUse',
|
|
121
99
|
definition: {
|
|
122
|
-
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-audit', 'postToolUse'),
|
|
100
|
+
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-audit', runnerPathMode, 'postToolUse'),
|
|
123
101
|
placement: 'append',
|
|
124
102
|
},
|
|
125
103
|
},
|
|
126
104
|
{
|
|
127
105
|
event: 'postToolUseFailure',
|
|
128
106
|
definition: {
|
|
129
|
-
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-audit', 'postToolUseFailure'),
|
|
107
|
+
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-audit', runnerPathMode, 'postToolUseFailure'),
|
|
130
108
|
placement: 'append',
|
|
131
109
|
},
|
|
132
110
|
},
|
|
133
111
|
{
|
|
134
112
|
event: 'stop',
|
|
135
113
|
definition: {
|
|
136
|
-
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-audit', 'stop'),
|
|
114
|
+
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-audit', runnerPathMode, 'stop'),
|
|
137
115
|
placement: 'append',
|
|
138
116
|
},
|
|
139
117
|
},
|
|
140
118
|
{
|
|
141
119
|
event: 'sessionEnd',
|
|
142
120
|
definition: {
|
|
143
|
-
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-audit', 'sessionEnd'),
|
|
121
|
+
command: runnerCommand(platform, resolvedHooksDir, resolvedRepo, 'belay-audit', runnerPathMode, 'sessionEnd'),
|
|
144
122
|
placement: 'append',
|
|
145
123
|
},
|
|
146
124
|
},
|
|
147
125
|
];
|
|
126
|
+
return entries.map(({ event, definition }) => ({
|
|
127
|
+
event,
|
|
128
|
+
definition: { ...definition, failClosed: true },
|
|
129
|
+
}));
|
|
148
130
|
}
|
|
149
131
|
/** @deprecated Use getManagedHookEntries instead. */
|
|
150
132
|
export function getManagedHookEvents(platform = process.platform) {
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import type { ScopedPaths } from '../adapters/layouts/scope.js';
|
|
2
2
|
import type { AdapterName } from '../adapters/layouts/types.js';
|
|
3
3
|
import type { BelayConfigV3 } from '../core/config.js';
|
|
4
|
+
export declare const CURSOR_COMMAND_ARTIFACTS: readonly ["belay-approve.md", "belay-why.md", "belay-explain.md", "belay-status.md", "belay-report.md", "belay-recover.md"];
|
|
4
5
|
export declare function bootstrapStateFiles(repoRoot: string, config: BelayConfigV3, paths: ScopedPaths): Promise<void>;
|
|
5
6
|
export declare function writeSkillArtifacts(adapterName: AdapterName, paths: ScopedPaths): Promise<void>;
|
|
@@ -4,7 +4,7 @@ import path from 'node:path';
|
|
|
4
4
|
import { approvedApprovalsPath, pendingApprovalsPath } from '../config-io.js';
|
|
5
5
|
import { EMPTY_APPROVALS } from '../defaults.js';
|
|
6
6
|
const BUNDLED_SKILL_TEMPLATE_URL = new URL('../../skills/belay/SKILL.md', import.meta.url);
|
|
7
|
-
const
|
|
7
|
+
export const CURSOR_COMMAND_ARTIFACTS = [
|
|
8
8
|
'belay-approve.md',
|
|
9
9
|
'belay-why.md',
|
|
10
10
|
'belay-explain.md',
|
|
@@ -53,7 +53,7 @@ export async function writeSkillArtifacts(adapterName, paths) {
|
|
|
53
53
|
await writeFile(path.join(paths.skillsDir, 'SKILL.md'), bundledSkill, 'utf8');
|
|
54
54
|
if (adapterName === 'cursor' && paths.commandsDir) {
|
|
55
55
|
await mkdir(paths.commandsDir, { recursive: true });
|
|
56
|
-
for (const fileName of
|
|
56
|
+
for (const fileName of CURSOR_COMMAND_ARTIFACTS) {
|
|
57
57
|
const bundledCommand = await readBundledTemplate(new URL(`../../skills/belay/${fileName}`, import.meta.url));
|
|
58
58
|
await writeFile(path.join(paths.commandsDir, fileName), bundledCommand, 'utf8');
|
|
59
59
|
}
|
|
@@ -1,23 +1,53 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { randomUUID } from 'node:crypto';
|
|
2
|
+
import { chmod, mkdir, realpath, rename, rm, writeFile } from 'node:fs/promises';
|
|
2
3
|
import path from 'node:path';
|
|
3
|
-
import { buildRunnerScript, buildWindowsRunnerScript } from '../node-resolution.js';
|
|
4
|
-
import { renderAuditHook, renderBeforeSubmitHook, renderRuntimeCore, renderShellGateHook, renderToolGateHook, } from '../templates.js';
|
|
4
|
+
import { buildRunnerScript, buildWindowsPowerShellRunnerScript, buildWindowsRunnerScript, } from '../node-resolution.js';
|
|
5
|
+
import { renderAuditHook, renderBeforeSubmitHook, renderCursorDispatcher, renderRuntimeCore, renderShellGateHook, renderToolGateHook, } from '../templates.js';
|
|
5
6
|
async function writeFileMaybeExecutable(filePath, content, executable = false) {
|
|
6
7
|
await mkdir(path.dirname(filePath), { recursive: true });
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
await
|
|
8
|
+
const temporaryPath = path.join(path.dirname(filePath), `.${path.basename(filePath)}.${process.pid}.${randomUUID()}.tmp`);
|
|
9
|
+
try {
|
|
10
|
+
await writeFile(temporaryPath, content, { encoding: 'utf8', flag: 'wx' });
|
|
11
|
+
if (executable) {
|
|
12
|
+
await chmod(temporaryPath, 0o755);
|
|
13
|
+
}
|
|
14
|
+
await rename(temporaryPath, filePath);
|
|
15
|
+
}
|
|
16
|
+
finally {
|
|
17
|
+
await rm(temporaryPath, { force: true });
|
|
10
18
|
}
|
|
11
19
|
}
|
|
12
20
|
export async function writeRuntimeArtifacts(adapterName, paths) {
|
|
13
21
|
const { hooksDir, runtimeDir } = paths;
|
|
22
|
+
const cursorOrigin = adapterName === 'cursor'
|
|
23
|
+
? paths.scope === 'global'
|
|
24
|
+
? { scope: 'global' }
|
|
25
|
+
: { scope: 'project', repoRoot: await realpath(paths.repoRoot) }
|
|
26
|
+
: undefined;
|
|
27
|
+
const artifacts = {
|
|
28
|
+
auditHook: renderAuditHook(adapterName, cursorOrigin),
|
|
29
|
+
beforeSubmitHook: renderBeforeSubmitHook(adapterName, cursorOrigin),
|
|
30
|
+
core: await renderRuntimeCore(adapterName),
|
|
31
|
+
dispatcher: adapterName === 'cursor' ? await renderCursorDispatcher() : undefined,
|
|
32
|
+
runner: buildRunnerScript(process.execPath),
|
|
33
|
+
runnerCmd: buildWindowsRunnerScript(process.execPath),
|
|
34
|
+
runnerPowerShell: adapterName === 'cursor' ? buildWindowsPowerShellRunnerScript(process.execPath) : undefined,
|
|
35
|
+
shellGateHook: renderShellGateHook(adapterName, cursorOrigin),
|
|
36
|
+
toolGateHook: renderToolGateHook(adapterName, cursorOrigin),
|
|
37
|
+
};
|
|
14
38
|
await mkdir(hooksDir, { recursive: true });
|
|
15
39
|
await mkdir(runtimeDir, { recursive: true });
|
|
16
|
-
await writeFileMaybeExecutable(path.join(
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
await writeFileMaybeExecutable(path.join(
|
|
21
|
-
await writeFileMaybeExecutable(path.join(hooksDir, 'belay-runner'),
|
|
22
|
-
|
|
40
|
+
await writeFileMaybeExecutable(path.join(runtimeDir, 'core.mjs'), artifacts.core);
|
|
41
|
+
if (artifacts.dispatcher !== undefined) {
|
|
42
|
+
await writeFileMaybeExecutable(path.join(runtimeDir, 'dispatcher.mjs'), artifacts.dispatcher);
|
|
43
|
+
}
|
|
44
|
+
await writeFileMaybeExecutable(path.join(hooksDir, 'belay-runner'), artifacts.runner, true);
|
|
45
|
+
await writeFileMaybeExecutable(path.join(hooksDir, 'belay-runner.cmd'), artifacts.runnerCmd);
|
|
46
|
+
if (artifacts.runnerPowerShell !== undefined) {
|
|
47
|
+
await writeFileMaybeExecutable(path.join(hooksDir, 'belay-runner.ps1'), artifacts.runnerPowerShell);
|
|
48
|
+
}
|
|
49
|
+
await writeFileMaybeExecutable(path.join(hooksDir, 'belay-before-submit.mjs'), artifacts.beforeSubmitHook);
|
|
50
|
+
await writeFileMaybeExecutable(path.join(hooksDir, 'belay-shell-gate.mjs'), artifacts.shellGateHook);
|
|
51
|
+
await writeFileMaybeExecutable(path.join(hooksDir, 'belay-tool-gate.mjs'), artifacts.toolGateHook);
|
|
52
|
+
await writeFileMaybeExecutable(path.join(hooksDir, 'belay-audit.mjs'), artifacts.auditHook);
|
|
23
53
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { existsSync } from 'node:fs';
|
|
2
2
|
import { getAdapterLayout } from '../adapters/layouts/index.js';
|
|
3
3
|
import { resolveInstallScope, resolveScopedPaths, } from '../adapters/layouts/scope.js';
|
|
4
|
-
import { loadConfigFile,
|
|
4
|
+
import { loadConfigFile, writeTrustedConfigFile } from '../config-io.js';
|
|
5
5
|
export async function resolveOperationScope(repoRoot, adapter, options = {}) {
|
|
6
6
|
const layout = getAdapterLayout(adapter);
|
|
7
7
|
let persisted;
|
|
@@ -17,7 +17,7 @@ export async function applyInstallScope(repoRoot, adapter, scope, config) {
|
|
|
17
17
|
return current;
|
|
18
18
|
}
|
|
19
19
|
const updated = { ...current, installScope: scope };
|
|
20
|
-
await
|
|
20
|
+
await writeTrustedConfigFile(repoRoot, updated, adapter);
|
|
21
21
|
return updated;
|
|
22
22
|
}
|
|
23
23
|
export function pathsForOperation(adapter, scope, repoRoot) {
|
package/dist/installer.js
CHANGED
|
@@ -1,19 +1,19 @@
|
|
|
1
1
|
import { existsSync } from 'node:fs';
|
|
2
2
|
import { mkdir, readFile, rm, writeFile } from 'node:fs/promises';
|
|
3
3
|
import path from 'node:path';
|
|
4
|
-
import { mergeCursorHooksFile, stripCursorHooksFile } from './adapters/cursor/hooks.js';
|
|
4
|
+
import { hasManagedCursorHookEntries, mergeCursorHooksFile, stripCursorHooksFile, } from './adapters/cursor/hooks.js';
|
|
5
5
|
import { cursorLayout } from './adapters/layouts/cursor.js';
|
|
6
6
|
import { resolveScopedPaths } from './adapters/layouts/scope.js';
|
|
7
7
|
import { getAdapter } from './adapters/registry.js';
|
|
8
8
|
import { dogfoodProject } from './commands/dogfood.js';
|
|
9
|
-
import { detectAdapterName, loadConfigFile, mergeAndWriteConfig,
|
|
9
|
+
import { detectAdapterName, loadConfigFile, mergeAndWriteConfig, writeTrustedConfigFile, } from './config-io.js';
|
|
10
10
|
import { appendCliAuditEvent } from './core/audit-io.js';
|
|
11
11
|
import { archiveLegacyAuditLogIfNeeded } from './core/audit-legacy-archive.js';
|
|
12
12
|
import { isFreshConfigInput, mergeConfig, normalizeConfig, } from './core/config.js';
|
|
13
13
|
import { runtimeIntegrityFiles, writeIntegrityManifest } from './core/integrity.js';
|
|
14
14
|
import { hasValidCloudConsent, isCloudJudgeConfig, migrateImplicitLocalJudgeIfNeeded, resolveInitJudgeConfig, } from './core/judge-config.js';
|
|
15
15
|
import { resolveJudgeTransport } from './core/judge-runtime-detection.js';
|
|
16
|
-
import { bootstrapStateFiles, writeSkillArtifacts } from './installer/bootstrap.js';
|
|
16
|
+
import { bootstrapStateFiles, CURSOR_COMMAND_ARTIFACTS, writeSkillArtifacts, } from './installer/bootstrap.js';
|
|
17
17
|
import { writeRuntimeArtifacts } from './installer/runtime-artifacts.js';
|
|
18
18
|
import { applyInstallScope, resolveOperationScope } from './installer/scope-config.js';
|
|
19
19
|
import { applyConfigPreset } from './presets.js';
|
|
@@ -64,7 +64,6 @@ export async function initCursorProject(options = {}) {
|
|
|
64
64
|
const mergedHooks = mergeCursorHooksFile(hooksFile, process.platform, paths.hooksDir, repoRoot);
|
|
65
65
|
await ensureDir(paths.hooksDir);
|
|
66
66
|
const config = await mergeAndWriteConfig(repoRoot, 'cursor');
|
|
67
|
-
await applyInstallScope(repoRoot, 'cursor', scope, config);
|
|
68
67
|
await writeRuntimeArtifacts('cursor', paths);
|
|
69
68
|
await bootstrapStateFiles(repoRoot, config, paths);
|
|
70
69
|
if (withSkill) {
|
|
@@ -72,8 +71,12 @@ export async function initCursorProject(options = {}) {
|
|
|
72
71
|
}
|
|
73
72
|
await mkdir(path.dirname(paths.hooksSettingsPath), { recursive: true });
|
|
74
73
|
await writeFile(paths.hooksSettingsPath, `${JSON.stringify(mergedHooks, null, 2)}\n`, 'utf8');
|
|
74
|
+
const installedConfig = await applyInstallScope(repoRoot, 'cursor', scope, config);
|
|
75
|
+
if (scope === 'global') {
|
|
76
|
+
await cleanupStaleProjectCursorInstall(repoRoot);
|
|
77
|
+
}
|
|
75
78
|
await writeIntegrityManifest(repoRoot, cursorLayout, runtimeIntegrityFiles(cursorLayout, paths));
|
|
76
|
-
await archiveLegacyAuditLogIfNeeded(repoRoot,
|
|
79
|
+
await archiveLegacyAuditLogIfNeeded(repoRoot, installedConfig);
|
|
77
80
|
return { repoRoot, withSkill };
|
|
78
81
|
}
|
|
79
82
|
export async function upgradeCursorProject(options = {}) {
|
|
@@ -81,17 +84,31 @@ export async function upgradeCursorProject(options = {}) {
|
|
|
81
84
|
const scope = await resolveOperationScope(repoRoot, 'cursor', options);
|
|
82
85
|
const paths = resolveScopedPaths(cursorLayout, scope, repoRoot);
|
|
83
86
|
const config = await mergeAndWriteConfig(repoRoot, 'cursor');
|
|
84
|
-
await applyInstallScope(repoRoot, 'cursor', scope, config);
|
|
85
87
|
await writeRuntimeArtifacts('cursor', paths);
|
|
86
88
|
const hooksFile = await loadHooksFile(paths.hooksSettingsPath);
|
|
87
89
|
const merged = mergeCursorHooksFile(hooksFile, process.platform, paths.hooksDir, repoRoot);
|
|
88
90
|
await mkdir(path.dirname(paths.hooksSettingsPath), { recursive: true });
|
|
89
91
|
await writeFile(paths.hooksSettingsPath, `${JSON.stringify(merged, null, 2)}\n`, 'utf8');
|
|
92
|
+
if (scope === 'project') {
|
|
93
|
+
const globalPaths = resolveScopedPaths(cursorLayout, 'global', repoRoot);
|
|
94
|
+
if (existsSync(globalPaths.hooksSettingsPath)) {
|
|
95
|
+
const globalHooks = await loadHooksFile(globalPaths.hooksSettingsPath);
|
|
96
|
+
if (hasManagedCursorHookEntries(globalHooks, process.platform, globalPaths.hooksDir, repoRoot)) {
|
|
97
|
+
await writeRuntimeArtifacts('cursor', globalPaths);
|
|
98
|
+
const mergedGlobal = mergeCursorHooksFile(globalHooks, process.platform, globalPaths.hooksDir, repoRoot);
|
|
99
|
+
await writeFile(globalPaths.hooksSettingsPath, `${JSON.stringify(mergedGlobal, null, 2)}\n`, 'utf8');
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
}
|
|
90
103
|
if (options.withSkill) {
|
|
91
104
|
await writeSkillArtifacts('cursor', paths);
|
|
92
105
|
}
|
|
106
|
+
const installedConfig = await applyInstallScope(repoRoot, 'cursor', scope, config);
|
|
107
|
+
if (scope === 'global') {
|
|
108
|
+
await cleanupStaleProjectCursorInstall(repoRoot);
|
|
109
|
+
}
|
|
93
110
|
await writeIntegrityManifest(repoRoot, cursorLayout, runtimeIntegrityFiles(cursorLayout, paths));
|
|
94
|
-
await archiveLegacyAuditLogIfNeeded(repoRoot,
|
|
111
|
+
await archiveLegacyAuditLogIfNeeded(repoRoot, installedConfig);
|
|
95
112
|
return { repoRoot };
|
|
96
113
|
}
|
|
97
114
|
const BELAY_HOOK_ARTIFACTS = [
|
|
@@ -101,16 +118,34 @@ const BELAY_HOOK_ARTIFACTS = [
|
|
|
101
118
|
'belay-audit.mjs',
|
|
102
119
|
'belay-runner',
|
|
103
120
|
'belay-runner.cmd',
|
|
121
|
+
'belay-runner.ps1',
|
|
104
122
|
];
|
|
105
123
|
async function removeBelayHookArtifacts(paths) {
|
|
106
124
|
for (const fileName of BELAY_HOOK_ARTIFACTS) {
|
|
107
125
|
await rm(path.join(paths.hooksDir, fileName), { force: true });
|
|
108
126
|
}
|
|
109
|
-
|
|
110
|
-
|
|
127
|
+
for (const fileName of ['core.mjs', 'dispatcher.mjs']) {
|
|
128
|
+
await rm(path.join(paths.runtimeDir, fileName), { force: true });
|
|
129
|
+
}
|
|
130
|
+
await rm(path.join(paths.skillsDir, 'SKILL.md'), { force: true });
|
|
111
131
|
if (paths.commandsDir) {
|
|
112
|
-
|
|
132
|
+
for (const fileName of CURSOR_COMMAND_ARTIFACTS) {
|
|
133
|
+
await rm(path.join(paths.commandsDir, fileName), { force: true });
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
async function cleanupStaleProjectCursorInstall(repoRoot) {
|
|
138
|
+
const projectPaths = resolveScopedPaths(cursorLayout, 'project', repoRoot);
|
|
139
|
+
if (!existsSync(projectPaths.hooksSettingsPath)) {
|
|
140
|
+
return;
|
|
141
|
+
}
|
|
142
|
+
const projectHooks = await loadHooksFile(projectPaths.hooksSettingsPath);
|
|
143
|
+
if (!hasManagedCursorHookEntries(projectHooks, process.platform, projectPaths.hooksDir, repoRoot)) {
|
|
144
|
+
return;
|
|
113
145
|
}
|
|
146
|
+
const stripped = stripCursorHooksFile(projectHooks, process.platform, projectPaths.hooksDir, repoRoot);
|
|
147
|
+
await writeFile(projectPaths.hooksSettingsPath, `${JSON.stringify(stripped, null, 2)}\n`, 'utf8');
|
|
148
|
+
await removeBelayHookArtifacts(projectPaths);
|
|
114
149
|
}
|
|
115
150
|
export async function uninstallCursorProject(options = {}) {
|
|
116
151
|
const repoRoot = path.resolve(options.targetDir ?? process.cwd());
|
|
@@ -195,7 +230,7 @@ async function applyInitJudgeConfig(repoRoot, adapterName, options, isFreshBefor
|
|
|
195
230
|
!hasValidCloudConsent(configWithJudge.judge)) {
|
|
196
231
|
process.stderr.write('Warning: Cloud judge saved without recorded consent. Tier1 cloud judge will fail closed until consent is granted (belay judge consent + belay approve, or TTY --accept-cloud-judge).\n');
|
|
197
232
|
}
|
|
198
|
-
await
|
|
233
|
+
await writeTrustedConfigFile(repoRoot, configWithJudge, adapterName);
|
|
199
234
|
if (migrated) {
|
|
200
235
|
await auditJudgeMigrationIfNeeded(repoRoot, adapterName, mergedConfig.judge, finalJudge, options.migrateJudgeDefault ? 'belay init --migrate-judge-default' : 'belay init');
|
|
201
236
|
}
|
|
@@ -228,7 +263,7 @@ export async function initProject(options = {}) {
|
|
|
228
263
|
const existing = await loadConfigFile(repoRoot, adapterName);
|
|
229
264
|
const presetConfig = mergeConfig(applyConfigPreset(options.preset));
|
|
230
265
|
const merged = mergeConfig(presetConfig, existing);
|
|
231
|
-
await
|
|
266
|
+
await writeTrustedConfigFile(repoRoot, merged, adapterName);
|
|
232
267
|
}
|
|
233
268
|
if (options.dogfood === true) {
|
|
234
269
|
await dogfoodProject({ targetDir: repoRoot, adapter: adapterName });
|
|
@@ -250,7 +285,7 @@ export async function upgradeProject(options = {}) {
|
|
|
250
285
|
const migrated = migrateImplicitLocalJudgeIfNeeded(mergedConfig.judge, adapterName);
|
|
251
286
|
if (migrated) {
|
|
252
287
|
const configWithJudge = normalizeConfig({ ...mergedConfig, version: 4, judge: migrated });
|
|
253
|
-
await
|
|
288
|
+
await writeTrustedConfigFile(repoRoot, configWithJudge, adapterName);
|
|
254
289
|
await auditJudgeMigrationIfNeeded(repoRoot, adapterName, mergedConfig.judge, migrated, 'belay upgrade --migrate-judge-default');
|
|
255
290
|
}
|
|
256
291
|
}
|
|
@@ -6,3 +6,4 @@ export interface NodeResolutionResult {
|
|
|
6
6
|
export declare function resolveNodeBinary(): NodeResolutionResult;
|
|
7
7
|
export declare function buildRunnerScript(defaultNodePath: string): string;
|
|
8
8
|
export declare function buildWindowsRunnerScript(defaultNodePath: string): string;
|
|
9
|
+
export declare function buildWindowsPowerShellRunnerScript(defaultNodePath: string): string;
|
package/dist/node-resolution.js
CHANGED
|
@@ -235,3 +235,64 @@ echo {}
|
|
|
235
235
|
exit /b 0
|
|
236
236
|
`;
|
|
237
237
|
}
|
|
238
|
+
export function buildWindowsPowerShellRunnerScript(defaultNodePath) {
|
|
239
|
+
const encodedDefault = Buffer.from(defaultNodePath, 'utf8').toString('base64');
|
|
240
|
+
return `$ErrorActionPreference = 'Stop'
|
|
241
|
+
|
|
242
|
+
$DefaultNode = [Text.Encoding]::UTF8.GetString([Convert]::FromBase64String('${encodedDefault}'))
|
|
243
|
+
$HookName = if ($args.Count -gt 0) { [string] $args[0] } else { '' }
|
|
244
|
+
$HookArguments = if ($args.Count -gt 1) { @($args[1..($args.Count - 1)]) } else { @() }
|
|
245
|
+
|
|
246
|
+
function Resolve-Node {
|
|
247
|
+
if ($DefaultNode -and (Test-Path -LiteralPath $DefaultNode -PathType Leaf)) {
|
|
248
|
+
return $DefaultNode
|
|
249
|
+
}
|
|
250
|
+
|
|
251
|
+
$PathNode = Get-Command node.exe -CommandType Application -ErrorAction SilentlyContinue
|
|
252
|
+
if ($null -ne $PathNode) {
|
|
253
|
+
return $PathNode.Source
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
if ($env:USERPROFILE) {
|
|
257
|
+
$NvmRoot = Join-Path $env:USERPROFILE '.nvm'
|
|
258
|
+
if (Test-Path -LiteralPath $NvmRoot -PathType Container) {
|
|
259
|
+
foreach ($VersionDirectory in Get-ChildItem -LiteralPath $NvmRoot -Directory | Sort-Object Name -Descending) {
|
|
260
|
+
$Candidate = Join-Path $VersionDirectory.FullName 'node.exe'
|
|
261
|
+
if (Test-Path -LiteralPath $Candidate -PathType Leaf) {
|
|
262
|
+
return $Candidate
|
|
263
|
+
}
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
return $null
|
|
269
|
+
}
|
|
270
|
+
|
|
271
|
+
function Fail-Audit {
|
|
272
|
+
[Console]::Error.WriteLine('belay: unable to resolve Node for audit hook')
|
|
273
|
+
[Console]::Out.WriteLine('{}')
|
|
274
|
+
exit 0
|
|
275
|
+
}
|
|
276
|
+
|
|
277
|
+
if (-not $HookName) {
|
|
278
|
+
Fail-Audit
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
$NodeBin = Resolve-Node
|
|
282
|
+
if (-not $NodeBin) {
|
|
283
|
+
if ($HookName -eq 'belay-before-submit') {
|
|
284
|
+
[Console]::Out.WriteLine('{"continue":false,"user_message":"belay could not resolve Node. Install or expose Node, run belay doctor, then retry."}')
|
|
285
|
+
exit 0
|
|
286
|
+
}
|
|
287
|
+
if ($HookName -in @('belay-shell-gate', 'belay-tool-gate')) {
|
|
288
|
+
[Console]::Out.WriteLine('{"permission":"deny","user_message":"belay could not resolve Node. Install or expose Node, run belay doctor, then retry."}')
|
|
289
|
+
exit 0
|
|
290
|
+
}
|
|
291
|
+
Fail-Audit
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
$ScriptPath = Join-Path $PSScriptRoot "$HookName.mjs"
|
|
295
|
+
& $NodeBin $ScriptPath @HookArguments
|
|
296
|
+
exit $LASTEXITCODE
|
|
297
|
+
`;
|
|
298
|
+
}
|
package/dist/templates.d.ts
CHANGED
|
@@ -1,7 +1,10 @@
|
|
|
1
|
+
import type { CursorHookOrigin } from './adapters/cursor/hook-router.js';
|
|
2
|
+
import type { AdapterName } from './adapters/layouts/types.js';
|
|
1
3
|
import type { BelayConfigV3 } from './core/config.js';
|
|
2
4
|
export declare function renderConfig(config: BelayConfigV3): string;
|
|
3
|
-
export declare function renderBeforeSubmitHook(): string;
|
|
4
|
-
export declare function renderShellGateHook(): string;
|
|
5
|
-
export declare function renderToolGateHook(): string;
|
|
6
|
-
export declare function renderAuditHook(): string;
|
|
5
|
+
export declare function renderBeforeSubmitHook(adapter: AdapterName, cursorOrigin?: CursorHookOrigin): string;
|
|
6
|
+
export declare function renderShellGateHook(adapter: AdapterName, cursorOrigin?: CursorHookOrigin): string;
|
|
7
|
+
export declare function renderToolGateHook(adapter: AdapterName, cursorOrigin?: CursorHookOrigin): string;
|
|
8
|
+
export declare function renderAuditHook(adapter: AdapterName, cursorOrigin?: CursorHookOrigin): string;
|
|
9
|
+
export declare function renderCursorDispatcher(): Promise<string>;
|
|
7
10
|
export declare function renderRuntimeCore(adapter?: 'cursor' | 'claude' | 'codex'): Promise<string>;
|
package/dist/templates.js
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { readFile } from 'node:fs/promises';
|
|
2
2
|
import path from 'node:path';
|
|
3
3
|
import { fileURLToPath } from 'node:url';
|
|
4
|
+
import { CURSOR_DISPATCHER_GENERATION_HEADER } from './adapters/cursor/dispatcher-generation.js';
|
|
4
5
|
import { hashValue } from './core/fingerprint.js';
|
|
5
6
|
import { PACKAGE_VERSION } from './version.js';
|
|
6
7
|
function inlineJson(value) {
|
|
@@ -9,26 +10,54 @@ function inlineJson(value) {
|
|
|
9
10
|
export function renderConfig(config) {
|
|
10
11
|
return `${inlineJson(config)}\n`;
|
|
11
12
|
}
|
|
12
|
-
|
|
13
|
+
function requireCursorOrigin(origin) {
|
|
14
|
+
if (!origin) {
|
|
15
|
+
throw new Error('Cursor hook origin is required when rendering dispatcher shims.');
|
|
16
|
+
}
|
|
17
|
+
return origin;
|
|
18
|
+
}
|
|
19
|
+
function renderCursorDispatchHook(origin, kind, eventName) {
|
|
20
|
+
return `import { dispatchCursorHook } from '../belay/runtime/dispatcher.mjs'
|
|
21
|
+
|
|
22
|
+
await dispatchCursorHook({
|
|
23
|
+
origin: ${JSON.stringify(origin)},
|
|
24
|
+
kind: ${JSON.stringify(kind)},
|
|
25
|
+
eventName: ${eventName},
|
|
26
|
+
})
|
|
27
|
+
`;
|
|
28
|
+
}
|
|
29
|
+
export function renderBeforeSubmitHook(adapter, cursorOrigin) {
|
|
30
|
+
if (adapter === 'cursor') {
|
|
31
|
+
return renderCursorDispatchHook(requireCursorOrigin(cursorOrigin), 'before-submit', JSON.stringify('beforeSubmitPrompt'));
|
|
32
|
+
}
|
|
13
33
|
return `import { runBeforeSubmitPromptHook } from '../belay/runtime/core.mjs'
|
|
14
34
|
|
|
15
35
|
await runBeforeSubmitPromptHook()
|
|
16
36
|
`;
|
|
17
37
|
}
|
|
18
|
-
export function renderShellGateHook() {
|
|
38
|
+
export function renderShellGateHook(adapter, cursorOrigin) {
|
|
39
|
+
if (adapter === 'cursor') {
|
|
40
|
+
return renderCursorDispatchHook(requireCursorOrigin(cursorOrigin), 'shell-gate', JSON.stringify('beforeShellExecution'));
|
|
41
|
+
}
|
|
19
42
|
return `import { runShellGateHook } from '../belay/runtime/core.mjs'
|
|
20
43
|
|
|
21
44
|
await runShellGateHook()
|
|
22
45
|
`;
|
|
23
46
|
}
|
|
24
|
-
export function renderToolGateHook() {
|
|
47
|
+
export function renderToolGateHook(adapter, cursorOrigin) {
|
|
48
|
+
if (adapter === 'cursor') {
|
|
49
|
+
return renderCursorDispatchHook(requireCursorOrigin(cursorOrigin), 'tool-gate', "process.argv[2] ?? 'preToolUse'");
|
|
50
|
+
}
|
|
25
51
|
return `import { runToolGateHook } from '../belay/runtime/core.mjs'
|
|
26
52
|
|
|
27
53
|
const eventName = process.argv[2] ?? 'preToolUse'
|
|
28
54
|
await runToolGateHook(eventName)
|
|
29
55
|
`;
|
|
30
56
|
}
|
|
31
|
-
export function renderAuditHook() {
|
|
57
|
+
export function renderAuditHook(adapter, cursorOrigin) {
|
|
58
|
+
if (adapter === 'cursor') {
|
|
59
|
+
return renderCursorDispatchHook(requireCursorOrigin(cursorOrigin), 'audit', "process.argv[2] ?? 'postToolUse'");
|
|
60
|
+
}
|
|
32
61
|
return `import { runAuditHook } from '../belay/runtime/core.mjs'
|
|
33
62
|
|
|
34
63
|
const eventName = process.argv[2] ?? 'postToolUse'
|
|
@@ -44,6 +73,15 @@ async function readRuntimeBundle(adapter = 'cursor') {
|
|
|
44
73
|
throw new Error('Runtime bundle missing. Run pnpm build before belay init or upgrade.');
|
|
45
74
|
}
|
|
46
75
|
}
|
|
76
|
+
export async function renderCursorDispatcher() {
|
|
77
|
+
const bundlePath = path.join(path.dirname(fileURLToPath(import.meta.url)), '..', 'dist', 'bundle', 'cursor-dispatcher.mjs');
|
|
78
|
+
try {
|
|
79
|
+
return `${CURSOR_DISPATCHER_GENERATION_HEADER}${await readFile(bundlePath, 'utf8')}`;
|
|
80
|
+
}
|
|
81
|
+
catch {
|
|
82
|
+
throw new Error('Runtime bundle missing. Run pnpm build before belay init or upgrade.');
|
|
83
|
+
}
|
|
84
|
+
}
|
|
47
85
|
export async function renderRuntimeCore(adapter = 'cursor') {
|
|
48
86
|
const bundle = await readRuntimeBundle(adapter);
|
|
49
87
|
const withoutStamp = bundle
|
package/dist/types.d.ts
CHANGED
|
@@ -7,6 +7,7 @@ import type { ApprovalRecord, ClassifyResult } from './core/types.js';
|
|
|
7
7
|
export interface HookEntry {
|
|
8
8
|
command: string;
|
|
9
9
|
matcher?: string;
|
|
10
|
+
failClosed?: boolean;
|
|
10
11
|
}
|
|
11
12
|
export interface HooksFile {
|
|
12
13
|
version: number;
|
|
@@ -237,6 +238,8 @@ export interface DogfoodOptions {
|
|
|
237
238
|
targetDir?: string;
|
|
238
239
|
enforce?: boolean;
|
|
239
240
|
force?: boolean;
|
|
241
|
+
check?: boolean;
|
|
242
|
+
since?: string;
|
|
240
243
|
adapter?: AdapterName;
|
|
241
244
|
}
|
|
242
245
|
export interface DogfoodResult {
|
|
@@ -247,6 +250,23 @@ export interface DogfoodResult {
|
|
|
247
250
|
mode: string;
|
|
248
251
|
unknownLocalEffect: string;
|
|
249
252
|
}
|
|
253
|
+
export interface DogfoodCheckOptions {
|
|
254
|
+
targetDir?: string;
|
|
255
|
+
adapter?: AdapterName;
|
|
256
|
+
since: string;
|
|
257
|
+
}
|
|
258
|
+
export interface DogfoodCheckResult {
|
|
259
|
+
ok: boolean;
|
|
260
|
+
repoRoot: string;
|
|
261
|
+
since: string;
|
|
262
|
+
gateEvents: number;
|
|
263
|
+
auditModeDenyCount: number;
|
|
264
|
+
hostDeniedAfterAllowCount: number;
|
|
265
|
+
shellPreToolUseCount: number;
|
|
266
|
+
mismatchedCohortCount: number;
|
|
267
|
+
environmentSkewCount: number;
|
|
268
|
+
failures: string[];
|
|
269
|
+
}
|
|
250
270
|
export type ExplainKind = 'shell' | 'tool' | 'subagent';
|
|
251
271
|
export interface ExplainReport {
|
|
252
272
|
repoRoot: string;
|
package/dist/version.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const PACKAGE_VERSION = "0.
|
|
1
|
+
export declare const PACKAGE_VERSION = "0.10.0";
|
package/dist/version.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
// Generated by scripts/sync-version.mjs — do not edit.
|
|
2
|
-
export const PACKAGE_VERSION = '0.
|
|
2
|
+
export const PACKAGE_VERSION = '0.10.0';
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@guilz-dev/belay",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.10.0",
|
|
4
4
|
"description": "Belay-style approval and audit gating for agent runtimes.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
@@ -56,10 +56,14 @@
|
|
|
56
56
|
"lint": "biome check src package.json README.md CHANGELOG.md CONTRIBUTING.md SECURITY.md tsconfig.json tsconfig.build.json vitest.config.ts scripts docs",
|
|
57
57
|
"typecheck": "tsc --noEmit",
|
|
58
58
|
"test": "pnpm build && vitest run",
|
|
59
|
+
"test:run": "vitest run",
|
|
59
60
|
"test:structural": "pnpm build && vitest run src/__tests__/verdict/structural-suite.test.ts",
|
|
61
|
+
"test:structural:run": "vitest run src/__tests__/verdict/structural-suite.test.ts",
|
|
60
62
|
"test:docker": "pnpm build && vitest run --config vitest.live.config.ts src/__tests__/capability/boundary-container-isolation.test.ts src/__tests__/capability/boundary-container-workspace-mount.test.ts src/__tests__/capability/boundary-driver-container.test.ts src/__tests__/contained-execution-docker.integration.test.ts",
|
|
61
63
|
"test:llm": "pnpm build && vitest run --config vitest.live.config.ts src/__tests__/verdict/llm/judge-accuracy.test.ts",
|
|
62
64
|
"test:stable": "pnpm build && vitest run && vitest run && vitest run",
|
|
65
|
+
"test:stable:run": "vitest run && vitest run && vitest run",
|
|
66
|
+
"test:macos": "vitest run src/__tests__/native-seatbelt-boundary-probe.test.ts src/__tests__/git-resource-identity.test.ts src/__tests__/installer-scope.test.ts src/__tests__/cursor-hook-precedence.integration.test.ts src/__tests__/cursor-hooks.test.ts",
|
|
63
67
|
"corpus": "pnpm build && node scripts/corpus.mjs",
|
|
64
68
|
"probe:adversarial": "pnpm build && node scripts/adversarial-probe.mjs",
|
|
65
69
|
"probe:cursor-shell-rewrite": "node scripts/cursor-shell-rewrite-probe.mjs",
|