@posthog/agent 2.1.87 → 2.1.98
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agent.js +4 -2
- package/dist/agent.js.map +1 -1
- package/dist/posthog-api.js +120 -1
- package/dist/posthog-api.js.map +1 -1
- package/dist/server/agent-server.d.ts +1 -0
- package/dist/server/agent-server.js +147 -139
- package/dist/server/agent-server.js.map +1 -1
- package/dist/server/bin.cjs +147 -139
- package/dist/server/bin.cjs.map +1 -1
- package/dist/types.d.ts +1 -0
- package/package.json +1 -1
- package/src/posthog-api.ts +4 -0
- package/src/server/agent-server.ts +29 -28
- package/src/server/types.ts +1 -0
- package/src/types.ts +1 -0
package/dist/posthog-api.js
CHANGED
|
@@ -1,3 +1,120 @@
|
|
|
1
|
+
// package.json
|
|
2
|
+
var package_default = {
|
|
3
|
+
name: "@posthog/agent",
|
|
4
|
+
version: "2.1.98",
|
|
5
|
+
repository: "https://github.com/PostHog/twig",
|
|
6
|
+
description: "TypeScript agent framework wrapping Claude Agent SDK with Git-based task execution for PostHog",
|
|
7
|
+
exports: {
|
|
8
|
+
".": {
|
|
9
|
+
types: "./dist/index.d.ts",
|
|
10
|
+
import: "./dist/index.js"
|
|
11
|
+
},
|
|
12
|
+
"./agent": {
|
|
13
|
+
types: "./dist/agent.d.ts",
|
|
14
|
+
import: "./dist/agent.js"
|
|
15
|
+
},
|
|
16
|
+
"./gateway-models": {
|
|
17
|
+
types: "./dist/gateway-models.d.ts",
|
|
18
|
+
import: "./dist/gateway-models.js"
|
|
19
|
+
},
|
|
20
|
+
"./posthog-api": {
|
|
21
|
+
types: "./dist/posthog-api.d.ts",
|
|
22
|
+
import: "./dist/posthog-api.js"
|
|
23
|
+
},
|
|
24
|
+
"./types": {
|
|
25
|
+
types: "./dist/types.d.ts",
|
|
26
|
+
import: "./dist/types.js"
|
|
27
|
+
},
|
|
28
|
+
"./adapters/claude/questions/utils": {
|
|
29
|
+
types: "./dist/adapters/claude/questions/utils.d.ts",
|
|
30
|
+
import: "./dist/adapters/claude/questions/utils.js"
|
|
31
|
+
},
|
|
32
|
+
"./adapters/claude/permissions/permission-options": {
|
|
33
|
+
types: "./dist/adapters/claude/permissions/permission-options.d.ts",
|
|
34
|
+
import: "./dist/adapters/claude/permissions/permission-options.js"
|
|
35
|
+
},
|
|
36
|
+
"./adapters/claude/tools": {
|
|
37
|
+
types: "./dist/adapters/claude/tools.d.ts",
|
|
38
|
+
import: "./dist/adapters/claude/tools.js"
|
|
39
|
+
},
|
|
40
|
+
"./adapters/claude/conversion/tool-use-to-acp": {
|
|
41
|
+
types: "./dist/adapters/claude/conversion/tool-use-to-acp.d.ts",
|
|
42
|
+
import: "./dist/adapters/claude/conversion/tool-use-to-acp.js"
|
|
43
|
+
},
|
|
44
|
+
"./server": {
|
|
45
|
+
types: "./dist/server/agent-server.d.ts",
|
|
46
|
+
import: "./dist/server/agent-server.js"
|
|
47
|
+
}
|
|
48
|
+
},
|
|
49
|
+
bin: {
|
|
50
|
+
"agent-server": "./dist/server/bin.cjs"
|
|
51
|
+
},
|
|
52
|
+
type: "module",
|
|
53
|
+
keywords: [
|
|
54
|
+
"posthog",
|
|
55
|
+
"claude",
|
|
56
|
+
"agent",
|
|
57
|
+
"ai",
|
|
58
|
+
"git",
|
|
59
|
+
"typescript"
|
|
60
|
+
],
|
|
61
|
+
author: "PostHog",
|
|
62
|
+
license: "SEE LICENSE IN LICENSE",
|
|
63
|
+
scripts: {
|
|
64
|
+
build: "rm -rf dist && tsup",
|
|
65
|
+
dev: "tsup --watch",
|
|
66
|
+
test: "vitest run",
|
|
67
|
+
"test:watch": "vitest",
|
|
68
|
+
typecheck: "pnpm exec tsc --noEmit",
|
|
69
|
+
prepublishOnly: "pnpm run build",
|
|
70
|
+
clean: "rm -rf dist .turbo"
|
|
71
|
+
},
|
|
72
|
+
engines: {
|
|
73
|
+
node: ">=20.0.0"
|
|
74
|
+
},
|
|
75
|
+
devDependencies: {
|
|
76
|
+
"@posthog/shared": "workspace:*",
|
|
77
|
+
"@twig/git": "workspace:*",
|
|
78
|
+
"@types/bun": "latest",
|
|
79
|
+
"@types/tar": "^6.1.13",
|
|
80
|
+
minimatch: "^10.0.3",
|
|
81
|
+
msw: "^2.12.7",
|
|
82
|
+
tsup: "^8.5.1",
|
|
83
|
+
tsx: "^4.20.6",
|
|
84
|
+
typescript: "^5.5.0",
|
|
85
|
+
vitest: "^2.1.8"
|
|
86
|
+
},
|
|
87
|
+
dependencies: {
|
|
88
|
+
"@agentclientprotocol/sdk": "^0.14.0",
|
|
89
|
+
"@anthropic-ai/claude-agent-sdk": "0.2.42",
|
|
90
|
+
"@anthropic-ai/sdk": "^0.71.0",
|
|
91
|
+
"@hono/node-server": "^1.19.9",
|
|
92
|
+
"@modelcontextprotocol/sdk": "^1.25.3",
|
|
93
|
+
"@opentelemetry/api-logs": "^0.208.0",
|
|
94
|
+
"@opentelemetry/exporter-logs-otlp-http": "^0.208.0",
|
|
95
|
+
"@opentelemetry/resources": "^2.0.0",
|
|
96
|
+
"@opentelemetry/sdk-logs": "^0.208.0",
|
|
97
|
+
"@opentelemetry/semantic-conventions": "^1.28.0",
|
|
98
|
+
"@types/jsonwebtoken": "^9.0.10",
|
|
99
|
+
commander: "^14.0.2",
|
|
100
|
+
hono: "^4.11.7",
|
|
101
|
+
jsonwebtoken: "^9.0.2",
|
|
102
|
+
tar: "^7.5.0",
|
|
103
|
+
uuid: "13.0.0",
|
|
104
|
+
"yoga-wasm-web": "^0.3.3",
|
|
105
|
+
zod: "^3.24.1"
|
|
106
|
+
},
|
|
107
|
+
files: [
|
|
108
|
+
"dist/**/*",
|
|
109
|
+
"src/**/*",
|
|
110
|
+
"README.md",
|
|
111
|
+
"CLAUDE.md"
|
|
112
|
+
],
|
|
113
|
+
publishConfig: {
|
|
114
|
+
access: "public"
|
|
115
|
+
}
|
|
116
|
+
};
|
|
117
|
+
|
|
1
118
|
// src/utils/gateway.ts
|
|
2
119
|
function getLlmGatewayUrl(posthogHost) {
|
|
3
120
|
const url = new URL(posthogHost);
|
|
@@ -13,6 +130,7 @@ function getLlmGatewayUrl(posthogHost) {
|
|
|
13
130
|
}
|
|
14
131
|
|
|
15
132
|
// src/posthog-api.ts
|
|
133
|
+
var DEFAULT_USER_AGENT = `posthog/agent.hog.dev; version: ${package_default.version}`;
|
|
16
134
|
var PostHogAPIClient = class {
|
|
17
135
|
config;
|
|
18
136
|
constructor(config) {
|
|
@@ -25,7 +143,8 @@ var PostHogAPIClient = class {
|
|
|
25
143
|
get headers() {
|
|
26
144
|
return {
|
|
27
145
|
Authorization: `Bearer ${this.config.getApiKey()}`,
|
|
28
|
-
"Content-Type": "application/json"
|
|
146
|
+
"Content-Type": "application/json",
|
|
147
|
+
"User-Agent": this.config.userAgent ?? DEFAULT_USER_AGENT
|
|
29
148
|
};
|
|
30
149
|
}
|
|
31
150
|
async apiRequest(endpoint, options = {}) {
|
package/dist/posthog-api.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/utils/gateway.ts","../src/posthog-api.ts"],"sourcesContent":["export function getLlmGatewayUrl(posthogHost: string): string {\n const url = new URL(posthogHost);\n const hostname = url.hostname;\n\n // Local development (normalize 127.0.0.1 to localhost)\n if (hostname === \"localhost\" || hostname === \"127.0.0.1\") {\n return `${url.protocol}//localhost:3308/twig`;\n }\n\n // Docker containers accessing host\n if (hostname === \"host.docker.internal\") {\n return `${url.protocol}//host.docker.internal:3308/twig`;\n }\n\n // Production - extract region from hostname, default to US\n const region = hostname.match(/^(us|eu)\\.posthog\\.com$/)?.[1] ?? \"us\";\n return `https://gateway.${region}.posthog.com/twig`;\n}\n","import type {\n ArtifactType,\n PostHogAPIConfig,\n StoredEntry,\n Task,\n TaskRun,\n TaskRunArtifact,\n} from \"./types.js\";\nimport { getLlmGatewayUrl } from \"./utils/gateway.js\";\n\nexport { getLlmGatewayUrl };\n\nexport interface TaskArtifactUploadPayload {\n name: string;\n type: ArtifactType;\n content: string;\n content_type?: string;\n}\n\nexport type TaskRunUpdate = Partial<\n Pick<\n TaskRun,\n | \"status\"\n | \"branch\"\n | \"stage\"\n | \"error_message\"\n | \"output\"\n | \"state\"\n | \"environment\"\n >\n>;\n\nexport class PostHogAPIClient {\n private config: PostHogAPIConfig;\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.getApiKey()}`,\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 getTeamId(): number {\n return this.config.projectId;\n }\n\n getApiKey(): string {\n return this.config.getApiKey();\n }\n\n getLlmGatewayUrl(): string {\n return getLlmGatewayUrl(this.baseUrl);\n }\n\n async getTask(taskId: string): Promise<Task> {\n const teamId = this.getTeamId();\n return this.apiRequest<Task>(`/api/projects/${teamId}/tasks/${taskId}/`);\n }\n\n async getTaskRun(taskId: string, runId: string): Promise<TaskRun> {\n const teamId = this.getTeamId();\n return this.apiRequest<TaskRun>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/`,\n );\n }\n\n async updateTaskRun(\n taskId: string,\n runId: string,\n payload: TaskRunUpdate,\n ): Promise<TaskRun> {\n const teamId = this.getTeamId();\n return this.apiRequest<TaskRun>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/`,\n {\n method: \"PATCH\",\n body: JSON.stringify(payload),\n },\n );\n }\n\n async appendTaskRunLog(\n taskId: string,\n runId: string,\n entries: StoredEntry[],\n ): Promise<TaskRun> {\n const teamId = this.getTeamId();\n return this.apiRequest<TaskRun>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/append_log/`,\n {\n method: \"POST\",\n body: JSON.stringify({ entries }),\n },\n );\n }\n\n async uploadTaskArtifacts(\n taskId: string,\n runId: string,\n artifacts: TaskArtifactUploadPayload[],\n ): Promise<TaskRunArtifact[]> {\n if (!artifacts.length) {\n return [];\n }\n\n const teamId = this.getTeamId();\n const response = await this.apiRequest<{ artifacts: TaskRunArtifact[] }>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/artifacts/`,\n {\n method: \"POST\",\n body: JSON.stringify({ artifacts }),\n },\n );\n\n return response.artifacts ?? [];\n }\n\n async getArtifactPresignedUrl(\n taskId: string,\n runId: string,\n storagePath: string,\n ): Promise<string | null> {\n const teamId = this.getTeamId();\n try {\n const response = await this.apiRequest<{\n url: string;\n expires_in: number;\n }>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/artifacts/presign/`,\n {\n method: \"POST\",\n body: JSON.stringify({ storage_path: storagePath }),\n },\n );\n return response.url;\n } catch {\n return null;\n }\n }\n\n /**\n * Download artifact content by storage path\n * Gets a presigned URL and fetches the content\n */\n async downloadArtifact(\n taskId: string,\n runId: string,\n storagePath: string,\n ): Promise<ArrayBuffer | null> {\n const url = await this.getArtifactPresignedUrl(taskId, runId, storagePath);\n if (!url) {\n return null;\n }\n\n try {\n const response = await fetch(url);\n if (!response.ok) {\n throw new Error(`Failed to download artifact: ${response.status}`);\n }\n return response.arrayBuffer();\n } catch {\n return null;\n }\n }\n\n /**\n * Fetch logs for a task run via the logs API endpoint\n * @param taskRun - The task run to fetch logs for\n * @returns Array of stored entries, or empty array if no logs available\n */\n async fetchTaskRunLogs(taskRun: TaskRun): Promise<StoredEntry[]> {\n const teamId = this.getTeamId();\n\n try {\n const response = await fetch(\n `${this.baseUrl}/api/projects/${teamId}/tasks/${taskRun.task}/runs/${taskRun.id}/logs`,\n { headers: this.headers },\n );\n\n if (!response.ok) {\n if (response.status === 404) {\n return [];\n }\n throw new Error(\n `Failed to fetch logs: ${response.status} ${response.statusText}`,\n );\n }\n\n const content = await response.text();\n\n if (!content.trim()) {\n return [];\n }\n\n // Parse newline-delimited JSON\n return content\n .trim()\n .split(\"\\n\")\n .map((line) => JSON.parse(line) as StoredEntry);\n } catch (error) {\n throw new Error(\n `Failed to fetch task run logs: ${error instanceof Error ? error.message : String(error)}`,\n );\n }\n }\n}\n"],"mappings":"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","names":[]}
|
|
1
|
+
{"version":3,"sources":["../package.json","../src/utils/gateway.ts","../src/posthog-api.ts"],"sourcesContent":["{\n \"name\": \"@posthog/agent\",\n \"version\": \"2.1.98\",\n \"repository\": \"https://github.com/PostHog/twig\",\n \"description\": \"TypeScript agent framework wrapping Claude Agent SDK with Git-based task execution for PostHog\",\n \"exports\": {\n \".\": {\n \"types\": \"./dist/index.d.ts\",\n \"import\": \"./dist/index.js\"\n },\n \"./agent\": {\n \"types\": \"./dist/agent.d.ts\",\n \"import\": \"./dist/agent.js\"\n },\n \"./gateway-models\": {\n \"types\": \"./dist/gateway-models.d.ts\",\n \"import\": \"./dist/gateway-models.js\"\n },\n \"./posthog-api\": {\n \"types\": \"./dist/posthog-api.d.ts\",\n \"import\": \"./dist/posthog-api.js\"\n },\n \"./types\": {\n \"types\": \"./dist/types.d.ts\",\n \"import\": \"./dist/types.js\"\n },\n \"./adapters/claude/questions/utils\": {\n \"types\": \"./dist/adapters/claude/questions/utils.d.ts\",\n \"import\": \"./dist/adapters/claude/questions/utils.js\"\n },\n \"./adapters/claude/permissions/permission-options\": {\n \"types\": \"./dist/adapters/claude/permissions/permission-options.d.ts\",\n \"import\": \"./dist/adapters/claude/permissions/permission-options.js\"\n },\n \"./adapters/claude/tools\": {\n \"types\": \"./dist/adapters/claude/tools.d.ts\",\n \"import\": \"./dist/adapters/claude/tools.js\"\n },\n \"./adapters/claude/conversion/tool-use-to-acp\": {\n \"types\": \"./dist/adapters/claude/conversion/tool-use-to-acp.d.ts\",\n \"import\": \"./dist/adapters/claude/conversion/tool-use-to-acp.js\"\n },\n \"./server\": {\n \"types\": \"./dist/server/agent-server.d.ts\",\n \"import\": \"./dist/server/agent-server.js\"\n }\n },\n \"bin\": {\n \"agent-server\": \"./dist/server/bin.cjs\"\n },\n \"type\": \"module\",\n \"keywords\": [\n \"posthog\",\n \"claude\",\n \"agent\",\n \"ai\",\n \"git\",\n \"typescript\"\n ],\n \"author\": \"PostHog\",\n \"license\": \"SEE LICENSE IN LICENSE\",\n \"scripts\": {\n \"build\": \"rm -rf dist && tsup\",\n \"dev\": \"tsup --watch\",\n \"test\": \"vitest run\",\n \"test:watch\": \"vitest\",\n \"typecheck\": \"pnpm exec tsc --noEmit\",\n \"prepublishOnly\": \"pnpm run build\",\n \"clean\": \"rm -rf dist .turbo\"\n },\n \"engines\": {\n \"node\": \">=20.0.0\"\n },\n \"devDependencies\": {\n \"@posthog/shared\": \"workspace:*\",\n \"@twig/git\": \"workspace:*\",\n \"@types/bun\": \"latest\",\n \"@types/tar\": \"^6.1.13\",\n \"minimatch\": \"^10.0.3\",\n \"msw\": \"^2.12.7\",\n \"tsup\": \"^8.5.1\",\n \"tsx\": \"^4.20.6\",\n \"typescript\": \"^5.5.0\",\n \"vitest\": \"^2.1.8\"\n },\n \"dependencies\": {\n \"@agentclientprotocol/sdk\": \"^0.14.0\",\n \"@anthropic-ai/claude-agent-sdk\": \"0.2.42\",\n \"@anthropic-ai/sdk\": \"^0.71.0\",\n \"@hono/node-server\": \"^1.19.9\",\n \"@modelcontextprotocol/sdk\": \"^1.25.3\",\n \"@opentelemetry/api-logs\": \"^0.208.0\",\n \"@opentelemetry/exporter-logs-otlp-http\": \"^0.208.0\",\n \"@opentelemetry/resources\": \"^2.0.0\",\n \"@opentelemetry/sdk-logs\": \"^0.208.0\",\n \"@opentelemetry/semantic-conventions\": \"^1.28.0\",\n \"@types/jsonwebtoken\": \"^9.0.10\",\n \"commander\": \"^14.0.2\",\n \"hono\": \"^4.11.7\",\n \"jsonwebtoken\": \"^9.0.2\",\n \"tar\": \"^7.5.0\",\n \"uuid\": \"13.0.0\",\n \"yoga-wasm-web\": \"^0.3.3\",\n \"zod\": \"^3.24.1\"\n },\n \"files\": [\n \"dist/**/*\",\n \"src/**/*\",\n \"README.md\",\n \"CLAUDE.md\"\n ],\n \"publishConfig\": {\n \"access\": \"public\"\n }\n}\n","export function getLlmGatewayUrl(posthogHost: string): string {\n const url = new URL(posthogHost);\n const hostname = url.hostname;\n\n // Local development (normalize 127.0.0.1 to localhost)\n if (hostname === \"localhost\" || hostname === \"127.0.0.1\") {\n return `${url.protocol}//localhost:3308/twig`;\n }\n\n // Docker containers accessing host\n if (hostname === \"host.docker.internal\") {\n return `${url.protocol}//host.docker.internal:3308/twig`;\n }\n\n // Production - extract region from hostname, default to US\n const region = hostname.match(/^(us|eu)\\.posthog\\.com$/)?.[1] ?? \"us\";\n return `https://gateway.${region}.posthog.com/twig`;\n}\n","import packageJson from \"../package.json\" with { type: \"json\" };\nimport type {\n ArtifactType,\n PostHogAPIConfig,\n StoredEntry,\n Task,\n TaskRun,\n TaskRunArtifact,\n} from \"./types.js\";\nimport { getLlmGatewayUrl } from \"./utils/gateway.js\";\n\nexport { getLlmGatewayUrl };\n\nconst DEFAULT_USER_AGENT = `posthog/agent.hog.dev; version: ${packageJson.version}`;\n\nexport interface TaskArtifactUploadPayload {\n name: string;\n type: ArtifactType;\n content: string;\n content_type?: string;\n}\n\nexport type TaskRunUpdate = Partial<\n Pick<\n TaskRun,\n | \"status\"\n | \"branch\"\n | \"stage\"\n | \"error_message\"\n | \"output\"\n | \"state\"\n | \"environment\"\n >\n>;\n\nexport class PostHogAPIClient {\n private config: PostHogAPIConfig;\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.getApiKey()}`,\n \"Content-Type\": \"application/json\",\n \"User-Agent\": this.config.userAgent ?? DEFAULT_USER_AGENT,\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 getTeamId(): number {\n return this.config.projectId;\n }\n\n getApiKey(): string {\n return this.config.getApiKey();\n }\n\n getLlmGatewayUrl(): string {\n return getLlmGatewayUrl(this.baseUrl);\n }\n\n async getTask(taskId: string): Promise<Task> {\n const teamId = this.getTeamId();\n return this.apiRequest<Task>(`/api/projects/${teamId}/tasks/${taskId}/`);\n }\n\n async getTaskRun(taskId: string, runId: string): Promise<TaskRun> {\n const teamId = this.getTeamId();\n return this.apiRequest<TaskRun>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/`,\n );\n }\n\n async updateTaskRun(\n taskId: string,\n runId: string,\n payload: TaskRunUpdate,\n ): Promise<TaskRun> {\n const teamId = this.getTeamId();\n return this.apiRequest<TaskRun>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/`,\n {\n method: \"PATCH\",\n body: JSON.stringify(payload),\n },\n );\n }\n\n async appendTaskRunLog(\n taskId: string,\n runId: string,\n entries: StoredEntry[],\n ): Promise<TaskRun> {\n const teamId = this.getTeamId();\n return this.apiRequest<TaskRun>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/append_log/`,\n {\n method: \"POST\",\n body: JSON.stringify({ entries }),\n },\n );\n }\n\n async uploadTaskArtifacts(\n taskId: string,\n runId: string,\n artifacts: TaskArtifactUploadPayload[],\n ): Promise<TaskRunArtifact[]> {\n if (!artifacts.length) {\n return [];\n }\n\n const teamId = this.getTeamId();\n const response = await this.apiRequest<{ artifacts: TaskRunArtifact[] }>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/artifacts/`,\n {\n method: \"POST\",\n body: JSON.stringify({ artifacts }),\n },\n );\n\n return response.artifacts ?? [];\n }\n\n async getArtifactPresignedUrl(\n taskId: string,\n runId: string,\n storagePath: string,\n ): Promise<string | null> {\n const teamId = this.getTeamId();\n try {\n const response = await this.apiRequest<{\n url: string;\n expires_in: number;\n }>(\n `/api/projects/${teamId}/tasks/${taskId}/runs/${runId}/artifacts/presign/`,\n {\n method: \"POST\",\n body: JSON.stringify({ storage_path: storagePath }),\n },\n );\n return response.url;\n } catch {\n return null;\n }\n }\n\n /**\n * Download artifact content by storage path\n * Gets a presigned URL and fetches the content\n */\n async downloadArtifact(\n taskId: string,\n runId: string,\n storagePath: string,\n ): Promise<ArrayBuffer | null> {\n const url = await this.getArtifactPresignedUrl(taskId, runId, storagePath);\n if (!url) {\n return null;\n }\n\n try {\n const response = await fetch(url);\n if (!response.ok) {\n throw new Error(`Failed to download artifact: ${response.status}`);\n }\n return response.arrayBuffer();\n } catch {\n return null;\n }\n }\n\n /**\n * Fetch logs for a task run via the logs API endpoint\n * @param taskRun - The task run to fetch logs for\n * @returns Array of stored entries, or empty array if no logs available\n */\n async fetchTaskRunLogs(taskRun: TaskRun): Promise<StoredEntry[]> {\n const teamId = this.getTeamId();\n\n try {\n const response = await fetch(\n `${this.baseUrl}/api/projects/${teamId}/tasks/${taskRun.task}/runs/${taskRun.id}/logs`,\n { headers: this.headers },\n );\n\n if (!response.ok) {\n if (response.status === 404) {\n return [];\n }\n throw new Error(\n `Failed to fetch logs: ${response.status} ${response.statusText}`,\n );\n }\n\n const content = await response.text();\n\n if (!content.trim()) {\n return [];\n }\n\n // Parse newline-delimited JSON\n return content\n .trim()\n .split(\"\\n\")\n .map((line) => JSON.parse(line) as StoredEntry);\n } catch (error) {\n throw new Error(\n `Failed to fetch task run logs: ${error instanceof Error ? error.message : String(error)}`,\n );\n }\n }\n}\n"],"mappings":"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","names":[]}
|
|
@@ -905,6 +905,123 @@ import {
|
|
|
905
905
|
import { serve } from "@hono/node-server";
|
|
906
906
|
import { Hono } from "hono";
|
|
907
907
|
|
|
908
|
+
// package.json
|
|
909
|
+
var package_default = {
|
|
910
|
+
name: "@posthog/agent",
|
|
911
|
+
version: "2.1.98",
|
|
912
|
+
repository: "https://github.com/PostHog/twig",
|
|
913
|
+
description: "TypeScript agent framework wrapping Claude Agent SDK with Git-based task execution for PostHog",
|
|
914
|
+
exports: {
|
|
915
|
+
".": {
|
|
916
|
+
types: "./dist/index.d.ts",
|
|
917
|
+
import: "./dist/index.js"
|
|
918
|
+
},
|
|
919
|
+
"./agent": {
|
|
920
|
+
types: "./dist/agent.d.ts",
|
|
921
|
+
import: "./dist/agent.js"
|
|
922
|
+
},
|
|
923
|
+
"./gateway-models": {
|
|
924
|
+
types: "./dist/gateway-models.d.ts",
|
|
925
|
+
import: "./dist/gateway-models.js"
|
|
926
|
+
},
|
|
927
|
+
"./posthog-api": {
|
|
928
|
+
types: "./dist/posthog-api.d.ts",
|
|
929
|
+
import: "./dist/posthog-api.js"
|
|
930
|
+
},
|
|
931
|
+
"./types": {
|
|
932
|
+
types: "./dist/types.d.ts",
|
|
933
|
+
import: "./dist/types.js"
|
|
934
|
+
},
|
|
935
|
+
"./adapters/claude/questions/utils": {
|
|
936
|
+
types: "./dist/adapters/claude/questions/utils.d.ts",
|
|
937
|
+
import: "./dist/adapters/claude/questions/utils.js"
|
|
938
|
+
},
|
|
939
|
+
"./adapters/claude/permissions/permission-options": {
|
|
940
|
+
types: "./dist/adapters/claude/permissions/permission-options.d.ts",
|
|
941
|
+
import: "./dist/adapters/claude/permissions/permission-options.js"
|
|
942
|
+
},
|
|
943
|
+
"./adapters/claude/tools": {
|
|
944
|
+
types: "./dist/adapters/claude/tools.d.ts",
|
|
945
|
+
import: "./dist/adapters/claude/tools.js"
|
|
946
|
+
},
|
|
947
|
+
"./adapters/claude/conversion/tool-use-to-acp": {
|
|
948
|
+
types: "./dist/adapters/claude/conversion/tool-use-to-acp.d.ts",
|
|
949
|
+
import: "./dist/adapters/claude/conversion/tool-use-to-acp.js"
|
|
950
|
+
},
|
|
951
|
+
"./server": {
|
|
952
|
+
types: "./dist/server/agent-server.d.ts",
|
|
953
|
+
import: "./dist/server/agent-server.js"
|
|
954
|
+
}
|
|
955
|
+
},
|
|
956
|
+
bin: {
|
|
957
|
+
"agent-server": "./dist/server/bin.cjs"
|
|
958
|
+
},
|
|
959
|
+
type: "module",
|
|
960
|
+
keywords: [
|
|
961
|
+
"posthog",
|
|
962
|
+
"claude",
|
|
963
|
+
"agent",
|
|
964
|
+
"ai",
|
|
965
|
+
"git",
|
|
966
|
+
"typescript"
|
|
967
|
+
],
|
|
968
|
+
author: "PostHog",
|
|
969
|
+
license: "SEE LICENSE IN LICENSE",
|
|
970
|
+
scripts: {
|
|
971
|
+
build: "rm -rf dist && tsup",
|
|
972
|
+
dev: "tsup --watch",
|
|
973
|
+
test: "vitest run",
|
|
974
|
+
"test:watch": "vitest",
|
|
975
|
+
typecheck: "pnpm exec tsc --noEmit",
|
|
976
|
+
prepublishOnly: "pnpm run build",
|
|
977
|
+
clean: "rm -rf dist .turbo"
|
|
978
|
+
},
|
|
979
|
+
engines: {
|
|
980
|
+
node: ">=20.0.0"
|
|
981
|
+
},
|
|
982
|
+
devDependencies: {
|
|
983
|
+
"@posthog/shared": "workspace:*",
|
|
984
|
+
"@twig/git": "workspace:*",
|
|
985
|
+
"@types/bun": "latest",
|
|
986
|
+
"@types/tar": "^6.1.13",
|
|
987
|
+
minimatch: "^10.0.3",
|
|
988
|
+
msw: "^2.12.7",
|
|
989
|
+
tsup: "^8.5.1",
|
|
990
|
+
tsx: "^4.20.6",
|
|
991
|
+
typescript: "^5.5.0",
|
|
992
|
+
vitest: "^2.1.8"
|
|
993
|
+
},
|
|
994
|
+
dependencies: {
|
|
995
|
+
"@agentclientprotocol/sdk": "^0.14.0",
|
|
996
|
+
"@anthropic-ai/claude-agent-sdk": "0.2.42",
|
|
997
|
+
"@anthropic-ai/sdk": "^0.71.0",
|
|
998
|
+
"@hono/node-server": "^1.19.9",
|
|
999
|
+
"@modelcontextprotocol/sdk": "^1.25.3",
|
|
1000
|
+
"@opentelemetry/api-logs": "^0.208.0",
|
|
1001
|
+
"@opentelemetry/exporter-logs-otlp-http": "^0.208.0",
|
|
1002
|
+
"@opentelemetry/resources": "^2.0.0",
|
|
1003
|
+
"@opentelemetry/sdk-logs": "^0.208.0",
|
|
1004
|
+
"@opentelemetry/semantic-conventions": "^1.28.0",
|
|
1005
|
+
"@types/jsonwebtoken": "^9.0.10",
|
|
1006
|
+
commander: "^14.0.2",
|
|
1007
|
+
hono: "^4.11.7",
|
|
1008
|
+
jsonwebtoken: "^9.0.2",
|
|
1009
|
+
tar: "^7.5.0",
|
|
1010
|
+
uuid: "13.0.0",
|
|
1011
|
+
"yoga-wasm-web": "^0.3.3",
|
|
1012
|
+
zod: "^3.24.1"
|
|
1013
|
+
},
|
|
1014
|
+
files: [
|
|
1015
|
+
"dist/**/*",
|
|
1016
|
+
"src/**/*",
|
|
1017
|
+
"README.md",
|
|
1018
|
+
"CLAUDE.md"
|
|
1019
|
+
],
|
|
1020
|
+
publishConfig: {
|
|
1021
|
+
access: "public"
|
|
1022
|
+
}
|
|
1023
|
+
};
|
|
1024
|
+
|
|
908
1025
|
// src/acp-extensions.ts
|
|
909
1026
|
var POSTHOG_NOTIFICATIONS = {
|
|
910
1027
|
/** Git branch was created for a task */
|
|
@@ -1180,123 +1297,6 @@ import {
|
|
|
1180
1297
|
} from "@anthropic-ai/claude-agent-sdk";
|
|
1181
1298
|
import { v7 as uuidv7 } from "uuid";
|
|
1182
1299
|
|
|
1183
|
-
// package.json
|
|
1184
|
-
var package_default = {
|
|
1185
|
-
name: "@posthog/agent",
|
|
1186
|
-
version: "2.1.87",
|
|
1187
|
-
repository: "https://github.com/PostHog/twig",
|
|
1188
|
-
description: "TypeScript agent framework wrapping Claude Agent SDK with Git-based task execution for PostHog",
|
|
1189
|
-
exports: {
|
|
1190
|
-
".": {
|
|
1191
|
-
types: "./dist/index.d.ts",
|
|
1192
|
-
import: "./dist/index.js"
|
|
1193
|
-
},
|
|
1194
|
-
"./agent": {
|
|
1195
|
-
types: "./dist/agent.d.ts",
|
|
1196
|
-
import: "./dist/agent.js"
|
|
1197
|
-
},
|
|
1198
|
-
"./gateway-models": {
|
|
1199
|
-
types: "./dist/gateway-models.d.ts",
|
|
1200
|
-
import: "./dist/gateway-models.js"
|
|
1201
|
-
},
|
|
1202
|
-
"./posthog-api": {
|
|
1203
|
-
types: "./dist/posthog-api.d.ts",
|
|
1204
|
-
import: "./dist/posthog-api.js"
|
|
1205
|
-
},
|
|
1206
|
-
"./types": {
|
|
1207
|
-
types: "./dist/types.d.ts",
|
|
1208
|
-
import: "./dist/types.js"
|
|
1209
|
-
},
|
|
1210
|
-
"./adapters/claude/questions/utils": {
|
|
1211
|
-
types: "./dist/adapters/claude/questions/utils.d.ts",
|
|
1212
|
-
import: "./dist/adapters/claude/questions/utils.js"
|
|
1213
|
-
},
|
|
1214
|
-
"./adapters/claude/permissions/permission-options": {
|
|
1215
|
-
types: "./dist/adapters/claude/permissions/permission-options.d.ts",
|
|
1216
|
-
import: "./dist/adapters/claude/permissions/permission-options.js"
|
|
1217
|
-
},
|
|
1218
|
-
"./adapters/claude/tools": {
|
|
1219
|
-
types: "./dist/adapters/claude/tools.d.ts",
|
|
1220
|
-
import: "./dist/adapters/claude/tools.js"
|
|
1221
|
-
},
|
|
1222
|
-
"./adapters/claude/conversion/tool-use-to-acp": {
|
|
1223
|
-
types: "./dist/adapters/claude/conversion/tool-use-to-acp.d.ts",
|
|
1224
|
-
import: "./dist/adapters/claude/conversion/tool-use-to-acp.js"
|
|
1225
|
-
},
|
|
1226
|
-
"./server": {
|
|
1227
|
-
types: "./dist/server/agent-server.d.ts",
|
|
1228
|
-
import: "./dist/server/agent-server.js"
|
|
1229
|
-
}
|
|
1230
|
-
},
|
|
1231
|
-
bin: {
|
|
1232
|
-
"agent-server": "./dist/server/bin.cjs"
|
|
1233
|
-
},
|
|
1234
|
-
type: "module",
|
|
1235
|
-
keywords: [
|
|
1236
|
-
"posthog",
|
|
1237
|
-
"claude",
|
|
1238
|
-
"agent",
|
|
1239
|
-
"ai",
|
|
1240
|
-
"git",
|
|
1241
|
-
"typescript"
|
|
1242
|
-
],
|
|
1243
|
-
author: "PostHog",
|
|
1244
|
-
license: "SEE LICENSE IN LICENSE",
|
|
1245
|
-
scripts: {
|
|
1246
|
-
build: "rm -rf dist && tsup",
|
|
1247
|
-
dev: "tsup --watch",
|
|
1248
|
-
test: "vitest run",
|
|
1249
|
-
"test:watch": "vitest",
|
|
1250
|
-
typecheck: "pnpm exec tsc --noEmit",
|
|
1251
|
-
prepublishOnly: "pnpm run build",
|
|
1252
|
-
clean: "rm -rf dist .turbo"
|
|
1253
|
-
},
|
|
1254
|
-
engines: {
|
|
1255
|
-
node: ">=20.0.0"
|
|
1256
|
-
},
|
|
1257
|
-
devDependencies: {
|
|
1258
|
-
"@posthog/shared": "workspace:*",
|
|
1259
|
-
"@twig/git": "workspace:*",
|
|
1260
|
-
"@types/bun": "latest",
|
|
1261
|
-
"@types/tar": "^6.1.13",
|
|
1262
|
-
minimatch: "^10.0.3",
|
|
1263
|
-
msw: "^2.12.7",
|
|
1264
|
-
tsup: "^8.5.1",
|
|
1265
|
-
tsx: "^4.20.6",
|
|
1266
|
-
typescript: "^5.5.0",
|
|
1267
|
-
vitest: "^2.1.8"
|
|
1268
|
-
},
|
|
1269
|
-
dependencies: {
|
|
1270
|
-
"@agentclientprotocol/sdk": "^0.14.0",
|
|
1271
|
-
"@anthropic-ai/claude-agent-sdk": "0.2.42",
|
|
1272
|
-
"@anthropic-ai/sdk": "^0.71.0",
|
|
1273
|
-
"@hono/node-server": "^1.19.9",
|
|
1274
|
-
"@modelcontextprotocol/sdk": "^1.25.3",
|
|
1275
|
-
"@opentelemetry/api-logs": "^0.208.0",
|
|
1276
|
-
"@opentelemetry/exporter-logs-otlp-http": "^0.208.0",
|
|
1277
|
-
"@opentelemetry/resources": "^2.0.0",
|
|
1278
|
-
"@opentelemetry/sdk-logs": "^0.208.0",
|
|
1279
|
-
"@opentelemetry/semantic-conventions": "^1.28.0",
|
|
1280
|
-
"@types/jsonwebtoken": "^9.0.10",
|
|
1281
|
-
commander: "^14.0.2",
|
|
1282
|
-
hono: "^4.11.7",
|
|
1283
|
-
jsonwebtoken: "^9.0.2",
|
|
1284
|
-
tar: "^7.5.0",
|
|
1285
|
-
uuid: "13.0.0",
|
|
1286
|
-
"yoga-wasm-web": "^0.3.3",
|
|
1287
|
-
zod: "^3.24.1"
|
|
1288
|
-
},
|
|
1289
|
-
files: [
|
|
1290
|
-
"dist/**/*",
|
|
1291
|
-
"src/**/*",
|
|
1292
|
-
"README.md",
|
|
1293
|
-
"CLAUDE.md"
|
|
1294
|
-
],
|
|
1295
|
-
publishConfig: {
|
|
1296
|
-
access: "public"
|
|
1297
|
-
}
|
|
1298
|
-
};
|
|
1299
|
-
|
|
1300
1300
|
// src/utils/common.ts
|
|
1301
1301
|
async function withTimeout(operation, timeoutMs) {
|
|
1302
1302
|
const timeoutPromise = new Promise(
|
|
@@ -4211,6 +4211,7 @@ function getLlmGatewayUrl(posthogHost) {
|
|
|
4211
4211
|
}
|
|
4212
4212
|
|
|
4213
4213
|
// src/posthog-api.ts
|
|
4214
|
+
var DEFAULT_USER_AGENT = `posthog/agent.hog.dev; version: ${package_default.version}`;
|
|
4214
4215
|
var PostHogAPIClient = class {
|
|
4215
4216
|
config;
|
|
4216
4217
|
constructor(config) {
|
|
@@ -4223,7 +4224,8 @@ var PostHogAPIClient = class {
|
|
|
4223
4224
|
get headers() {
|
|
4224
4225
|
return {
|
|
4225
4226
|
Authorization: `Bearer ${this.config.getApiKey()}`,
|
|
4226
|
-
"Content-Type": "application/json"
|
|
4227
|
+
"Content-Type": "application/json",
|
|
4228
|
+
"User-Agent": this.config.userAgent ?? DEFAULT_USER_AGENT
|
|
4227
4229
|
};
|
|
4228
4230
|
}
|
|
4229
4231
|
async apiRequest(endpoint, options = {}) {
|
|
@@ -10250,7 +10252,8 @@ var AgentServer = class {
|
|
|
10250
10252
|
this.posthogAPI = new PostHogAPIClient({
|
|
10251
10253
|
apiUrl: config.apiUrl,
|
|
10252
10254
|
projectId: config.projectId,
|
|
10253
|
-
getApiKey: () => config.apiKey
|
|
10255
|
+
getApiKey: () => config.apiKey,
|
|
10256
|
+
userAgent: `posthog/cloud.hog.dev; version: ${config.version ?? package_default.version}`
|
|
10254
10257
|
});
|
|
10255
10258
|
this.app = this.createApp();
|
|
10256
10259
|
}
|
|
@@ -10458,16 +10461,18 @@ var AgentServer = class {
|
|
|
10458
10461
|
`Processing user message: ${content.substring(0, 100)}...`
|
|
10459
10462
|
);
|
|
10460
10463
|
const result = await this.session.clientConnection.prompt({
|
|
10461
|
-
sessionId: this.session.
|
|
10464
|
+
sessionId: this.session.acpSessionId,
|
|
10462
10465
|
prompt: [{ type: "text", text: content }]
|
|
10463
10466
|
});
|
|
10464
10467
|
return { stopReason: result.stopReason };
|
|
10465
10468
|
}
|
|
10466
10469
|
case POSTHOG_NOTIFICATIONS.CANCEL:
|
|
10467
10470
|
case "cancel": {
|
|
10468
|
-
this.logger.info("Cancel requested"
|
|
10471
|
+
this.logger.info("Cancel requested", {
|
|
10472
|
+
acpSessionId: this.session.acpSessionId
|
|
10473
|
+
});
|
|
10469
10474
|
await this.session.clientConnection.cancel({
|
|
10470
|
-
sessionId: this.session.
|
|
10475
|
+
sessionId: this.session.acpSessionId
|
|
10471
10476
|
});
|
|
10472
10477
|
return { cancelled: true };
|
|
10473
10478
|
}
|
|
@@ -10503,7 +10508,8 @@ var AgentServer = class {
|
|
|
10503
10508
|
const posthogAPI = new PostHogAPIClient({
|
|
10504
10509
|
apiUrl: this.config.apiUrl,
|
|
10505
10510
|
projectId: this.config.projectId,
|
|
10506
|
-
getApiKey: () => this.config.apiKey
|
|
10511
|
+
getApiKey: () => this.config.apiKey,
|
|
10512
|
+
userAgent: `posthog/cloud.hog.dev; version: ${this.config.version ?? package_default.version}`
|
|
10507
10513
|
});
|
|
10508
10514
|
const logWriter = new SessionLogWriter({
|
|
10509
10515
|
posthogAPI,
|
|
@@ -10541,7 +10547,7 @@ var AgentServer = class {
|
|
|
10541
10547
|
protocolVersion: PROTOCOL_VERSION,
|
|
10542
10548
|
clientCapabilities: {}
|
|
10543
10549
|
});
|
|
10544
|
-
await clientConnection.newSession({
|
|
10550
|
+
const sessionResponse = await clientConnection.newSession({
|
|
10545
10551
|
cwd: this.config.repositoryPath,
|
|
10546
10552
|
mcpServers: [],
|
|
10547
10553
|
_meta: {
|
|
@@ -10550,8 +10556,14 @@ var AgentServer = class {
|
|
|
10550
10556
|
systemPrompt: { append: this.buildCloudSystemPrompt() }
|
|
10551
10557
|
}
|
|
10552
10558
|
});
|
|
10559
|
+
const acpSessionId = sessionResponse.sessionId;
|
|
10560
|
+
this.logger.info("ACP session created", {
|
|
10561
|
+
acpSessionId,
|
|
10562
|
+
runId: payload.run_id
|
|
10563
|
+
});
|
|
10553
10564
|
this.session = {
|
|
10554
10565
|
payload,
|
|
10566
|
+
acpSessionId,
|
|
10555
10567
|
acpConnection,
|
|
10556
10568
|
clientConnection,
|
|
10557
10569
|
treeTracker,
|
|
@@ -10581,28 +10593,18 @@ var AgentServer = class {
|
|
|
10581
10593
|
descriptionLength: task.description.length
|
|
10582
10594
|
});
|
|
10583
10595
|
const result = await this.session.clientConnection.prompt({
|
|
10584
|
-
sessionId:
|
|
10596
|
+
sessionId: this.session.acpSessionId,
|
|
10585
10597
|
prompt: [{ type: "text", text: task.description }]
|
|
10586
10598
|
});
|
|
10587
10599
|
this.logger.info("Initial task message completed", {
|
|
10588
10600
|
stopReason: result.stopReason
|
|
10589
10601
|
});
|
|
10590
|
-
const mode = this.getEffectiveMode(payload);
|
|
10591
|
-
if (mode === "background") {
|
|
10592
|
-
await this.session.logWriter.flushAll();
|
|
10593
|
-
await this.signalTaskComplete(payload, result.stopReason);
|
|
10594
|
-
} else {
|
|
10595
|
-
this.logger.info("Interactive mode - staying open for conversation");
|
|
10596
|
-
}
|
|
10597
10602
|
} catch (error) {
|
|
10598
10603
|
this.logger.error("Failed to send initial task message", error);
|
|
10599
|
-
|
|
10600
|
-
|
|
10601
|
-
if (this.session) {
|
|
10602
|
-
await this.session.logWriter.flushAll();
|
|
10603
|
-
}
|
|
10604
|
-
await this.signalTaskComplete(payload, "error");
|
|
10604
|
+
if (this.session) {
|
|
10605
|
+
await this.session.logWriter.flushAll();
|
|
10605
10606
|
}
|
|
10607
|
+
await this.signalTaskComplete(payload, "error");
|
|
10606
10608
|
}
|
|
10607
10609
|
}
|
|
10608
10610
|
buildCloudSystemPrompt() {
|
|
@@ -10633,7 +10635,13 @@ Important:
|
|
|
10633
10635
|
});
|
|
10634
10636
|
}
|
|
10635
10637
|
}
|
|
10636
|
-
|
|
10638
|
+
if (stopReason !== "error") {
|
|
10639
|
+
this.logger.info("Skipping status update for non-error stop reason", {
|
|
10640
|
+
stopReason
|
|
10641
|
+
});
|
|
10642
|
+
return;
|
|
10643
|
+
}
|
|
10644
|
+
const status = "failed";
|
|
10637
10645
|
try {
|
|
10638
10646
|
await this.posthogAPI.updateTaskRun(payload.task_id, payload.run_id, {
|
|
10639
10647
|
status,
|