@cleocode/contracts 2026.9.26 → 2026.10.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/dist/cloud/api.d.ts +469 -2
- package/dist/cloud/api.d.ts.map +1 -1
- package/dist/cloud/api.js +209 -8
- package/dist/cloud/api.js.map +1 -1
- package/dist/cloud/envelope.d.ts +6 -0
- package/dist/cloud/envelope.d.ts.map +1 -1
- package/dist/cloud/envelope.js +12 -0
- package/dist/cloud/envelope.js.map +1 -1
- package/dist/config.d.ts +13 -0
- package/dist/config.d.ts.map +1 -1
- package/dist/heavy-command-hook.d.ts +123 -0
- package/dist/heavy-command-hook.d.ts.map +1 -0
- package/dist/heavy-command-hook.js +17 -0
- package/dist/heavy-command-hook.js.map +1 -0
- package/dist/index.d.ts +9 -4
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +6 -2
- package/dist/index.js.map +1 -1
- package/dist/install.d.ts +8 -0
- package/dist/install.d.ts.map +1 -1
- package/dist/invariants/index.d.ts +2 -0
- package/dist/invariants/index.d.ts.map +1 -1
- package/dist/invariants/index.js +1 -0
- package/dist/invariants/index.js.map +1 -1
- package/dist/invariants/sync-write-invariants.d.ts +115 -0
- package/dist/invariants/sync-write-invariants.d.ts.map +1 -0
- package/dist/invariants/sync-write-invariants.js +123 -0
- package/dist/invariants/sync-write-invariants.js.map +1 -0
- package/dist/nexus-account.d.ts +91 -3
- package/dist/nexus-account.d.ts.map +1 -1
- package/dist/nexus-account.js +30 -1
- package/dist/nexus-account.js.map +1 -1
- package/dist/nexus-cloud.d.ts +718 -0
- package/dist/nexus-cloud.d.ts.map +1 -0
- package/dist/nexus-cloud.js +418 -0
- package/dist/nexus-cloud.js.map +1 -0
- package/dist/nexus-vault.d.ts +266 -0
- package/dist/nexus-vault.d.ts.map +1 -0
- package/dist/nexus-vault.js +82 -0
- package/dist/nexus-vault.js.map +1 -0
- package/dist/portable-bundle.d.ts +5 -0
- package/dist/portable-bundle.d.ts.map +1 -1
- package/dist/resource-governor.d.ts +13 -0
- package/dist/resource-governor.d.ts.map +1 -1
- package/dist/resource-governor.js +13 -0
- package/dist/resource-governor.js.map +1 -1
- package/dist/sync-schema.d.ts +34 -0
- package/dist/sync-schema.d.ts.map +1 -0
- package/dist/sync-schema.js +34 -0
- package/dist/sync-schema.js.map +1 -0
- package/dist/task.d.ts +49 -1
- package/dist/task.d.ts.map +1 -1
- package/dist/tasks.d.ts +6 -0
- package/dist/tasks.d.ts.map +1 -1
- package/dist/tasks.js.map +1 -1
- package/package.json +2 -2
- package/src/cloud/api.ts +258 -9
- package/src/cloud/envelope.ts +12 -0
- package/src/config.ts +13 -0
- package/src/heavy-command-hook.ts +136 -0
- package/src/index.ts +108 -0
- package/src/install.ts +9 -0
- package/src/invariants/index.ts +6 -0
- package/src/invariants/sync-write-invariants.ts +460 -0
- package/src/nexus-account.ts +120 -3
- package/src/nexus-cloud.ts +673 -0
- package/src/nexus-vault.ts +280 -0
- package/src/portable-bundle.ts +5 -0
- package/src/resource-governor.ts +15 -0
- package/src/sync-schema.ts +34 -0
- package/src/task.ts +49 -1
- package/src/tasks.ts +6 -0
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Heavy-command provider hook — shared types.
|
|
3
|
+
*
|
|
4
|
+
* CLEO ships a pre-exec hook for agent harnesses (Claude Code, Codex, Kimi,
|
|
5
|
+
* opencode) that recognises heavy shell commands (test runners, compilers,
|
|
6
|
+
* builds, installs) and routes them through `cleo run`, so every agent on the
|
|
7
|
+
* machine shares the ResourceGovernor's one budget. The planner lives in
|
|
8
|
+
* `@cleocode/core` (`resources/heavy-command`, on top of `resources/run-class`),
|
|
9
|
+
* the provider wire formats and the entry point (`cleo hook heavy-command`) in
|
|
10
|
+
* `@cleocode/cleo` (`cli/hook-entry`), and the per-provider installers in
|
|
11
|
+
* `@cleocode/adapters` (`providers/shared/heavy-command-hook-install`).
|
|
12
|
+
*
|
|
13
|
+
* @task T12983
|
|
14
|
+
* @epic T12978
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* How the hook treats a recognised heavy command.
|
|
19
|
+
*
|
|
20
|
+
* - `rewrite` — DEFAULT. Wrap it in place as
|
|
21
|
+
* `cleo run --wait --passthrough --class <c> -- <cmd>`, when the harness
|
|
22
|
+
* runs in `bypassPermissions` or `auto` mode and no deny or ask rule names
|
|
23
|
+
* the command (otherwise the hook warns: a rewrite would change which
|
|
24
|
+
* permission rules match).
|
|
25
|
+
* - `warn` — leave the command alone; add a context line naming the governed
|
|
26
|
+
* form.
|
|
27
|
+
* - `off` — do nothing (the installer also removes the hook entry).
|
|
28
|
+
*
|
|
29
|
+
* Set by the `CLEO_HEAVY_COMMAND_HOOK` environment variable or the
|
|
30
|
+
* `resources.heavyCommandHook` config key (the variable wins).
|
|
31
|
+
*/
|
|
32
|
+
export type HeavyCommandHookMode = 'rewrite' | 'warn' | 'off';
|
|
33
|
+
|
|
34
|
+
/** The harnesses `cleo hook heavy-command --provider <p>` answers for. */
|
|
35
|
+
export type HeavyCommandHookProvider = 'claude-code' | 'codex' | 'kimi' | 'opencode';
|
|
36
|
+
|
|
37
|
+
/** One heavy command found in a shell command line. */
|
|
38
|
+
export interface HeavyCommandSegment {
|
|
39
|
+
/** The list element exactly as written (a simple command or a pipeline). */
|
|
40
|
+
readonly text: string;
|
|
41
|
+
/** The `cleo run --class` value: `test`, `build`, `full-build` or `db`. */
|
|
42
|
+
readonly runClass: string;
|
|
43
|
+
/** The element with `cleo run --wait --passthrough … --` inserted before the heavy command. */
|
|
44
|
+
readonly governed: string;
|
|
45
|
+
/** The heavy command's own words (quotes removed), command word first. */
|
|
46
|
+
readonly argv: readonly string[];
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* What the planner decided for one shell command line.
|
|
51
|
+
*
|
|
52
|
+
* - `none` — nothing heavy (or already governed): leave it alone.
|
|
53
|
+
* - `rewrite` — `command` is the whole line with every heavy command wrapped
|
|
54
|
+
* in place; every other byte is unchanged.
|
|
55
|
+
* - `warn` — heavy, but rewriting could change what the line does (a heavy
|
|
56
|
+
* command inside `$(…)`, a subshell, a compound command, a background job,
|
|
57
|
+
* reading a heredoc, or sharing a pipeline with another heavy command), or
|
|
58
|
+
* the hook may not rewrite here; `reason` says which.
|
|
59
|
+
*/
|
|
60
|
+
export type HeavyCommandPlan =
|
|
61
|
+
| { readonly action: 'none' }
|
|
62
|
+
| {
|
|
63
|
+
readonly action: 'rewrite';
|
|
64
|
+
readonly command: string;
|
|
65
|
+
readonly segments: readonly HeavyCommandSegment[];
|
|
66
|
+
}
|
|
67
|
+
| {
|
|
68
|
+
readonly action: 'warn';
|
|
69
|
+
readonly reason: string;
|
|
70
|
+
readonly segments: readonly HeavyCommandSegment[];
|
|
71
|
+
};
|
|
72
|
+
|
|
73
|
+
/** A JSON value as a hook receives it on stdin. */
|
|
74
|
+
export type HookJsonValue =
|
|
75
|
+
| string
|
|
76
|
+
| number
|
|
77
|
+
| boolean
|
|
78
|
+
| null
|
|
79
|
+
| readonly HookJsonValue[]
|
|
80
|
+
| { readonly [key: string]: HookJsonValue };
|
|
81
|
+
|
|
82
|
+
/**
|
|
83
|
+
* A shell tool's input: Claude Code and Codex `Bash`, Kimi `Shell`, opencode
|
|
84
|
+
* `bash`. Every harness carries the command line in `command`; the other
|
|
85
|
+
* fields (`timeout`, `description`, `run_in_background`, …) vary.
|
|
86
|
+
*/
|
|
87
|
+
export interface ShellToolInput {
|
|
88
|
+
/** The shell command line the agent wants to run. */
|
|
89
|
+
readonly command: string;
|
|
90
|
+
/** Harness-specific fields, passed back unchanged unless noted. */
|
|
91
|
+
readonly [field: string]: HookJsonValue;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
/**
|
|
95
|
+
* The fields of a `PreToolUse` hook's stdin JSON the heavy-command hook reads.
|
|
96
|
+
* Claude Code, Codex and Kimi send this shape; CLEO's generated opencode
|
|
97
|
+
* plugin sends the same fields.
|
|
98
|
+
*/
|
|
99
|
+
export interface PreToolUseHookInput {
|
|
100
|
+
readonly hook_event_name?: string;
|
|
101
|
+
/** `Bash` (Claude Code, Codex), `Shell` (Kimi), `bash` (opencode). */
|
|
102
|
+
readonly tool_name?: string;
|
|
103
|
+
readonly tool_input?: ShellToolInput;
|
|
104
|
+
/** The session's working directory. */
|
|
105
|
+
readonly cwd?: string;
|
|
106
|
+
/** Claude Code and Codex: `default`, `plan`, `acceptEdits`, `auto`, `dontAsk`, `bypassPermissions`. */
|
|
107
|
+
readonly permission_mode?: string;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
/** The answer `cleo hook heavy-command --provider opencode` prints for CLEO's opencode plugin. */
|
|
111
|
+
export interface OpencodeHeavyCommandAnswer {
|
|
112
|
+
/** Replacement for `output.args.command`, when the command was rewritten. */
|
|
113
|
+
readonly command?: string;
|
|
114
|
+
/** Replacement for `output.args.timeout` (ms): the old one plus the queue wait. */
|
|
115
|
+
readonly timeout?: number;
|
|
116
|
+
/** What the hook tells the agent; the plugin appends it to the tool's output. */
|
|
117
|
+
readonly context?: string;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
/**
|
|
121
|
+
* The Claude-style `PreToolUse` hook answer on stdout. Claude Code, Codex and
|
|
122
|
+
* Kimi share this shape (each honours a different subset of it).
|
|
123
|
+
*/
|
|
124
|
+
export interface PreToolUseHookOutput {
|
|
125
|
+
readonly hookSpecificOutput: {
|
|
126
|
+
readonly hookEventName: 'PreToolUse';
|
|
127
|
+
/** Omitted unless the provider requires it (Codex rewrites need `allow`). */
|
|
128
|
+
readonly permissionDecision?: 'allow' | 'deny';
|
|
129
|
+
/** Shown to the agent on `deny`. */
|
|
130
|
+
readonly permissionDecisionReason?: string;
|
|
131
|
+
/** Replaces the whole tool input. */
|
|
132
|
+
readonly updatedInput?: ShellToolInput;
|
|
133
|
+
/** Added to the agent's context alongside the tool result. */
|
|
134
|
+
readonly additionalContext?: string;
|
|
135
|
+
};
|
|
136
|
+
}
|
package/src/index.ts
CHANGED
|
@@ -774,6 +774,18 @@ export {
|
|
|
774
774
|
confidenceLabelFromNumeric,
|
|
775
775
|
provenanceFromNumeric,
|
|
776
776
|
} from './graph.js';
|
|
777
|
+
// === Heavy-command provider hook (T12983 / Epic T12978) ===
|
|
778
|
+
export type {
|
|
779
|
+
HeavyCommandHookMode,
|
|
780
|
+
HeavyCommandHookProvider,
|
|
781
|
+
HeavyCommandPlan,
|
|
782
|
+
HeavyCommandSegment,
|
|
783
|
+
HookJsonValue,
|
|
784
|
+
OpencodeHeavyCommandAnswer,
|
|
785
|
+
PreToolUseHookInput,
|
|
786
|
+
PreToolUseHookOutput,
|
|
787
|
+
ShellToolInput,
|
|
788
|
+
} from './heavy-command-hook.js';
|
|
777
789
|
export type { AdapterHookProvider } from './hooks.js';
|
|
778
790
|
export type { AdapterInstallProvider, InstallOptions, InstallResult } from './install.js';
|
|
779
791
|
// === Invariants Registry (Saga T10326 / Epic T10327 / Task T10335 — SG-SUBSTRATE-RECONCILIATION) ===
|
|
@@ -783,6 +795,9 @@ export type {
|
|
|
783
795
|
InvariantRuntimeGate,
|
|
784
796
|
InvariantSeverity,
|
|
785
797
|
RegisteredInvariant,
|
|
798
|
+
SyncWriteInvariant,
|
|
799
|
+
SyncWriteInvariantClass,
|
|
800
|
+
SyncWriteInvariantPending,
|
|
786
801
|
} from './invariants/index.js';
|
|
787
802
|
export {
|
|
788
803
|
ADR_056_INVARIANTS,
|
|
@@ -790,6 +805,7 @@ export {
|
|
|
790
805
|
getInvariant,
|
|
791
806
|
getInvariantsByAdr,
|
|
792
807
|
INVARIANTS_REGISTRY,
|
|
808
|
+
SYNC_WRITE_INVARIANTS,
|
|
793
809
|
} from './invariants/index.js';
|
|
794
810
|
// === Background Job Status (T9955 — promoted from core/store/tasks-schema.ts) ===
|
|
795
811
|
export type { BackgroundJobStatus } from './jobs.js';
|
|
@@ -2265,6 +2281,8 @@ export {
|
|
|
2265
2281
|
RESOURCE_BACKPRESSURE_CODE,
|
|
2266
2282
|
RESOURCE_CLASSES,
|
|
2267
2283
|
RESOURCE_DEFERRED_CODE,
|
|
2284
|
+
RUN_COMMAND_FAILED_CODE,
|
|
2285
|
+
RUN_DEFERRED_EXIT_CODE,
|
|
2268
2286
|
} from './resource-governor.js';
|
|
2269
2287
|
// === Result Types (Dashboard, Stats, Log, Context, Sequence, Analysis, Deps) ===
|
|
2270
2288
|
export type {
|
|
@@ -2993,11 +3011,15 @@ export type {
|
|
|
2993
3011
|
NexusAccountOrganization,
|
|
2994
3012
|
NexusAccountStatus,
|
|
2995
3013
|
NexusAccountUser,
|
|
3014
|
+
NexusDeviceEndOutcome,
|
|
3015
|
+
NexusDeviceLogoutResult,
|
|
3016
|
+
NexusDeviceLogoutRow,
|
|
2996
3017
|
NexusLoginDevice,
|
|
2997
3018
|
NexusLoginResult,
|
|
2998
3019
|
NexusLogoutResult,
|
|
2999
3020
|
NexusProjectLink,
|
|
3000
3021
|
NexusProjectLinkResult,
|
|
3022
|
+
NexusReplicaAttachment,
|
|
3001
3023
|
NexusSessionState,
|
|
3002
3024
|
} from './nexus-account.js';
|
|
3003
3025
|
export {
|
|
@@ -3009,4 +3031,90 @@ export {
|
|
|
3009
3031
|
nexusAccountOrganizationSchema,
|
|
3010
3032
|
nexusAccountUserSchema,
|
|
3011
3033
|
} from './nexus-account.js';
|
|
3034
|
+
export type {
|
|
3035
|
+
CloudDevicesResult,
|
|
3036
|
+
CloudPaging,
|
|
3037
|
+
CloudProjectShowResult,
|
|
3038
|
+
CloudProjectsResult,
|
|
3039
|
+
CloudStatusGlobalStore,
|
|
3040
|
+
CloudStatusLocal,
|
|
3041
|
+
CloudStatusOfflineDetails,
|
|
3042
|
+
CloudStatusResult,
|
|
3043
|
+
CloudStatusSummary,
|
|
3044
|
+
CloudStatusVerdict,
|
|
3045
|
+
CloudWarning,
|
|
3046
|
+
CloudWhoamiResult,
|
|
3047
|
+
NexusCloudCredential,
|
|
3048
|
+
NexusCloudDevice,
|
|
3049
|
+
NexusCloudDeviceCounts,
|
|
3050
|
+
NexusCloudProjectDetail,
|
|
3051
|
+
NexusCloudProjectListItem,
|
|
3052
|
+
NexusCloudReplica,
|
|
3053
|
+
NexusCloudStatus,
|
|
3054
|
+
NexusCloudStatusCheck,
|
|
3055
|
+
NexusCloudWhoami,
|
|
3056
|
+
NexusDeviceListState,
|
|
3057
|
+
NexusErrorMapping,
|
|
3058
|
+
NexusStatusCheckId,
|
|
3059
|
+
} from './nexus-cloud.js';
|
|
3060
|
+
export {
|
|
3061
|
+
CLOUD_STATUS_VERDICTS,
|
|
3062
|
+
NEXUS_CLOUD_MAX_PAGES,
|
|
3063
|
+
NEXUS_CLOUD_PROFILES,
|
|
3064
|
+
NEXUS_CONFLICT_ERRORS,
|
|
3065
|
+
NEXUS_DEVICE_LIST_STATES,
|
|
3066
|
+
NEXUS_DEVICE_STATE_UNKNOWN,
|
|
3067
|
+
NEXUS_DEVICE_STATES,
|
|
3068
|
+
NEXUS_FORBIDDEN_ERRORS,
|
|
3069
|
+
NEXUS_FORBIDDEN_REASONS,
|
|
3070
|
+
NEXUS_PAGE_LIMIT_MAX,
|
|
3071
|
+
NEXUS_PRESENCE_FRESH_SECONDS,
|
|
3072
|
+
NEXUS_REVOKED_REASON_ERRORS,
|
|
3073
|
+
NEXUS_REVOKED_REASONS,
|
|
3074
|
+
NEXUS_STATUS_CHECK_IDS,
|
|
3075
|
+
NEXUS_STATUS_VERDICTS,
|
|
3076
|
+
NEXUS_UNAUTHENTICATED_ERRORS,
|
|
3077
|
+
NEXUS_UNAUTHENTICATED_REASONS,
|
|
3078
|
+
NEXUS_UNREACHABLE_ERROR,
|
|
3079
|
+
nexusCloudCredentialSchema,
|
|
3080
|
+
nexusCloudDeviceCountsSchema,
|
|
3081
|
+
nexusCloudDevicePageSchema,
|
|
3082
|
+
nexusCloudDeviceSchema,
|
|
3083
|
+
nexusCloudOrganizationSchema,
|
|
3084
|
+
nexusCloudPresenceSchema,
|
|
3085
|
+
nexusCloudProjectDetailSchema,
|
|
3086
|
+
nexusCloudProjectListItemSchema,
|
|
3087
|
+
nexusCloudProjectPageSchema,
|
|
3088
|
+
nexusCloudReplicaPageSchema,
|
|
3089
|
+
nexusCloudReplicaSchema,
|
|
3090
|
+
nexusCloudStatusCheckSchema,
|
|
3091
|
+
nexusCloudStatusSchema,
|
|
3092
|
+
nexusCloudUserSchema,
|
|
3093
|
+
nexusCloudWhoamiSchema,
|
|
3094
|
+
} from './nexus-cloud.js';
|
|
3095
|
+
export {
|
|
3096
|
+
type CloudActivityItem,
|
|
3097
|
+
type CloudActivityResult,
|
|
3098
|
+
type CloudLeaseReleaseResult,
|
|
3099
|
+
type CloudPushResult,
|
|
3100
|
+
type CloudRestoreResult,
|
|
3101
|
+
type CloudVaultLease,
|
|
3102
|
+
type CloudVaultScope,
|
|
3103
|
+
type CloudVaultSnapshot,
|
|
3104
|
+
type CloudVaultStatusResult,
|
|
3105
|
+
type CloudVaultTable,
|
|
3106
|
+
type CloudVaultTableDiff,
|
|
3107
|
+
type CloudVerifyResult,
|
|
3108
|
+
NEXUS_VAULT_LEASE_ROLE,
|
|
3109
|
+
type NexusActivityEvent,
|
|
3110
|
+
nexusActivityEventSchema,
|
|
3111
|
+
nexusActivityPageSchema,
|
|
3112
|
+
nexusLeaseAcquireSchema,
|
|
3113
|
+
nexusLeaseSchema,
|
|
3114
|
+
nexusProjectKeysSchema,
|
|
3115
|
+
nexusStreamHeadSchema,
|
|
3116
|
+
nexusUserKeysSchema,
|
|
3117
|
+
} from './nexus-vault.js';
|
|
3118
|
+
// === Sync schema version, shared by the change journal and the cloud vault (T13034) ===
|
|
3119
|
+
export { SYNC_SCHEMA_VERSION } from './sync-schema.js';
|
|
3012
3120
|
export { isStorableTaskId, isTaskId, TASK_ID_REGEX, type TaskId } from './task-id.js';
|
package/src/install.ts
CHANGED
|
@@ -5,6 +5,8 @@
|
|
|
5
5
|
* @task T5240
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
|
+
import type { HeavyCommandHookMode } from './heavy-command-hook.js';
|
|
9
|
+
|
|
8
10
|
export interface AdapterInstallProvider {
|
|
9
11
|
install(options: InstallOptions): Promise<InstallResult>;
|
|
10
12
|
uninstall(): Promise<void>;
|
|
@@ -16,6 +18,13 @@ export interface AdapterInstallProvider {
|
|
|
16
18
|
export interface InstallOptions {
|
|
17
19
|
projectDir: string;
|
|
18
20
|
global?: boolean;
|
|
21
|
+
/**
|
|
22
|
+
* The heavy-command hook mode (`resources.heavyCommandHook`, T12983).
|
|
23
|
+
* `rewrite`/`warn` install or refresh the project-level hook entry, `off`
|
|
24
|
+
* removes it, and `undefined` leaves the hook alone (callers that are not a
|
|
25
|
+
* project init/upgrade, such as global bootstrap, pass nothing).
|
|
26
|
+
*/
|
|
27
|
+
heavyCommandHook?: HeavyCommandHookMode;
|
|
19
28
|
}
|
|
20
29
|
|
|
21
30
|
export interface InstallResult {
|
package/src/invariants/index.ts
CHANGED
|
@@ -36,6 +36,12 @@ import { ADR_073_INVARIANTS } from './adr-073-saga.js';
|
|
|
36
36
|
export { ADR_056_INVARIANTS } from './adr-056-release.js';
|
|
37
37
|
export { ADR_070_INVARIANTS } from './adr-070-orchestration.js';
|
|
38
38
|
export { ADR_073_INVARIANTS } from './adr-073-saga.js';
|
|
39
|
+
export type {
|
|
40
|
+
SyncWriteInvariant,
|
|
41
|
+
SyncWriteInvariantClass,
|
|
42
|
+
SyncWriteInvariantPending,
|
|
43
|
+
} from './sync-write-invariants.js';
|
|
44
|
+
export { SYNC_WRITE_INVARIANTS } from './sync-write-invariants.js';
|
|
39
45
|
|
|
40
46
|
/**
|
|
41
47
|
* Severity tier for a registered invariant.
|