@posthog/agent 2.3.104 → 2.3.116
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 +72 -31
- package/dist/agent.js.map +1 -1
- package/dist/posthog-api.d.ts +6 -2
- package/dist/posthog-api.js +36 -19
- package/dist/posthog-api.js.map +1 -1
- package/dist/server/agent-server.js +81 -31
- package/dist/server/agent-server.js.map +1 -1
- package/dist/server/bin.cjs +81 -31
- package/dist/server/bin.cjs.map +1 -1
- package/dist/types.d.ts +2 -1
- package/package.json +1 -1
- package/src/agent.ts +5 -5
- package/src/posthog-api.test.ts +48 -0
- package/src/posthog-api.ts +54 -20
- package/src/server/agent-server.ts +13 -4
- package/src/session-log-writer.test.ts +216 -0
- package/src/session-log-writer.ts +48 -11
- package/src/types.ts +2 -1
package/dist/server/bin.cjs
CHANGED
|
@@ -904,7 +904,7 @@ var import_hono = require("hono");
|
|
|
904
904
|
// package.json
|
|
905
905
|
var package_default = {
|
|
906
906
|
name: "@posthog/agent",
|
|
907
|
-
version: "2.3.
|
|
907
|
+
version: "2.3.116",
|
|
908
908
|
repository: "https://github.com/PostHog/code",
|
|
909
909
|
description: "TypeScript agent framework wrapping Claude Agent SDK with Git-based task execution for PostHog",
|
|
910
910
|
exports: {
|
|
@@ -5433,22 +5433,41 @@ var PostHogAPIClient = class {
|
|
|
5433
5433
|
const host = this.config.apiUrl.endsWith("/") ? this.config.apiUrl.slice(0, -1) : this.config.apiUrl;
|
|
5434
5434
|
return host;
|
|
5435
5435
|
}
|
|
5436
|
-
|
|
5437
|
-
return
|
|
5438
|
-
Authorization: `Bearer ${this.config.getApiKey()}`,
|
|
5439
|
-
"Content-Type": "application/json",
|
|
5440
|
-
"User-Agent": this.config.userAgent ?? DEFAULT_USER_AGENT
|
|
5441
|
-
};
|
|
5436
|
+
isAuthFailure(status) {
|
|
5437
|
+
return status === 401 || status === 403;
|
|
5442
5438
|
}
|
|
5443
|
-
async
|
|
5439
|
+
async resolveApiKey(forceRefresh = false) {
|
|
5440
|
+
if (forceRefresh && this.config.refreshApiKey) {
|
|
5441
|
+
return this.config.refreshApiKey();
|
|
5442
|
+
}
|
|
5443
|
+
return this.config.getApiKey();
|
|
5444
|
+
}
|
|
5445
|
+
async buildHeaders(options, forceRefresh = false) {
|
|
5446
|
+
const headers = new Headers(options.headers);
|
|
5447
|
+
headers.set(
|
|
5448
|
+
"Authorization",
|
|
5449
|
+
`Bearer ${await this.resolveApiKey(forceRefresh)}`
|
|
5450
|
+
);
|
|
5451
|
+
headers.set("Content-Type", "application/json");
|
|
5452
|
+
headers.set("User-Agent", this.config.userAgent ?? DEFAULT_USER_AGENT);
|
|
5453
|
+
return headers;
|
|
5454
|
+
}
|
|
5455
|
+
async performRequest(endpoint, options, forceRefresh = false) {
|
|
5444
5456
|
const url = `${this.baseUrl}${endpoint}`;
|
|
5445
|
-
|
|
5457
|
+
return fetch(url, {
|
|
5446
5458
|
...options,
|
|
5447
|
-
headers:
|
|
5448
|
-
...this.headers,
|
|
5449
|
-
...options.headers
|
|
5450
|
-
}
|
|
5459
|
+
headers: await this.buildHeaders(options, forceRefresh)
|
|
5451
5460
|
});
|
|
5461
|
+
}
|
|
5462
|
+
async performRequestWithRetry(endpoint, options = {}) {
|
|
5463
|
+
let response = await this.performRequest(endpoint, options);
|
|
5464
|
+
if (!response.ok && this.isAuthFailure(response.status)) {
|
|
5465
|
+
response = await this.performRequest(endpoint, options, true);
|
|
5466
|
+
}
|
|
5467
|
+
return response;
|
|
5468
|
+
}
|
|
5469
|
+
async apiRequest(endpoint, options = {}) {
|
|
5470
|
+
const response = await this.performRequestWithRetry(endpoint, options);
|
|
5452
5471
|
if (!response.ok) {
|
|
5453
5472
|
let errorMessage;
|
|
5454
5473
|
try {
|
|
@@ -5464,8 +5483,8 @@ var PostHogAPIClient = class {
|
|
|
5464
5483
|
getTeamId() {
|
|
5465
5484
|
return this.config.projectId;
|
|
5466
5485
|
}
|
|
5467
|
-
getApiKey() {
|
|
5468
|
-
return this.
|
|
5486
|
+
async getApiKey(forceRefresh = false) {
|
|
5487
|
+
return this.resolveApiKey(forceRefresh);
|
|
5469
5488
|
}
|
|
5470
5489
|
getLlmGatewayUrl() {
|
|
5471
5490
|
return getLlmGatewayUrl(this.baseUrl);
|
|
@@ -5565,11 +5584,9 @@ var PostHogAPIClient = class {
|
|
|
5565
5584
|
*/
|
|
5566
5585
|
async fetchTaskRunLogs(taskRun) {
|
|
5567
5586
|
const teamId = this.getTeamId();
|
|
5587
|
+
const endpoint = `/api/projects/${teamId}/tasks/${taskRun.task}/runs/${taskRun.id}/logs`;
|
|
5568
5588
|
try {
|
|
5569
|
-
const response = await
|
|
5570
|
-
`${this.baseUrl}/api/projects/${teamId}/tasks/${taskRun.task}/runs/${taskRun.id}/logs`,
|
|
5571
|
-
{ headers: this.headers }
|
|
5572
|
-
);
|
|
5589
|
+
const response = await this.performRequestWithRetry(endpoint);
|
|
5573
5590
|
if (!response.ok) {
|
|
5574
5591
|
if (response.status === 404) {
|
|
5575
5592
|
return [];
|
|
@@ -11340,9 +11357,9 @@ var SessionLogWriter = class _SessionLogWriter {
|
|
|
11340
11357
|
this.logger = options.logger ?? new Logger({ debug: false, prefix: "[SessionLogWriter]" });
|
|
11341
11358
|
}
|
|
11342
11359
|
async flushAll() {
|
|
11343
|
-
const sessionIds = [...this.sessions.keys()];
|
|
11344
11360
|
const flushPromises = [];
|
|
11345
|
-
for (const sessionId of
|
|
11361
|
+
for (const [sessionId, session] of this.sessions) {
|
|
11362
|
+
this.emitCoalescedMessage(sessionId, session);
|
|
11346
11363
|
flushPromises.push(this.flush(sessionId));
|
|
11347
11364
|
}
|
|
11348
11365
|
await Promise.all(flushPromises);
|
|
@@ -11398,7 +11415,11 @@ var SessionLogWriter = class _SessionLogWriter {
|
|
|
11398
11415
|
}
|
|
11399
11416
|
return;
|
|
11400
11417
|
}
|
|
11401
|
-
this.
|
|
11418
|
+
if (this.isDirectAgentMessage(message) && session.chunkBuffer) {
|
|
11419
|
+
session.chunkBuffer = void 0;
|
|
11420
|
+
} else {
|
|
11421
|
+
this.emitCoalescedMessage(sessionId, session);
|
|
11422
|
+
}
|
|
11402
11423
|
const nonChunkAgentText = this.extractAgentMessageText(message);
|
|
11403
11424
|
if (nonChunkAgentText) {
|
|
11404
11425
|
session.lastAgentMessage = nonChunkAgentText;
|
|
@@ -11424,7 +11445,13 @@ var SessionLogWriter = class _SessionLogWriter {
|
|
|
11424
11445
|
});
|
|
11425
11446
|
}
|
|
11426
11447
|
}
|
|
11427
|
-
async flush(sessionId) {
|
|
11448
|
+
async flush(sessionId, { coalesce = false } = {}) {
|
|
11449
|
+
if (coalesce) {
|
|
11450
|
+
const session = this.sessions.get(sessionId);
|
|
11451
|
+
if (session) {
|
|
11452
|
+
this.emitCoalescedMessage(sessionId, session);
|
|
11453
|
+
}
|
|
11454
|
+
}
|
|
11428
11455
|
const prev = this.flushQueues.get(sessionId) ?? Promise.resolve();
|
|
11429
11456
|
const next = prev.catch(() => {
|
|
11430
11457
|
}).then(() => this._doFlush(sessionId));
|
|
@@ -11442,7 +11469,6 @@ var SessionLogWriter = class _SessionLogWriter {
|
|
|
11442
11469
|
this.logger.warn("flush: no session found", { sessionId });
|
|
11443
11470
|
return;
|
|
11444
11471
|
}
|
|
11445
|
-
this.emitCoalescedMessage(sessionId, session);
|
|
11446
11472
|
const pending = this.pendingEntries.get(sessionId);
|
|
11447
11473
|
if (!this.posthogAPI || !pending?.length) {
|
|
11448
11474
|
return;
|
|
@@ -11491,11 +11517,17 @@ var SessionLogWriter = class _SessionLogWriter {
|
|
|
11491
11517
|
}
|
|
11492
11518
|
}
|
|
11493
11519
|
}
|
|
11494
|
-
|
|
11495
|
-
if (message.method !== "session/update") return
|
|
11520
|
+
getSessionUpdateType(message) {
|
|
11521
|
+
if (message.method !== "session/update") return void 0;
|
|
11496
11522
|
const params = message.params;
|
|
11497
11523
|
const update = params?.update;
|
|
11498
|
-
return update?.sessionUpdate
|
|
11524
|
+
return update?.sessionUpdate;
|
|
11525
|
+
}
|
|
11526
|
+
isDirectAgentMessage(message) {
|
|
11527
|
+
return this.getSessionUpdateType(message) === "agent_message";
|
|
11528
|
+
}
|
|
11529
|
+
isAgentMessageChunk(message) {
|
|
11530
|
+
return this.getSessionUpdateType(message) === "agent_message_chunk";
|
|
11499
11531
|
}
|
|
11500
11532
|
extractChunkText(message) {
|
|
11501
11533
|
const params = message.params;
|
|
@@ -11540,6 +11572,15 @@ var SessionLogWriter = class _SessionLogWriter {
|
|
|
11540
11572
|
getFullAgentResponse(sessionId) {
|
|
11541
11573
|
const session = this.sessions.get(sessionId);
|
|
11542
11574
|
if (!session || session.currentTurnMessages.length === 0) return void 0;
|
|
11575
|
+
if (session.chunkBuffer) {
|
|
11576
|
+
this.logger.warn(
|
|
11577
|
+
"getFullAgentResponse called with non-empty chunk buffer",
|
|
11578
|
+
{
|
|
11579
|
+
sessionId,
|
|
11580
|
+
bufferedLength: session.chunkBuffer.text.length
|
|
11581
|
+
}
|
|
11582
|
+
);
|
|
11583
|
+
}
|
|
11543
11584
|
return session.currentTurnMessages.join("\n\n");
|
|
11544
11585
|
}
|
|
11545
11586
|
resetTurnMessages(sessionId) {
|
|
@@ -12151,7 +12192,9 @@ You MUST NOT create a new branch, close the existing PR, or create a new PR.`
|
|
|
12151
12192
|
}
|
|
12152
12193
|
let assistantMessage;
|
|
12153
12194
|
try {
|
|
12154
|
-
await this.session.logWriter.flush(this.session.payload.run_id
|
|
12195
|
+
await this.session.logWriter.flush(this.session.payload.run_id, {
|
|
12196
|
+
coalesce: true
|
|
12197
|
+
});
|
|
12155
12198
|
assistantMessage = this.session.logWriter.getFullAgentResponse(
|
|
12156
12199
|
this.session.payload.run_id
|
|
12157
12200
|
);
|
|
@@ -12324,6 +12367,9 @@ You MUST NOT create a new branch, close the existing PR, or create a new PR.`
|
|
|
12324
12367
|
}
|
|
12325
12368
|
});
|
|
12326
12369
|
this.logger.info("Session initialized successfully");
|
|
12370
|
+
this.logger.info(
|
|
12371
|
+
`Agent version: ${this.config.version ?? package_default.version}`
|
|
12372
|
+
);
|
|
12327
12373
|
this.posthogAPI.updateTaskRun(payload.task_id, payload.run_id, {
|
|
12328
12374
|
status: "in_progress"
|
|
12329
12375
|
}).catch(
|
|
@@ -12601,7 +12647,9 @@ Important:
|
|
|
12601
12647
|
async signalTaskComplete(payload, stopReason) {
|
|
12602
12648
|
if (this.session?.payload.run_id === payload.run_id) {
|
|
12603
12649
|
try {
|
|
12604
|
-
await this.session.logWriter.flush(payload.run_id
|
|
12650
|
+
await this.session.logWriter.flush(payload.run_id, {
|
|
12651
|
+
coalesce: true
|
|
12652
|
+
});
|
|
12605
12653
|
} catch (error) {
|
|
12606
12654
|
this.logger.warn("Failed to flush session logs before completion", {
|
|
12607
12655
|
taskId: payload.task_id,
|
|
@@ -12710,7 +12758,7 @@ Important:
|
|
|
12710
12758
|
return;
|
|
12711
12759
|
}
|
|
12712
12760
|
try {
|
|
12713
|
-
await this.session.logWriter.flush(payload.run_id);
|
|
12761
|
+
await this.session.logWriter.flush(payload.run_id, { coalesce: true });
|
|
12714
12762
|
} catch (error) {
|
|
12715
12763
|
this.logger.warn("Failed to flush logs before Slack relay", {
|
|
12716
12764
|
taskId: payload.task_id,
|
|
@@ -12859,7 +12907,9 @@ Important:
|
|
|
12859
12907
|
this.logger.error("Failed to capture final tree state", error);
|
|
12860
12908
|
}
|
|
12861
12909
|
try {
|
|
12862
|
-
await this.session.logWriter.flush(this.session.payload.run_id
|
|
12910
|
+
await this.session.logWriter.flush(this.session.payload.run_id, {
|
|
12911
|
+
coalesce: true
|
|
12912
|
+
});
|
|
12863
12913
|
} catch (error) {
|
|
12864
12914
|
this.logger.error("Failed to flush session logs", error);
|
|
12865
12915
|
}
|