@treeseed/sdk 0.8.10 → 0.8.12
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 +7 -0
- package/dist/capacity.d.ts +233 -1
- package/dist/capacity.js +1227 -44
- package/dist/control-plane.d.ts +2 -1
- package/dist/control-plane.js +7 -0
- package/dist/d1-store.js +6 -0
- package/dist/git-runtime.js +4 -2
- package/dist/graph/context-query-contracts.d.ts +48 -0
- package/dist/graph/context-query-contracts.js +126 -0
- package/dist/index.d.ts +5 -3
- package/dist/index.js +85 -1
- package/dist/operations/agent-tools.d.ts +114 -0
- package/dist/operations/agent-tools.js +183 -0
- package/dist/operations/services/commit-message-provider.js +1 -1
- package/dist/operations/services/d1-migration.js +27 -0
- package/dist/operations/services/hub-provider-launch.js +1 -1
- package/dist/operations/services/runtime-tools.js +1 -1
- package/dist/operations.d.ts +1 -0
- package/dist/operations.js +16 -0
- package/dist/platform/environment.js +5 -0
- package/dist/platform/plugins/constants.js +1 -1
- package/dist/plugin-default.js +1 -1
- package/dist/sdk-types.d.ts +231 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/treeseed.site.yaml +1 -1
- package/dist/types/agents.d.ts +12 -0
- package/package.json +9 -1
|
@@ -0,0 +1,183 @@
|
|
|
1
|
+
const AGENT_OPERATION_NAMES = [
|
|
2
|
+
"switch",
|
|
3
|
+
"dev",
|
|
4
|
+
"verify",
|
|
5
|
+
"save",
|
|
6
|
+
"stage",
|
|
7
|
+
"merge_to_staging",
|
|
8
|
+
"close",
|
|
9
|
+
"release"
|
|
10
|
+
];
|
|
11
|
+
const AGENT_OPERATION_MODES = ["dry_run", "read_only", "mutating"];
|
|
12
|
+
function normalizePath(value) {
|
|
13
|
+
return value.replace(/\\/gu, "/").replace(/^\.?\//u, "").replace(/\/+/gu, "/");
|
|
14
|
+
}
|
|
15
|
+
function matchesPattern(path, pattern) {
|
|
16
|
+
const normalizedPath = normalizePath(path);
|
|
17
|
+
const normalizedPattern = normalizePath(pattern);
|
|
18
|
+
if (normalizedPattern.endsWith("/**")) {
|
|
19
|
+
const prefix = normalizedPattern.slice(0, -3);
|
|
20
|
+
return normalizedPath === prefix || normalizedPath.startsWith(`${prefix}/`);
|
|
21
|
+
}
|
|
22
|
+
if (normalizedPattern.endsWith("/")) {
|
|
23
|
+
return normalizedPath.startsWith(normalizedPattern);
|
|
24
|
+
}
|
|
25
|
+
return normalizedPath === normalizedPattern || normalizedPath.startsWith(`${normalizedPattern}/`);
|
|
26
|
+
}
|
|
27
|
+
function listMatches(value, allowed) {
|
|
28
|
+
return !allowed?.length || value !== void 0 && allowed.includes(value);
|
|
29
|
+
}
|
|
30
|
+
function grantActive(grant, now) {
|
|
31
|
+
if ((grant.state ?? "active") !== "active") {
|
|
32
|
+
return "operation_grant_inactive";
|
|
33
|
+
}
|
|
34
|
+
if (grant.expiresAt && Date.parse(grant.expiresAt) <= now.valueOf()) {
|
|
35
|
+
return "operation_grant_expired";
|
|
36
|
+
}
|
|
37
|
+
return null;
|
|
38
|
+
}
|
|
39
|
+
function deny(code, summary, options = {}) {
|
|
40
|
+
return {
|
|
41
|
+
allowed: false,
|
|
42
|
+
status: options.status ?? "waiting",
|
|
43
|
+
code,
|
|
44
|
+
summary,
|
|
45
|
+
grant: options.grant,
|
|
46
|
+
metadata: options.metadata ?? {}
|
|
47
|
+
};
|
|
48
|
+
}
|
|
49
|
+
function allow(grant, metadata = {}) {
|
|
50
|
+
return {
|
|
51
|
+
allowed: true,
|
|
52
|
+
status: "completed",
|
|
53
|
+
code: "allowed",
|
|
54
|
+
summary: `Operation grant ${grant.id} allows this request.`,
|
|
55
|
+
grant,
|
|
56
|
+
metadata
|
|
57
|
+
};
|
|
58
|
+
}
|
|
59
|
+
function isAgentOperationName(value) {
|
|
60
|
+
return AGENT_OPERATION_NAMES.includes(value);
|
|
61
|
+
}
|
|
62
|
+
function resolveAgentOperationGrant(request, grants, now = /* @__PURE__ */ new Date()) {
|
|
63
|
+
return grants.find((grant) => {
|
|
64
|
+
if (request.permissionGrantId && grant.id !== request.permissionGrantId) return false;
|
|
65
|
+
if (grantActive(grant, now)) return false;
|
|
66
|
+
if (!grant.operations.includes(request.operation)) return false;
|
|
67
|
+
return true;
|
|
68
|
+
}) ?? null;
|
|
69
|
+
}
|
|
70
|
+
function decideAgentOperationPermission(input) {
|
|
71
|
+
const { request } = input;
|
|
72
|
+
const now = input.now ?? /* @__PURE__ */ new Date();
|
|
73
|
+
if (!isAgentOperationName(request.operation)) {
|
|
74
|
+
return deny("invalid_operation", `Unsupported agent operation "${String(request.operation)}".`, { status: "failed" });
|
|
75
|
+
}
|
|
76
|
+
if (request.operation === "release") {
|
|
77
|
+
const approval = request.approval;
|
|
78
|
+
if (!approval || approval.state !== "approved" || request.approvalId && approval.id !== request.approvalId) {
|
|
79
|
+
return deny("operation_release_approval_required", "Release requires an explicit approved release approval.");
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
const grant = resolveAgentOperationGrant(request, input.grants, now);
|
|
83
|
+
if (!grant) {
|
|
84
|
+
return deny("operation_permission_required", `No operation grant allows ${request.agentRole} to run ${request.operation}.`);
|
|
85
|
+
}
|
|
86
|
+
const activeCode = grantActive(grant, now);
|
|
87
|
+
if (activeCode) {
|
|
88
|
+
return deny(activeCode, `Operation grant ${grant.id} is not active.`, { grant });
|
|
89
|
+
}
|
|
90
|
+
if (!grant.modes.includes(request.mode)) {
|
|
91
|
+
return deny("operation_mode_not_granted", `Operation grant ${grant.id} does not allow ${request.mode} mode.`, { grant });
|
|
92
|
+
}
|
|
93
|
+
if (!listMatches(request.agentRole, grant.agentRoles)) {
|
|
94
|
+
return deny("operation_role_not_granted", `Operation grant ${grant.id} does not allow role ${request.agentRole}.`, { grant });
|
|
95
|
+
}
|
|
96
|
+
if (!listMatches(request.taskKind, grant.taskKinds)) {
|
|
97
|
+
return deny("operation_task_kind_not_granted", `Operation grant ${grant.id} does not allow task kind ${request.taskKind ?? "<none>"}.`, { grant });
|
|
98
|
+
}
|
|
99
|
+
if (!listMatches(request.projectId, grant.projectIds)) {
|
|
100
|
+
return deny("operation_project_not_granted", `Operation grant ${grant.id} does not allow project ${request.projectId}.`, { grant });
|
|
101
|
+
}
|
|
102
|
+
if (!listMatches(request.environment, grant.environments)) {
|
|
103
|
+
return deny("operation_environment_not_granted", `Operation grant ${grant.id} does not allow environment ${request.environment}.`, { grant });
|
|
104
|
+
}
|
|
105
|
+
if (grant.requiresApproval && (!request.approval || request.approval.state !== "approved")) {
|
|
106
|
+
return deny("operation_approval_required", `Operation grant ${grant.id} requires approval.`, { grant });
|
|
107
|
+
}
|
|
108
|
+
if (grant.approvalIds?.length && (!request.approval || !grant.approvalIds.includes(request.approval.id) || request.approval.state !== "approved")) {
|
|
109
|
+
return deny("operation_approval_required", `Operation grant ${grant.id} requires one of its approved approval ids.`, { grant });
|
|
110
|
+
}
|
|
111
|
+
if (request.mode === "mutating" && !request.worktreeRoot && request.operation !== "release") {
|
|
112
|
+
return deny("operation_worktree_required", `Mutating operation ${request.operation} requires an assigned worktree root.`, { grant });
|
|
113
|
+
}
|
|
114
|
+
const allowedPaths = request.allowedPaths?.length ? request.allowedPaths : grant.allowedPaths ?? [];
|
|
115
|
+
const forbiddenPaths = [...grant.forbiddenPaths ?? [], ...request.forbiddenPaths ?? []];
|
|
116
|
+
const changedPaths = request.changedPaths ?? [];
|
|
117
|
+
if ((request.operation === "stage" || request.operation === "merge_to_staging") && allowedPaths.length === 0) {
|
|
118
|
+
return deny("operation_allowed_paths_required", `${request.operation} requires allowed paths.`, { grant });
|
|
119
|
+
}
|
|
120
|
+
for (const changedPath of changedPaths) {
|
|
121
|
+
if (forbiddenPaths.some((pattern) => matchesPattern(changedPath, pattern))) {
|
|
122
|
+
return deny("operation_path_forbidden", `${changedPath} is forbidden.`, {
|
|
123
|
+
grant,
|
|
124
|
+
status: "failed",
|
|
125
|
+
metadata: { changedPath, forbiddenPaths }
|
|
126
|
+
});
|
|
127
|
+
}
|
|
128
|
+
if (allowedPaths.length > 0 && !allowedPaths.some((pattern) => matchesPattern(changedPath, pattern))) {
|
|
129
|
+
return deny("operation_path_not_allowed", `${changedPath} is outside allowed paths.`, {
|
|
130
|
+
grant,
|
|
131
|
+
status: "failed",
|
|
132
|
+
metadata: { changedPath, allowedPaths }
|
|
133
|
+
});
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
return allow(grant, { allowedPaths, forbiddenPaths });
|
|
137
|
+
}
|
|
138
|
+
function deniedAgentOperationResult(request, decision) {
|
|
139
|
+
return {
|
|
140
|
+
operation: request.operation,
|
|
141
|
+
status: decision.status,
|
|
142
|
+
summary: decision.summary,
|
|
143
|
+
changedPaths: request.changedPaths ?? [],
|
|
144
|
+
stagedPaths: [],
|
|
145
|
+
commandsRun: [],
|
|
146
|
+
artifacts: [],
|
|
147
|
+
error: {
|
|
148
|
+
code: decision.code,
|
|
149
|
+
message: decision.summary,
|
|
150
|
+
retryable: decision.status === "waiting"
|
|
151
|
+
},
|
|
152
|
+
metadata: {
|
|
153
|
+
permission: decision
|
|
154
|
+
}
|
|
155
|
+
};
|
|
156
|
+
}
|
|
157
|
+
function createAgentOperationEvent(input) {
|
|
158
|
+
return {
|
|
159
|
+
operation: input.request.operation,
|
|
160
|
+
mode: input.request.mode,
|
|
161
|
+
agentRole: input.request.agentRole,
|
|
162
|
+
taskId: input.request.taskId,
|
|
163
|
+
permissionGrantId: input.request.permissionGrantId,
|
|
164
|
+
inputSummary: {
|
|
165
|
+
projectId: input.request.projectId,
|
|
166
|
+
environment: input.request.environment,
|
|
167
|
+
allowedPaths: input.request.allowedPaths ?? [],
|
|
168
|
+
forbiddenPaths: input.request.forbiddenPaths ?? [],
|
|
169
|
+
changedPaths: input.request.changedPaths ?? []
|
|
170
|
+
},
|
|
171
|
+
result: input.result,
|
|
172
|
+
createdAt: input.createdAt ?? (/* @__PURE__ */ new Date()).toISOString()
|
|
173
|
+
};
|
|
174
|
+
}
|
|
175
|
+
export {
|
|
176
|
+
AGENT_OPERATION_MODES,
|
|
177
|
+
AGENT_OPERATION_NAMES,
|
|
178
|
+
createAgentOperationEvent,
|
|
179
|
+
decideAgentOperationPermission,
|
|
180
|
+
deniedAgentOperationResult,
|
|
181
|
+
isAgentOperationName,
|
|
182
|
+
resolveAgentOperationGrant
|
|
183
|
+
};
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { existsSync, readdirSync } from "node:fs";
|
|
2
|
+
import { readFileSync } from "node:fs";
|
|
2
3
|
import { resolve } from "node:path";
|
|
3
4
|
import { spawnSync } from "node:child_process";
|
|
4
5
|
import { resolveWranglerBin } from "./runtime-tools.js";
|
|
@@ -98,6 +99,28 @@ function markMigrationApplied({ cwd, wranglerConfig, persistTo, migration }) {
|
|
|
98
99
|
command: `INSERT OR REPLACE INTO treeseed_schema_migrations (name, applied_at) VALUES ('${migration.replace(/'/g, "''")}', datetime('now'));`
|
|
99
100
|
});
|
|
100
101
|
}
|
|
102
|
+
function tableColumns({ cwd, wranglerConfig, persistTo, tableName }) {
|
|
103
|
+
const result = executeSqlCommand({
|
|
104
|
+
cwd,
|
|
105
|
+
wranglerConfig,
|
|
106
|
+
persistTo,
|
|
107
|
+
capture: true,
|
|
108
|
+
command: `PRAGMA table_info(${tableName.replace(/[^A-Za-z0-9_]/g, "")});`
|
|
109
|
+
});
|
|
110
|
+
const parsed = parseWranglerJsonOutput(result.stdout);
|
|
111
|
+
const rows = (Array.isArray(parsed) ? parsed : [parsed]).flatMap((entry) => entry.results ?? []);
|
|
112
|
+
return new Set(rows.map((row) => row.name).filter(Boolean));
|
|
113
|
+
}
|
|
114
|
+
function migrationAlreadySatisfied({ cwd, wranglerConfig, persistTo, filePath }) {
|
|
115
|
+
const sql = readFileSync(filePath, "utf8");
|
|
116
|
+
if (!sql.includes("execution_profile_id") || !sql.includes("task_estimate_profiles")) {
|
|
117
|
+
return false;
|
|
118
|
+
}
|
|
119
|
+
const estimateColumns = tableColumns({ cwd, wranglerConfig, persistTo, tableName: "task_estimates" });
|
|
120
|
+
const actualColumns = tableColumns({ cwd, wranglerConfig, persistTo, tableName: "task_usage_actuals" });
|
|
121
|
+
const profileColumns = tableColumns({ cwd, wranglerConfig, persistTo, tableName: "task_estimate_profiles" });
|
|
122
|
+
return estimateColumns.has("execution_profile_id") && actualColumns.has("execution_profile_id") && profileColumns.has("execution_profile_id") && profileColumns.has("completed_sample_count") && profileColumns.has("interrupted_sample_count") && profileColumns.has("confidence_score");
|
|
123
|
+
}
|
|
101
124
|
function runLocalD1Migrations({ cwd, wranglerConfig, migrationsRoot, persistTo }) {
|
|
102
125
|
ensureSchemaMigrationsTable({ cwd, wranglerConfig, persistTo });
|
|
103
126
|
const appliedMigrations = loadAppliedMigrations({ cwd, wranglerConfig, persistTo });
|
|
@@ -111,6 +134,10 @@ function runLocalD1Migrations({ cwd, wranglerConfig, migrationsRoot, persistTo }
|
|
|
111
134
|
console.error(`Unable to find migration file at ${filePath}.`);
|
|
112
135
|
process.exit(1);
|
|
113
136
|
}
|
|
137
|
+
if (migrationAlreadySatisfied({ cwd, wranglerConfig, persistTo, filePath })) {
|
|
138
|
+
markMigrationApplied({ cwd, wranglerConfig, persistTo, migration });
|
|
139
|
+
continue;
|
|
140
|
+
}
|
|
114
141
|
executeSqlFile({ cwd, wranglerConfig, filePath, persistTo });
|
|
115
142
|
markMigrationApplied({ cwd, wranglerConfig, persistTo, migration });
|
|
116
143
|
}
|
|
@@ -352,7 +352,7 @@ function applyManagedProjectDefaults(projectRoot, input) {
|
|
|
352
352
|
...config.providers ?? {},
|
|
353
353
|
forms: config.providers?.forms ?? "store_only",
|
|
354
354
|
agents: {
|
|
355
|
-
execution: "
|
|
355
|
+
execution: "codex",
|
|
356
356
|
mutation: "local_branch",
|
|
357
357
|
repository: "git",
|
|
358
358
|
verification: "local",
|
package/dist/operations.d.ts
CHANGED
|
@@ -5,5 +5,6 @@ export { TreeseedOperationsSdk } from './operations/runtime.ts';
|
|
|
5
5
|
export type { HubContentResolutionPolicy, KnowledgeHubLaunchIntent, KnowledgeHubLaunchPhase, KnowledgeHubLaunchPlan, KnowledgeHubLaunchResult, KnowledgeHubRepositoryPlan, RepositoryHost, } from './operations/services/hub-launch.ts';
|
|
6
6
|
export type { TreeseedOperationContext, TreeseedOperationImplementation, TreeseedOperationId, TreeseedOperationMetadata, TreeseedOperationProvider, TreeseedOperationProviderId, TreeseedOperationRequest, TreeseedOperationResult, TreeseedOperationGroup, } from './operations-types.ts';
|
|
7
7
|
export { TreeseedOperationError } from './operations-types.ts';
|
|
8
|
+
export { AGENT_OPERATION_MODES, AGENT_OPERATION_NAMES, createAgentOperationEvent, decideAgentOperationPermission, deniedAgentOperationResult, isAgentOperationName, resolveAgentOperationGrant, type AgentDeterministicOperationStep, type AgentOperationApprovalRef, type AgentOperationEvent, type AgentOperationGrant, type AgentOperationMergeFailure, type AgentOperationMode, type AgentOperationName, type AgentOperationPermissionCode, type AgentOperationPermissionDecision, type AgentOperationRequest, type AgentOperationResult, type AgentOperationStatus, } from './operations/agent-tools.ts';
|
|
8
9
|
export { TreeseedWorkflowSdk } from './workflow.ts';
|
|
9
10
|
export type * from './workflow.ts';
|
package/dist/operations.js
CHANGED
|
@@ -15,20 +15,36 @@ import {
|
|
|
15
15
|
} from "./operations/services/hub-launch.js";
|
|
16
16
|
import { TreeseedOperationsSdk } from "./operations/runtime.js";
|
|
17
17
|
import { TreeseedOperationError } from "./operations-types.js";
|
|
18
|
+
import {
|
|
19
|
+
AGENT_OPERATION_MODES,
|
|
20
|
+
AGENT_OPERATION_NAMES,
|
|
21
|
+
createAgentOperationEvent,
|
|
22
|
+
decideAgentOperationPermission,
|
|
23
|
+
deniedAgentOperationResult,
|
|
24
|
+
isAgentOperationName,
|
|
25
|
+
resolveAgentOperationGrant
|
|
26
|
+
} from "./operations/agent-tools.js";
|
|
18
27
|
import { TreeseedWorkflowSdk } from "./workflow.js";
|
|
19
28
|
export {
|
|
29
|
+
AGENT_OPERATION_MODES,
|
|
30
|
+
AGENT_OPERATION_NAMES,
|
|
20
31
|
TRESEED_OPERATION_SPECS,
|
|
21
32
|
TreeseedOperationError,
|
|
22
33
|
TreeseedOperationsSdk,
|
|
23
34
|
TreeseedWorkflowSdk,
|
|
24
35
|
collectTreeseedConfigSeedValues,
|
|
36
|
+
createAgentOperationEvent,
|
|
25
37
|
createKnowledgeHubRepositories,
|
|
38
|
+
decideAgentOperationPermission,
|
|
26
39
|
defaultHubContentResolutionPolicy,
|
|
40
|
+
deniedAgentOperationResult,
|
|
27
41
|
executeKnowledgeHubLaunch,
|
|
28
42
|
findTreeseedOperation,
|
|
43
|
+
isAgentOperationName,
|
|
29
44
|
listTreeseedOperationNames,
|
|
30
45
|
normalizeKnowledgeHubLaunchIntent,
|
|
31
46
|
planKnowledgeHubLaunch,
|
|
32
47
|
planKnowledgeHubRepositories,
|
|
48
|
+
resolveAgentOperationGrant,
|
|
33
49
|
validateRepositoryHost
|
|
34
50
|
};
|
|
@@ -106,6 +106,10 @@ function processingPlaneEnabled(context) {
|
|
|
106
106
|
function formsEnabled(context) {
|
|
107
107
|
return webSurfaceEnabled(context) && (context.deployConfig.providers?.forms ?? "store_only") !== "none";
|
|
108
108
|
}
|
|
109
|
+
function codexExecutionSelected(context) {
|
|
110
|
+
const execution = context.deployConfig.providers?.agents?.execution ?? "codex";
|
|
111
|
+
return execution === "codex" || execution === "codex_subscription";
|
|
112
|
+
}
|
|
109
113
|
function railwayManagedEnabled(context) {
|
|
110
114
|
if (!workflowPlaneAllows("processing")) {
|
|
111
115
|
return false;
|
|
@@ -333,6 +337,7 @@ const PREDICATES = {
|
|
|
333
337
|
apiSurfaceEnabled: (context) => apiSurfaceEnabled(context),
|
|
334
338
|
processingPlaneEnabled: (context) => processingPlaneEnabled(context),
|
|
335
339
|
formsEnabled: (context) => formsEnabled(context),
|
|
340
|
+
codexExecutionSelected: (context) => codexExecutionSelected(context),
|
|
336
341
|
railwayManagedEnabled: (context) => railwayManagedEnabled(context),
|
|
337
342
|
hubTreeseedHosted: (context) => resolveHubMode(context) === "treeseed_hosted",
|
|
338
343
|
hubCustomerHosted: (context) => resolveHubMode(context) === "customer_hosted",
|
package/dist/plugin-default.js
CHANGED
|
@@ -6,7 +6,7 @@ var plugin_default_default = defineTreeseedPlugin({
|
|
|
6
6
|
forms: ["store_only", "notify_admin", "full_email"],
|
|
7
7
|
operations: ["default"],
|
|
8
8
|
agents: {
|
|
9
|
-
execution: ["stub", "manual", "copilot"],
|
|
9
|
+
execution: ["stub", "manual", "copilot", "codex", "codex_subscription"],
|
|
10
10
|
mutation: ["local_branch"],
|
|
11
11
|
repository: ["stub", "git"],
|
|
12
12
|
verification: ["stub", "local"],
|
package/dist/sdk-types.d.ts
CHANGED
|
@@ -412,6 +412,224 @@ export type CapacityReservationState = 'reserved' | 'consuming' | 'consumed' | '
|
|
|
412
412
|
export type CapacityEstimatePhase = 'intent' | 'discovery' | 'plan' | 'execution' | 'actual';
|
|
413
413
|
export type CapacityEstimateConfidence = 'low' | 'medium' | 'high';
|
|
414
414
|
export type CapacityApprovalState = 'pending' | 'approved' | 'rejected' | 'expired' | 'superseded';
|
|
415
|
+
export type TaskRiskClass = 'low' | 'medium' | 'high';
|
|
416
|
+
export type TaskMutationScope = 'none' | 'repository_read' | 'repository_write' | 'production';
|
|
417
|
+
export type TaskConcurrencyClass = 'read_only' | 'repository_claim' | 'exclusive_project' | 'human_attention';
|
|
418
|
+
export type TaskAdmissionOutcome = 'admitted' | 'planning_required' | 'approval_required' | 'budget_blocked' | 'deferred' | 'rejected';
|
|
419
|
+
export type CanonicalTaskState = 'pending' | 'queued' | 'claimed' | 'running' | 'completed' | 'failed' | 'waiting' | 'paused_for_approval' | 'checkpointing' | 'checkpointed' | 'continuation_required' | 'rollback_required' | 'rollback_complete' | 'provider_exhausted' | 'reservation_exhausted';
|
|
420
|
+
export type RepositoryWorkState = 'clean' | 'claimed_dirty' | 'checkpointed_dirty' | 'parked_dirty' | 'rollback_required';
|
|
421
|
+
export interface TaskClassification {
|
|
422
|
+
taskSignature: string;
|
|
423
|
+
risk: TaskRiskClass;
|
|
424
|
+
mutationScope: TaskMutationScope;
|
|
425
|
+
concurrencyClass: TaskConcurrencyClass;
|
|
426
|
+
expectedFanout: number;
|
|
427
|
+
confidence: CapacityEstimateConfidence;
|
|
428
|
+
requiresPlanning: boolean;
|
|
429
|
+
requiresApproval: boolean;
|
|
430
|
+
features?: Record<string, unknown>;
|
|
431
|
+
}
|
|
432
|
+
export interface ExecutionProfile {
|
|
433
|
+
id: string;
|
|
434
|
+
providerId?: string | null;
|
|
435
|
+
laneId?: string | null;
|
|
436
|
+
modelFamily?: string | null;
|
|
437
|
+
modelClass?: string | null;
|
|
438
|
+
contextWindowTokens?: number | null;
|
|
439
|
+
qualityWeight: number;
|
|
440
|
+
costMultiplier: number;
|
|
441
|
+
latencyClass: 'low' | 'medium' | 'high' | string;
|
|
442
|
+
concurrencyClass?: TaskConcurrencyClass | null;
|
|
443
|
+
quotaBehavior?: 'api_metered' | 'subscription_limited' | 'compute_bound' | 'attention_bound' | string | null;
|
|
444
|
+
metadata?: Record<string, unknown>;
|
|
445
|
+
}
|
|
446
|
+
export interface AttentionEstimate {
|
|
447
|
+
attentionWeight: number;
|
|
448
|
+
coordinationWeight: number;
|
|
449
|
+
totalAttentionWeight: number;
|
|
450
|
+
estimatedContextTokens: number;
|
|
451
|
+
requiredContextTokens: number;
|
|
452
|
+
source: string;
|
|
453
|
+
metadata?: Record<string, unknown>;
|
|
454
|
+
}
|
|
455
|
+
export interface AttentionPolicy {
|
|
456
|
+
maxAttentionLoad: number | null;
|
|
457
|
+
reserveAttentionPercent: number;
|
|
458
|
+
maxContextTokens: number | null;
|
|
459
|
+
maxContextSaturationPercent: number;
|
|
460
|
+
coordinationOverheadFactor: number;
|
|
461
|
+
}
|
|
462
|
+
export interface UtilityEstimate {
|
|
463
|
+
utilityValue: number;
|
|
464
|
+
maintenanceValue: number;
|
|
465
|
+
deadlinePressure: number;
|
|
466
|
+
successProbability: number;
|
|
467
|
+
qualityScore: number;
|
|
468
|
+
riskPenalty: number;
|
|
469
|
+
utilityScore: number;
|
|
470
|
+
utilityPerCredit: number;
|
|
471
|
+
source: string;
|
|
472
|
+
metadata?: Record<string, unknown>;
|
|
473
|
+
}
|
|
474
|
+
export interface UtilityPolicy {
|
|
475
|
+
minimumUtilityScore: number | null;
|
|
476
|
+
minimumUtilityPerCredit: number | null;
|
|
477
|
+
riskPenaltyFactor: number;
|
|
478
|
+
deadlineWindowHours: number;
|
|
479
|
+
maintenanceWeight: number;
|
|
480
|
+
priorityWeight: number;
|
|
481
|
+
}
|
|
482
|
+
export interface PredictiveReservePolicy {
|
|
483
|
+
enabled: boolean;
|
|
484
|
+
baseReservePercent: number;
|
|
485
|
+
maxReservePercent: number;
|
|
486
|
+
incidentReservePercent: number;
|
|
487
|
+
triggerBurstReservePercent: number;
|
|
488
|
+
deploymentWindowReservePercent: number;
|
|
489
|
+
providerDegradationReservePercent: number;
|
|
490
|
+
quotaPressureReservePercent: number;
|
|
491
|
+
}
|
|
492
|
+
export interface ReservePrediction {
|
|
493
|
+
reservePercent: number;
|
|
494
|
+
reserveCredits: number;
|
|
495
|
+
activelyAllocatableCredits: number;
|
|
496
|
+
reasons: string[];
|
|
497
|
+
signals: Record<string, unknown>;
|
|
498
|
+
}
|
|
499
|
+
export interface HybridExecutionPhase {
|
|
500
|
+
id: string;
|
|
501
|
+
kind: 'planning' | 'implementation' | 'review' | 'human_escalation' | string;
|
|
502
|
+
executionProfileId: string;
|
|
503
|
+
taskSignature?: string | null;
|
|
504
|
+
required: boolean;
|
|
505
|
+
admissionRequired: boolean;
|
|
506
|
+
mutationAllowed: boolean;
|
|
507
|
+
metadata?: Record<string, unknown>;
|
|
508
|
+
}
|
|
509
|
+
export interface HybridExecutionPlan {
|
|
510
|
+
schemaVersion: 1;
|
|
511
|
+
planId: string;
|
|
512
|
+
phases: HybridExecutionPhase[];
|
|
513
|
+
escalationPolicy?: Record<string, unknown>;
|
|
514
|
+
metadata?: Record<string, unknown>;
|
|
515
|
+
}
|
|
516
|
+
export interface WorkdayBudgetEnvelope {
|
|
517
|
+
dailyCreditBudget: number;
|
|
518
|
+
usedCredits: number;
|
|
519
|
+
queuedCredits: number;
|
|
520
|
+
reserveBufferCredits: number;
|
|
521
|
+
recoveryBudgetCredits: number;
|
|
522
|
+
activelyAllocatableCredits: number;
|
|
523
|
+
remainingCredits: number;
|
|
524
|
+
}
|
|
525
|
+
export interface TaskAdmissionPolicy {
|
|
526
|
+
planningThresholdCredits: number;
|
|
527
|
+
approvalThresholdCredits: number;
|
|
528
|
+
reserveBufferPercent: number;
|
|
529
|
+
recoveryBudgetCredits: number;
|
|
530
|
+
maxDownstreamTasks: number;
|
|
531
|
+
maxPlanningDepth: number;
|
|
532
|
+
maxAdmittedPlanTasksPerCycle: number;
|
|
533
|
+
planningTaskSignature: string;
|
|
534
|
+
allowBackfill?: boolean;
|
|
535
|
+
maxAttentionLoad?: number | null;
|
|
536
|
+
reserveAttentionPercent?: number | null;
|
|
537
|
+
maxContextTokens?: number | null;
|
|
538
|
+
maxContextSaturationPercent?: number | null;
|
|
539
|
+
coordinationOverheadFactor?: number | null;
|
|
540
|
+
predictiveReservePolicy?: Partial<PredictiveReservePolicy> | null;
|
|
541
|
+
utilityPolicy?: Partial<UtilityPolicy> | null;
|
|
542
|
+
}
|
|
543
|
+
export interface TaskAdmissionDecision {
|
|
544
|
+
outcome: TaskAdmissionOutcome;
|
|
545
|
+
taskSignature: string;
|
|
546
|
+
estimatedCreditsP50: number;
|
|
547
|
+
estimatedCreditsP90: number;
|
|
548
|
+
reservedCredits: number;
|
|
549
|
+
baseReservedCredits?: number;
|
|
550
|
+
executionProfileId?: string | null;
|
|
551
|
+
costMultiplier?: number | null;
|
|
552
|
+
reasons: string[];
|
|
553
|
+
requiresApproval: boolean;
|
|
554
|
+
requiresPlanning: boolean;
|
|
555
|
+
budget: WorkdayBudgetEnvelope;
|
|
556
|
+
policySnapshot: TaskAdmissionPolicy;
|
|
557
|
+
metadata?: Record<string, unknown>;
|
|
558
|
+
}
|
|
559
|
+
export interface TaskCheckpointArtifact {
|
|
560
|
+
id?: string;
|
|
561
|
+
taskId: string;
|
|
562
|
+
checkpointId?: string;
|
|
563
|
+
branch?: string | null;
|
|
564
|
+
baseCommit?: string | null;
|
|
565
|
+
currentCommit?: string | null;
|
|
566
|
+
currentGoal?: string | null;
|
|
567
|
+
currentPhase?: string | null;
|
|
568
|
+
filesChanged: string[];
|
|
569
|
+
commandsRun: string[];
|
|
570
|
+
testStatus?: 'not_run' | 'passing' | 'failing' | 'unknown' | string;
|
|
571
|
+
knownFailures: string[];
|
|
572
|
+
completedWork: string[];
|
|
573
|
+
remainingWorkEstimate?: {
|
|
574
|
+
p50: number;
|
|
575
|
+
p90: number;
|
|
576
|
+
} | null;
|
|
577
|
+
rollbackStrategy?: string | null;
|
|
578
|
+
continuationStrategy?: string | null;
|
|
579
|
+
repositoryState: RepositoryWorkState;
|
|
580
|
+
createdAt: string;
|
|
581
|
+
metadata?: Record<string, unknown>;
|
|
582
|
+
}
|
|
583
|
+
export interface PlannedTaskNode {
|
|
584
|
+
id?: string;
|
|
585
|
+
type: string;
|
|
586
|
+
agentId?: string | null;
|
|
587
|
+
title?: string | null;
|
|
588
|
+
priority?: number | null;
|
|
589
|
+
taskSignature?: string | null;
|
|
590
|
+
payload?: Record<string, unknown>;
|
|
591
|
+
estimatedCreditsP50?: number | null;
|
|
592
|
+
estimatedCreditsP90?: number | null;
|
|
593
|
+
risk?: TaskRiskClass | null;
|
|
594
|
+
mutationScope?: TaskMutationScope | null;
|
|
595
|
+
confidence?: CapacityEstimateConfidence | null;
|
|
596
|
+
expectedFanout?: number | null;
|
|
597
|
+
requiresApproval?: boolean | null;
|
|
598
|
+
requiresPlanning?: boolean | null;
|
|
599
|
+
dependsOn?: string[];
|
|
600
|
+
metadata?: Record<string, unknown>;
|
|
601
|
+
}
|
|
602
|
+
export interface TaskPlanProposal {
|
|
603
|
+
schemaVersion: 1;
|
|
604
|
+
planId: string;
|
|
605
|
+
sourceTaskId?: string | null;
|
|
606
|
+
parentTaskId?: string | null;
|
|
607
|
+
planningDepth: number;
|
|
608
|
+
tasks: PlannedTaskNode[];
|
|
609
|
+
totalEstimatedCreditsP50: number;
|
|
610
|
+
totalEstimatedCreditsP90: number;
|
|
611
|
+
createdAt?: string | null;
|
|
612
|
+
metadata?: Record<string, unknown>;
|
|
613
|
+
}
|
|
614
|
+
export interface PlanningPolicy {
|
|
615
|
+
maxDownstreamTasks: number;
|
|
616
|
+
maxPlanningDepth: number;
|
|
617
|
+
maxAdmittedPlanTasksPerCycle: number;
|
|
618
|
+
planningTaskSignature: string;
|
|
619
|
+
}
|
|
620
|
+
export interface PlanningAdmissionResult {
|
|
621
|
+
proposal: TaskPlanProposal;
|
|
622
|
+
admitted: PlannedTaskNode[];
|
|
623
|
+
deferred: PlannedTaskNode[];
|
|
624
|
+
rejected: Array<{
|
|
625
|
+
node: PlannedTaskNode;
|
|
626
|
+
reasons: string[];
|
|
627
|
+
}>;
|
|
628
|
+
totalEstimatedCreditsP50: number;
|
|
629
|
+
totalEstimatedCreditsP90: number;
|
|
630
|
+
admittedCreditsP90: number;
|
|
631
|
+
reasons: string[];
|
|
632
|
+
}
|
|
415
633
|
export interface CapacityProvider {
|
|
416
634
|
id: string;
|
|
417
635
|
teamId: string | null;
|
|
@@ -536,6 +754,7 @@ export interface TaskEstimate {
|
|
|
536
754
|
projectId: string;
|
|
537
755
|
estimatePhase: CapacityEstimatePhase;
|
|
538
756
|
taskSignature: string;
|
|
757
|
+
executionProfileId: string;
|
|
539
758
|
confidence: CapacityEstimateConfidence;
|
|
540
759
|
estimatedCreditsP50: number;
|
|
541
760
|
estimatedCreditsP90: number;
|
|
@@ -555,6 +774,7 @@ export interface TaskUsageActual {
|
|
|
555
774
|
workDayId: string | null;
|
|
556
775
|
projectId: string;
|
|
557
776
|
taskSignature: string;
|
|
777
|
+
executionProfileId: string;
|
|
558
778
|
capacityProviderId: string | null;
|
|
559
779
|
laneId: string | null;
|
|
560
780
|
businessModel: CapacityBusinessModel | string;
|
|
@@ -577,7 +797,10 @@ export interface TaskUsageActual {
|
|
|
577
797
|
}
|
|
578
798
|
export interface TaskEstimateProfile {
|
|
579
799
|
taskSignature: string;
|
|
800
|
+
executionProfileId: string;
|
|
580
801
|
sampleCount: number;
|
|
802
|
+
completedSampleCount?: number;
|
|
803
|
+
interruptedSampleCount?: number;
|
|
581
804
|
inputTokensP50: number | null;
|
|
582
805
|
inputTokensP90: number | null;
|
|
583
806
|
outputTokensP50: number | null;
|
|
@@ -588,6 +811,12 @@ export interface TaskEstimateProfile {
|
|
|
588
811
|
filesChangedP90: number | null;
|
|
589
812
|
creditsP50: number | null;
|
|
590
813
|
creditsP90: number | null;
|
|
814
|
+
creditsVariance?: number | null;
|
|
815
|
+
confidenceScore?: number | null;
|
|
816
|
+
outlierCount?: number;
|
|
817
|
+
partialCredits?: number | null;
|
|
818
|
+
firstSampleAt?: string | null;
|
|
819
|
+
lastSampleAt?: string | null;
|
|
591
820
|
updatedAt: string;
|
|
592
821
|
}
|
|
593
822
|
export interface ApprovalRequest {
|
|
@@ -1690,6 +1919,7 @@ export interface CreateTaskEstimateRequest {
|
|
|
1690
1919
|
projectId: string;
|
|
1691
1920
|
estimatePhase: CapacityEstimatePhase;
|
|
1692
1921
|
taskSignature: string;
|
|
1922
|
+
executionProfileId?: string | null;
|
|
1693
1923
|
confidence: CapacityEstimateConfidence;
|
|
1694
1924
|
estimatedCreditsP50: number;
|
|
1695
1925
|
estimatedCreditsP90: number;
|
|
@@ -1708,6 +1938,7 @@ export interface CreateTaskUsageActualRequest {
|
|
|
1708
1938
|
workDayId?: string | null;
|
|
1709
1939
|
projectId: string;
|
|
1710
1940
|
taskSignature: string;
|
|
1941
|
+
executionProfileId?: string | null;
|
|
1711
1942
|
capacityProviderId?: string | null;
|
|
1712
1943
|
laneId?: string | null;
|
|
1713
1944
|
businessModel: CapacityBusinessModel | string;
|
package/dist/types/agents.d.ts
CHANGED
|
@@ -27,6 +27,18 @@ export interface AgentOutputContract {
|
|
|
27
27
|
modelMutations: string[];
|
|
28
28
|
}
|
|
29
29
|
export interface AgentExecutionConfig {
|
|
30
|
+
provider?: string;
|
|
31
|
+
model?: string;
|
|
32
|
+
approvalPolicy?: 'never' | 'on_request' | 'always' | string;
|
|
33
|
+
sandboxMode?: 'read_only' | 'workspace_write' | string;
|
|
34
|
+
reasoningEffort?: 'low' | 'medium' | 'high' | string;
|
|
35
|
+
allowedPaths?: string[];
|
|
36
|
+
forbiddenPaths?: string[];
|
|
37
|
+
worktree?: {
|
|
38
|
+
enabled?: boolean;
|
|
39
|
+
root?: string;
|
|
40
|
+
branchPrefix?: string;
|
|
41
|
+
};
|
|
30
42
|
maxConcurrency: number;
|
|
31
43
|
timeoutSeconds: number;
|
|
32
44
|
cooldownSeconds: number;
|