@copilotkit/runtime 1.56.3 → 1.56.4-canary.1777529757
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/converters/tanstack.cjs +121 -25
- package/dist/agent/converters/tanstack.cjs.map +1 -1
- package/dist/agent/converters/tanstack.d.cts.map +1 -1
- package/dist/agent/converters/tanstack.d.mts.map +1 -1
- package/dist/agent/converters/tanstack.mjs +121 -25
- package/dist/agent/converters/tanstack.mjs.map +1 -1
- package/dist/lib/runtime/agent-integrations/langgraph/agent.cjs +8 -1
- package/dist/lib/runtime/agent-integrations/langgraph/agent.cjs.map +1 -1
- package/dist/lib/runtime/agent-integrations/langgraph/agent.d.cts.map +1 -1
- package/dist/lib/runtime/agent-integrations/langgraph/agent.d.mts.map +1 -1
- package/dist/lib/runtime/agent-integrations/langgraph/agent.mjs +8 -1
- package/dist/lib/runtime/agent-integrations/langgraph/agent.mjs.map +1 -1
- package/dist/package.cjs +6 -6
- package/dist/package.mjs +6 -6
- package/dist/v2/index.d.cts +2 -2
- package/dist/v2/index.d.mts +2 -2
- package/dist/v2/runtime/core/fetch-handler.cjs +2 -0
- package/dist/v2/runtime/core/fetch-handler.cjs.map +1 -1
- package/dist/v2/runtime/core/fetch-handler.d.cts.map +1 -1
- package/dist/v2/runtime/core/fetch-handler.d.mts.map +1 -1
- package/dist/v2/runtime/core/fetch-handler.mjs +2 -0
- package/dist/v2/runtime/core/fetch-handler.mjs.map +1 -1
- package/dist/v2/runtime/core/runtime.d.mts +0 -1
- package/dist/v2/runtime/core/runtime.d.mts.map +1 -1
- package/dist/v2/runtime/endpoints/express.cjs +5 -5
- package/dist/v2/runtime/endpoints/express.cjs.map +1 -1
- package/dist/v2/runtime/endpoints/express.mjs +5 -5
- package/dist/v2/runtime/endpoints/express.mjs.map +1 -1
- package/dist/v2/runtime/handlers/handle-connect.cjs +2 -3
- package/dist/v2/runtime/handlers/handle-connect.cjs.map +1 -1
- package/dist/v2/runtime/handlers/handle-connect.mjs +2 -3
- package/dist/v2/runtime/handlers/handle-connect.mjs.map +1 -1
- package/dist/v2/runtime/handlers/intelligence/connect.cjs +21 -31
- package/dist/v2/runtime/handlers/intelligence/connect.cjs.map +1 -1
- package/dist/v2/runtime/handlers/intelligence/connect.mjs +22 -31
- package/dist/v2/runtime/handlers/intelligence/connect.mjs.map +1 -1
- package/dist/v2/runtime/handlers/intelligence/run.cjs +111 -26
- package/dist/v2/runtime/handlers/intelligence/run.cjs.map +1 -1
- package/dist/v2/runtime/handlers/intelligence/run.mjs +111 -26
- package/dist/v2/runtime/handlers/intelligence/run.mjs.map +1 -1
- package/dist/v2/runtime/handlers/shared/intelligence-utils.cjs +7 -3
- package/dist/v2/runtime/handlers/shared/intelligence-utils.cjs.map +1 -1
- package/dist/v2/runtime/handlers/shared/intelligence-utils.mjs +7 -3
- package/dist/v2/runtime/handlers/shared/intelligence-utils.mjs.map +1 -1
- package/dist/v2/runtime/index.d.cts +1 -1
- package/dist/v2/runtime/index.d.mts +1 -2
- package/dist/v2/runtime/index.d.mts.map +1 -1
- package/dist/v2/runtime/intelligence-platform/client.cjs +5 -2
- package/dist/v2/runtime/intelligence-platform/client.cjs.map +1 -1
- package/dist/v2/runtime/intelligence-platform/client.d.cts +16 -18
- package/dist/v2/runtime/intelligence-platform/client.d.cts.map +1 -1
- package/dist/v2/runtime/intelligence-platform/client.d.mts +16 -18
- package/dist/v2/runtime/intelligence-platform/client.d.mts.map +1 -1
- package/dist/v2/runtime/intelligence-platform/client.mjs +5 -2
- package/dist/v2/runtime/intelligence-platform/client.mjs.map +1 -1
- package/dist/v2/runtime/runner/agent-runner.cjs.map +1 -1
- package/dist/v2/runtime/runner/agent-runner.d.cts +0 -1
- package/dist/v2/runtime/runner/agent-runner.d.cts.map +1 -1
- package/dist/v2/runtime/runner/agent-runner.d.mts +0 -1
- package/dist/v2/runtime/runner/agent-runner.d.mts.map +1 -1
- package/dist/v2/runtime/runner/agent-runner.mjs.map +1 -1
- package/dist/v2/runtime/runner/index.d.cts +1 -1
- package/dist/v2/runtime/runner/index.d.mts +1 -1
- package/dist/v2/runtime/runner/intelligence.cjs +30 -5
- package/dist/v2/runtime/runner/intelligence.cjs.map +1 -1
- package/dist/v2/runtime/runner/intelligence.d.cts +7 -1
- package/dist/v2/runtime/runner/intelligence.d.cts.map +1 -1
- package/dist/v2/runtime/runner/intelligence.d.mts +7 -1
- package/dist/v2/runtime/runner/intelligence.d.mts.map +1 -1
- package/dist/v2/runtime/runner/intelligence.mjs +30 -5
- package/dist/v2/runtime/runner/intelligence.mjs.map +1 -1
- package/dist/v2/runtime/telemetry/instance-created.cjs +33 -0
- package/dist/v2/runtime/telemetry/instance-created.cjs.map +1 -0
- package/dist/v2/runtime/telemetry/instance-created.mjs +33 -0
- package/dist/v2/runtime/telemetry/instance-created.mjs.map +1 -0
- package/dist/v2/runtime/telemetry/telemetry-client.cjs +1 -38
- package/dist/v2/runtime/telemetry/telemetry-client.cjs.map +1 -1
- package/dist/v2/runtime/telemetry/telemetry-client.mjs +1 -37
- package/dist/v2/runtime/telemetry/telemetry-client.mjs.map +1 -1
- package/package.json +7 -7
- package/src/agent/__tests__/agent-test-helpers.ts +31 -1
- package/src/agent/__tests__/converter-tanstack.test.ts +280 -0
- package/src/agent/converters/tanstack.ts +167 -10
- package/src/lib/runtime/agent-integrations/langgraph/agent.ts +8 -1
- package/src/v2/runtime/__tests__/express-fetch-bridge.test.ts +1 -1
- package/src/v2/runtime/__tests__/express-single-telemetry.integration.test.ts +65 -0
- package/src/v2/runtime/__tests__/express-telemetry.integration.test.ts +101 -0
- package/src/v2/runtime/__tests__/handle-connect.test.ts +155 -48
- package/src/v2/runtime/__tests__/handle-run.test.ts +380 -29
- package/src/v2/runtime/__tests__/hono-single-telemetry.integration.test.ts +46 -0
- package/src/v2/runtime/__tests__/hono-telemetry.integration.test.ts +99 -0
- package/src/v2/runtime/__tests__/intelligence-run-telemetry.test.ts +194 -0
- package/src/v2/runtime/__tests__/sse-response-telemetry.test.ts +108 -0
- package/src/v2/runtime/__tests__/telemetry.test.ts +0 -61
- package/src/v2/runtime/core/fetch-handler.ts +3 -0
- package/src/v2/runtime/endpoints/express.ts +9 -3
- package/src/v2/runtime/handlers/handle-connect.ts +1 -2
- package/src/v2/runtime/handlers/intelligence/connect.ts +48 -68
- package/src/v2/runtime/handlers/intelligence/run.ts +162 -21
- package/src/v2/runtime/handlers/shared/intelligence-utils.ts +21 -1
- package/src/v2/runtime/intelligence-platform/__tests__/client.test.ts +33 -39
- package/src/v2/runtime/intelligence-platform/client.ts +36 -31
- package/src/v2/runtime/runner/__tests__/intelligence-runner.test.ts +15 -7
- package/src/v2/runtime/runner/agent-runner.ts +0 -1
- package/src/v2/runtime/runner/intelligence.ts +47 -6
- package/src/v2/runtime/telemetry/__tests__/instance-created.test.ts +96 -0
- package/src/v2/runtime/telemetry/instance-created.ts +44 -0
- package/src/v2/runtime/telemetry/telemetry-client.ts +1 -57
- package/dist/v2/runtime/intelligence-platform/index.d.mts +0 -2
- package/dist/v2/runtime/telemetry/utils.cjs +0 -15
- package/dist/v2/runtime/telemetry/utils.cjs.map +0 -1
- package/dist/v2/runtime/telemetry/utils.mjs +0 -14
- package/dist/v2/runtime/telemetry/utils.mjs.map +0 -1
- package/src/v2/runtime/telemetry/utils.ts +0 -15
|
@@ -619,10 +619,9 @@ describe("IntelligenceAgentRunner", () => {
|
|
|
619
619
|
});
|
|
620
620
|
});
|
|
621
621
|
|
|
622
|
-
describe("run
|
|
623
|
-
it("uses
|
|
622
|
+
describe("run channel ownership", () => {
|
|
623
|
+
it("uses runId for the ingestion channel topic", async () => {
|
|
624
624
|
const threadId = "t-jc";
|
|
625
|
-
const joinCode = "join-abc-123";
|
|
626
625
|
const input = createRunInput({ threadId, runId: "r-jc" });
|
|
627
626
|
const agent = new MockAgent([
|
|
628
627
|
{
|
|
@@ -633,15 +632,16 @@ describe("IntelligenceAgentRunner", () => {
|
|
|
633
632
|
]);
|
|
634
633
|
|
|
635
634
|
const eventsPromise = collectEvents(
|
|
636
|
-
runner.run({ threadId, agent, input
|
|
635
|
+
runner.run({ threadId, agent, input }),
|
|
637
636
|
);
|
|
638
637
|
const ch = mockChannels[0];
|
|
639
|
-
expect(ch.topic).toBe(
|
|
638
|
+
expect(ch.topic).toBe("ingestion:r-jc");
|
|
639
|
+
expect(ch.params).toEqual({ thread_id: threadId, run_id: "r-jc" });
|
|
640
640
|
ch.triggerJoin("ok");
|
|
641
641
|
await eventsPromise;
|
|
642
642
|
});
|
|
643
643
|
|
|
644
|
-
it("
|
|
644
|
+
it("keeps pushed event payload ownership on canonical threadId and runId", async () => {
|
|
645
645
|
const threadId = "t-no-jc";
|
|
646
646
|
const input = createRunInput({ threadId, runId: "r-no-jc" });
|
|
647
647
|
const agent = new MockAgent([
|
|
@@ -656,9 +656,17 @@ describe("IntelligenceAgentRunner", () => {
|
|
|
656
656
|
runner.run({ threadId, agent, input }),
|
|
657
657
|
);
|
|
658
658
|
const ch = mockChannels[0];
|
|
659
|
-
expect(ch.topic).toBe(`ingestion:${threadId}`);
|
|
660
659
|
ch.triggerJoin("ok");
|
|
661
660
|
await eventsPromise;
|
|
661
|
+
|
|
662
|
+
expect(ch.pushLog[0].payload).toEqual(
|
|
663
|
+
expect.objectContaining({
|
|
664
|
+
threadId,
|
|
665
|
+
runId: "r-no-jc",
|
|
666
|
+
thread_id: threadId,
|
|
667
|
+
run_id: "r-no-jc",
|
|
668
|
+
}),
|
|
669
|
+
);
|
|
662
670
|
});
|
|
663
671
|
});
|
|
664
672
|
|
|
@@ -32,6 +32,11 @@ export interface IntelligenceAgentRunnerOptions {
|
|
|
32
32
|
maxRejoinMs?: number;
|
|
33
33
|
}
|
|
34
34
|
|
|
35
|
+
export interface RunnerStartupBoundary {
|
|
36
|
+
events: Observable<BaseEvent>;
|
|
37
|
+
startup: Promise<void>;
|
|
38
|
+
}
|
|
39
|
+
|
|
35
40
|
interface ThreadState {
|
|
36
41
|
socket: Socket;
|
|
37
42
|
channel: Channel;
|
|
@@ -153,7 +158,36 @@ export class IntelligenceAgentRunner extends AgentRunner {
|
|
|
153
158
|
}
|
|
154
159
|
|
|
155
160
|
run(request: AgentRunnerRunRequest): Observable<BaseEvent> {
|
|
156
|
-
|
|
161
|
+
return this.createRunObservable(request);
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
runWithStartupBoundary(
|
|
165
|
+
request: AgentRunnerRunRequest,
|
|
166
|
+
): RunnerStartupBoundary {
|
|
167
|
+
let resolveStartup: (() => void) | undefined;
|
|
168
|
+
let rejectStartup: ((reason: Error) => void) | undefined;
|
|
169
|
+
const startup = new Promise<void>((resolve, reject) => {
|
|
170
|
+
resolveStartup = resolve;
|
|
171
|
+
rejectStartup = reject;
|
|
172
|
+
});
|
|
173
|
+
|
|
174
|
+
return {
|
|
175
|
+
events: this.createRunObservable(request, {
|
|
176
|
+
resolveStartup: () => resolveStartup?.(),
|
|
177
|
+
rejectStartup: (error) => rejectStartup?.(error),
|
|
178
|
+
}),
|
|
179
|
+
startup,
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
private createRunObservable(
|
|
184
|
+
request: AgentRunnerRunRequest,
|
|
185
|
+
startupBoundary?: {
|
|
186
|
+
resolveStartup: () => void;
|
|
187
|
+
rejectStartup: (error: Error) => void;
|
|
188
|
+
},
|
|
189
|
+
): Observable<BaseEvent> {
|
|
190
|
+
const { threadId, agent, input } = request;
|
|
157
191
|
|
|
158
192
|
const existing = this.threads.get(threadId);
|
|
159
193
|
if (existing?.isRunning) {
|
|
@@ -163,9 +197,9 @@ export class IntelligenceAgentRunner extends AgentRunner {
|
|
|
163
197
|
return new Observable((observer) => {
|
|
164
198
|
const socket = this.createSocket();
|
|
165
199
|
|
|
166
|
-
const
|
|
167
|
-
|
|
168
|
-
|
|
200
|
+
const channel = socket.channel(`ingestion:${input.runId}`, {
|
|
201
|
+
thread_id: threadId,
|
|
202
|
+
run_id: input.runId,
|
|
169
203
|
});
|
|
170
204
|
|
|
171
205
|
const state: ThreadState = {
|
|
@@ -229,30 +263,37 @@ export class IntelligenceAgentRunner extends AgentRunner {
|
|
|
229
263
|
channel
|
|
230
264
|
.join()
|
|
231
265
|
.receive("ok", () => {
|
|
266
|
+
startupBoundary?.resolveStartup();
|
|
232
267
|
this.executeAgentRun(request, state, threadId).subscribe({
|
|
233
268
|
complete: () => observer.complete(),
|
|
234
269
|
});
|
|
235
270
|
})
|
|
236
271
|
.receive("error", (resp) => {
|
|
272
|
+
const error = new Error(
|
|
273
|
+
`Failed to join channel: ${JSON.stringify(resp)}`,
|
|
274
|
+
);
|
|
237
275
|
const errorEvent = {
|
|
238
276
|
type: EventType.RUN_ERROR,
|
|
239
|
-
message:
|
|
277
|
+
message: error.message,
|
|
240
278
|
code: "CHANNEL_JOIN_ERROR",
|
|
241
279
|
} as BaseEvent;
|
|
242
280
|
observer.next(errorEvent);
|
|
243
281
|
state.currentEvents.push(errorEvent);
|
|
244
282
|
this.removeThread(threadId);
|
|
283
|
+
startupBoundary?.rejectStartup(error);
|
|
245
284
|
observer.complete();
|
|
246
285
|
})
|
|
247
286
|
.receive("timeout", () => {
|
|
287
|
+
const error = new Error("Timed out joining channel");
|
|
248
288
|
const errorEvent = {
|
|
249
289
|
type: EventType.RUN_ERROR,
|
|
250
|
-
message:
|
|
290
|
+
message: error.message,
|
|
251
291
|
code: "CHANNEL_JOIN_TIMEOUT",
|
|
252
292
|
} as BaseEvent;
|
|
253
293
|
observer.next(errorEvent);
|
|
254
294
|
state.currentEvents.push(errorEvent);
|
|
255
295
|
this.removeThread(threadId);
|
|
296
|
+
startupBoundary?.rejectStartup(error);
|
|
256
297
|
observer.complete();
|
|
257
298
|
});
|
|
258
299
|
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import { describe, it, expect, vi, beforeEach, afterEach } from "vitest";
|
|
2
|
+
import { telemetry } from "..";
|
|
3
|
+
import { fireInstanceCreatedTelemetry } from "../instance-created";
|
|
4
|
+
import type { CopilotRuntimeLike } from "../../core/runtime";
|
|
5
|
+
|
|
6
|
+
// Minimal runtime stub: we only use `agents` from CopilotRuntimeLike inside
|
|
7
|
+
// the helper, so we cast the stub rather than construct a full runtime.
|
|
8
|
+
function makeRuntime(
|
|
9
|
+
agents:
|
|
10
|
+
| Record<string, unknown>
|
|
11
|
+
| Promise<Record<string, unknown>>
|
|
12
|
+
| ((ctx: { request: Request }) => Record<string, unknown>),
|
|
13
|
+
): CopilotRuntimeLike {
|
|
14
|
+
return { agents } as unknown as CopilotRuntimeLike;
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
describe("fireInstanceCreatedTelemetry", () => {
|
|
18
|
+
let captureSpy: ReturnType<typeof vi.spyOn>;
|
|
19
|
+
|
|
20
|
+
beforeEach(() => {
|
|
21
|
+
captureSpy = vi.spyOn(telemetry, "capture").mockResolvedValue(undefined);
|
|
22
|
+
});
|
|
23
|
+
|
|
24
|
+
afterEach(() => {
|
|
25
|
+
captureSpy.mockRestore();
|
|
26
|
+
});
|
|
27
|
+
|
|
28
|
+
it("captures instance_created with agent count from static agents record", async () => {
|
|
29
|
+
fireInstanceCreatedTelemetry({
|
|
30
|
+
runtime: makeRuntime({ a1: {}, a2: {}, a3: {} }),
|
|
31
|
+
});
|
|
32
|
+
|
|
33
|
+
await vi.waitFor(() => expect(captureSpy).toHaveBeenCalled());
|
|
34
|
+
|
|
35
|
+
expect(captureSpy).toHaveBeenCalledWith("oss.runtime.instance_created", {
|
|
36
|
+
actionsAmount: 0,
|
|
37
|
+
endpointTypes: [],
|
|
38
|
+
endpointsAmount: 0,
|
|
39
|
+
agentsAmount: 3,
|
|
40
|
+
"cloud.api_key_provided": false,
|
|
41
|
+
});
|
|
42
|
+
});
|
|
43
|
+
|
|
44
|
+
it("awaits Promise-based agents before capturing", async () => {
|
|
45
|
+
fireInstanceCreatedTelemetry({
|
|
46
|
+
runtime: makeRuntime(Promise.resolve({ only: {} })),
|
|
47
|
+
});
|
|
48
|
+
|
|
49
|
+
await vi.waitFor(() => expect(captureSpy).toHaveBeenCalled());
|
|
50
|
+
|
|
51
|
+
const call = captureSpy.mock.calls[0][1] as { agentsAmount: number | null };
|
|
52
|
+
expect(call.agentsAmount).toBe(1);
|
|
53
|
+
});
|
|
54
|
+
|
|
55
|
+
it("reports agentsAmount: null when agents is a factory (cannot resolve without request)", async () => {
|
|
56
|
+
fireInstanceCreatedTelemetry({
|
|
57
|
+
runtime: makeRuntime(() => ({ x: {} })),
|
|
58
|
+
});
|
|
59
|
+
|
|
60
|
+
await vi.waitFor(() => expect(captureSpy).toHaveBeenCalled());
|
|
61
|
+
|
|
62
|
+
const call = captureSpy.mock.calls[0][1] as { agentsAmount: number | null };
|
|
63
|
+
expect(call.agentsAmount).toBeNull();
|
|
64
|
+
});
|
|
65
|
+
|
|
66
|
+
it("does not hardcode cloud.api_key_provided — it is false at handler-creation time by design (key arrives per-request via header)", async () => {
|
|
67
|
+
fireInstanceCreatedTelemetry({
|
|
68
|
+
runtime: makeRuntime({ a1: {} }),
|
|
69
|
+
});
|
|
70
|
+
|
|
71
|
+
await vi.waitFor(() => expect(captureSpy).toHaveBeenCalled());
|
|
72
|
+
|
|
73
|
+
const call = captureSpy.mock.calls[0][1] as {
|
|
74
|
+
"cloud.api_key_provided": boolean;
|
|
75
|
+
};
|
|
76
|
+
expect(call["cloud.api_key_provided"]).toBe(false);
|
|
77
|
+
});
|
|
78
|
+
|
|
79
|
+
it("does not throw or reject when agents Promise rejects", async () => {
|
|
80
|
+
// Swallow the unhandled rejection from the input Promise itself — the
|
|
81
|
+
// Promise we pass in rejects synchronously regardless of whether we
|
|
82
|
+
// attach a .catch downstream.
|
|
83
|
+
const rejectingAgents = Promise.reject(new Error("boom"));
|
|
84
|
+
rejectingAgents.catch(() => {});
|
|
85
|
+
|
|
86
|
+
expect(() =>
|
|
87
|
+
fireInstanceCreatedTelemetry({
|
|
88
|
+
runtime: makeRuntime(rejectingAgents as any),
|
|
89
|
+
}),
|
|
90
|
+
).not.toThrow();
|
|
91
|
+
|
|
92
|
+
// Wait a microtask to let the internal catch fire; no capture should happen.
|
|
93
|
+
await new Promise((resolve) => setTimeout(resolve, 10));
|
|
94
|
+
expect(captureSpy).not.toHaveBeenCalled();
|
|
95
|
+
});
|
|
96
|
+
});
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import { telemetry } from ".";
|
|
2
|
+
import type { CopilotRuntimeLike } from "../core/runtime";
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Fire the `oss.runtime.instance_created` telemetry event for a v2 runtime
|
|
6
|
+
* handler. Called once per handler factory invocation (not per request).
|
|
7
|
+
*
|
|
8
|
+
* v2 does not have a concept of remote endpoints or standalone actions, so
|
|
9
|
+
* those counts are 0 / []. `cloud.api_key_provided` is false at this level
|
|
10
|
+
* because in v2 the cloud public key arrives per-request via the
|
|
11
|
+
* `x-copilotcloud-public-api-key` header — not at handler creation time.
|
|
12
|
+
* See `handlers/handle-run.ts` for the per-request event that DOES carry
|
|
13
|
+
* the key when present.
|
|
14
|
+
*
|
|
15
|
+
* Errors resolving agents are swallowed — telemetry must never break
|
|
16
|
+
* runtime setup.
|
|
17
|
+
*/
|
|
18
|
+
export function fireInstanceCreatedTelemetry({
|
|
19
|
+
runtime,
|
|
20
|
+
}: {
|
|
21
|
+
runtime: CopilotRuntimeLike;
|
|
22
|
+
}): void {
|
|
23
|
+
// agents can be a static Record, a Promise, or a per-request factory.
|
|
24
|
+
// Factory configs cannot be resolved at handler-creation time (no Request
|
|
25
|
+
// context), so report agentsAmount as null in that case.
|
|
26
|
+
const agentsPromise =
|
|
27
|
+
typeof runtime.agents === "function"
|
|
28
|
+
? Promise.resolve<Record<string, unknown> | null>(null)
|
|
29
|
+
: Promise.resolve(runtime.agents);
|
|
30
|
+
|
|
31
|
+
agentsPromise
|
|
32
|
+
.then((agents) => {
|
|
33
|
+
telemetry.capture("oss.runtime.instance_created", {
|
|
34
|
+
actionsAmount: 0,
|
|
35
|
+
endpointTypes: [],
|
|
36
|
+
endpointsAmount: 0,
|
|
37
|
+
agentsAmount: agents ? Object.keys(agents).length : null,
|
|
38
|
+
"cloud.api_key_provided": false,
|
|
39
|
+
});
|
|
40
|
+
})
|
|
41
|
+
.catch(() => {
|
|
42
|
+
// Swallow — telemetry must not break runtime creation.
|
|
43
|
+
});
|
|
44
|
+
}
|
|
@@ -1,7 +1,4 @@
|
|
|
1
|
-
import { Analytics } from "@segment/analytics-node";
|
|
2
1
|
import { AnalyticsEvents } from "./events";
|
|
3
|
-
import { flattenObject } from "./utils";
|
|
4
|
-
import { v4 as uuidv4 } from "uuid";
|
|
5
2
|
import scarfClient from "./scarf-client";
|
|
6
3
|
|
|
7
4
|
export function isTelemetryDisabled(): boolean {
|
|
@@ -17,11 +14,8 @@ export function isTelemetryDisabled(): boolean {
|
|
|
17
14
|
}
|
|
18
15
|
|
|
19
16
|
export class TelemetryClient {
|
|
20
|
-
segment: Analytics | undefined;
|
|
21
|
-
globalProperties: Record<string, any> = {};
|
|
22
17
|
private telemetryDisabled: boolean = false;
|
|
23
18
|
private sampleRate: number = 0.05;
|
|
24
|
-
private anonymousId = `anon_${uuidv4()}`;
|
|
25
19
|
|
|
26
20
|
constructor({
|
|
27
21
|
telemetryDisabled,
|
|
@@ -31,21 +25,7 @@ export class TelemetryClient {
|
|
|
31
25
|
sampleRate?: number;
|
|
32
26
|
} = {}) {
|
|
33
27
|
this.telemetryDisabled = telemetryDisabled ?? isTelemetryDisabled();
|
|
34
|
-
|
|
35
|
-
if (this.telemetryDisabled) {
|
|
36
|
-
this.setSampleRate(sampleRate);
|
|
37
|
-
return;
|
|
38
|
-
}
|
|
39
|
-
|
|
40
28
|
this.setSampleRate(sampleRate);
|
|
41
|
-
|
|
42
|
-
const writeKey =
|
|
43
|
-
process.env.COPILOTKIT_SEGMENT_WRITE_KEY ||
|
|
44
|
-
"n7XAZtQCGS2v1vvBy3LgBCv2h3Y8whja";
|
|
45
|
-
|
|
46
|
-
this.segment = new Analytics({
|
|
47
|
-
writeKey,
|
|
48
|
-
});
|
|
49
29
|
}
|
|
50
30
|
|
|
51
31
|
private shouldSendEvent() {
|
|
@@ -58,48 +38,17 @@ export class TelemetryClient {
|
|
|
58
38
|
|
|
59
39
|
async capture<K extends keyof AnalyticsEvents>(
|
|
60
40
|
event: K,
|
|
61
|
-
|
|
41
|
+
_properties: AnalyticsEvents[K],
|
|
62
42
|
) {
|
|
63
43
|
if (!this.shouldSendEvent()) {
|
|
64
44
|
return;
|
|
65
45
|
}
|
|
66
46
|
|
|
67
|
-
const flattenedProperties = flattenObject(properties);
|
|
68
|
-
const propertiesWithGlobal = {
|
|
69
|
-
...this.globalProperties,
|
|
70
|
-
...flattenedProperties,
|
|
71
|
-
};
|
|
72
|
-
const orderedPropertiesWithGlobal = Object.keys(propertiesWithGlobal)
|
|
73
|
-
.sort()
|
|
74
|
-
.reduce(
|
|
75
|
-
(obj, key) => {
|
|
76
|
-
obj[key] = propertiesWithGlobal[key];
|
|
77
|
-
return obj;
|
|
78
|
-
},
|
|
79
|
-
{} as Record<string, any>,
|
|
80
|
-
);
|
|
81
|
-
|
|
82
|
-
if (this.segment) {
|
|
83
|
-
this.segment.track({
|
|
84
|
-
anonymousId: this.anonymousId,
|
|
85
|
-
event,
|
|
86
|
-
properties: { ...orderedPropertiesWithGlobal },
|
|
87
|
-
});
|
|
88
|
-
}
|
|
89
|
-
|
|
90
47
|
await scarfClient.logEvent({
|
|
91
48
|
event,
|
|
92
49
|
});
|
|
93
50
|
}
|
|
94
51
|
|
|
95
|
-
setGlobalProperties(properties: Record<string, any>) {
|
|
96
|
-
const flattenedProperties = flattenObject(properties);
|
|
97
|
-
this.globalProperties = {
|
|
98
|
-
...this.globalProperties,
|
|
99
|
-
...flattenedProperties,
|
|
100
|
-
};
|
|
101
|
-
}
|
|
102
|
-
|
|
103
52
|
private setSampleRate(sampleRate: number | undefined) {
|
|
104
53
|
let _sampleRate: number;
|
|
105
54
|
|
|
@@ -114,11 +63,6 @@ export class TelemetryClient {
|
|
|
114
63
|
}
|
|
115
64
|
|
|
116
65
|
this.sampleRate = _sampleRate;
|
|
117
|
-
this.setGlobalProperties({
|
|
118
|
-
sampleRate: this.sampleRate,
|
|
119
|
-
sampleRateAdjustmentFactor: 1 - this.sampleRate,
|
|
120
|
-
sampleWeight: 1 / this.sampleRate,
|
|
121
|
-
});
|
|
122
66
|
}
|
|
123
67
|
}
|
|
124
68
|
|
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
require("reflect-metadata");
|
|
2
|
-
|
|
3
|
-
//#region src/v2/runtime/telemetry/utils.ts
|
|
4
|
-
function flattenObject(obj, parentKey = "", res = {}) {
|
|
5
|
-
for (const key in obj) {
|
|
6
|
-
const propName = parentKey ? `${parentKey}.${key}` : key;
|
|
7
|
-
if (typeof obj[key] === "object" && obj[key] !== null) flattenObject(obj[key], propName, res);
|
|
8
|
-
else res[propName] = obj[key];
|
|
9
|
-
}
|
|
10
|
-
return res;
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
//#endregion
|
|
14
|
-
exports.flattenObject = flattenObject;
|
|
15
|
-
//# sourceMappingURL=utils.cjs.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"utils.cjs","names":[],"sources":["../../../../src/v2/runtime/telemetry/utils.ts"],"sourcesContent":["export function flattenObject(\n obj: Record<string, any>,\n parentKey = \"\",\n res: Record<string, any> = {},\n): Record<string, any> {\n for (const key in obj) {\n const propName = parentKey ? `${parentKey}.${key}` : key;\n if (typeof obj[key] === \"object\" && obj[key] !== null) {\n flattenObject(obj[key], propName, res);\n } else {\n res[propName] = obj[key];\n }\n }\n return res;\n}\n"],"mappings":";;;AAAA,SAAgB,cACd,KACA,YAAY,IACZ,MAA2B,EAAE,EACR;AACrB,MAAK,MAAM,OAAO,KAAK;EACrB,MAAM,WAAW,YAAY,GAAG,UAAU,GAAG,QAAQ;AACrD,MAAI,OAAO,IAAI,SAAS,YAAY,IAAI,SAAS,KAC/C,eAAc,IAAI,MAAM,UAAU,IAAI;MAEtC,KAAI,YAAY,IAAI;;AAGxB,QAAO"}
|
|
@@ -1,14 +0,0 @@
|
|
|
1
|
-
import "reflect-metadata";
|
|
2
|
-
//#region src/v2/runtime/telemetry/utils.ts
|
|
3
|
-
function flattenObject(obj, parentKey = "", res = {}) {
|
|
4
|
-
for (const key in obj) {
|
|
5
|
-
const propName = parentKey ? `${parentKey}.${key}` : key;
|
|
6
|
-
if (typeof obj[key] === "object" && obj[key] !== null) flattenObject(obj[key], propName, res);
|
|
7
|
-
else res[propName] = obj[key];
|
|
8
|
-
}
|
|
9
|
-
return res;
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
//#endregion
|
|
13
|
-
export { flattenObject };
|
|
14
|
-
//# sourceMappingURL=utils.mjs.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"utils.mjs","names":[],"sources":["../../../../src/v2/runtime/telemetry/utils.ts"],"sourcesContent":["export function flattenObject(\n obj: Record<string, any>,\n parentKey = \"\",\n res: Record<string, any> = {},\n): Record<string, any> {\n for (const key in obj) {\n const propName = parentKey ? `${parentKey}.${key}` : key;\n if (typeof obj[key] === \"object\" && obj[key] !== null) {\n flattenObject(obj[key], propName, res);\n } else {\n res[propName] = obj[key];\n }\n }\n return res;\n}\n"],"mappings":";;AAAA,SAAgB,cACd,KACA,YAAY,IACZ,MAA2B,EAAE,EACR;AACrB,MAAK,MAAM,OAAO,KAAK;EACrB,MAAM,WAAW,YAAY,GAAG,UAAU,GAAG,QAAQ;AACrD,MAAI,OAAO,IAAI,SAAS,YAAY,IAAI,SAAS,KAC/C,eAAc,IAAI,MAAM,UAAU,IAAI;MAEtC,KAAI,YAAY,IAAI;;AAGxB,QAAO"}
|
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
export function flattenObject(
|
|
2
|
-
obj: Record<string, any>,
|
|
3
|
-
parentKey = "",
|
|
4
|
-
res: Record<string, any> = {},
|
|
5
|
-
): Record<string, any> {
|
|
6
|
-
for (const key in obj) {
|
|
7
|
-
const propName = parentKey ? `${parentKey}.${key}` : key;
|
|
8
|
-
if (typeof obj[key] === "object" && obj[key] !== null) {
|
|
9
|
-
flattenObject(obj[key], propName, res);
|
|
10
|
-
} else {
|
|
11
|
-
res[propName] = obj[key];
|
|
12
|
-
}
|
|
13
|
-
}
|
|
14
|
-
return res;
|
|
15
|
-
}
|