@posthog/agent 1.30.0 → 2.0.1
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/LICENSE +1 -1
- package/README.md +221 -219
- package/dist/adapters/claude/conversion/tool-use-to-acp.d.ts +21 -0
- package/dist/adapters/claude/conversion/tool-use-to-acp.js +547 -0
- package/dist/adapters/claude/conversion/tool-use-to-acp.js.map +1 -0
- package/dist/adapters/claude/permissions/permission-options.d.ts +13 -0
- package/dist/adapters/claude/permissions/permission-options.js +117 -0
- package/dist/adapters/claude/permissions/permission-options.js.map +1 -0
- package/dist/adapters/claude/questions/utils.d.ts +132 -0
- package/dist/adapters/claude/questions/utils.js +63 -0
- package/dist/adapters/claude/questions/utils.js.map +1 -0
- package/dist/adapters/claude/tools.d.ts +18 -0
- package/dist/adapters/claude/tools.js +95 -0
- package/dist/adapters/claude/tools.js.map +1 -0
- package/dist/agent-DBQY1BfC.d.ts +123 -0
- package/dist/agent.d.ts +5 -0
- package/dist/agent.js +3656 -0
- package/dist/agent.js.map +1 -0
- package/dist/claude-cli/cli.js +3695 -2746
- package/dist/claude-cli/vendor/ripgrep/COPYING +3 -0
- package/dist/claude-cli/vendor/ripgrep/arm64-darwin/rg +0 -0
- package/dist/claude-cli/vendor/ripgrep/arm64-darwin/ripgrep.node +0 -0
- package/dist/claude-cli/vendor/ripgrep/arm64-linux/rg +0 -0
- package/dist/claude-cli/vendor/ripgrep/arm64-linux/ripgrep.node +0 -0
- package/dist/claude-cli/vendor/ripgrep/x64-darwin/rg +0 -0
- package/dist/claude-cli/vendor/ripgrep/x64-darwin/ripgrep.node +0 -0
- package/dist/claude-cli/vendor/ripgrep/x64-linux/rg +0 -0
- package/dist/claude-cli/vendor/ripgrep/x64-linux/ripgrep.node +0 -0
- package/dist/claude-cli/vendor/ripgrep/x64-win32/rg.exe +0 -0
- package/dist/claude-cli/vendor/ripgrep/x64-win32/ripgrep.node +0 -0
- package/dist/gateway-models.d.ts +24 -0
- package/dist/gateway-models.js +93 -0
- package/dist/gateway-models.js.map +1 -0
- package/dist/index.d.ts +172 -1203
- package/dist/index.js +3704 -6826
- package/dist/index.js.map +1 -1
- package/dist/logger-DDBiMOOD.d.ts +24 -0
- package/dist/posthog-api.d.ts +40 -0
- package/dist/posthog-api.js +175 -0
- package/dist/posthog-api.js.map +1 -0
- package/dist/server/agent-server.d.ts +41 -0
- package/dist/server/agent-server.js +4451 -0
- package/dist/server/agent-server.js.map +1 -0
- package/dist/server/bin.d.ts +1 -0
- package/dist/server/bin.js +4507 -0
- package/dist/server/bin.js.map +1 -0
- package/dist/types.d.ts +129 -0
- package/dist/types.js +1 -0
- package/dist/types.js.map +1 -0
- package/package.json +66 -14
- package/src/acp-extensions.ts +93 -61
- package/src/adapters/acp-connection.ts +494 -0
- package/src/adapters/base-acp-agent.ts +150 -0
- package/src/adapters/claude/claude-agent.ts +596 -0
- package/src/adapters/claude/conversion/acp-to-sdk.ts +102 -0
- package/src/adapters/claude/conversion/sdk-to-acp.ts +571 -0
- package/src/adapters/claude/conversion/tool-use-to-acp.ts +618 -0
- package/src/adapters/claude/hooks.ts +64 -0
- package/src/adapters/claude/mcp/tool-metadata.ts +102 -0
- package/src/adapters/claude/permissions/permission-handlers.ts +433 -0
- package/src/adapters/claude/permissions/permission-options.ts +103 -0
- package/src/adapters/claude/plan/utils.ts +56 -0
- package/src/adapters/claude/questions/utils.ts +92 -0
- package/src/adapters/claude/session/commands.ts +38 -0
- package/src/adapters/claude/session/mcp-config.ts +37 -0
- package/src/adapters/claude/session/models.ts +12 -0
- package/src/adapters/claude/session/options.ts +236 -0
- package/src/adapters/claude/tool-meta.ts +143 -0
- package/src/adapters/claude/tools.ts +53 -611
- package/src/adapters/claude/types.ts +61 -0
- package/src/adapters/codex/spawn.ts +130 -0
- package/src/agent.ts +97 -734
- package/src/execution-mode.ts +43 -0
- package/src/gateway-models.ts +135 -0
- package/src/index.ts +79 -0
- package/src/otel-log-writer.test.ts +105 -0
- package/src/otel-log-writer.ts +94 -0
- package/src/posthog-api.ts +75 -235
- package/src/resume.ts +115 -0
- package/src/sagas/apply-snapshot-saga.test.ts +690 -0
- package/src/sagas/apply-snapshot-saga.ts +88 -0
- package/src/sagas/capture-tree-saga.test.ts +892 -0
- package/src/sagas/capture-tree-saga.ts +141 -0
- package/src/sagas/resume-saga.test.ts +558 -0
- package/src/sagas/resume-saga.ts +332 -0
- package/src/sagas/test-fixtures.ts +250 -0
- package/src/server/agent-server.test.ts +220 -0
- package/src/server/agent-server.ts +748 -0
- package/src/server/bin.ts +88 -0
- package/src/server/jwt.ts +65 -0
- package/src/server/schemas.ts +47 -0
- package/src/server/types.ts +13 -0
- package/src/server/utils/retry.test.ts +122 -0
- package/src/server/utils/retry.ts +61 -0
- package/src/server/utils/sse-parser.test.ts +93 -0
- package/src/server/utils/sse-parser.ts +46 -0
- package/src/session-log-writer.test.ts +140 -0
- package/src/session-log-writer.ts +137 -0
- package/src/test/assertions.ts +114 -0
- package/src/test/controllers/sse-controller.ts +107 -0
- package/src/test/fixtures/api.ts +111 -0
- package/src/test/fixtures/config.ts +33 -0
- package/src/test/fixtures/notifications.ts +92 -0
- package/src/test/mocks/claude-sdk.ts +251 -0
- package/src/test/mocks/msw-handlers.ts +48 -0
- package/src/test/setup.ts +114 -0
- package/src/test/wait.ts +41 -0
- package/src/tree-tracker.ts +173 -0
- package/src/types.ts +51 -154
- package/src/utils/acp-content.ts +58 -0
- package/src/utils/async-mutex.test.ts +104 -0
- package/src/utils/async-mutex.ts +31 -0
- package/src/utils/common.ts +15 -0
- package/src/utils/gateway.ts +9 -6
- package/src/utils/logger.ts +0 -30
- package/src/utils/streams.ts +220 -0
- package/CLAUDE.md +0 -331
- package/dist/templates/plan-template.md +0 -41
- package/src/adapters/claude/claude.ts +0 -1543
- package/src/adapters/claude/mcp-server.ts +0 -810
- package/src/adapters/claude/utils.ts +0 -267
- package/src/agents/execution.ts +0 -37
- package/src/agents/planning.ts +0 -60
- package/src/agents/research.ts +0 -160
- package/src/file-manager.ts +0 -306
- package/src/git-manager.ts +0 -577
- package/src/prompt-builder.ts +0 -499
- package/src/schemas.ts +0 -241
- package/src/session-store.ts +0 -259
- package/src/task-manager.ts +0 -163
- package/src/template-manager.ts +0 -236
- package/src/templates/plan-template.md +0 -41
- package/src/todo-manager.ts +0 -180
- package/src/tools/registry.ts +0 -129
- package/src/tools/types.ts +0 -127
- package/src/utils/tapped-stream.ts +0 -60
- package/src/workflow/config.ts +0 -53
- package/src/workflow/steps/build.ts +0 -135
- package/src/workflow/steps/finalize.ts +0 -241
- package/src/workflow/steps/plan.ts +0 -167
- package/src/workflow/steps/research.ts +0 -223
- package/src/workflow/types.ts +0 -62
- package/src/workflow/utils.ts +0 -53
- package/src/worktree-manager.ts +0 -928
package/src/file-manager.ts
DELETED
|
@@ -1,306 +0,0 @@
|
|
|
1
|
-
import { promises as fs } from "node:fs";
|
|
2
|
-
import { extname, join } from "node:path";
|
|
3
|
-
import z from "zod";
|
|
4
|
-
import type { ResearchEvaluation, SupportingFile } from "./types.js";
|
|
5
|
-
import { Logger } from "./utils/logger.js";
|
|
6
|
-
|
|
7
|
-
export interface TaskFile {
|
|
8
|
-
name: string;
|
|
9
|
-
content: string;
|
|
10
|
-
type: "plan" | "context" | "reference" | "output" | "artifact";
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
export interface LocalArtifact {
|
|
14
|
-
name: string;
|
|
15
|
-
content: string;
|
|
16
|
-
type: TaskFile["type"];
|
|
17
|
-
contentType: string;
|
|
18
|
-
size: number;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
export class PostHogFileManager {
|
|
22
|
-
private repositoryPath: string;
|
|
23
|
-
private logger: Logger;
|
|
24
|
-
|
|
25
|
-
constructor(repositoryPath: string, logger?: Logger) {
|
|
26
|
-
this.repositoryPath = repositoryPath;
|
|
27
|
-
this.logger =
|
|
28
|
-
logger || new Logger({ debug: false, prefix: "[FileManager]" });
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
private getTaskDirectory(taskId: string): string {
|
|
32
|
-
return join(this.repositoryPath, ".posthog", taskId);
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
private getTaskFilePath(taskId: string, fileName: string): string {
|
|
36
|
-
return join(this.getTaskDirectory(taskId), fileName);
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
async ensureTaskDirectory(taskId: string): Promise<void> {
|
|
40
|
-
const taskDir = this.getTaskDirectory(taskId);
|
|
41
|
-
try {
|
|
42
|
-
await fs.access(taskDir);
|
|
43
|
-
} catch {
|
|
44
|
-
await fs.mkdir(taskDir, { recursive: true });
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
async writeTaskFile(taskId: string, file: TaskFile): Promise<void> {
|
|
49
|
-
await this.ensureTaskDirectory(taskId);
|
|
50
|
-
const filePath = this.getTaskFilePath(taskId, file.name);
|
|
51
|
-
|
|
52
|
-
this.logger.debug("Writing task file", {
|
|
53
|
-
filePath,
|
|
54
|
-
contentLength: file.content.length,
|
|
55
|
-
contentType: typeof file.content,
|
|
56
|
-
});
|
|
57
|
-
|
|
58
|
-
await fs.writeFile(filePath, file.content, "utf8");
|
|
59
|
-
|
|
60
|
-
this.logger.debug("File written successfully", { filePath });
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
async readTaskFile(taskId: string, fileName: string): Promise<string | null> {
|
|
64
|
-
try {
|
|
65
|
-
const filePath = this.getTaskFilePath(taskId, fileName);
|
|
66
|
-
return await fs.readFile(filePath, "utf8");
|
|
67
|
-
} catch (error) {
|
|
68
|
-
if ((error as NodeJS.ErrnoException).code === "ENOENT") {
|
|
69
|
-
return null;
|
|
70
|
-
}
|
|
71
|
-
throw error;
|
|
72
|
-
}
|
|
73
|
-
}
|
|
74
|
-
|
|
75
|
-
async listTaskFiles(taskId: string): Promise<string[]> {
|
|
76
|
-
try {
|
|
77
|
-
const taskDir = this.getTaskDirectory(taskId);
|
|
78
|
-
const files = await fs.readdir(taskDir);
|
|
79
|
-
return files.filter((file) => !file.startsWith("."));
|
|
80
|
-
} catch (error) {
|
|
81
|
-
if ((error as NodeJS.ErrnoException).code === "ENOENT") {
|
|
82
|
-
return [];
|
|
83
|
-
}
|
|
84
|
-
throw error;
|
|
85
|
-
}
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
async deleteTaskFile(taskId: string, fileName: string): Promise<void> {
|
|
89
|
-
try {
|
|
90
|
-
const filePath = this.getTaskFilePath(taskId, fileName);
|
|
91
|
-
await fs.unlink(filePath);
|
|
92
|
-
} catch (error) {
|
|
93
|
-
if ((error as NodeJS.ErrnoException).code !== "ENOENT") {
|
|
94
|
-
throw error;
|
|
95
|
-
}
|
|
96
|
-
}
|
|
97
|
-
}
|
|
98
|
-
|
|
99
|
-
async taskDirectoryExists(taskId: string): Promise<boolean> {
|
|
100
|
-
try {
|
|
101
|
-
const taskDir = this.getTaskDirectory(taskId);
|
|
102
|
-
await fs.access(taskDir);
|
|
103
|
-
return true;
|
|
104
|
-
} catch {
|
|
105
|
-
return false;
|
|
106
|
-
}
|
|
107
|
-
}
|
|
108
|
-
|
|
109
|
-
async cleanupTaskDirectory(taskId: string): Promise<void> {
|
|
110
|
-
try {
|
|
111
|
-
const taskDir = this.getTaskDirectory(taskId);
|
|
112
|
-
await fs.rm(taskDir, { recursive: true, force: true });
|
|
113
|
-
} catch (error) {
|
|
114
|
-
if ((error as NodeJS.ErrnoException).code !== "ENOENT") {
|
|
115
|
-
throw error;
|
|
116
|
-
}
|
|
117
|
-
}
|
|
118
|
-
}
|
|
119
|
-
|
|
120
|
-
// Convenience methods for common file types
|
|
121
|
-
async writePlan(taskId: string, plan: string): Promise<void> {
|
|
122
|
-
this.logger.debug("Writing plan", {
|
|
123
|
-
taskId,
|
|
124
|
-
planLength: plan.length,
|
|
125
|
-
contentPreview: plan.substring(0, 200),
|
|
126
|
-
});
|
|
127
|
-
|
|
128
|
-
await this.writeTaskFile(taskId, {
|
|
129
|
-
name: "plan.md",
|
|
130
|
-
content: plan,
|
|
131
|
-
type: "plan",
|
|
132
|
-
});
|
|
133
|
-
|
|
134
|
-
this.logger.info("Plan file written", { taskId });
|
|
135
|
-
}
|
|
136
|
-
|
|
137
|
-
async readPlan(taskId: string): Promise<string | null> {
|
|
138
|
-
return await this.readTaskFile(taskId, "plan.md");
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
async writeContext(taskId: string, context: string): Promise<void> {
|
|
142
|
-
await this.writeTaskFile(taskId, {
|
|
143
|
-
name: "context.md",
|
|
144
|
-
content: context,
|
|
145
|
-
type: "context",
|
|
146
|
-
});
|
|
147
|
-
}
|
|
148
|
-
|
|
149
|
-
async readContext(taskId: string): Promise<string | null> {
|
|
150
|
-
return await this.readTaskFile(taskId, "context.md");
|
|
151
|
-
}
|
|
152
|
-
|
|
153
|
-
async writeRequirements(taskId: string, requirements: string): Promise<void> {
|
|
154
|
-
await this.writeTaskFile(taskId, {
|
|
155
|
-
name: "requirements.md",
|
|
156
|
-
content: requirements,
|
|
157
|
-
type: "reference",
|
|
158
|
-
});
|
|
159
|
-
}
|
|
160
|
-
|
|
161
|
-
async readRequirements(taskId: string): Promise<string | null> {
|
|
162
|
-
return await this.readTaskFile(taskId, "requirements.md");
|
|
163
|
-
}
|
|
164
|
-
|
|
165
|
-
async writeResearch(taskId: string, data: ResearchEvaluation): Promise<void> {
|
|
166
|
-
this.logger.debug("Writing research", {
|
|
167
|
-
taskId,
|
|
168
|
-
score: data.actionabilityScore,
|
|
169
|
-
hasQuestions: !!data.questions,
|
|
170
|
-
questionCount: data.questions?.length ?? 0,
|
|
171
|
-
answered: data.answered ?? false,
|
|
172
|
-
});
|
|
173
|
-
|
|
174
|
-
await this.writeTaskFile(taskId, {
|
|
175
|
-
name: "research.json",
|
|
176
|
-
content: JSON.stringify(data, null, 2),
|
|
177
|
-
type: "artifact",
|
|
178
|
-
});
|
|
179
|
-
|
|
180
|
-
this.logger.info("Research file written", {
|
|
181
|
-
taskId,
|
|
182
|
-
score: data.actionabilityScore,
|
|
183
|
-
hasQuestions: !!data.questions,
|
|
184
|
-
answered: data.answered ?? false,
|
|
185
|
-
});
|
|
186
|
-
}
|
|
187
|
-
|
|
188
|
-
async readResearch(taskId: string): Promise<ResearchEvaluation | null> {
|
|
189
|
-
try {
|
|
190
|
-
const content = await this.readTaskFile(taskId, "research.json");
|
|
191
|
-
return content ? (JSON.parse(content) as ResearchEvaluation) : null;
|
|
192
|
-
} catch (error) {
|
|
193
|
-
this.logger.debug("Failed to parse research.json", { error });
|
|
194
|
-
return null;
|
|
195
|
-
}
|
|
196
|
-
}
|
|
197
|
-
|
|
198
|
-
async writeTodos(taskId: string, data: unknown): Promise<void> {
|
|
199
|
-
const todos = z.object({
|
|
200
|
-
metadata: z.object({
|
|
201
|
-
total: z.number(),
|
|
202
|
-
completed: z.number(),
|
|
203
|
-
}),
|
|
204
|
-
});
|
|
205
|
-
|
|
206
|
-
const validatedData = todos.parse(data);
|
|
207
|
-
this.logger.debug("Writing todos", {
|
|
208
|
-
taskId,
|
|
209
|
-
total: validatedData.metadata?.total ?? 0,
|
|
210
|
-
completed: validatedData.metadata?.completed ?? 0,
|
|
211
|
-
});
|
|
212
|
-
|
|
213
|
-
await this.writeTaskFile(taskId, {
|
|
214
|
-
name: "todos.json",
|
|
215
|
-
content: JSON.stringify(validatedData, null, 2),
|
|
216
|
-
type: "artifact",
|
|
217
|
-
});
|
|
218
|
-
|
|
219
|
-
this.logger.info("Todos file written", {
|
|
220
|
-
taskId,
|
|
221
|
-
total: validatedData.metadata?.total ?? 0,
|
|
222
|
-
completed: validatedData.metadata?.completed ?? 0,
|
|
223
|
-
});
|
|
224
|
-
}
|
|
225
|
-
|
|
226
|
-
async readTodos(taskId: string): Promise<unknown | null> {
|
|
227
|
-
try {
|
|
228
|
-
const content = await this.readTaskFile(taskId, "todos.json");
|
|
229
|
-
return content ? JSON.parse(content) : null;
|
|
230
|
-
} catch (error) {
|
|
231
|
-
this.logger.debug("Failed to parse todos.json", { error });
|
|
232
|
-
return null;
|
|
233
|
-
}
|
|
234
|
-
}
|
|
235
|
-
|
|
236
|
-
async getTaskFiles(taskId: string): Promise<SupportingFile[]> {
|
|
237
|
-
const fileNames = await this.listTaskFiles(taskId);
|
|
238
|
-
const files: SupportingFile[] = [];
|
|
239
|
-
|
|
240
|
-
for (const fileName of fileNames) {
|
|
241
|
-
const content = await this.readTaskFile(taskId, fileName);
|
|
242
|
-
if (content !== null) {
|
|
243
|
-
// Determine type based on file name
|
|
244
|
-
const type = this.resolveFileType(fileName);
|
|
245
|
-
|
|
246
|
-
files.push({
|
|
247
|
-
name: fileName,
|
|
248
|
-
content,
|
|
249
|
-
type,
|
|
250
|
-
created_at: new Date().toISOString(), // Could be enhanced with file stats
|
|
251
|
-
});
|
|
252
|
-
}
|
|
253
|
-
}
|
|
254
|
-
|
|
255
|
-
return files;
|
|
256
|
-
}
|
|
257
|
-
|
|
258
|
-
async collectTaskArtifacts(taskId: string): Promise<LocalArtifact[]> {
|
|
259
|
-
const fileNames = await this.listTaskFiles(taskId);
|
|
260
|
-
const artifacts: LocalArtifact[] = [];
|
|
261
|
-
|
|
262
|
-
for (const fileName of fileNames) {
|
|
263
|
-
const content = await this.readTaskFile(taskId, fileName);
|
|
264
|
-
if (content === null) {
|
|
265
|
-
continue;
|
|
266
|
-
}
|
|
267
|
-
|
|
268
|
-
const type = this.resolveFileType(fileName);
|
|
269
|
-
const contentType = this.inferContentType(fileName);
|
|
270
|
-
const size = Buffer.byteLength(content, "utf8");
|
|
271
|
-
|
|
272
|
-
artifacts.push({
|
|
273
|
-
name: fileName,
|
|
274
|
-
content,
|
|
275
|
-
type,
|
|
276
|
-
contentType,
|
|
277
|
-
size,
|
|
278
|
-
});
|
|
279
|
-
}
|
|
280
|
-
|
|
281
|
-
return artifacts;
|
|
282
|
-
}
|
|
283
|
-
|
|
284
|
-
private resolveFileType(fileName: string): TaskFile["type"] {
|
|
285
|
-
if (fileName === "plan.md") return "plan";
|
|
286
|
-
if (fileName === "context.md") return "context";
|
|
287
|
-
if (fileName === "requirements.md") return "reference";
|
|
288
|
-
if (fileName.startsWith("output_")) return "output";
|
|
289
|
-
if (fileName.endsWith(".md")) return "reference";
|
|
290
|
-
return "artifact";
|
|
291
|
-
}
|
|
292
|
-
|
|
293
|
-
private inferContentType(fileName: string): string {
|
|
294
|
-
const extension = extname(fileName).toLowerCase();
|
|
295
|
-
switch (extension) {
|
|
296
|
-
case ".md":
|
|
297
|
-
return "text/markdown";
|
|
298
|
-
case ".json":
|
|
299
|
-
return "application/json";
|
|
300
|
-
case ".txt":
|
|
301
|
-
return "text/plain";
|
|
302
|
-
default:
|
|
303
|
-
return "text/plain";
|
|
304
|
-
}
|
|
305
|
-
}
|
|
306
|
-
}
|