@copado/agentia-cli 1.0.0-beta.8 → 1.0.0-rc.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.
Files changed (41) hide show
  1. package/CHANGELOG.md +29 -0
  2. package/README.md +494 -278
  3. package/dist/commands/adv/auth/status.js +1 -0
  4. package/dist/commands/adv/component/add.js +3 -0
  5. package/dist/commands/adv/component/remove.js +3 -0
  6. package/dist/commands/adv/component/types.js +1 -0
  7. package/dist/commands/adv/job/wait.js +1 -1
  8. package/dist/commands/adv/organization/list.js +1 -0
  9. package/dist/commands/cicd/template/defaults.js +42 -0
  10. package/dist/commands/cicd/template/delete.js +36 -0
  11. package/dist/commands/cicd/template/get.js +48 -0
  12. package/dist/commands/cicd/template/list.js +53 -0
  13. package/dist/commands/cicd/template/upsert.js +45 -0
  14. package/dist/commands/cicd/work/ahead-behind.js +51 -0
  15. package/dist/commands/cicd/work/environment-sync.js +1 -0
  16. package/dist/commands/cicd/work/submit.js +17 -4
  17. package/dist/commands/update.js +10 -2
  18. package/dist/lib/adv-operations.js +3 -1
  19. package/dist/lib/agentia-command.js +35 -0
  20. package/dist/lib/cli-version.js +6 -2
  21. package/dist/lib/headless-file-upload.js +10 -0
  22. package/dist/lib/java-runtime.js +6 -0
  23. package/dist/lib/mcp/adv-tools.js +40 -26
  24. package/dist/lib/mcp/tool-annotations.js +5 -0
  25. package/dist/lib/mcp/tools.js +118 -0
  26. package/dist/lib/mcp/work-tools.js +18 -4
  27. package/dist/lib/runtime.js +1 -1
  28. package/dist/lib/template-flags.js +8 -0
  29. package/dist/lib/template-types.js +21 -0
  30. package/dist/lib/version-warning.js +24 -8
  31. package/dist/lib/work-ahead-behind.js +5 -0
  32. package/dist/lib/work-push.js +2 -1
  33. package/dist/lib/work-types.js +2 -1
  34. package/oclif.manifest.json +898 -508
  35. package/package.json +1 -1
  36. package/templates/AGENTS.md +1 -1
  37. package/templates/skills/agentia-adv/SKILL.md +7 -1
  38. package/templates/skills/agentia-adv/references/pipelines-advanced.md +7 -7
  39. package/templates/skills/agentia-cicd/SKILL.md +5 -1
  40. package/templates/skills/agentia-cicd/references/functions.md +148 -0
  41. package/templates/skills/agentia-cicd/references/templates.md +132 -0
@@ -10,6 +10,20 @@ const componentReferenceSchema = z.union([
10
10
  }),
11
11
  ]);
12
12
  const componentInputSchema = z.array(componentReferenceSchema).min(1).describe('Components as Type/Name strings or {type, fullName, excluded} objects.');
