kanna-code 0.26.5 → 0.26.7
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/client/assets/index-CH3ZbXse.js +2583 -0
- package/dist/client/index.html +1 -1
- package/package.json +1 -1
- package/src/server/agent.ts +128 -0
- package/src/server/event-store.test.ts +102 -5
- package/src/server/event-store.ts +73 -17
- package/src/server/ws-router.test.ts +80 -0
- package/src/server/ws-router.ts +63 -2
- package/src/shared/protocol.ts +2 -0
- package/dist/client/assets/index-BaEB4jie.js +0 -2583
package/src/server/ws-router.ts
CHANGED
|
@@ -15,9 +15,32 @@ import { deriveChatSnapshot, deriveLocalProjectsSnapshot, deriveSidebarData } fr
|
|
|
15
15
|
|
|
16
16
|
const DEFAULT_CHAT_RECENT_LIMIT = 200
|
|
17
17
|
|
|
18
|
+
function isSendToStartingProfilingEnabled() {
|
|
19
|
+
return process.env.KANNA_PROFILE_SEND_TO_STARTING === "1"
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
function logSendToStartingProfile(
|
|
23
|
+
traceId: string | null | undefined,
|
|
24
|
+
startedAt: number | null | undefined,
|
|
25
|
+
stage: string,
|
|
26
|
+
details?: Record<string, unknown>
|
|
27
|
+
) {
|
|
28
|
+
if (!traceId || startedAt === undefined || startedAt === null || !isSendToStartingProfilingEnabled()) {
|
|
29
|
+
return
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
console.log("[kanna/send->starting][server]", JSON.stringify({
|
|
33
|
+
traceId,
|
|
34
|
+
stage,
|
|
35
|
+
elapsedMs: Number((performance.now() - startedAt).toFixed(1)),
|
|
36
|
+
...details,
|
|
37
|
+
}))
|
|
38
|
+
}
|
|
39
|
+
|
|
18
40
|
export interface ClientState {
|
|
19
41
|
subscriptions: Map<string, SubscriptionTopic>
|
|
20
42
|
snapshotSignatures: Map<string, string>
|
|
43
|
+
protectedDraftChatIds?: Set<string>
|
|
21
44
|
}
|
|
22
45
|
|
|
23
46
|
interface CreateWsRouterArgs {
|
|
@@ -83,9 +106,28 @@ export function createWsRouter({
|
|
|
83
106
|
])
|
|
84
107
|
}
|
|
85
108
|
|
|
86
|
-
|
|
109
|
+
function getProtectedDraftChatIds(extraSockets?: Iterable<ServerWebSocket<ClientState>>) {
|
|
110
|
+
const protectedChatIds = new Set<string>()
|
|
111
|
+
|
|
112
|
+
for (const socket of sockets) {
|
|
113
|
+
for (const chatId of socket.data.protectedDraftChatIds ?? []) {
|
|
114
|
+
protectedChatIds.add(chatId)
|
|
115
|
+
}
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
for (const socket of extraSockets ?? []) {
|
|
119
|
+
for (const chatId of socket.data.protectedDraftChatIds ?? []) {
|
|
120
|
+
protectedChatIds.add(chatId)
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
return protectedChatIds
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
async function maybePruneStaleEmptyChats(extraSockets?: Iterable<ServerWebSocket<ClientState>>) {
|
|
87
128
|
await store.pruneStaleEmptyChats?.({
|
|
88
129
|
activeChatIds: getProtectedChatIds(),
|
|
130
|
+
protectedChatIds: getProtectedDraftChatIds(extraSockets),
|
|
89
131
|
})
|
|
90
132
|
}
|
|
91
133
|
|
|
@@ -194,7 +236,7 @@ export function createWsRouter({
|
|
|
194
236
|
|
|
195
237
|
async function pushSnapshots(ws: ServerWebSocket<ClientState>, options?: { skipPrune?: boolean }) {
|
|
196
238
|
if (!options?.skipPrune) {
|
|
197
|
-
await maybePruneStaleEmptyChats()
|
|
239
|
+
await maybePruneStaleEmptyChats([ws])
|
|
198
240
|
}
|
|
199
241
|
const snapshotSignatures = ensureSnapshotSignatures(ws)
|
|
200
242
|
for (const [id, topic] of ws.data.subscriptions.entries()) {
|
|
@@ -205,6 +247,14 @@ export function createWsRouter({
|
|
|
205
247
|
continue
|
|
206
248
|
}
|
|
207
249
|
snapshotSignatures.set(id, signature)
|
|
250
|
+
if (topic.type === "chat" && envelope.snapshot.type === "chat" && envelope.snapshot.data?.runtime.status === "starting") {
|
|
251
|
+
const profile = agent.getActiveTurnProfile(topic.chatId)
|
|
252
|
+
logSendToStartingProfile(profile?.traceId, profile?.startedAt, "ws.snapshot_sent", {
|
|
253
|
+
chatId: topic.chatId,
|
|
254
|
+
status: envelope.snapshot.data.runtime.status,
|
|
255
|
+
messageCount: envelope.snapshot.data.messages.length,
|
|
256
|
+
})
|
|
257
|
+
}
|
|
208
258
|
send(ws, envelope)
|
|
209
259
|
}
|
|
210
260
|
}
|
|
@@ -410,8 +460,19 @@ export function createWsRouter({
|
|
|
410
460
|
send(ws, { v: PROTOCOL_VERSION, type: "ack", id })
|
|
411
461
|
break
|
|
412
462
|
}
|
|
463
|
+
case "chat.setDraftProtection": {
|
|
464
|
+
ws.data.protectedDraftChatIds = new Set(command.chatIds)
|
|
465
|
+
send(ws, { v: PROTOCOL_VERSION, type: "ack", id })
|
|
466
|
+
break
|
|
467
|
+
}
|
|
413
468
|
case "chat.send": {
|
|
414
469
|
const result = await agent.send(command)
|
|
470
|
+
const profile = command.clientTraceId && result.chatId
|
|
471
|
+
? agent.getActiveTurnProfile(result.chatId)
|
|
472
|
+
: null
|
|
473
|
+
logSendToStartingProfile(profile?.traceId ?? command.clientTraceId, profile?.startedAt, "ws.chat_send_ack", {
|
|
474
|
+
chatId: result.chatId ?? null,
|
|
475
|
+
})
|
|
415
476
|
send(ws, { v: PROTOCOL_VERSION, type: "ack", id, result })
|
|
416
477
|
break
|
|
417
478
|
}
|
package/src/shared/protocol.ts
CHANGED
|
@@ -67,11 +67,13 @@ export type ClientCommand =
|
|
|
67
67
|
| { type: "chat.create"; projectId: string }
|
|
68
68
|
| { type: "chat.rename"; chatId: string; title: string }
|
|
69
69
|
| { type: "chat.delete"; chatId: string }
|
|
70
|
+
| { type: "chat.setDraftProtection"; chatIds: string[] }
|
|
70
71
|
| { type: "chat.markRead"; chatId: string }
|
|
71
72
|
| {
|
|
72
73
|
type: "chat.send"
|
|
73
74
|
chatId?: string
|
|
74
75
|
projectId?: string
|
|
76
|
+
clientTraceId?: string
|
|
75
77
|
provider?: AgentProvider
|
|
76
78
|
content: string
|
|
77
79
|
attachments?: ChatAttachment[]
|