@posthog/agent 1.0.2 → 1.2.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/CLAUDE.md +68 -35
- package/README.md +46 -14
- package/dist/index.js +4 -5
- package/dist/index.js.map +1 -1
- package/dist/src/agent-registry.js +4 -2
- package/dist/src/agent-registry.js.map +1 -1
- package/dist/src/agent.d.ts +4 -1
- package/dist/src/agent.d.ts.map +1 -1
- package/dist/src/agent.js +45 -14
- package/dist/src/agent.js.map +1 -1
- package/dist/src/agents/execution.js +4 -2
- package/dist/src/agents/execution.js.map +1 -1
- package/dist/src/agents/planning.js +4 -2
- package/dist/src/agents/planning.js.map +1 -1
- package/dist/src/event-transformer.d.ts +2 -0
- package/dist/src/event-transformer.d.ts.map +1 -1
- package/dist/src/event-transformer.js +57 -7
- package/dist/src/event-transformer.js.map +1 -1
- package/dist/src/file-manager.js +17 -14
- package/dist/src/file-manager.js.map +1 -1
- package/dist/src/git-manager.js +5 -2
- package/dist/src/git-manager.js.map +1 -1
- package/dist/src/posthog-api.d.ts +34 -0
- package/dist/src/posthog-api.d.ts.map +1 -1
- package/dist/src/posthog-api.js +42 -2
- package/dist/src/posthog-api.js.map +1 -1
- package/dist/src/prompt-builder.js +5 -2
- package/dist/src/prompt-builder.js.map +1 -1
- package/dist/src/stage-executor.d.ts +4 -2
- package/dist/src/stage-executor.d.ts.map +1 -1
- package/dist/src/stage-executor.js +22 -9
- package/dist/src/stage-executor.js.map +1 -1
- package/dist/src/task-manager.js +5 -2
- package/dist/src/task-manager.js.map +1 -1
- package/dist/src/task-progress-reporter.d.ts +44 -0
- package/dist/src/task-progress-reporter.d.ts.map +1 -0
- package/dist/src/task-progress-reporter.js +234 -0
- package/dist/src/task-progress-reporter.js.map +1 -0
- package/dist/src/template-manager.d.ts.map +1 -1
- package/dist/src/template-manager.js +16 -6
- package/dist/src/template-manager.js.map +1 -1
- package/dist/src/types.js +4 -2
- package/dist/src/types.js.map +1 -1
- package/dist/src/utils/logger.js +5 -3
- package/dist/src/utils/logger.js.map +1 -1
- package/dist/src/utils/mcp.js +4 -2
- package/dist/src/utils/mcp.js.map +1 -1
- package/dist/src/workflow-registry.js +4 -3
- package/dist/src/workflow-registry.js.map +1 -1
- package/dist/templates/plan-template.md +45 -0
- package/package.json +8 -2
- package/src/agent.ts +41 -8
- package/src/event-transformer.ts +61 -7
- package/src/posthog-api.ts +79 -0
- package/src/stage-executor.ts +24 -8
- package/src/task-progress-reporter.ts +287 -0
- package/src/template-manager.ts +11 -3
- package/dist/example.js +0 -49
- package/dist/example.js.map +0 -1
- package/dist/src/workflow-types.js +0 -2
- package/dist/src/workflow-types.js.map +0 -1
package/dist/src/posthog-api.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
|
|
1
|
+
class PostHogAPIClient {
|
|
2
2
|
config;
|
|
3
3
|
_teamId = null;
|
|
4
4
|
constructor(config) {
|
|
@@ -81,10 +81,48 @@ export class PostHogAPIClient {
|
|
|
81
81
|
body: JSON.stringify({ current_stage: stageId }),
|
|
82
82
|
});
|
|
83
83
|
}
|
|
84
|
+
async setTaskBranch(taskId, branch) {
|
|
85
|
+
const teamId = await this.getTeamId();
|
|
86
|
+
return this.apiRequest(`/api/projects/${teamId}/tasks/${taskId}/set_branch/`, {
|
|
87
|
+
method: "POST",
|
|
88
|
+
body: JSON.stringify({ branch }),
|
|
89
|
+
});
|
|
90
|
+
}
|
|
91
|
+
async attachTaskPullRequest(taskId, prUrl, branch) {
|
|
92
|
+
const teamId = await this.getTeamId();
|
|
93
|
+
const payload = { pr_url: prUrl };
|
|
94
|
+
if (branch) {
|
|
95
|
+
payload.branch = branch;
|
|
96
|
+
}
|
|
97
|
+
return this.apiRequest(`/api/projects/${teamId}/tasks/${taskId}/attach_pr/`, {
|
|
98
|
+
method: "POST",
|
|
99
|
+
body: JSON.stringify(payload),
|
|
100
|
+
});
|
|
101
|
+
}
|
|
84
102
|
async getTaskProgress(taskId) {
|
|
85
103
|
const teamId = await this.getTeamId();
|
|
86
104
|
return this.apiRequest(`/api/projects/${teamId}/tasks/${taskId}/progress/`);
|
|
87
105
|
}
|
|
106
|
+
async createTaskProgress(taskId, payload) {
|
|
107
|
+
const teamId = await this.getTeamId();
|
|
108
|
+
return this.apiRequest(`/api/projects/${teamId}/task_progress/`, {
|
|
109
|
+
method: "POST",
|
|
110
|
+
body: JSON.stringify({
|
|
111
|
+
...payload,
|
|
112
|
+
task: taskId,
|
|
113
|
+
}),
|
|
114
|
+
});
|
|
115
|
+
}
|
|
116
|
+
async updateTaskProgress(taskId, progressId, payload) {
|
|
117
|
+
const teamId = await this.getTeamId();
|
|
118
|
+
return this.apiRequest(`/api/projects/${teamId}/task_progress/${progressId}/`, {
|
|
119
|
+
method: "PATCH",
|
|
120
|
+
body: JSON.stringify({
|
|
121
|
+
...payload,
|
|
122
|
+
task: taskId,
|
|
123
|
+
}),
|
|
124
|
+
});
|
|
125
|
+
}
|
|
88
126
|
// Workflow endpoints
|
|
89
127
|
async fetchWorkflow(workflowId) {
|
|
90
128
|
const teamId = await this.getTeamId();
|
|
@@ -107,4 +145,6 @@ export class PostHogAPIClient {
|
|
|
107
145
|
});
|
|
108
146
|
}
|
|
109
147
|
}
|
|
110
|
-
|
|
148
|
+
|
|
149
|
+
export { PostHogAPIClient };
|
|
150
|
+
//# sourceMappingURL=posthog-api.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"posthog-api.js","sourceRoot":"","sources":["../../src/posthog-api.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"posthog-api.js","sources":["../../src/posthog-api.ts"],"sourcesContent":["import type { Task, SupportingFile, PostHogAPIConfig } from './types.js';\nimport type { WorkflowDefinition, AgentDefinition } from './workflow-types.js';\n\ninterface PostHogApiResponse<T> {\n results?: T[];\n count?: number;\n next?: string | null;\n previous?: string | null;\n}\n\ninterface TaskProgressResponse {\n has_progress: boolean;\n id?: string;\n status?: \"started\" | \"in_progress\" | \"completed\" | \"failed\";\n current_step?: string;\n completed_steps?: number;\n total_steps?: number;\n progress_percentage?: number;\n output_log?: string;\n error_message?: string;\n created_at?: string;\n updated_at?: string;\n completed_at?: string;\n workflow_id?: string;\n workflow_run_id?: string;\n message?: string;\n}\n\nexport interface TaskProgressRecord {\n id: string;\n task: string;\n status: \"started\" | \"in_progress\" | \"completed\" | \"failed\";\n current_step?: string | null;\n completed_steps?: number | null;\n total_steps?: number | null;\n progress_percentage?: number | null;\n output_log?: string | null;\n error_message?: string | null;\n workflow_id?: string | null;\n workflow_run_id?: string | null;\n activity_id?: string | null;\n created_at: string;\n updated_at: string;\n completed_at?: string | null;\n}\n\nexport interface TaskProgressUpdate {\n status?: TaskProgressRecord[\"status\"];\n current_step?: string | null;\n completed_steps?: number | null;\n total_steps?: number | null;\n output_log?: string | null;\n error_message?: string | null;\n workflow_id?: string | null;\n workflow_run_id?: string | null;\n activity_id?: string | null;\n}\n\nexport class PostHogAPIClient {\n private config: PostHogAPIConfig;\n private _teamId: number | null = null;\n\n constructor(config: PostHogAPIConfig) {\n this.config = config;\n }\n\n private get baseUrl(): string {\n const host = this.config.apiUrl.endsWith(\"/\") \n ? this.config.apiUrl.slice(0, -1) \n : this.config.apiUrl;\n return host;\n }\n\n private get headers(): Record<string, string> {\n return {\n 'Authorization': `Bearer ${this.config.apiKey}`,\n 'Content-Type': 'application/json',\n };\n }\n\n private async apiRequest<T>(\n endpoint: string, \n options: RequestInit = {}\n ): Promise<T> {\n const url = `${this.baseUrl}${endpoint}`;\n \n const response = await fetch(url, {\n ...options,\n headers: {\n ...this.headers,\n ...options.headers,\n },\n });\n\n if (!response.ok) {\n let errorMessage: string;\n try {\n const errorResponse = await response.json();\n errorMessage = `Failed request: [${response.status}] ${JSON.stringify(errorResponse)}`;\n } catch {\n errorMessage = `Failed request: [${response.status}] ${response.statusText}`;\n }\n throw new Error(errorMessage);\n }\n\n return response.json();\n }\n\n private async getTeamId(): Promise<number> {\n if (this._teamId !== null) {\n return this._teamId;\n }\n\n // Fetch user info to get team ID (following Array's pattern)\n const userResponse = await this.apiRequest<any>('/api/users/@me/');\n \n if (!userResponse.team?.id) {\n throw new Error('No team found for user');\n }\n\n const teamId = Number(userResponse.team.id);\n this._teamId = teamId;\n return teamId;\n }\n\n async fetchTask(taskId: string): Promise<Task> {\n const teamId = await this.getTeamId();\n return this.apiRequest<Task>(`/api/projects/${teamId}/tasks/${taskId}/`);\n }\n\n async listTasks(filters?: {\n repository?: string;\n organization?: string;\n origin_product?: string;\n workflow?: string;\n current_stage?: string;\n }): Promise<Task[]> {\n const teamId = await this.getTeamId();\n const url = new URL(`${this.baseUrl}/api/projects/${teamId}/tasks/`);\n \n if (filters) {\n Object.entries(filters).forEach(([key, value]) => {\n if (value) url.searchParams.append(key, value);\n });\n }\n\n const response = await this.apiRequest<PostHogApiResponse<Task>>(\n url.pathname + url.search\n );\n \n return response.results || [];\n }\n\n async updateTask(taskId: string, updates: Partial<Task>): Promise<Task> {\n const teamId = await this.getTeamId();\n return this.apiRequest<Task>(`/api/projects/${teamId}/tasks/${taskId}/`, {\n method: 'PATCH',\n body: JSON.stringify(updates),\n });\n }\n\n async updateTaskStage(taskId: string, stageId: string): Promise<Task> {\n const teamId = await this.getTeamId();\n return this.apiRequest<Task>(`/api/projects/${teamId}/tasks/${taskId}/update_stage/`, {\n method: 'PATCH',\n body: JSON.stringify({ current_stage: stageId }),\n });\n }\n\n async setTaskBranch(taskId: string, branch: string): Promise<Task> {\n const teamId = await this.getTeamId();\n return this.apiRequest<Task>(`/api/projects/${teamId}/tasks/${taskId}/set_branch/`, {\n method: \"POST\",\n body: JSON.stringify({ branch }),\n });\n }\n\n async attachTaskPullRequest(taskId: string, prUrl: string, branch?: string): Promise<Task> {\n const teamId = await this.getTeamId();\n const payload: Record<string, string> = { pr_url: prUrl };\n if (branch) {\n payload.branch = branch;\n }\n return this.apiRequest<Task>(`/api/projects/${teamId}/tasks/${taskId}/attach_pr/`, {\n method: \"POST\",\n body: JSON.stringify(payload),\n });\n }\n\n async getTaskProgress(taskId: string): Promise<TaskProgressResponse> {\n const teamId = await this.getTeamId();\n return this.apiRequest<TaskProgressResponse>(`/api/projects/${teamId}/tasks/${taskId}/progress/`);\n }\n\n async createTaskProgress(\n taskId: string,\n payload: TaskProgressUpdate & { status: TaskProgressRecord[\"status\"] }\n ): Promise<TaskProgressRecord> {\n const teamId = await this.getTeamId();\n return this.apiRequest<TaskProgressRecord>(`/api/projects/${teamId}/task_progress/`, {\n method: \"POST\",\n body: JSON.stringify({\n ...payload,\n task: taskId,\n }),\n });\n }\n\n async updateTaskProgress(\n taskId: string,\n progressId: string,\n payload: TaskProgressUpdate\n ): Promise<TaskProgressRecord> {\n const teamId = await this.getTeamId();\n return this.apiRequest<TaskProgressRecord>(`/api/projects/${teamId}/task_progress/${progressId}/`, {\n method: \"PATCH\",\n body: JSON.stringify({\n ...payload,\n task: taskId,\n }),\n });\n }\n\n // Workflow endpoints\n async fetchWorkflow(workflowId: string): Promise<WorkflowDefinition> {\n const teamId = await this.getTeamId();\n return this.apiRequest<WorkflowDefinition>(`/api/projects/${teamId}/task_workflows/${workflowId}/`);\n }\n\n async listWorkflows(): Promise<WorkflowDefinition[]> {\n const teamId = await this.getTeamId();\n const response = await this.apiRequest<PostHogApiResponse<WorkflowDefinition>>(`/api/projects/${teamId}/task_workflows/`);\n return response.results || [];\n }\n\n // Agent catalog exposure\n async listAgents(): Promise<AgentDefinition[]> {\n return this.apiRequest<AgentDefinition[]>(`/api/agents/`);\n }\n\n async progressTask(taskId: string, options?: { next_stage_id?: string; auto?: boolean }): Promise<Task> {\n const teamId = await this.getTeamId();\n return this.apiRequest<Task>(`/api/projects/${teamId}/tasks/${taskId}/progress_task/`, {\n method: 'POST',\n body: JSON.stringify(options || {}),\n });\n }\n}\n"],"names":[],"mappings":"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"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { Logger } from './utils/logger.js';
|
|
2
|
-
|
|
2
|
+
|
|
3
|
+
class PromptBuilder {
|
|
3
4
|
getTaskFiles;
|
|
4
5
|
generatePlanTemplate;
|
|
5
6
|
logger;
|
|
@@ -72,4 +73,6 @@ export class PromptBuilder {
|
|
|
72
73
|
return prompt;
|
|
73
74
|
}
|
|
74
75
|
}
|
|
75
|
-
|
|
76
|
+
|
|
77
|
+
export { PromptBuilder };
|
|
78
|
+
//# sourceMappingURL=prompt-builder.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"prompt-builder.js","
|
|
1
|
+
{"version":3,"file":"prompt-builder.js","sources":["../../src/prompt-builder.ts"],"sourcesContent":["import type { Task } from './types.js';\nimport type { TemplateVariables } from './template-manager.js';\nimport { Logger } from './utils/logger.js';\n\nexport interface PromptBuilderDeps {\n getTaskFiles: (taskId: string) => Promise<any[]>;\n generatePlanTemplate: (vars: TemplateVariables) => Promise<string>;\n logger?: Logger;\n}\n\nexport class PromptBuilder {\n private getTaskFiles: PromptBuilderDeps['getTaskFiles'];\n private generatePlanTemplate: PromptBuilderDeps['generatePlanTemplate'];\n private logger: Logger;\n\n constructor(deps: PromptBuilderDeps) {\n this.getTaskFiles = deps.getTaskFiles;\n this.generatePlanTemplate = deps.generatePlanTemplate;\n this.logger = deps.logger || new Logger({ debug: false, prefix: '[PromptBuilder]' });\n }\n\n async buildPlanningPrompt(task: Task): Promise<string> {\n let prompt = '';\n prompt += `## Current Task\\n\\n**Task**: ${task.title}\\n**Description**: ${task.description}`;\n\n if ((task as any).primary_repository) {\n prompt += `\\n**Repository**: ${(task as any).primary_repository}`;\n }\n\n try {\n const taskFiles = await this.getTaskFiles(task.id);\n const contextFiles = taskFiles.filter((f: any) => f.type === 'context' || f.type === 'reference');\n if (contextFiles.length > 0) {\n prompt += `\\n\\n## Supporting Files`;\n for (const file of contextFiles) {\n prompt += `\\n\\n### ${file.name} (${file.type})\\n${file.content}`;\n }\n }\n } catch (error) {\n this.logger.debug('No existing task files found for planning', { taskId: task.id });\n }\n\n const templateVariables = {\n task_id: task.id,\n task_title: task.title,\n task_description: task.description,\n date: new Date().toISOString().split('T')[0],\n repository: ((task as any).primary_repository || '') as string,\n };\n\n const planTemplate = await this.generatePlanTemplate(templateVariables);\n\n prompt += `\\n\\nPlease analyze the codebase and create a detailed implementation plan for this task. Use the following template structure for your plan:\\n\\n${planTemplate}\\n\\nFill in each section with specific, actionable information based on your analysis. Replace all placeholder content with actual details about this task.`;\n\n return prompt;\n }\n\n async buildExecutionPrompt(task: Task): Promise<string> {\n let prompt = '';\n prompt += `## Current Task\\n\\n**Task**: ${task.title}\\n**Description**: ${task.description}`;\n\n if ((task as any).primary_repository) {\n prompt += `\\n**Repository**: ${(task as any).primary_repository}`;\n }\n\n try {\n const taskFiles = await this.getTaskFiles(task.id);\n const hasPlan = taskFiles.some((f: any) => f.type === 'plan');\n if (taskFiles.length > 0) {\n prompt += `\\n\\n## Context and Supporting Information`;\n for (const file of taskFiles) {\n if (file.type === 'plan') {\n prompt += `\\n\\n### Execution Plan\\n${file.content}`;\n } else {\n prompt += `\\n\\n### ${file.name} (${file.type})\\n${file.content}`;\n }\n }\n }\n if (hasPlan) {\n prompt += `\\n\\nPlease implement the changes described in the execution plan above. Follow the plan step-by-step and make the necessary file modifications. You must actually edit files and make changes - do not just analyze or review.`;\n } else {\n prompt += `\\n\\nPlease implement the changes described in the task above. You must actually edit files and make changes - do not just analyze or review.`;\n }\n } catch (error) {\n this.logger.debug('No supporting files found for execution', { taskId: task.id });\n prompt += `\\n\\nPlease implement the changes described in the task above.`;\n }\n return prompt;\n }\n}\n\n\n"],"names":[],"mappings":"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"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Logger } from './utils/logger.js';
|
|
2
2
|
import { AgentRegistry } from './agent-registry.js';
|
|
3
|
-
import type { Task } from './types.js';
|
|
3
|
+
import type { AgentEvent, Task } from './types.js';
|
|
4
4
|
import type { WorkflowStage, WorkflowStageExecutionResult, WorkflowExecutionOptions } from './workflow-types.js';
|
|
5
5
|
import { PromptBuilder } from './prompt-builder.js';
|
|
6
6
|
export declare class StageExecutor {
|
|
@@ -8,7 +8,9 @@ export declare class StageExecutor {
|
|
|
8
8
|
private logger;
|
|
9
9
|
private eventTransformer;
|
|
10
10
|
private promptBuilder;
|
|
11
|
-
|
|
11
|
+
private eventHandler?;
|
|
12
|
+
constructor(registry: AgentRegistry, logger: Logger, promptBuilder?: PromptBuilder, eventHandler?: (event: AgentEvent) => void);
|
|
13
|
+
setEventHandler(handler?: (event: AgentEvent) => void): void;
|
|
12
14
|
execute(task: Task, stage: WorkflowStage, options: WorkflowExecutionOptions): Promise<WorkflowStageExecutionResult>;
|
|
13
15
|
private runPlanning;
|
|
14
16
|
private runExecution;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"stage-executor.d.ts","sourceRoot":"","sources":["../../src/stage-executor.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,MAAM,EAAE,MAAM,mBAAmB,CAAC;AAE3C,OAAO,EAAE,aAAa,EAAE,MAAM,qBAAqB,CAAC;AACpD,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"stage-executor.d.ts","sourceRoot":"","sources":["../../src/stage-executor.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,MAAM,EAAE,MAAM,mBAAmB,CAAC;AAE3C,OAAO,EAAE,aAAa,EAAE,MAAM,qBAAqB,CAAC;AACpD,OAAO,KAAK,EAAE,UAAU,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AACnD,OAAO,KAAK,EAAE,aAAa,EAAE,4BAA4B,EAAE,wBAAwB,EAAE,MAAM,qBAAqB,CAAC;AAGjH,OAAO,EAAE,aAAa,EAAE,MAAM,qBAAqB,CAAC;AAGpD,qBAAa,aAAa;IACxB,OAAO,CAAC,QAAQ,CAAgB;IAChC,OAAO,CAAC,MAAM,CAAS;IACvB,OAAO,CAAC,gBAAgB,CAAmB;IAC3C,OAAO,CAAC,aAAa,CAAgB;IACrC,OAAO,CAAC,YAAY,CAAC,CAA8B;gBAGjD,QAAQ,EAAE,aAAa,EACvB,MAAM,EAAE,MAAM,EACd,aAAa,CAAC,EAAE,aAAa,EAC7B,YAAY,CAAC,EAAE,CAAC,KAAK,EAAE,UAAU,KAAK,IAAI;IAa5C,eAAe,CAAC,OAAO,CAAC,EAAE,CAAC,KAAK,EAAE,UAAU,KAAK,IAAI,GAAG,IAAI;IAItD,OAAO,CAAC,IAAI,EAAE,IAAI,EAAE,KAAK,EAAE,aAAa,EAAE,OAAO,EAAE,wBAAwB,GAAG,OAAO,CAAC,4BAA4B,CAAC;YA+B3G,WAAW;YA4CX,YAAY;CAqC3B"}
|
|
@@ -1,17 +1,18 @@
|
|
|
1
1
|
import { query } from '@anthropic-ai/claude-agent-sdk';
|
|
2
|
-
import
|
|
2
|
+
import './utils/logger.js';
|
|
3
3
|
import { EventTransformer } from './event-transformer.js';
|
|
4
|
-
import { AgentRegistry } from './agent-registry.js';
|
|
5
4
|
import { PLANNING_SYSTEM_PROMPT } from './agents/planning.js';
|
|
6
5
|
import { EXECUTION_SYSTEM_PROMPT } from './agents/execution.js';
|
|
7
6
|
import { PromptBuilder } from './prompt-builder.js';
|
|
8
7
|
import { POSTHOG_MCP } from './utils/mcp.js';
|
|
9
|
-
|
|
8
|
+
|
|
9
|
+
class StageExecutor {
|
|
10
10
|
registry;
|
|
11
11
|
logger;
|
|
12
12
|
eventTransformer;
|
|
13
13
|
promptBuilder;
|
|
14
|
-
|
|
14
|
+
eventHandler;
|
|
15
|
+
constructor(registry, logger, promptBuilder, eventHandler) {
|
|
15
16
|
this.registry = registry;
|
|
16
17
|
this.logger = logger.child('StageExecutor');
|
|
17
18
|
this.eventTransformer = new EventTransformer();
|
|
@@ -20,6 +21,10 @@ export class StageExecutor {
|
|
|
20
21
|
generatePlanTemplate: async () => '',
|
|
21
22
|
logger,
|
|
22
23
|
});
|
|
24
|
+
this.eventHandler = eventHandler;
|
|
25
|
+
}
|
|
26
|
+
setEventHandler(handler) {
|
|
27
|
+
this.eventHandler = handler;
|
|
23
28
|
}
|
|
24
29
|
async execute(task, stage, options) {
|
|
25
30
|
const isManual = stage.is_manual_only === true;
|
|
@@ -72,8 +77,11 @@ export class StageExecutor {
|
|
|
72
77
|
let plan = '';
|
|
73
78
|
for await (const message of response) {
|
|
74
79
|
const transformed = this.eventTransformer.transform(message);
|
|
75
|
-
if (transformed
|
|
76
|
-
|
|
80
|
+
if (transformed) {
|
|
81
|
+
if (transformed.type !== 'token') {
|
|
82
|
+
this.logger.debug('Planning event', { type: transformed.type });
|
|
83
|
+
}
|
|
84
|
+
this.eventHandler?.(transformed);
|
|
77
85
|
}
|
|
78
86
|
if (message.type === 'assistant' && message.message?.content) {
|
|
79
87
|
for (const c of message.message.content) {
|
|
@@ -108,12 +116,17 @@ export class StageExecutor {
|
|
|
108
116
|
const results = [];
|
|
109
117
|
for await (const message of response) {
|
|
110
118
|
const transformed = this.eventTransformer.transform(message);
|
|
111
|
-
if (transformed
|
|
112
|
-
|
|
119
|
+
if (transformed) {
|
|
120
|
+
if (transformed.type !== 'token') {
|
|
121
|
+
this.logger.debug('Execution event', { type: transformed.type });
|
|
122
|
+
}
|
|
123
|
+
this.eventHandler?.(transformed);
|
|
113
124
|
}
|
|
114
125
|
results.push(message);
|
|
115
126
|
}
|
|
116
127
|
return { results };
|
|
117
128
|
}
|
|
118
129
|
}
|
|
119
|
-
|
|
130
|
+
|
|
131
|
+
export { StageExecutor };
|
|
132
|
+
//# sourceMappingURL=stage-executor.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"stage-executor.js","
|
|
1
|
+
{"version":3,"file":"stage-executor.js","sources":["../../src/stage-executor.ts"],"sourcesContent":["import { query } from '@anthropic-ai/claude-agent-sdk';\nimport { Logger } from './utils/logger.js';\nimport { EventTransformer } from './event-transformer.js';\nimport { AgentRegistry } from './agent-registry.js';\nimport type { AgentEvent, Task } from './types.js';\nimport type { WorkflowStage, WorkflowStageExecutionResult, WorkflowExecutionOptions } from './workflow-types.js';\nimport { PLANNING_SYSTEM_PROMPT } from './agents/planning.js';\nimport { EXECUTION_SYSTEM_PROMPT } from './agents/execution.js';\nimport { PromptBuilder } from './prompt-builder.js';\nimport { POSTHOG_MCP } from './utils/mcp.js';\n\nexport class StageExecutor {\n private registry: AgentRegistry;\n private logger: Logger;\n private eventTransformer: EventTransformer;\n private promptBuilder: PromptBuilder;\n private eventHandler?: (event: AgentEvent) => void;\n\n constructor(\n registry: AgentRegistry,\n logger: Logger,\n promptBuilder?: PromptBuilder,\n eventHandler?: (event: AgentEvent) => void,\n ) {\n this.registry = registry;\n this.logger = logger.child('StageExecutor');\n this.eventTransformer = new EventTransformer();\n this.promptBuilder = promptBuilder || new PromptBuilder({\n getTaskFiles: async () => [],\n generatePlanTemplate: async () => '',\n logger,\n });\n this.eventHandler = eventHandler;\n }\n\n setEventHandler(handler?: (event: AgentEvent) => void): void {\n this.eventHandler = handler;\n }\n\n async execute(task: Task, stage: WorkflowStage, options: WorkflowExecutionOptions): Promise<WorkflowStageExecutionResult> {\n const isManual = stage.is_manual_only === true;\n if (isManual) {\n this.logger.info('Manual stage detected; skipping agent execution', { stage: stage.key });\n return { results: [] };\n }\n\n const inferredAgent = stage.key.toLowerCase().includes('plan') ? 'planning_basic' : 'code_generation';\n const agentName = stage.agent_name || inferredAgent;\n const agent = this.registry.getAgent(agentName);\n if (!agent) {\n throw new Error(`Unknown agent '${agentName}' for stage '${stage.key}'`);\n }\n\n const permissionMode = (options.permissionMode as any) || 'acceptEdits';\n const cwd = options.repositoryPath || process.cwd();\n\n switch (agent.agent_type) {\n case 'planning':\n return this.runPlanning(task, cwd, options, stage.key);\n case 'execution':\n return this.runExecution(task, cwd, permissionMode, options, stage.key);\n case 'review': // TODO: Implement review\n case 'testing': // TODO: Implement testing\n default:\n // throw new Error(`Unsupported agent type: ${agent.agent_type}`);\n console.warn(`Unsupported agent type: ${agent.agent_type}`);\n return { results: [] };\n }\n }\n\n private async runPlanning(task: Task, cwd: string, options: WorkflowExecutionOptions, stageKey: string): Promise<WorkflowStageExecutionResult> {\n const contextPrompt = await this.promptBuilder.buildPlanningPrompt(task);\n let prompt = PLANNING_SYSTEM_PROMPT + '\\n\\n' + contextPrompt;\n\n const stageOverrides = options.stageOverrides?.[stageKey] || options.stageOverrides?.['plan'];\n const mergedOverrides = {\n ...(options.queryOverrides || {}),\n ...(stageOverrides?.queryOverrides || {}),\n } as Record<string, any>;\n\n const baseOptions: Record<string, any> = {\n model: 'claude-sonnet-4-5-20250929',\n cwd,\n permissionMode: 'plan',\n settingSources: ['local'],\n mcpServers: {\n ...POSTHOG_MCP\n }\n };\n\n const response = query({\n prompt,\n options: { ...baseOptions, ...mergedOverrides },\n });\n\n let plan = '';\n for await (const message of response) {\n const transformed = this.eventTransformer.transform(message);\n if (transformed) {\n if (transformed.type !== 'token') {\n this.logger.debug('Planning event', { type: transformed.type });\n }\n this.eventHandler?.(transformed);\n }\n if (message.type === 'assistant' && message.message?.content) {\n for (const c of message.message.content) {\n if (c.type === 'text' && c.text) plan += c.text + '\\n';\n }\n }\n }\n\n return { plan: plan.trim() };\n }\n\n private async runExecution(task: Task, cwd: string, permissionMode: WorkflowExecutionOptions['permissionMode'], options: WorkflowExecutionOptions, stageKey: string): Promise<WorkflowStageExecutionResult> {\n const contextPrompt = await this.promptBuilder.buildExecutionPrompt(task);\n let prompt = EXECUTION_SYSTEM_PROMPT + '\\n\\n' + contextPrompt;\n\n const stageOverrides = options.stageOverrides?.[stageKey];\n const mergedOverrides = {\n ...(options.queryOverrides || {}),\n ...(stageOverrides?.queryOverrides || {}),\n } as Record<string, any>;\n\n const baseOptions: Record<string, any> = {\n model: 'claude-sonnet-4-5-20250929',\n cwd,\n permissionMode,\n settingSources: ['local'],\n mcpServers: {\n ...POSTHOG_MCP\n }\n };\n\n const response = query({\n prompt,\n options: { ...baseOptions, ...mergedOverrides },\n });\n const results: any[] = [];\n for await (const message of response) {\n const transformed = this.eventTransformer.transform(message);\n if (transformed) {\n if (transformed.type !== 'token') {\n this.logger.debug('Execution event', { type: transformed.type });\n }\n this.eventHandler?.(transformed);\n }\n results.push(message);\n }\n return { results };\n }\n}\n"],"names":[],"mappings":"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"}
|
package/dist/src/task-manager.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { randomBytes } from 'crypto';
|
|
2
|
-
|
|
2
|
+
|
|
3
|
+
class TaskManager {
|
|
3
4
|
executionStates = new Map();
|
|
4
5
|
defaultTimeout = 10 * 60 * 1000; // 10 minutes
|
|
5
6
|
generateExecutionId() {
|
|
@@ -116,4 +117,6 @@ export class TaskManager {
|
|
|
116
117
|
}
|
|
117
118
|
}
|
|
118
119
|
}
|
|
119
|
-
|
|
120
|
+
|
|
121
|
+
export { TaskManager };
|
|
122
|
+
//# sourceMappingURL=task-manager.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"task-manager.js","
|
|
1
|
+
{"version":3,"file":"task-manager.js","sources":["../../src/task-manager.ts"],"sourcesContent":["import { randomBytes } from 'crypto';\n\nexport interface TaskExecutionState {\n taskId: string;\n status: 'running' | 'completed' | 'failed' | 'canceled' | 'timeout';\n mode: 'plan_only' | 'plan_and_build' | 'build_only';\n result?: any;\n startedAt: number;\n completedAt?: number;\n abortController?: AbortController;\n}\n\nexport class TaskManager {\n private executionStates = new Map<string, TaskExecutionState>();\n private defaultTimeout = 10 * 60 * 1000; // 10 minutes\n\n generateExecutionId(): string {\n return randomBytes(16).toString('hex');\n }\n\n startExecution(\n taskId: string, \n mode: 'plan_only' | 'plan_and_build' | 'build_only',\n executionId: string = this.generateExecutionId()\n ): TaskExecutionState {\n const executionState: TaskExecutionState = {\n taskId,\n status: 'running',\n mode,\n startedAt: Date.now(),\n abortController: new AbortController(),\n };\n\n this.executionStates.set(executionId, executionState);\n this.scheduleTimeout(executionId);\n \n return executionState;\n }\n\n async waitForCompletion(executionId: string): Promise<any> {\n const execution = this.executionStates.get(executionId);\n if (!execution) {\n throw new Error(`Execution ${executionId} not found`);\n }\n\n if (execution.result && execution.status === 'completed') {\n return execution.result;\n }\n\n return new Promise((resolve, reject) => {\n const checkInterval = setInterval(() => {\n const currentExecution = this.executionStates.get(executionId);\n if (!currentExecution) {\n clearInterval(checkInterval);\n reject(new Error(`Execution ${executionId} disappeared`));\n return;\n }\n\n if (currentExecution.status === 'completed' && currentExecution.result) {\n clearInterval(checkInterval);\n resolve(currentExecution.result);\n } else if (\n currentExecution.status === 'failed' || \n currentExecution.status === 'canceled' || \n currentExecution.status === 'timeout'\n ) {\n clearInterval(checkInterval);\n reject(new Error(`Execution ${executionId} ${currentExecution.status}`));\n }\n }, 100);\n });\n }\n\n completeExecution(executionId: string, result: any): void {\n const execution = this.executionStates.get(executionId);\n if (!execution) {\n throw new Error(`Execution ${executionId} not found`);\n }\n\n execution.status = 'completed';\n execution.result = result;\n execution.completedAt = Date.now();\n }\n\n failExecution(executionId: string, error: Error): void {\n const execution = this.executionStates.get(executionId);\n if (!execution) {\n throw new Error(`Execution ${executionId} not found`);\n }\n\n execution.status = 'failed';\n execution.completedAt = Date.now();\n execution.result = {\n error: error.message,\n status: 'failed',\n };\n }\n\n cancelExecution(executionId: string): void {\n const execution = this.executionStates.get(executionId);\n if (!execution) {\n throw new Error(`Execution ${executionId} not found`);\n }\n\n execution.status = 'canceled';\n execution.completedAt = Date.now();\n execution.abortController?.abort();\n \n if (!execution.result) {\n execution.result = {\n status: 'canceled',\n message: 'Execution was canceled',\n };\n }\n }\n\n getExecution(executionId: string): TaskExecutionState | undefined {\n return this.executionStates.get(executionId);\n }\n\n getAbortSignal(executionId: string): AbortSignal | undefined {\n return this.executionStates.get(executionId)?.abortController?.signal;\n }\n\n getAbortController(executionId: string): AbortController | undefined {\n return this.executionStates.get(executionId)?.abortController;\n }\n\n private scheduleTimeout(executionId: string, timeout: number = this.defaultTimeout): void {\n setTimeout(() => {\n const execution = this.executionStates.get(executionId);\n if (execution && execution.status === 'running') {\n execution.status = 'timeout';\n execution.completedAt = Date.now();\n execution.abortController?.abort();\n \n if (!execution.result) {\n execution.result = {\n status: 'timeout',\n message: 'Execution timed out',\n };\n }\n }\n }, timeout);\n }\n\n cleanup(olderThan: number = 60 * 60 * 1000): void {\n const cutoff = Date.now() - olderThan;\n for (const [executionId, execution] of this.executionStates) {\n if (execution.completedAt && execution.completedAt < cutoff) {\n this.executionStates.delete(executionId);\n }\n }\n }\n}"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import type { Logger } from './utils/logger.js';
|
|
2
|
+
import type { PostHogAPIClient } from './posthog-api.js';
|
|
3
|
+
import type { AgentEvent } from './types.js';
|
|
4
|
+
interface ProgressMetadata {
|
|
5
|
+
workflowId?: string;
|
|
6
|
+
workflowRunId?: string;
|
|
7
|
+
activityId?: string;
|
|
8
|
+
totalSteps?: number;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* Persists task execution progress to PostHog so clients can poll for updates.
|
|
12
|
+
*
|
|
13
|
+
* The reporter is intentionally best-effort – failures are logged but never
|
|
14
|
+
* allowed to break the agent execution flow.
|
|
15
|
+
*/
|
|
16
|
+
export declare class TaskProgressReporter {
|
|
17
|
+
private posthogAPI?;
|
|
18
|
+
private logger;
|
|
19
|
+
private progressRecord?;
|
|
20
|
+
private taskId?;
|
|
21
|
+
private outputLog;
|
|
22
|
+
private totalSteps?;
|
|
23
|
+
private lastLogEntry?;
|
|
24
|
+
constructor(posthogAPI: PostHogAPIClient | undefined, logger: Logger);
|
|
25
|
+
get progressId(): string | undefined;
|
|
26
|
+
start(taskId: string, metadata?: ProgressMetadata): Promise<void>;
|
|
27
|
+
stageStarted(stageKey: string, stageIndex: number): Promise<void>;
|
|
28
|
+
stageCompleted(stageKey: string, completedStages: number): Promise<void>;
|
|
29
|
+
branchCreated(stageKey: string, branchName: string): Promise<void>;
|
|
30
|
+
commitMade(stageKey: string, kind: 'plan' | 'implementation'): Promise<void>;
|
|
31
|
+
pullRequestCreated(stageKey: string, prUrl: string): Promise<void>;
|
|
32
|
+
noNextStage(stageKey?: string): Promise<void>;
|
|
33
|
+
complete(): Promise<void>;
|
|
34
|
+
fail(error: Error | string): Promise<void>;
|
|
35
|
+
appendLog(line: string): Promise<void>;
|
|
36
|
+
recordEvent(event: AgentEvent): Promise<void>;
|
|
37
|
+
private update;
|
|
38
|
+
private summarizeUserMessage;
|
|
39
|
+
private formatFileWriteEvent;
|
|
40
|
+
private formatDiffEvent;
|
|
41
|
+
private truncateMultiline;
|
|
42
|
+
}
|
|
43
|
+
export {};
|
|
44
|
+
//# sourceMappingURL=task-progress-reporter.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"task-progress-reporter.d.ts","sourceRoot":"","sources":["../../src/task-progress-reporter.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,KAAK,EAAE,gBAAgB,EAA0C,MAAM,kBAAkB,CAAC;AACjG,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AAE7C,UAAU,gBAAgB;IACxB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED;;;;;GAKG;AACH,qBAAa,oBAAoB;IAC/B,OAAO,CAAC,UAAU,CAAC,CAAmB;IACtC,OAAO,CAAC,MAAM,CAAS;IACvB,OAAO,CAAC,cAAc,CAAC,CAAqB;IAC5C,OAAO,CAAC,MAAM,CAAC,CAAS;IACxB,OAAO,CAAC,SAAS,CAAgB;IACjC,OAAO,CAAC,UAAU,CAAC,CAAS;IAC5B,OAAO,CAAC,YAAY,CAAC,CAAS;gBAElB,UAAU,EAAE,gBAAgB,GAAG,SAAS,EAAE,MAAM,EAAE,MAAM;IAKpE,IAAI,UAAU,IAAI,MAAM,GAAG,SAAS,CAEnC;IAEK,KAAK,CAAC,MAAM,EAAE,MAAM,EAAE,QAAQ,GAAE,gBAAqB,GAAG,OAAO,CAAC,IAAI,CAAC;IA2BrE,YAAY,CAAC,QAAQ,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAQjE,cAAc,CAAC,QAAQ,EAAE,MAAM,EAAE,eAAe,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAQxE,aAAa,CAAC,QAAQ,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAIlE,UAAU,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,gBAAgB,GAAG,OAAO,CAAC,IAAI,CAAC;IAI5E,kBAAkB,CAAC,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAIlE,WAAW,CAAC,QAAQ,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAQ7C,QAAQ,IAAI,OAAO,CAAC,IAAI,CAAC;IAIzB,IAAI,CAAC,KAAK,EAAE,KAAK,GAAG,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAK1C,SAAS,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAItC,WAAW,CAAC,KAAK,EAAE,UAAU,GAAG,OAAO,CAAC,IAAI,CAAC;YA8DrC,MAAM;IA6BpB,OAAO,CAAC,oBAAoB;IAiE5B,OAAO,CAAC,oBAAoB;IAK5B,OAAO,CAAC,eAAe;IAOvB,OAAO,CAAC,iBAAiB;CAO1B"}
|
|
@@ -0,0 +1,234 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Persists task execution progress to PostHog so clients can poll for updates.
|
|
3
|
+
*
|
|
4
|
+
* The reporter is intentionally best-effort – failures are logged but never
|
|
5
|
+
* allowed to break the agent execution flow.
|
|
6
|
+
*/
|
|
7
|
+
class TaskProgressReporter {
|
|
8
|
+
posthogAPI;
|
|
9
|
+
logger;
|
|
10
|
+
progressRecord;
|
|
11
|
+
taskId;
|
|
12
|
+
outputLog = [];
|
|
13
|
+
totalSteps;
|
|
14
|
+
lastLogEntry;
|
|
15
|
+
constructor(posthogAPI, logger) {
|
|
16
|
+
this.posthogAPI = posthogAPI;
|
|
17
|
+
this.logger = logger.child('TaskProgressReporter');
|
|
18
|
+
}
|
|
19
|
+
get progressId() {
|
|
20
|
+
return this.progressRecord?.id;
|
|
21
|
+
}
|
|
22
|
+
async start(taskId, metadata = {}) {
|
|
23
|
+
if (!this.posthogAPI) {
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
this.taskId = taskId;
|
|
27
|
+
this.totalSteps = metadata.totalSteps;
|
|
28
|
+
try {
|
|
29
|
+
const record = await this.posthogAPI.createTaskProgress(taskId, {
|
|
30
|
+
status: 'started',
|
|
31
|
+
current_step: 'initializing',
|
|
32
|
+
total_steps: metadata.totalSteps ?? 0,
|
|
33
|
+
completed_steps: 0,
|
|
34
|
+
workflow_id: metadata.workflowId,
|
|
35
|
+
workflow_run_id: metadata.workflowRunId,
|
|
36
|
+
activity_id: metadata.activityId,
|
|
37
|
+
output_log: '',
|
|
38
|
+
});
|
|
39
|
+
this.progressRecord = record;
|
|
40
|
+
this.outputLog = record.output_log ? record.output_log.split('\n') : [];
|
|
41
|
+
this.logger.debug('Created task progress record', { taskId, progressId: record.id });
|
|
42
|
+
}
|
|
43
|
+
catch (error) {
|
|
44
|
+
this.logger.warn('Failed to create task progress record', { taskId, error: error.message });
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
async stageStarted(stageKey, stageIndex) {
|
|
48
|
+
await this.update({
|
|
49
|
+
status: 'in_progress',
|
|
50
|
+
current_step: stageKey,
|
|
51
|
+
completed_steps: Math.min(stageIndex, this.totalSteps ?? stageIndex),
|
|
52
|
+
}, `Stage started: ${stageKey}`);
|
|
53
|
+
}
|
|
54
|
+
async stageCompleted(stageKey, completedStages) {
|
|
55
|
+
await this.update({
|
|
56
|
+
status: 'in_progress',
|
|
57
|
+
current_step: stageKey,
|
|
58
|
+
completed_steps: Math.min(completedStages, this.totalSteps ?? completedStages),
|
|
59
|
+
}, `Stage completed: ${stageKey}`);
|
|
60
|
+
}
|
|
61
|
+
async branchCreated(stageKey, branchName) {
|
|
62
|
+
await this.appendLog(`Branch created (${stageKey}): ${branchName}`);
|
|
63
|
+
}
|
|
64
|
+
async commitMade(stageKey, kind) {
|
|
65
|
+
await this.appendLog(`Commit made (${stageKey}, ${kind})`);
|
|
66
|
+
}
|
|
67
|
+
async pullRequestCreated(stageKey, prUrl) {
|
|
68
|
+
await this.appendLog(`Pull request created (${stageKey}): ${prUrl}`);
|
|
69
|
+
}
|
|
70
|
+
async noNextStage(stageKey) {
|
|
71
|
+
await this.appendLog(stageKey
|
|
72
|
+
? `No next stage available after '${stageKey}'. Execution halted.`
|
|
73
|
+
: 'No next stage available. Execution halted.');
|
|
74
|
+
}
|
|
75
|
+
async complete() {
|
|
76
|
+
await this.update({ status: 'completed', completed_steps: this.totalSteps }, 'Workflow execution completed');
|
|
77
|
+
}
|
|
78
|
+
async fail(error) {
|
|
79
|
+
const message = typeof error === 'string' ? error : error.message;
|
|
80
|
+
await this.update({ status: 'failed', error_message: message }, `Workflow execution failed: ${message}`);
|
|
81
|
+
}
|
|
82
|
+
async appendLog(line) {
|
|
83
|
+
await this.update({}, line);
|
|
84
|
+
}
|
|
85
|
+
async recordEvent(event) {
|
|
86
|
+
if (!this.posthogAPI || !this.progressId || !this.taskId) {
|
|
87
|
+
return;
|
|
88
|
+
}
|
|
89
|
+
switch (event.type) {
|
|
90
|
+
case 'token':
|
|
91
|
+
case 'message_delta':
|
|
92
|
+
case 'content_block_start':
|
|
93
|
+
case 'content_block_stop':
|
|
94
|
+
case 'compact_boundary':
|
|
95
|
+
case 'tool_call':
|
|
96
|
+
case 'tool_result':
|
|
97
|
+
case 'message_start':
|
|
98
|
+
case 'message_stop':
|
|
99
|
+
case 'metric':
|
|
100
|
+
case 'artifact':
|
|
101
|
+
// Skip verbose streaming artifacts from persistence
|
|
102
|
+
return;
|
|
103
|
+
case 'file_write':
|
|
104
|
+
await this.appendLog(this.formatFileWriteEvent(event));
|
|
105
|
+
return;
|
|
106
|
+
case 'diff':
|
|
107
|
+
await this.appendLog(this.formatDiffEvent(event));
|
|
108
|
+
return;
|
|
109
|
+
case 'status':
|
|
110
|
+
// Status events are covered by dedicated progress updates
|
|
111
|
+
return;
|
|
112
|
+
case 'error':
|
|
113
|
+
await this.appendLog(`[error] ${event.message}`);
|
|
114
|
+
return;
|
|
115
|
+
case 'done': {
|
|
116
|
+
const cost = event.totalCostUsd !== undefined ? ` cost=$${event.totalCostUsd.toFixed(2)}` : '';
|
|
117
|
+
await this.appendLog(`[done] duration=${event.durationMs ?? 'unknown'}ms turns=${event.numTurns ?? 'unknown'}${cost}`);
|
|
118
|
+
return;
|
|
119
|
+
}
|
|
120
|
+
case 'init':
|
|
121
|
+
// Omit verbose init messages from persisted log
|
|
122
|
+
return;
|
|
123
|
+
case 'user_message': {
|
|
124
|
+
const summary = this.summarizeUserMessage(event.content);
|
|
125
|
+
if (summary) {
|
|
126
|
+
await this.appendLog(summary);
|
|
127
|
+
}
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
130
|
+
default:
|
|
131
|
+
// For any unfamiliar event types, avoid spamming the log.
|
|
132
|
+
return;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
async update(update, logLine) {
|
|
136
|
+
if (!this.posthogAPI || !this.progressId || !this.taskId) {
|
|
137
|
+
return;
|
|
138
|
+
}
|
|
139
|
+
if (logLine) {
|
|
140
|
+
if (logLine !== this.lastLogEntry) {
|
|
141
|
+
this.outputLog.push(logLine);
|
|
142
|
+
this.lastLogEntry = logLine;
|
|
143
|
+
}
|
|
144
|
+
update.output_log = this.outputLog.join('\n');
|
|
145
|
+
}
|
|
146
|
+
try {
|
|
147
|
+
const record = await this.posthogAPI.updateTaskProgress(this.taskId, this.progressId, update);
|
|
148
|
+
// Sync local cache with server response to avoid drift if server modifies values
|
|
149
|
+
this.progressRecord = record;
|
|
150
|
+
if (record.output_log !== undefined && record.output_log !== null) {
|
|
151
|
+
this.outputLog = record.output_log ? record.output_log.split('\n') : [];
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
catch (error) {
|
|
155
|
+
this.logger.warn('Failed to update task progress record', {
|
|
156
|
+
taskId: this.taskId,
|
|
157
|
+
progressId: this.progressId,
|
|
158
|
+
error: error.message,
|
|
159
|
+
});
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
summarizeUserMessage(content) {
|
|
163
|
+
if (!content) {
|
|
164
|
+
return null;
|
|
165
|
+
}
|
|
166
|
+
const trimmed = content.trim();
|
|
167
|
+
if (!trimmed) {
|
|
168
|
+
return null;
|
|
169
|
+
}
|
|
170
|
+
const fileUpdateMatch = trimmed.match(/The file\s+([^\s]+)\s+has been updated/i);
|
|
171
|
+
if (fileUpdateMatch) {
|
|
172
|
+
return `[user] file updated: ${fileUpdateMatch[1]}`;
|
|
173
|
+
}
|
|
174
|
+
if (/Todos have been modified/i.test(trimmed)) {
|
|
175
|
+
return '[todo] list updated';
|
|
176
|
+
}
|
|
177
|
+
const diffMatch = trimmed.match(/diff --git a\/([^\s]+) b\/([^\s]+)/);
|
|
178
|
+
if (diffMatch) {
|
|
179
|
+
return `[diff] ${diffMatch[2] ?? diffMatch[1]}`;
|
|
180
|
+
}
|
|
181
|
+
const gitStatusMatch = trimmed.match(/^On branch ([^\n]+)/);
|
|
182
|
+
if (gitStatusMatch) {
|
|
183
|
+
return `[git] status ${gitStatusMatch[1]}`;
|
|
184
|
+
}
|
|
185
|
+
if (/This Bash command contains multiple operations/i.test(trimmed)) {
|
|
186
|
+
return '[approval] multi-step command pending';
|
|
187
|
+
}
|
|
188
|
+
if (/This command requires approval/i.test(trimmed)) {
|
|
189
|
+
return '[approval] command awaiting approval';
|
|
190
|
+
}
|
|
191
|
+
if (/^Exit plan mode\?/i.test(trimmed)) {
|
|
192
|
+
return null;
|
|
193
|
+
}
|
|
194
|
+
if (trimmed.includes('node_modules')) {
|
|
195
|
+
return null;
|
|
196
|
+
}
|
|
197
|
+
if (trimmed.includes('total ') && trimmed.includes('drwx')) {
|
|
198
|
+
return null;
|
|
199
|
+
}
|
|
200
|
+
if (trimmed.includes('→')) {
|
|
201
|
+
return null;
|
|
202
|
+
}
|
|
203
|
+
if (trimmed.split('\n').length > 2) {
|
|
204
|
+
return null;
|
|
205
|
+
}
|
|
206
|
+
const normalized = trimmed.replace(/\s+/g, ' ');
|
|
207
|
+
const maxLen = 120;
|
|
208
|
+
if (!normalized) {
|
|
209
|
+
return null;
|
|
210
|
+
}
|
|
211
|
+
const preview = normalized.length > maxLen ? `${normalized.slice(0, maxLen)}…` : normalized;
|
|
212
|
+
return `[user] ${preview}`;
|
|
213
|
+
}
|
|
214
|
+
formatFileWriteEvent(event) {
|
|
215
|
+
const size = event.bytes !== undefined ? ` (${event.bytes} bytes)` : '';
|
|
216
|
+
return `[file] wrote ${event.path}${size}`;
|
|
217
|
+
}
|
|
218
|
+
formatDiffEvent(event) {
|
|
219
|
+
const summary = event.summary
|
|
220
|
+
? event.summary.trim()
|
|
221
|
+
: this.truncateMultiline(event.patch ?? '', 160);
|
|
222
|
+
return `[diff] ${event.file}${summary ? ` | ${summary}` : ''}`;
|
|
223
|
+
}
|
|
224
|
+
truncateMultiline(text, max = 160) {
|
|
225
|
+
if (!text) {
|
|
226
|
+
return '';
|
|
227
|
+
}
|
|
228
|
+
const compact = text.replace(/\s+/g, ' ').trim();
|
|
229
|
+
return compact.length > max ? `${compact.slice(0, max)}…` : compact;
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
export { TaskProgressReporter };
|
|
234
|
+
//# sourceMappingURL=task-progress-reporter.js.map
|