@zooid/transport-matrix 0.13.0 → 0.14.0
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/index.d.ts +152 -4
- package/dist/index.js +898 -94
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
- package/src/context-provider.test.ts +61 -4
- package/src/context-provider.ts +40 -2
- package/src/index.ts +23 -3
- package/src/invocation-registry.test.ts +22 -0
- package/src/invocation-registry.ts +32 -0
- package/src/matrix-client.ts +58 -34
- package/src/router.test.ts +129 -10
- package/src/router.ts +78 -2
- package/src/task-completion.test.ts +23 -0
- package/src/task-completion.ts +37 -0
- package/src/task-dispatch.test.ts +53 -0
- package/src/task-dispatch.ts +68 -0
- package/src/task-envelope.test.ts +27 -0
- package/src/task-registry.test.ts +50 -0
- package/src/task-registry.ts +152 -0
- package/src/transport.test.ts +403 -114
- package/src/transport.ts +719 -110
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { TransportContextProvider, HistoryOptions, HistoryPage, ThreadOverviewPage, Member,
|
|
1
|
+
import { TransportContextProvider, RoomBinding, HistoryOptions, HistoryPage, ThreadOverviewPage, Member, RoomInfo, SendMessageInput as SendMessageInput$1, SendMessageResult, AcpRegistry, ApprovalCorrelator, PendingInputRegistry, TaskActions, InvocationRecord, ThreadCompletion, ThreadStartContent } from '@zooid/core';
|
|
2
2
|
import * as hono_types from 'hono/types';
|
|
3
3
|
import { Hono } from 'hono';
|
|
4
4
|
|
|
@@ -16,12 +16,14 @@ interface SendMessageInput {
|
|
|
16
16
|
[k: string]: unknown;
|
|
17
17
|
};
|
|
18
18
|
threadRoot?: string;
|
|
19
|
+
txnId?: string;
|
|
19
20
|
}
|
|
20
21
|
interface SendCustomEventInput {
|
|
21
22
|
roomId: string;
|
|
22
23
|
asUserId: string;
|
|
23
24
|
eventType: string;
|
|
24
25
|
content: Record<string, unknown>;
|
|
26
|
+
txnId?: string;
|
|
25
27
|
}
|
|
26
28
|
interface SetTypingInput {
|
|
27
29
|
roomId: string;
|
|
@@ -192,6 +194,15 @@ interface MatrixContextProviderOpts {
|
|
|
192
194
|
asUserId: string;
|
|
193
195
|
/** Map of Matrix user IDs → agent names, for is_agent / agent_name flags. */
|
|
194
196
|
agentBots: Map<string, string>;
|
|
197
|
+
/**
|
|
198
|
+
* This agent's own room bindings — the live array `BotPool.bootstrap`
|
|
199
|
+
* rewrites `.alias` on in place, so reads through this field after
|
|
200
|
+
* bootstrap see canonical room IDs. Backs `getRooms()` and the
|
|
201
|
+
* `sendMessage()` authorization check. Absent/empty = no rooms known
|
|
202
|
+
* (context providers built before this field existed, or in tests that
|
|
203
|
+
* don't exercise either method).
|
|
204
|
+
*/
|
|
205
|
+
rooms?: RoomBinding[];
|
|
195
206
|
}
|
|
196
207
|
declare class MatrixContextProvider implements TransportContextProvider {
|
|
197
208
|
private readonly opts;
|
|
@@ -201,7 +212,9 @@ declare class MatrixContextProvider implements TransportContextProvider {
|
|
|
201
212
|
getThreadHistory(channelId: string, threadId: string, hopts: HistoryOptions): Promise<HistoryPage>;
|
|
202
213
|
private toMessage;
|
|
203
214
|
getChannelMembers(channelId: string): Promise<Member[]>;
|
|
204
|
-
|
|
215
|
+
getRoomInfo(channelId: string): Promise<RoomInfo>;
|
|
216
|
+
getRooms(): Promise<RoomInfo[]>;
|
|
217
|
+
sendMessage(input: SendMessageInput$1): Promise<SendMessageResult>;
|
|
205
218
|
}
|
|
206
219
|
|
|
207
220
|
interface MatrixTransportConfig {
|
|
@@ -290,6 +303,10 @@ interface ThreadState {
|
|
|
290
303
|
*/
|
|
291
304
|
handoffs: Record<string, string[]>;
|
|
292
305
|
}
|
|
306
|
+
interface TaskThreadContext {
|
|
307
|
+
assignee: string;
|
|
308
|
+
isRoot: boolean;
|
|
309
|
+
}
|
|
293
310
|
interface MaybeEvent {
|
|
294
311
|
type?: string;
|
|
295
312
|
room_id?: string;
|
|
@@ -303,7 +320,7 @@ interface MaybeEvent {
|
|
|
303
320
|
};
|
|
304
321
|
}
|
|
305
322
|
type RouteMatch = AgentBinding;
|
|
306
|
-
declare function route(event: MaybeEvent, agents: AgentBinding[], threadStates?: Map<string, ThreadState
|
|
323
|
+
declare function route(event: MaybeEvent, agents: AgentBinding[], threadStates?: Map<string, ThreadState>, task?: TaskThreadContext): RouteMatch[];
|
|
307
324
|
|
|
308
325
|
interface BootstrapOpts {
|
|
309
326
|
/** Invited to any newly-created room; absent = no invite. */
|
|
@@ -378,6 +395,69 @@ declare class SyncLoop {
|
|
|
378
395
|
stop(): void;
|
|
379
396
|
}
|
|
380
397
|
|
|
398
|
+
declare const MAX_OPEN_TASKS_PER_ROOM = 5;
|
|
399
|
+
type TaskPhase = 'reserved' | 'uncertain' | 'open' | 'closed';
|
|
400
|
+
interface TaskRecord {
|
|
401
|
+
taskId: string;
|
|
402
|
+
attemptId: string;
|
|
403
|
+
roomId: string;
|
|
404
|
+
assignee: string;
|
|
405
|
+
notify: 'caller' | 'none';
|
|
406
|
+
parent: {
|
|
407
|
+
agent: string;
|
|
408
|
+
threadRoot: string;
|
|
409
|
+
sessionKey: string;
|
|
410
|
+
generation: number;
|
|
411
|
+
};
|
|
412
|
+
phase: TaskPhase;
|
|
413
|
+
threadRoot?: string;
|
|
414
|
+
summary?: string;
|
|
415
|
+
runId?: string;
|
|
416
|
+
closedAt?: string;
|
|
417
|
+
}
|
|
418
|
+
interface PersistedTask extends Required<Pick<TaskRecord, 'taskId' | 'attemptId' | 'roomId' | 'assignee' | 'notify' | 'parent' | 'phase'>> {
|
|
419
|
+
threadRoot?: string;
|
|
420
|
+
summary?: string;
|
|
421
|
+
runId: string;
|
|
422
|
+
closedAt?: string;
|
|
423
|
+
}
|
|
424
|
+
interface TaskJournal {
|
|
425
|
+
load(): PersistedTask[];
|
|
426
|
+
save(tasks: PersistedTask[]): void;
|
|
427
|
+
}
|
|
428
|
+
declare class TaskRegistry {
|
|
429
|
+
private readonly opts;
|
|
430
|
+
private readonly tasks;
|
|
431
|
+
private readonly byRoot;
|
|
432
|
+
private readonly generations;
|
|
433
|
+
private readonly runIdValue;
|
|
434
|
+
constructor(opts?: {
|
|
435
|
+
maxOpenPerRoom?: number;
|
|
436
|
+
newId?: () => string;
|
|
437
|
+
journal?: TaskJournal;
|
|
438
|
+
runId?: string;
|
|
439
|
+
maxClosedRecords?: number;
|
|
440
|
+
});
|
|
441
|
+
private get max();
|
|
442
|
+
private get runId();
|
|
443
|
+
private save;
|
|
444
|
+
openCount(roomId: string): number;
|
|
445
|
+
reserve(input: Omit<TaskRecord, 'taskId' | 'attemptId' | 'phase' | 'threadRoot' | 'summary'>): TaskRecord | undefined;
|
|
446
|
+
activate(taskId: string, threadRoot: string): void;
|
|
447
|
+
abandon(taskId: string): void;
|
|
448
|
+
markUncertain(taskId: string): void;
|
|
449
|
+
adopt(attemptId: string, threadRoot: string): TaskRecord | undefined;
|
|
450
|
+
taskForRoot(threadRoot: string): TaskRecord | undefined;
|
|
451
|
+
openTaskFor(agent: string, root: string): TaskRecord | undefined;
|
|
452
|
+
recordSummary(id: string, summary: string): "recorded" | "already_recorded";
|
|
453
|
+
clearSummary(id: string): void;
|
|
454
|
+
close(id: string): boolean;
|
|
455
|
+
/** Reconcile records from a prior daemon run and retain closed roots for trust checks. */
|
|
456
|
+
restore(): TaskRecord[];
|
|
457
|
+
generationOf(agent: string, session: string): number;
|
|
458
|
+
bumpGeneration(agent: string, session: string): void;
|
|
459
|
+
}
|
|
460
|
+
|
|
381
461
|
interface MediaClientLike {
|
|
382
462
|
download(input: {
|
|
383
463
|
mxcUri: string;
|
|
@@ -428,9 +508,16 @@ interface CreateMatrixTransportOptions {
|
|
|
428
508
|
loadSince?: (agentUserId: string) => string | null;
|
|
429
509
|
/** Pull mode: persist the `since` cursor after each sync poll. */
|
|
430
510
|
saveSince?: (agentUserId: string, since: string) => void;
|
|
511
|
+
/** Durable lifecycle state; supplied by the daemon when it has a data directory. */
|
|
512
|
+
taskJournal?: TaskJournal;
|
|
513
|
+
taskRunId?: string;
|
|
514
|
+
pendingInput?: PendingInputRegistry;
|
|
515
|
+
/** Deferred-return fallback window. Defaults to `RETURN_GRACE_MS`. */
|
|
516
|
+
returnGraceMs?: number;
|
|
431
517
|
}
|
|
432
518
|
declare function createMatrixTransport(opts: CreateMatrixTransportOptions): {
|
|
433
519
|
app: Hono<hono_types.BlankEnv, hono_types.BlankSchema, "/">;
|
|
520
|
+
taskActions: TaskActions;
|
|
434
521
|
syncLoops: SyncLoop[] | undefined;
|
|
435
522
|
bootstrap: (bootstrapOpts?: {
|
|
436
523
|
spaceRoomId?: string;
|
|
@@ -576,4 +663,65 @@ declare class PendingMediaStore {
|
|
|
576
663
|
drain(roomId: string, threadKey: string | undefined, sender: string): PendingMediaItem[];
|
|
577
664
|
}
|
|
578
665
|
|
|
579
|
-
|
|
666
|
+
declare class InvocationRegistry {
|
|
667
|
+
private readonly opts;
|
|
668
|
+
private readonly records;
|
|
669
|
+
private readonly byCallee;
|
|
670
|
+
private readonly byEvent;
|
|
671
|
+
constructor(opts?: {
|
|
672
|
+
newId?: () => string;
|
|
673
|
+
});
|
|
674
|
+
open(input: Omit<InvocationRecord, 'invocationId' | 'state'>): InvocationRecord;
|
|
675
|
+
attachCallEvent(id: string, eventId: string, sessionKey: string): void;
|
|
676
|
+
get(id: string): InvocationRecord | undefined;
|
|
677
|
+
byCallEvent(eventId: string): InvocationRecord | undefined;
|
|
678
|
+
forCalleeSession(session: string): InvocationRecord | undefined;
|
|
679
|
+
outstandingFor(session: string): InvocationRecord[];
|
|
680
|
+
outstandingForTask(taskId: string): InvocationRecord[];
|
|
681
|
+
resolve(id: string): InvocationRecord | undefined;
|
|
682
|
+
cancelForTask(taskId: string): InvocationRecord[];
|
|
683
|
+
ancestorAgents(session: string): string[];
|
|
684
|
+
isOutstandingAncestor(session: string, agent: string): boolean;
|
|
685
|
+
}
|
|
686
|
+
|
|
687
|
+
/** ACP's stable prompt termination values (kept local to avoid an SDK runtime dep). */
|
|
688
|
+
type StopReason = 'end_turn' | 'max_tokens' | 'max_turn_requests' | 'refusal' | 'cancelled';
|
|
689
|
+
interface CompletionInputs {
|
|
690
|
+
agent: string;
|
|
691
|
+
threadId: string;
|
|
692
|
+
stopReason?: StopReason;
|
|
693
|
+
error?: unknown;
|
|
694
|
+
summary?: string;
|
|
695
|
+
prose?: string;
|
|
696
|
+
outstanding: number;
|
|
697
|
+
awaitingHuman: number;
|
|
698
|
+
}
|
|
699
|
+
type CompletionDecision = {
|
|
700
|
+
decision: 'stay_open';
|
|
701
|
+
reason: 'outstanding_handoff' | 'awaiting_human';
|
|
702
|
+
} | {
|
|
703
|
+
decision: 'finish';
|
|
704
|
+
completion: ThreadCompletion;
|
|
705
|
+
};
|
|
706
|
+
declare function evaluateCompletion(input: CompletionInputs): CompletionDecision;
|
|
707
|
+
|
|
708
|
+
type Admission = {
|
|
709
|
+
ok: true;
|
|
710
|
+
} | {
|
|
711
|
+
ok: false;
|
|
712
|
+
reason: string;
|
|
713
|
+
};
|
|
714
|
+
declare function checkDelegable(agentName: string, roomId: string, bindings: AgentBinding[]): Admission;
|
|
715
|
+
declare function buildAssignmentContent(input: {
|
|
716
|
+
assigneeUserId: string;
|
|
717
|
+
prompt: string;
|
|
718
|
+
start: ThreadStartContent;
|
|
719
|
+
}): {
|
|
720
|
+
msgtype: string;
|
|
721
|
+
body: string;
|
|
722
|
+
[key: string]: unknown;
|
|
723
|
+
};
|
|
724
|
+
declare function renderCompletionPrompt(c: ThreadCompletion): string;
|
|
725
|
+
declare function renderInvocationReturn(c: ThreadCompletion): string;
|
|
726
|
+
|
|
727
|
+
export { AGENT_KEY_RE, type AgentBinding, BotPool, type CompletionDecision, type CompletionInputs, type CreateMatrixTransportOptions, type EnsureDefaultChannelOpts, type EnsureSpaceOpts, INLINE_IMAGE_MIMES, InvocationRegistry, MAX_DOWNLOAD_BYTES, MAX_INLINE_IMAGE_BYTES, MAX_MEDIA_PER_TURN, MAX_OPEN_TASKS_PER_ROOM, MEDIA_MSGTYPES, MatrixClient, type MatrixClientOptions, MatrixContextProvider, type MatrixContextProviderOpts, type MatrixTransportConfig, type MaybeMessage, MediaClient, type MediaClientLike, type MediaClientOptions, type PendingMediaItem, PendingMediaStore, type PersistedTask, type PublishOpts, type PublisherHandle, type RouteMatch, SLUG_RE, type SendCustomEventInput, type SendMessageInput, type StartOpts as StartWorkforcePublisherOpts, type StopReason, type SyncClient, SyncLoop, type SyncLoopOptions, type SyncResponse, type TaskJournal, type TaskPhase, type TaskRecord, TaskRegistry, type WorkforceRoster, type WriteAttachmentInput, agentMxid, buildAssignmentContent, buildWorkforceRoster, checkDelegable, createMatrixTransport, ensureDefaultChannel, ensureWorkforceSpace, evaluateCompletion, extractMentions, isMediaMsgtype, isValidAgentKey, isValidWorkstation, parseMxcUri, publishWorkforce, renderCompletionPrompt, renderInvocationReturn, renderRegistration, route, serverNameFromMxid, splitAgentLocalpart, startWorkforcePublisher, workstationUserNamespace, writeAttachment };
|