13
+ const deploymentIdSchema = z.number().int().positive().describe('Deployment ID.');
14
+ const deploymentIdInputSchema = {
15
+ deploymentId: deploymentIdSchema.optional().describe('Canonical deployment ID.'),
16
+ flow: deploymentIdSchema.optional().describe('Deprecated alias for deploymentId.'),
17
+ id: deploymentIdSchema.optional().describe('Deprecated alias for deploymentId.'),
18
+ };
19
+ function resolveDeploymentId(input) {
20
+ const supplied = [input.deploymentId, input.id, input.flow].filter((value) => value !== undefined);
21
+ if (supplied.length === 0)
22
+ throw new Error('Provide deploymentId.');
23
+ if (new Set(supplied).size !== 1)
24
+ throw new Error('Deployment ID aliases must have the same value.');
25
+ return supplied[0];
26
+ }
13
27
  function componentList(components) {
14
28
  return components.map((component) => {
15
29
  if (typeof component === 'string')
@@ -30,7 +44,7 @@ async function deploymentAction(args) {
30
44
  return {
31
45
  result: await runAdvDeploymentAction({
32
46
  backup: args.backup,
33
- id: args.id,
47
+ id: resolveDeploymentId(args),
34
48
  kind: args.kind,
35
49
  wait: args.wait,
36
50
  waitIntervalSeconds: args.interval,
@@ -66,9 +80,9 @@ export function registerAgentiaMcpAdvTools(server) {
66
80
  }, (args) => safelyHandleTool(async () => ({ result: await listAdvDeployments({ includeArchived: args.includeArchived }) })));
67
81
  server.registerTool('agentia_adv_deployment_get', {
68
82
  description: 'Get one Copado Pipelines Advanced deployment.',
69
- inputSchema: { id: z.number().int().positive().describe('Deployment ID.') },
83
+ inputSchema: deploymentIdInputSchema,
70
84
  title: 'Agentia ADV Deployment Get',
71
- }, (args) => safelyHandleTool(async () => ({ result: await getAdvDeployment(args.id) })));
85
+ }, (args) => safelyHandleTool(async () => ({ result: await getAdvDeployment(resolveDeploymentId(args)) })));
72
86
  server.registerTool('agentia_adv_deployment_create', {
73
87
  description: 'Create a Copado Pipelines Advanced deployment.',
74
88
  inputSchema: {
@@ -81,15 +95,15 @@ export function registerAgentiaMcpAdvTools(server) {
81
95
  server.registerTool('agentia_adv_deployment_options', {
82
96
  description: 'Update Copado Pipelines Advanced deployment options.',
83
97
  inputSchema: {
84
- id: z.number().int().positive().describe('Deployment ID.'),
98
+ ...deploymentIdInputSchema,
85
99
  set: z.array(z.string()).optional().describe('Options as name=value entries; booleans, null, and finite JavaScript Number values are converted.'),
86
100
  },
87
101
  title: 'Agentia ADV Deployment Options',
88
- }, (args) => safelyHandleTool(async () => ({ result: await updateAdvDeploymentOptions({ id: args.id, set: args.set }) })));
102
+ }, (args) => safelyHandleTool(async () => ({ result: await updateAdvDeploymentOptions({ id: resolveDeploymentId(args), set: args.set }) })));
89
103
  server.registerTool('agentia_adv_deployment_validate', {
90
104
  description: 'Start a check-only Copado Pipelines Advanced validation run.',
91
105
  inputSchema: {
92
- id: z.number().int().positive().describe('Deployment ID.'),
106
+ ...deploymentIdInputSchema,
93
107
  interval: z.number().positive().optional().describe('Seconds between polls when wait is true.'),
94
108
  timeout: z.number().positive().optional().describe('Maximum seconds to wait.'),
95
109
  wait: z.boolean().optional().describe('Wait for the run to finish.'),
@@ -100,7 +114,7 @@ export function registerAgentiaMcpAdvTools(server) {
100
114
  description: 'Start a real Copado Pipelines Advanced deployment run.',
101
115
  inputSchema: {
102
116
  confirm: z.boolean().optional().describe('Required true to start a deployment.'),
103
- id: z.number().int().positive().describe('Deployment ID.'),
117
+ ...deploymentIdInputSchema,
104
118
  interval: z.number().positive().optional().describe('Seconds between polls when wait is true.'),
105
119
  timeout: z.number().positive().optional().describe('Maximum seconds to wait.'),
106
120
  wait: z.boolean().optional().describe('Wait for the run to finish.'),
@@ -112,7 +126,7 @@ export function registerAgentiaMcpAdvTools(server) {
112
126
  inputSchema: {
113
127
  backup: z.boolean().optional().describe('Run backupThenDeploy instead of a quick deploy.'),
114
128
  confirm: z.boolean().optional().describe('Required true to start a quick deploy.'),
115
- id: z.number().int().positive().describe('Deployment ID.'),
129
+ ...deploymentIdInputSchema,
116
130
  interval: z.number().positive().optional().describe('Seconds between polls when wait is true.'),
117
131
  timeout: z.number().positive().optional().describe('Maximum seconds to wait.'),
118
132
  wait: z.boolean().optional().describe('Wait for the run to finish.'),
@@ -123,7 +137,7 @@ export function registerAgentiaMcpAdvTools(server) {
123
137
  description: 'Cancel the current Copado Pipelines Advanced run.',
124
138
  inputSchema: {
125
139
  confirm: z.boolean().optional().describe('Required true to request cancellation.'),
126
- id: z.number().int().positive().describe('Deployment ID.'),
140
+ ...deploymentIdInputSchema,
127
141
  interval: z.number().positive().optional().describe('Seconds between polls when wait is true.'),
128
142
  timeout: z.number().positive().optional().describe('Maximum seconds to wait.'),
129
143
  wait: z.boolean().optional().describe('Wait for the run to finish.'),
@@ -133,7 +147,7 @@ export function registerAgentiaMcpAdvTools(server) {
133
147
  requireConfirm(args.confirm, 'Pipelines Advanced deployment cancellation');
134
148
  return {
135
149
  result: await cancelAdvDeployment({
136
- id: args.id,
150
+ id: resolveDeploymentId(args),
137
151
  wait: args.wait,
138
152
  waitIntervalSeconds: args.interval,
139
153
  waitTimeoutSeconds: args.timeout,
@@ -148,37 +162,37 @@ export function registerAgentiaMcpAdvTools(server) {
148
162
  server.registerTool('agentia_adv_component_list', {
149
163
  description: 'List source components for a Copado Pipelines Advanced deployment.',
150
164
  inputSchema: {
151
- flow: z.number().int().positive().describe('Deployment ID.'),
165
+ ...deploymentIdInputSchema,
152
166
  includeManagedPackage: z.boolean().optional().describe('Include managed package components.'),
153
167
  type: z.string().describe('Comma-separated component type names.'),
154
168
  },
155
169
  title: 'Agentia ADV Component List',
156
- }, (args) => safelyHandleTool(async () => ({ result: await listAdvComponents(args) })));
170
+ }, (args) => safelyHandleTool(async () => ({ result: await listAdvComponents({ ...args, flow: resolveDeploymentId(args) }) })));
157
171
  server.registerTool('agentia_adv_component_refresh', {
158
172
  description: 'Refresh Copado Pipelines Advanced component comparison cache.',
159
173
  inputSchema: {
160
- flow: z.number().int().positive().describe('Deployment ID.'),
174
+ ...deploymentIdInputSchema,
161
175
  full: z.boolean().optional().describe('Delete cached comparison data before refreshing.'),
162
176
  type: z.string().describe('Comma-separated component type names.'),
163
177
  },
164
178
  title: 'Agentia ADV Component Refresh',
165
- }, (args) => safelyHandleTool(async () => ({ result: await refreshAdvComponents(args) })));
179
+ }, (args) => safelyHandleTool(async () => ({ result: await refreshAdvComponents({ ...args, flow: resolveDeploymentId(args) }) })));
166
180
  server.registerTool('agentia_adv_component_selected', {
167
181
  description: 'List selected components for a Copado Pipelines Advanced deployment.',
168
- inputSchema: { deploymentId: z.number().int().positive().describe('Deployment ID.') },
182
+ inputSchema: deploymentIdInputSchema,
169
183
  title: 'Agentia ADV Component Selected',
170
- }, (args) => safelyHandleTool(async () => ({ result: await selectedAdvComponents(args.deploymentId) })));
184
+ }, (args) => safelyHandleTool(async () => ({ result: await selectedAdvComponents(resolveDeploymentId(args)) })));
171
185
  server.registerTool('agentia_adv_component_add', {
172
186
  description: 'Add components to a Copado Pipelines Advanced deployment selection.',
173
187
  inputSchema: {
174
188
  components: componentInputSchema,
175
- deploymentId: z.number().int().positive().describe('Deployment ID.'),
189
+ ...deploymentIdInputSchema,
176
190
  },
177
191
  title: 'Agentia ADV Component Add',
178
192
  }, (args) => safelyHandleTool(async () => ({
179
193
  result: await addAdvComponents({
180
194
  components: componentList(args.components),
181
- deploymentId: args.deploymentId,
195
+ deploymentId: resolveDeploymentId(args),
182
196
  mode: componentAddMode(args.components),
183
197
  }),
184
198
  })));
@@ -186,37 +200,37 @@ export function registerAgentiaMcpAdvTools(server) {
186
200
  description: 'Remove components from a Copado Pipelines Advanced deployment selection.',
187
201
  inputSchema: {
188
202
  components: componentInputSchema,
189
- deploymentId: z.number().int().positive().describe('Deployment ID.'),
203
+ ...deploymentIdInputSchema,
190
204
  },
191
205
  title: 'Agentia ADV Component Remove',
192
206
  }, (args) => safelyHandleTool(async () => ({
193
- result: await removeAdvComponents({ components: componentList(args.components), deploymentId: args.deploymentId }),
207
+ result: await removeAdvComponents({ components: componentList(args.components), deploymentId: resolveDeploymentId(args) }),
194
208
  })));
195
209
  server.registerTool('agentia_adv_job_get', {
196
210
  description: 'Get the latest Copado Pipelines Advanced run for a deployment.',
197
- inputSchema: { deploymentId: z.number().int().positive().describe('Deployment ID.') },
211
+ inputSchema: deploymentIdInputSchema,
198
212
  title: 'Agentia ADV Job Get',
199
- }, (args) => safelyHandleTool(async () => ({ result: await getAdvJob(args.deploymentId) })));
213
+ }, (args) => safelyHandleTool(async () => ({ result: await getAdvJob(resolveDeploymentId(args)) })));
200
214
  server.registerTool('agentia_adv_job_list', {
201
215
  description: 'List Copado Pipelines Advanced run history for a deployment.',
202
216
  inputSchema: {
203
- deploymentId: z.number().int().positive().describe('Deployment ID.'),
217
+ ...deploymentIdInputSchema,
204
218
  page: z.number().int().min(0).optional().describe('Page number starting at 0.'),
205
219
  pageSize: z.number().int().positive().optional().describe('Rows per page.'),
206
220
  },
207
221
  title: 'Agentia ADV Job List',
208
- }, (args) => safelyHandleTool(async () => ({ result: await listAdvJobs(args) })));
222
+ }, (args) => safelyHandleTool(async () => ({ result: await listAdvJobs({ ...args, deploymentId: resolveDeploymentId(args) }) })));
209
223
  server.registerTool('agentia_adv_job_wait', {
210
224
  description: 'Wait for the latest Copado Pipelines Advanced run to finish.',
211
225
  inputSchema: {
212
- deploymentId: z.number().int().positive().describe('Deployment ID.'),
226
+ ...deploymentIdInputSchema,
213
227
  interval: z.number().positive().optional().describe('Seconds between polls.'),
214
228
  timeout: z.number().positive().optional().describe('Maximum seconds to wait.'),
215
229
  },
216
230
  title: 'Agentia ADV Job Wait',
217
231
  }, (args) => safelyHandleTool(async () => {
218
232
  const result = await waitForAdvJob({
219
- deploymentId: args.deploymentId,
233
+ deploymentId: resolveDeploymentId(args),
220
234
  intervalSeconds: args.interval,
221
235
  timeoutSeconds: args.timeout,
222
236
  });
@@ -93,6 +93,7 @@ const DELETE_TOOLS = [
93
93
  'agentia_data_filter_delete',
94
94
  'agentia_data_template_delete',
95
95
  'agentia_function_delete',
96
+ 'agentia_template_delete',
96
97
  'agentia_pipeline_connection_delete',
97
98
  'agentia_pipeline_stage_connection_delete',
98
99
  'agentia_project_delete',
@@ -146,6 +147,9 @@ const READ_TOOLS = [
146
147
  'agentia_function_list',
147
148
  'agentia_function_result_get',
148
149
  'agentia_function_result_log_get',
150
+ 'agentia_template_defaults',
151
+ 'agentia_template_get',
152
+ 'agentia_template_list',
149
153
  'agentia_health_check',
150
154
  'agentia_job_get',
151
155
  'agentia_job_list',
@@ -226,6 +230,7 @@ const UPDATE_TOOLS = [
226
230
  'agentia_data_template_save_detail',
227
231
  'agentia_environment_update',
228
232
  'agentia_function_upsert',
233
+ 'agentia_template_upsert',
229
234
  'agentia_pipeline_connection_update',
230
235
  'agentia_pipeline_stage_connection_update',
231
236
  'agentia_pipeline_update',
@@ -46,6 +46,8 @@ import { normalizeRepositoriesListPage, normalizeRepository, normalizeRepository
46
46
  import { buildStageMutationPayload, validateStagePayload } from '../stage-flags.js';
47
47
  import { fetchStages } from '../stage-list.js';
48
48
  import { normalizePipelineStageConnection, normalizeStage, pipelineStageConnectionEndpoint, pipelineStageConnectionsEndpoint, STAGE_META_STAGE_SUGGESTIONS, stageEndpoint, stagesEndpoint, } from '../stage-types.js';
49
+ import { buildTemplateDefaultsQuery } from '../template-flags.js';
50
+ import { normalizeTemplate, normalizeTemplatesListPage, normalizeTemplateUpsertPayload, TEMPLATE_LIST_TYPES, templateDefaultsEndpoint, templateEndpoint, templatesEndpoint, } from '../template-types.js';
49
51
  import { getUserContext } from '../user-context.js';
50
52
  import { fetchUser } from '../user-get.js';
51
53
  import { DEFAULT_USER_ID } from '../user-types.js';
@@ -637,6 +639,52 @@ async function functionDelete(args) {
637
639
  });
638
640
  return { apiName };
639
641
  }
642
+ async function templateList(args = {}) {
643
+ const response = await CicdGateway.call({
644
+ endpoint: templatesEndpoint({ ...args, type: args.type ?? 'custom' }),
645
+ method: 'GET',
646
+ });
647
+ return mcpPaginatedListPayload('templates', normalizeTemplatesListPage(response));
648
+ }
649
+ async function templateGet(args) {
650
+ const response = await CicdGateway.call({
651
+ endpoint: templateEndpoint(assertRequired(args.apiName, 'apiName')),
652
+ method: 'GET',
653
+ });
654
+ return { template: normalizeTemplate(response) };
655
+ }
656
+ async function templateDefaults(args) {
657
+ const query = buildTemplateDefaultsQuery({
658
+ name: assertRequired(args.name, 'name'),
659
+ ...(args.apiName === undefined ? {} : { 'api-name': args.apiName }),
660
+ });
661
+ const response = await CicdGateway.call({
662
+ endpoint: templateDefaultsEndpoint(query),
663
+ method: 'GET',
664
+ });
665
+ return { template: normalizeTemplate(response) };
666
+ }
667
+ async function templateUpsert(args) {
668
+ const apiName = assertRequired(args.apiName, 'apiName');
669
+ const payload = normalizeTemplateUpsertPayload(apiName, args);
670
+ const response = await CicdGateway.call({
671
+ body: payload,
672
+ endpoint: templateEndpoint(apiName),
673
+ headers: {
674
+ 'Content-Type': 'application/json',
675
+ },
676
+ method: 'PUT',
677
+ });
678
+ return { template: normalizeTemplate(response) };
679
+ }
680
+ async function templateDelete(args) {
681
+ const apiName = assertRequired(args.apiName, 'apiName');
682
+ await CicdGateway.call({
683
+ endpoint: templateEndpoint(apiName),
684
+ method: 'DELETE',
685
+ });
686
+ return { apiName };
687
+ }
640
688
  async function functionRun(args) {
641
689
  const apiName = assertRequired(args.apiName, 'apiName');
642
690
  const response = await CicdGateway.call({
@@ -1280,6 +1328,11 @@ export const agentiaMcpToolHandlers = wrapMcpToolHandlers({
1280
1328
  stageGet,
1281
1329
  stageList,
1282
1330
  stageUpdate,
1331
+ templateDefaults,
1332
+ templateDelete,
1333
+ templateGet,
1334
+ templateList,
1335
+ templateUpsert,
1283
1336
  userGet,
1284
1337
  workStatus,
1285
1338
  ...agentiaMcpTestingToolHandlers,
@@ -2117,6 +2170,71 @@ export function registerAgentiaMcpTools(server) {
2117
2170
  },
2118
2171
  title: 'Agentia Function Result Log Get',
2119
2172
  }, (args) => safelyHandleTool(() => functionResultLogGet(args)));
2173
+ server.registerTool('agentia_template_list', {
2174
+ description: 'List Copado Job Templates via the CICD gateway.',
2175
+ inputSchema: {
2176
+ fetchAll: z.boolean().optional().describe('Fetch all matching templates.'),
2177
+ name: z.string().optional().describe('Filter by name substring.'),
2178
+ type: z.enum(TEMPLATE_LIST_TYPES).optional().describe('List Custom templates only, or all templates.'),
2179
+ ...listPaginationZodFields,
2180
+ },
2181
+ title: 'Agentia Template List',
2182
+ }, (args) => safelyHandleTool(() => templateList(args)));
2183
+ server.registerTool('agentia_template_get', {
2184
+ description: 'Get a Copado Job Template by API name via the CICD gateway.',
2185
+ inputSchema: { apiName: z.string().describe('Template API name.') },
2186
+ title: 'Agentia Template Get',
2187
+ }, (args) => safelyHandleTool(() => templateGet(args)));
2188
+ server.registerTool('agentia_template_defaults', {
2189
+ description: 'Scaffold default Copado Job Template metadata without writing to Salesforce.',
2190
+ inputSchema: {
2191
+ apiName: z.string().optional().describe('Optional template API name for the scaffold.'),
2192
+ name: z.string().describe('Template display name.'),
2193
+ },
2194
+ title: 'Agentia Template Defaults',
2195
+ }, (args) => safelyHandleTool(() => templateDefaults(args)));
2196
+ server.registerTool('agentia_template_upsert', {
2197
+ description: 'Create or update a Copado Job Template by API name via the CICD gateway.',
2198
+ inputSchema: {
2199
+ apiName: z.string().describe('Template API name.'),
2200
+ description: z.string().nullable().optional().describe('Template description.'),
2201
+ name: z.string().optional().describe('Template display name.'),
2202
+ steps: z
2203
+ .array(z.object({
2204
+ apiName: z.string().describe('Step API name.'),
2205
+ config: z.unknown().nullable().optional().describe('Step config JSON.'),
2206
+ customType: z.string().nullable().optional().describe('Step custom type.'),
2207
+ name: z.string().describe('Step display name.'),
2208
+ order: z.number().nullable().optional().describe('Step order (server may reassign).'),
2209
+ type: z.string().describe('Step type.'),
2210
+ }))
2211
+ .describe('Full step list (replace semantics; use [] to clear all steps).'),
2212
+ type: z.string().optional().describe('Template type.'),
2213
+ version: z.string().optional().describe('Template version.'),
2214
+ volumeOptions: z.unknown().nullable().optional().describe('Volume options JSON or string.'),
2215
+ },
2216
+ title: 'Agentia Template Upsert',
2217
+ }, (args) => safelyHandleTool(() => templateUpsert({
2218
+ apiName: args.apiName,
2219
+ description: args.description,
2220
+ name: args.name,
2221
+ steps: args.steps.map((step) => ({
2222
+ apiName: step.apiName,
2223
+ customType: step.customType,
2224
+ name: step.name,
2225
+ order: step.order,
2226
+ type: step.type,
2227
+ ...(step.config === undefined ? {} : { config: step.config }),
2228
+ })),
2229
+ type: args.type,
2230
+ version: args.version,
2231
+ volumeOptions: args.volumeOptions,
2232
+ })));
2233
+ server.registerTool('agentia_template_delete', {
2234
+ description: 'Delete a Copado Job Template by API name via the CICD gateway.',
2235
+ inputSchema: { apiName: z.string().describe('Template API name.') },
2236
+ title: 'Agentia Template Delete',
2237
+ }, (args) => safelyHandleTool(() => templateDelete(args)));
2120
2238
  server.registerTool('agentia_promotion_conflict_list', {
2121
2239
  description: 'List merge conflicts for a Copado promotion.',
2122
2240
  inputSchema: { promotionId: z.string().describe('Copado promotion ID.') },
@@ -1,10 +1,10 @@
1
1
  import { z } from 'zod';
2
2
  import { assertRequired } from '../assert.js';
3
3
  import { CicdGateway } from '../cicd-gateway.js';
4
- import { attachCapturedOutputLogs, MCP_STDIO_CAPTURE_OPTIONS, withCapturedCommandOutput, } from '../command-output-buffer.js';
4
+ import { MCP_STDIO_CAPTURE_OPTIONS, withCapturedCommandOutput, } from '../command-output-buffer.js';
5
5
  import { reconcileWorkSetCredential, sanitizeWorkSetUserStory } from '../credential-sync.js';
6
6
  import { readDefaults, resolveDefaults, writeLastWorkSelection, } from '../defaults-store.js';
7
- import { checkoutFeatureBranch, fetchOriginBranch, fetchOriginBranchIfExists, listPendingChanges, } from '../git-worktree.js';
7
+ import { checkoutFeatureBranch, fetchOriginBranch, fetchOriginBranchIfExists, getHeadCommitId, listPendingChanges, } from '../git-worktree.js';
8
8
  import { listPaginationZodFields, mcpPaginatedListPayload } from '../list-pagination.js';
9
9
  import { LocalQualityGatesError, parseQualityGatesEnvAssignments, runLocalQualityGates, } from '../local-quality-gates.js';
10
10
  import { FULL_METADATA_SELECTION_TYPES_HELP } from '../nested-metadata-registry.js';
@@ -21,7 +21,7 @@ import { validateWorkMutationPayload, WORK_LONG_TEXT_MAX_LENGTH, WORK_SHORT_TEXT
21
21
  import { fetchWorkItem, fetchWorkItems } from '../work-get.js';
22
22
  import { performWorkLocalCommit } from '../work-local-commit.js';
23
23
  import { reportLocalQualityGatesFailure, reportLocalQualityGatesOutcome, } from '../work-local-run-tests.js';
24
- import { capturingWorkPushHooks, performWorkPush, resolveActiveFeatureWorkItem, resolveWorkPushContext, resolveWorkPushNeed, } from '../work-push.js';
24
+ import { capturingWorkPushHooks, performWorkPush, resolveActiveFeatureWorkItem, resolveWorkPushContext, resolveWorkPushNeed, uploadCapturedPublishLogsBestEffort, } from '../work-push.js';
25
25
  import { performWorkSetNone } from '../work-set-none.js';
26
26
  import { isWorkSetWarning, parseWorkSetSelection, toWorkSetWarningResult, writeWorkSetWarningSelection, } from '../work-set-selection.js';
27
27
  import { reportSubmitUserStoriesAheadBehind } from '../work-submit-ahead-behind.js';
@@ -276,6 +276,7 @@ async function promoteWorkItemDone(args = {}) {
276
276
  pushResult = await performWorkPush({
277
277
  ...pushContext,
278
278
  hooks: capturingWorkPushHooks,
279
+ skipLogUpload: true,
279
280
  skipNestedMetadataDetection: args.skipNestedMetadataDetection,
280
281
  });
281
282
  }
@@ -293,6 +294,12 @@ async function promoteWorkItemDone(args = {}) {
293
294
  },
294
295
  method: 'POST',
295
296
  }));
297
+ const tipCommitId = pushResult?.commits.at(-1)?.id ?? (await getHeadCommitId());
298
+ await uploadCapturedPublishLogsBestEffort({
299
+ commitId: tipCommitId,
300
+ hooks: capturingWorkPushHooks,
301
+ linkedEntityId: await resolveWorkItemId(),
302
+ });
296
303
  return {
297
304
  branch,
298
305
  done,
@@ -343,6 +350,7 @@ async function workSubmit(args = {}) {
343
350
  pushResult = await performWorkPush({
344
351
  ...pushContext,
345
352
  hooks: capturingWorkPushHooks,
353
+ skipLogUpload: true,
346
354
  skipNestedMetadataDetection: args.skipNestedMetadataDetection,
347
355
  });
348
356
  }
@@ -352,13 +360,19 @@ async function workSubmit(args = {}) {
352
360
  workItem,
353
361
  });
354
362
  const submit = await capturingWorkPushHooks.withSpinner('Submitting work item', () => CicdGateway.call({
355
- body: attachCapturedOutputLogs({ workItem }),
363
+ body: { workItem },
356
364
  endpoint: workSubmitEndpoint(),
357
365
  headers: {
358
366
  'Content-Type': 'application/json',
359
367
  },
360
368
  method: 'POST',
361
369
  }));
370
+ const tipCommitId = pushResult?.commits.at(-1)?.id ?? (await getHeadCommitId());
371
+ await uploadCapturedPublishLogsBestEffort({
372
+ commitId: tipCommitId,
373
+ hooks: capturingWorkPushHooks,
374
+ linkedEntityId: await resolveWorkItemId(),
375
+ });
362
376
  return {
363
377
  branch,
364
378
  push: pushResult,