@parall/sdk 1.30.0 → 1.32.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/client.d.ts +59 -9
- package/dist/client.d.ts.map +1 -1
- package/dist/client.js +165 -22
- package/dist/constants.d.ts +31 -0
- package/dist/constants.d.ts.map +1 -1
- package/dist/constants.js +242 -38
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/types.d.ts +241 -10
- package/dist/types.d.ts.map +1 -1
- package/dist/ws.d.ts +3 -3
- package/dist/ws.d.ts.map +1 -1
- package/dist/ws.js +12 -7
- package/package.json +1 -1
- package/src/client.ts +805 -170
- package/src/constants.ts +307 -86
- package/src/index.ts +7 -1
- package/src/types.ts +358 -25
- package/src/ws.ts +26 -11
package/src/types.ts
CHANGED
|
@@ -104,15 +104,22 @@ export interface TransferChatOwnershipRequest {
|
|
|
104
104
|
export interface UnreadEntry {
|
|
105
105
|
count: number;
|
|
106
106
|
mentions: number;
|
|
107
|
+
since?: string;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
export interface ThreadUnreadEntry {
|
|
111
|
+
unread: number;
|
|
112
|
+
total: number;
|
|
113
|
+
since: string | null;
|
|
107
114
|
}
|
|
108
115
|
|
|
109
116
|
export type MessageType =
|
|
110
117
|
| 'text'
|
|
111
|
-
| 'file'
|
|
112
|
-
| 'tool_call'
|
|
113
|
-
| 'tool_result'
|
|
114
|
-
| 'approval_card'
|
|
115
|
-
| 'state_delta'
|
|
118
|
+
| 'file' // deprecated: attachments are now schema-level on Message
|
|
119
|
+
| 'tool_call' // deprecated: use AgentStep
|
|
120
|
+
| 'tool_result' // deprecated: use AgentStep
|
|
121
|
+
| 'approval_card' // deprecated: use 'card' with card_type='approval'
|
|
122
|
+
| 'state_delta' // deprecated: use AgentStep
|
|
116
123
|
| 'card'
|
|
117
124
|
| 'system';
|
|
118
125
|
|
|
@@ -197,7 +204,13 @@ export type CardContent =
|
|
|
197
204
|
| ApprovalCardContent
|
|
198
205
|
| { card_type: string; entity_id?: string; data?: Record<string, unknown> };
|
|
199
206
|
|
|
200
|
-
export type AgentState =
|
|
207
|
+
export type AgentState =
|
|
208
|
+
| 'thinking'
|
|
209
|
+
| 'tool_calling'
|
|
210
|
+
| 'streaming'
|
|
211
|
+
| 'waiting_approval'
|
|
212
|
+
| 'completed'
|
|
213
|
+
| 'error';
|
|
201
214
|
|
|
202
215
|
export interface StateDeltaContent {
|
|
203
216
|
state: AgentState;
|
|
@@ -317,6 +330,9 @@ export interface Organization {
|
|
|
317
330
|
created_at: string;
|
|
318
331
|
/** Per-member flag: true when the user has dismissed the onboarding popup for this org. */
|
|
319
332
|
onboarding_dismissed: boolean;
|
|
333
|
+
/** Caller's membership role in this org (owner/admin/member). Present on the
|
|
334
|
+
* GET /orgs list response; omitted on single-org fetches that don't join membership. */
|
|
335
|
+
role?: OrgMemberRole;
|
|
320
336
|
}
|
|
321
337
|
|
|
322
338
|
export interface OrgInviteCode {
|
|
@@ -367,6 +383,52 @@ export interface InvitationPublicInfo {
|
|
|
367
383
|
expires_at: string;
|
|
368
384
|
}
|
|
369
385
|
|
|
386
|
+
// ---- Org-level shareable invite link ----
|
|
387
|
+
|
|
388
|
+
/** Single regenerable token per org. Sits alongside (not replacing) the
|
|
389
|
+
* per-email OrgInvitation flow. */
|
|
390
|
+
export interface OrgInviteLink {
|
|
391
|
+
org_id: string;
|
|
392
|
+
token: string;
|
|
393
|
+
require_approval: boolean;
|
|
394
|
+
expires_at: string;
|
|
395
|
+
created_at: string;
|
|
396
|
+
regenerated_at: string;
|
|
397
|
+
}
|
|
398
|
+
|
|
399
|
+
export interface JoinByLinkRequest {
|
|
400
|
+
token: string;
|
|
401
|
+
}
|
|
402
|
+
|
|
403
|
+
export interface JoinByLinkResponse {
|
|
404
|
+
org_id: string;
|
|
405
|
+
joined: boolean;
|
|
406
|
+
status: 'active' | 'pending_approval' | 'already_member';
|
|
407
|
+
join_request_id?: string;
|
|
408
|
+
/** Minimal org summary so the join page can render the real org name
|
|
409
|
+
* in success / pending-approval copy without a second round-trip. */
|
|
410
|
+
org?: JoinByLinkOrgInfo;
|
|
411
|
+
}
|
|
412
|
+
|
|
413
|
+
export interface JoinByLinkOrgInfo {
|
|
414
|
+
id: string;
|
|
415
|
+
name: string;
|
|
416
|
+
avatar_url?: string | null;
|
|
417
|
+
}
|
|
418
|
+
|
|
419
|
+
export type OrgJoinRequestStatus = 'pending' | 'approved' | 'rejected';
|
|
420
|
+
|
|
421
|
+
export interface OrgJoinRequest {
|
|
422
|
+
id: string;
|
|
423
|
+
org_id: string;
|
|
424
|
+
user_id: string;
|
|
425
|
+
status: OrgJoinRequestStatus;
|
|
426
|
+
decided_by?: string;
|
|
427
|
+
decided_at?: string;
|
|
428
|
+
created_at: string;
|
|
429
|
+
user?: User;
|
|
430
|
+
}
|
|
431
|
+
|
|
370
432
|
export interface CreateInvitationRequest {
|
|
371
433
|
email: string;
|
|
372
434
|
role?: OrgMemberRole;
|
|
@@ -571,11 +633,10 @@ export type AgentLLMSource = 'parall' | 'custom' | 'runtime_auth';
|
|
|
571
633
|
* `llm_source` makes that source explicit. Missing values are backward-
|
|
572
634
|
* compatible: empty config means Parall provided, while legacy rows with
|
|
573
635
|
* credential fields but no source are inferred as custom. Custom provider
|
|
574
|
-
* fields let admins bring their own
|
|
575
|
-
* at Azure OpenAI, or use an OpenAI / Anthropic-compatible proxy.
|
|
576
|
-
*
|
|
577
|
-
*
|
|
578
|
-
* effort control.
|
|
636
|
+
* fields let admins bring their own OpenAI / Anthropic subscription, point
|
|
637
|
+
* at Azure OpenAI, or use an OpenAI / Anthropic-compatible proxy. Hosted
|
|
638
|
+
* runtime OAuth is no longer accepted; self-hosted daemon runtimes manage
|
|
639
|
+
* local CLI OAuth outside provider_config.
|
|
579
640
|
*
|
|
580
641
|
* Each runtime consumes exactly one credential family:
|
|
581
642
|
* - codex → openai_*
|
|
@@ -631,7 +692,14 @@ export interface UpdateAgentRequest {
|
|
|
631
692
|
|
|
632
693
|
// ---- Machine types ----
|
|
633
694
|
|
|
634
|
-
export type MachineStatus =
|
|
695
|
+
export type MachineStatus =
|
|
696
|
+
| 'provisioning'
|
|
697
|
+
| 'starting'
|
|
698
|
+
| 'restarting'
|
|
699
|
+
| 'running'
|
|
700
|
+
| 'stopped'
|
|
701
|
+
| 'error'
|
|
702
|
+
| 'terminated';
|
|
635
703
|
|
|
636
704
|
export interface Machine {
|
|
637
705
|
id: string;
|
|
@@ -650,6 +718,7 @@ export interface Machine {
|
|
|
650
718
|
daemon_mode: boolean;
|
|
651
719
|
llm_source?: string;
|
|
652
720
|
compute_mode: 'hosted' | 'local';
|
|
721
|
+
daemon_version?: string | null;
|
|
653
722
|
region: string | null;
|
|
654
723
|
created_by: string;
|
|
655
724
|
created_at: string;
|
|
@@ -811,6 +880,20 @@ export interface MachineFilesystemBrowseData {
|
|
|
811
880
|
path: string;
|
|
812
881
|
}
|
|
813
882
|
|
|
883
|
+
export interface MachineUpdateData {
|
|
884
|
+
machine_id: string;
|
|
885
|
+
new_version: string;
|
|
886
|
+
mandatory: boolean;
|
|
887
|
+
reason?: string;
|
|
888
|
+
}
|
|
889
|
+
|
|
890
|
+
export interface MachineClipInstallData {
|
|
891
|
+
clip_id: string;
|
|
892
|
+
alias: string;
|
|
893
|
+
source_ref: string;
|
|
894
|
+
version?: string;
|
|
895
|
+
}
|
|
896
|
+
|
|
814
897
|
export interface AgentNewSessionData {
|
|
815
898
|
previous_session_id?: string;
|
|
816
899
|
}
|
|
@@ -876,8 +959,20 @@ export interface AvatarUploadResponse {
|
|
|
876
959
|
|
|
877
960
|
export type TaskStatus = 'todo' | 'in_progress' | 'in_review' | 'done' | 'canceled';
|
|
878
961
|
export type TaskPriority = 'high' | 'normal' | 'low';
|
|
879
|
-
export type TaskRelationTargetType =
|
|
880
|
-
|
|
962
|
+
export type TaskRelationTargetType =
|
|
963
|
+
| 'task'
|
|
964
|
+
| 'message'
|
|
965
|
+
| 'chat'
|
|
966
|
+
| 'agent_session'
|
|
967
|
+
| 'wiki_changeset';
|
|
968
|
+
export type TaskRelationType =
|
|
969
|
+
| 'blocks'
|
|
970
|
+
| 'related'
|
|
971
|
+
| 'duplicate'
|
|
972
|
+
| 'source'
|
|
973
|
+
| 'reference'
|
|
974
|
+
| 'discussion'
|
|
975
|
+
| 'execution';
|
|
881
976
|
|
|
882
977
|
export interface Task {
|
|
883
978
|
id: string;
|
|
@@ -943,6 +1038,24 @@ export interface TaskRelation {
|
|
|
943
1038
|
created_at: string;
|
|
944
1039
|
}
|
|
945
1040
|
|
|
1041
|
+
export type RefSearchKind = 'user' | 'task' | 'channel';
|
|
1042
|
+
|
|
1043
|
+
export interface RefSearchItem {
|
|
1044
|
+
kind: RefSearchKind;
|
|
1045
|
+
id: string;
|
|
1046
|
+
uri: string;
|
|
1047
|
+
display: string;
|
|
1048
|
+
label: string;
|
|
1049
|
+
title: string;
|
|
1050
|
+
subtitle?: string;
|
|
1051
|
+
subtitle_key?: string;
|
|
1052
|
+
status?: string;
|
|
1053
|
+
}
|
|
1054
|
+
|
|
1055
|
+
export interface RefSearchResponse {
|
|
1056
|
+
data: RefSearchItem[];
|
|
1057
|
+
}
|
|
1058
|
+
|
|
946
1059
|
export interface CreateTaskRequest {
|
|
947
1060
|
title: string;
|
|
948
1061
|
description?: string;
|
|
@@ -1026,6 +1139,8 @@ export interface Schedule {
|
|
|
1026
1139
|
attached_to_uri: string | null;
|
|
1027
1140
|
name: string;
|
|
1028
1141
|
description: string;
|
|
1142
|
+
attachment_ids: string[];
|
|
1143
|
+
attachments?: Attachment[];
|
|
1029
1144
|
spec_type: ScheduleSpecType;
|
|
1030
1145
|
cron_expr: string | null;
|
|
1031
1146
|
interval_seconds: number | null;
|
|
@@ -1054,6 +1169,8 @@ export interface ScheduleRun {
|
|
|
1054
1169
|
status: ScheduleRunStatus;
|
|
1055
1170
|
fired_description: string | null;
|
|
1056
1171
|
fired_attached_uri: string | null;
|
|
1172
|
+
fired_attachment_ids: string[];
|
|
1173
|
+
fired_attachments?: Attachment[];
|
|
1057
1174
|
error: string | null;
|
|
1058
1175
|
created_at: string;
|
|
1059
1176
|
}
|
|
@@ -1063,6 +1180,7 @@ export interface CreateScheduleInput {
|
|
|
1063
1180
|
description: string;
|
|
1064
1181
|
target_ids: string[];
|
|
1065
1182
|
attached_to_uri?: string;
|
|
1183
|
+
attachment_ids?: string[];
|
|
1066
1184
|
spec_type: ScheduleSpecType;
|
|
1067
1185
|
cron_expr?: string;
|
|
1068
1186
|
interval_seconds?: number;
|
|
@@ -1082,6 +1200,9 @@ export interface UpdateScheduleInput {
|
|
|
1082
1200
|
attached_to_uri?: string;
|
|
1083
1201
|
/** Explicitly clear attached_to_uri. Server honors this over `attached_to_uri`. */
|
|
1084
1202
|
attached_to_uri_clear?: boolean;
|
|
1203
|
+
attachment_ids?: string[];
|
|
1204
|
+
/** Explicitly clear attachment_ids. Server honors this over `attachment_ids`. */
|
|
1205
|
+
attachment_ids_clear?: boolean;
|
|
1085
1206
|
cron_expr?: string;
|
|
1086
1207
|
interval_seconds?: number;
|
|
1087
1208
|
run_at?: string;
|
|
@@ -1561,7 +1682,23 @@ export interface ChatCreatedData extends Chat {}
|
|
|
1561
1682
|
|
|
1562
1683
|
export interface ChatUpdateData {
|
|
1563
1684
|
chat_id: string;
|
|
1564
|
-
changes: Partial<
|
|
1685
|
+
changes: Partial<
|
|
1686
|
+
Pick<
|
|
1687
|
+
Chat,
|
|
1688
|
+
| 'name'
|
|
1689
|
+
| 'avatar_url'
|
|
1690
|
+
| 'description'
|
|
1691
|
+
| 'visibility'
|
|
1692
|
+
| 'agent_routing_mode'
|
|
1693
|
+
| 'smart_routing_strategy'
|
|
1694
|
+
| 'smart_routing_agent_id'
|
|
1695
|
+
| 'last_message_at'
|
|
1696
|
+
| 'last_message_preview'
|
|
1697
|
+
| 'last_message_sender'
|
|
1698
|
+
| 'archived_at'
|
|
1699
|
+
| 'deleted_at'
|
|
1700
|
+
>
|
|
1701
|
+
>;
|
|
1565
1702
|
}
|
|
1566
1703
|
|
|
1567
1704
|
export interface ChatDeletedData {
|
|
@@ -1666,7 +1803,7 @@ export interface AgentSessionDB {
|
|
|
1666
1803
|
id: string;
|
|
1667
1804
|
agent_id: string;
|
|
1668
1805
|
org_id: string;
|
|
1669
|
-
status: string;
|
|
1806
|
+
status: string; // open | closed | failed | cancelled | superseded
|
|
1670
1807
|
runtime_type: string;
|
|
1671
1808
|
runtime_key: string | null;
|
|
1672
1809
|
runtime_lane_key: string;
|
|
@@ -1677,6 +1814,13 @@ export interface AgentSessionDB {
|
|
|
1677
1814
|
started_at: string;
|
|
1678
1815
|
finished_at: string | null;
|
|
1679
1816
|
created_at: string;
|
|
1817
|
+
|
|
1818
|
+
// Computed fields populated by ListSessions enrichment.
|
|
1819
|
+
trigger_chat_id?: string | null;
|
|
1820
|
+
trigger_chat_name?: string | null;
|
|
1821
|
+
trigger_chat_type?: string | null;
|
|
1822
|
+
trigger_sender_name?: string | null;
|
|
1823
|
+
step_count?: number | null;
|
|
1680
1824
|
}
|
|
1681
1825
|
|
|
1682
1826
|
export interface AgentStep {
|
|
@@ -1755,6 +1899,7 @@ export interface Comment {
|
|
|
1755
1899
|
export interface CreateCommentRequest {
|
|
1756
1900
|
target_uri: string;
|
|
1757
1901
|
body: string;
|
|
1902
|
+
parent_id?: string;
|
|
1758
1903
|
}
|
|
1759
1904
|
|
|
1760
1905
|
export interface UpdateCommentRequest {
|
|
@@ -1774,9 +1919,14 @@ export interface CommentDeletedData {
|
|
|
1774
1919
|
// ============================================================
|
|
1775
1920
|
|
|
1776
1921
|
export type InboxItemType =
|
|
1777
|
-
| 'mention'
|
|
1778
|
-
| '
|
|
1779
|
-
| '
|
|
1922
|
+
| 'mention'
|
|
1923
|
+
| 'task_assign'
|
|
1924
|
+
| 'task_update'
|
|
1925
|
+
| 'task_comment'
|
|
1926
|
+
| 'approval_request'
|
|
1927
|
+
| 'agent_alert'
|
|
1928
|
+
| 'invitation'
|
|
1929
|
+
| 'schedule_fire'
|
|
1780
1930
|
| 'thread_reply';
|
|
1781
1931
|
|
|
1782
1932
|
export interface InboxItem {
|
|
@@ -1808,8 +1958,15 @@ export interface InboxItem {
|
|
|
1808
1958
|
// Dispatch Types (agent event delivery)
|
|
1809
1959
|
// ============================================================
|
|
1810
1960
|
|
|
1811
|
-
export type DispatchEventType =
|
|
1812
|
-
|
|
1961
|
+
export type DispatchEventType =
|
|
1962
|
+
| 'message'
|
|
1963
|
+
| 'task_assign'
|
|
1964
|
+
| 'task_update'
|
|
1965
|
+
| 'task_comment'
|
|
1966
|
+
| 'wiki_comment'
|
|
1967
|
+
| 'schedule.fire'
|
|
1968
|
+
| 'approval_decided';
|
|
1969
|
+
export type DispatchStatus = 'pending' | 'received' | 'acked';
|
|
1813
1970
|
export type DispatchDeliveryReason = 'mention' | 'watcher' | 'assignee' | 'creator';
|
|
1814
1971
|
|
|
1815
1972
|
export interface DispatchEvent {
|
|
@@ -1842,6 +1999,16 @@ export interface DispatchEvent {
|
|
|
1842
1999
|
|
|
1843
2000
|
export type DispatchNewData = DispatchEvent;
|
|
1844
2001
|
|
|
2002
|
+
export interface DispatchReceivedData {
|
|
2003
|
+
agent_id: string;
|
|
2004
|
+
event_type: string;
|
|
2005
|
+
source_type: string;
|
|
2006
|
+
source_id: string;
|
|
2007
|
+
chat_id?: string | null;
|
|
2008
|
+
task_id?: string | null;
|
|
2009
|
+
org_id: string;
|
|
2010
|
+
}
|
|
2011
|
+
|
|
1845
2012
|
export type InboxNewData = InboxItem;
|
|
1846
2013
|
|
|
1847
2014
|
export interface InboxUpdateData {
|
|
@@ -1873,7 +2040,7 @@ export interface NotificationAlertData {
|
|
|
1873
2040
|
}
|
|
1874
2041
|
|
|
1875
2042
|
export type WsEventMap = {
|
|
1876
|
-
|
|
2043
|
+
hello: HelloData;
|
|
1877
2044
|
'message.new': MessageNewData;
|
|
1878
2045
|
'message.patch': MessagePatchData;
|
|
1879
2046
|
'message.edit': MessageEditData;
|
|
@@ -1885,8 +2052,8 @@ export type WsEventMap = {
|
|
|
1885
2052
|
'approval.update': ApprovalUpdateData; // deprecated, kept for backward compat
|
|
1886
2053
|
'card.update': CardUpdateData;
|
|
1887
2054
|
'recovery.overflow': RecoveryOverflowData;
|
|
1888
|
-
|
|
1889
|
-
|
|
2055
|
+
watching: WatchingData;
|
|
2056
|
+
pong: { ts: number };
|
|
1890
2057
|
'membership.changed': MembershipChangedData;
|
|
1891
2058
|
'task.created': TaskCreatedData;
|
|
1892
2059
|
'task.updated': TaskUpdatedData;
|
|
@@ -1905,6 +2072,8 @@ export type WsEventMap = {
|
|
|
1905
2072
|
'invitation.accepted': InvitationAcceptedEventData;
|
|
1906
2073
|
'invitation.declined': InvitationDeclinedEventData;
|
|
1907
2074
|
'invitation.revoked': InvitationRevokedEventData;
|
|
2075
|
+
'org.join_request.new': OrgJoinRequestNewEventData;
|
|
2076
|
+
'org.invite_link.joined': OrgInviteLinkJoinedEventData;
|
|
1908
2077
|
'agent_config.update': AgentConfigUpdateData;
|
|
1909
2078
|
'presence.update': PresenceUpdateData;
|
|
1910
2079
|
'wiki.changeset.created': WikiChangesetCreatedData;
|
|
@@ -1918,6 +2087,7 @@ export type WsEventMap = {
|
|
|
1918
2087
|
'inbox.bulk_update': InboxBulkUpdateData;
|
|
1919
2088
|
'read_position.updated': ReadPositionUpdateData;
|
|
1920
2089
|
'dispatch.new': DispatchNewData;
|
|
2090
|
+
'dispatch.received': DispatchReceivedData;
|
|
1921
2091
|
'schedule.created': ScheduleCreatedData;
|
|
1922
2092
|
'schedule.updated': ScheduleUpdatedData;
|
|
1923
2093
|
'schedule.deleted': ScheduleDeletedData;
|
|
@@ -1934,6 +2104,11 @@ export type WsEventMap = {
|
|
|
1934
2104
|
'machine.workspace.setup.requested': MachineWorkspaceSetupRequestedData;
|
|
1935
2105
|
'machine.stop': MachineStopData;
|
|
1936
2106
|
'machine.filesystem.browse': MachineFilesystemBrowseData;
|
|
2107
|
+
'machine.update': MachineUpdateData;
|
|
2108
|
+
'machine.clip.install': MachineClipInstallData;
|
|
2109
|
+
'clip.installed': ClipInstalledData;
|
|
2110
|
+
'clip.removed': ClipRemovedData;
|
|
2111
|
+
'clip.updated': ClipUpdatedData;
|
|
1937
2112
|
'agent.new_session': AgentNewSessionData;
|
|
1938
2113
|
};
|
|
1939
2114
|
|
|
@@ -1966,6 +2141,25 @@ export interface InvitationRevokedEventData {
|
|
|
1966
2141
|
org_id: string;
|
|
1967
2142
|
}
|
|
1968
2143
|
|
|
2144
|
+
/** Fan-out to org admins when an end-user submits a join-request via the
|
|
2145
|
+
* shareable org invite link. Mirrors the payload published by
|
|
2146
|
+
* publishJoinRequested in server/internal/api/handler/org_invite_link.go. */
|
|
2147
|
+
export interface OrgJoinRequestNewEventData {
|
|
2148
|
+
join_request_id: string;
|
|
2149
|
+
org_id: string;
|
|
2150
|
+
user_id: string;
|
|
2151
|
+
display_name: string;
|
|
2152
|
+
created_at: string;
|
|
2153
|
+
}
|
|
2154
|
+
|
|
2155
|
+
export interface OrgInviteLinkJoinedEventData {
|
|
2156
|
+
org_id: string;
|
|
2157
|
+
user_id: string;
|
|
2158
|
+
display_name: string;
|
|
2159
|
+
role: OrgMemberRole;
|
|
2160
|
+
source: 'invite_link';
|
|
2161
|
+
}
|
|
2162
|
+
|
|
1969
2163
|
// ============================================================
|
|
1970
2164
|
// Platform Config Types
|
|
1971
2165
|
// ============================================================
|
|
@@ -2186,7 +2380,17 @@ export interface CreditWallet {
|
|
|
2186
2380
|
export interface CreditTransaction {
|
|
2187
2381
|
id: string;
|
|
2188
2382
|
org_id: string;
|
|
2189
|
-
type:
|
|
2383
|
+
type:
|
|
2384
|
+
| 'topup'
|
|
2385
|
+
| 'auto_reload'
|
|
2386
|
+
| 'llm_deduct'
|
|
2387
|
+
| 'compute_deduct'
|
|
2388
|
+
| 'compute_hold'
|
|
2389
|
+
| 'compute_settle'
|
|
2390
|
+
| 'adjustment'
|
|
2391
|
+
| 'refund'
|
|
2392
|
+
| 'grant'
|
|
2393
|
+
| 'grant_expire';
|
|
2190
2394
|
amount: number;
|
|
2191
2395
|
balance_after: number;
|
|
2192
2396
|
grant_id: string | null;
|
|
@@ -2343,3 +2547,132 @@ export interface BillingMachineStoppedEvent {
|
|
|
2343
2547
|
export interface BillingInsufficientEvent {
|
|
2344
2548
|
org_id: string;
|
|
2345
2549
|
}
|
|
2550
|
+
|
|
2551
|
+
// ============================================================
|
|
2552
|
+
// Clip Types
|
|
2553
|
+
// ============================================================
|
|
2554
|
+
|
|
2555
|
+
export type ClipSourceType = 'registry' | 'custom' | 'builtin';
|
|
2556
|
+
export type ClipStatus = 'active' | 'disabled';
|
|
2557
|
+
|
|
2558
|
+
export interface Clip {
|
|
2559
|
+
id: string;
|
|
2560
|
+
org_id: string;
|
|
2561
|
+
alias: string;
|
|
2562
|
+
name: string;
|
|
2563
|
+
description: string | null;
|
|
2564
|
+
manifest: Record<string, unknown>;
|
|
2565
|
+
source_type: ClipSourceType;
|
|
2566
|
+
source_ref: string | null;
|
|
2567
|
+
version: string | null;
|
|
2568
|
+
status: ClipStatus;
|
|
2569
|
+
created_by: string | null;
|
|
2570
|
+
/** Registry clip that reconciles onto every org machine, including machines
|
|
2571
|
+
* that join after creation. Targeted installs leave this false and persist
|
|
2572
|
+
* per-machine pending clip_instances instead. */
|
|
2573
|
+
install_on_all_machines: boolean;
|
|
2574
|
+
created_at: string;
|
|
2575
|
+
updated_at: string;
|
|
2576
|
+
}
|
|
2577
|
+
|
|
2578
|
+
export interface AgentClip {
|
|
2579
|
+
agent_id: string;
|
|
2580
|
+
clip_id: string;
|
|
2581
|
+
config: Record<string, unknown> | null;
|
|
2582
|
+
created_at: string;
|
|
2583
|
+
}
|
|
2584
|
+
|
|
2585
|
+
export interface CreateClipRequest {
|
|
2586
|
+
alias: string;
|
|
2587
|
+
name: string;
|
|
2588
|
+
description?: string;
|
|
2589
|
+
manifest: Record<string, unknown>;
|
|
2590
|
+
source_type?: ClipSourceType;
|
|
2591
|
+
source_ref?: string;
|
|
2592
|
+
version?: string;
|
|
2593
|
+
target_machine_ids?: string[];
|
|
2594
|
+
}
|
|
2595
|
+
|
|
2596
|
+
export interface UpdateClipRequest {
|
|
2597
|
+
name?: string;
|
|
2598
|
+
description?: string;
|
|
2599
|
+
manifest?: Record<string, unknown>;
|
|
2600
|
+
status?: ClipStatus;
|
|
2601
|
+
version?: string;
|
|
2602
|
+
}
|
|
2603
|
+
|
|
2604
|
+
export interface BindAgentClipRequest {
|
|
2605
|
+
clip_id: string;
|
|
2606
|
+
config?: Record<string, unknown>;
|
|
2607
|
+
}
|
|
2608
|
+
|
|
2609
|
+
export interface InvokeClipRequest {
|
|
2610
|
+
alias: string;
|
|
2611
|
+
command: string;
|
|
2612
|
+
input?: unknown;
|
|
2613
|
+
timeout_ms?: number;
|
|
2614
|
+
}
|
|
2615
|
+
|
|
2616
|
+
export interface InvokeClipResponse {
|
|
2617
|
+
output: unknown;
|
|
2618
|
+
error: string | null;
|
|
2619
|
+
}
|
|
2620
|
+
|
|
2621
|
+
export type ClipInstanceStatus = 'pending' | 'installed' | 'running' | 'stopped' | 'error';
|
|
2622
|
+
|
|
2623
|
+
export interface ClipInstance {
|
|
2624
|
+
id: string;
|
|
2625
|
+
clip_id: string;
|
|
2626
|
+
machine_id: string | null;
|
|
2627
|
+
status: ClipInstanceStatus;
|
|
2628
|
+
version: string | null;
|
|
2629
|
+
error_msg: string | null;
|
|
2630
|
+
last_seen: string | null;
|
|
2631
|
+
created_at: string;
|
|
2632
|
+
updated_at: string;
|
|
2633
|
+
}
|
|
2634
|
+
|
|
2635
|
+
export interface OnlineClipInfo {
|
|
2636
|
+
alias: string;
|
|
2637
|
+
name: string;
|
|
2638
|
+
version: string;
|
|
2639
|
+
commands: Array<{ name: string; description: string }>;
|
|
2640
|
+
provider_name: string;
|
|
2641
|
+
}
|
|
2642
|
+
|
|
2643
|
+
// Durable install reconcile — a registry clip the machine should install.
|
|
2644
|
+
export interface MachineClipInstall {
|
|
2645
|
+
clip_id: string;
|
|
2646
|
+
alias: string;
|
|
2647
|
+
source_ref?: string;
|
|
2648
|
+
version?: string;
|
|
2649
|
+
}
|
|
2650
|
+
|
|
2651
|
+
// Pinix registry catalog clip info (from GET /clip/v1/registry/clips,
|
|
2652
|
+
// which proxies the public Pinix registry GET /search).
|
|
2653
|
+
export interface RegistryCommandInfo {
|
|
2654
|
+
name: string;
|
|
2655
|
+
description: string;
|
|
2656
|
+
input?: string;
|
|
2657
|
+
output?: string;
|
|
2658
|
+
}
|
|
2659
|
+
|
|
2660
|
+
export interface RegistryClipInfo {
|
|
2661
|
+
name: string; // @scope/name (canonical package id)
|
|
2662
|
+
package: string; // @scope/name (alias derivation + install source_ref)
|
|
2663
|
+
version: string;
|
|
2664
|
+
type: string; // registry package type (e.g. "clip")
|
|
2665
|
+
description?: string;
|
|
2666
|
+
domain?: string;
|
|
2667
|
+
author?: string;
|
|
2668
|
+
commands: RegistryCommandInfo[];
|
|
2669
|
+
dependencies: string[];
|
|
2670
|
+
}
|
|
2671
|
+
|
|
2672
|
+
// Clip WS event data types
|
|
2673
|
+
export type ClipInstalledData = Clip;
|
|
2674
|
+
export type ClipUpdatedData = Clip;
|
|
2675
|
+
export interface ClipRemovedData {
|
|
2676
|
+
clip_id: string;
|
|
2677
|
+
org_id: string;
|
|
2678
|
+
}
|
package/src/ws.ts
CHANGED
|
@@ -5,9 +5,9 @@ export type WsEventType = keyof WsEventMap;
|
|
|
5
5
|
export type WsEventHandler<T extends WsEventType> = (data: WsEventMap[T], seq?: number) => void;
|
|
6
6
|
|
|
7
7
|
export type WsClientEventMap = {
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
8
|
+
ping: { ts: number };
|
|
9
|
+
typing: { chat_id: string; thread_root_id: string | null; action: 'start' | 'stop' };
|
|
10
|
+
watch: { chat_ids: string[] };
|
|
11
11
|
'agent.heartbeat': { session_id: string; telemetry?: Record<string, unknown> };
|
|
12
12
|
};
|
|
13
13
|
|
|
@@ -26,10 +26,10 @@ export interface ParallWsOptions {
|
|
|
26
26
|
|
|
27
27
|
function isRetryableNetworkError(err: unknown): boolean {
|
|
28
28
|
return (
|
|
29
|
-
err instanceof Error
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
29
|
+
err instanceof Error &&
|
|
30
|
+
err.name === 'ApiError' &&
|
|
31
|
+
'status' in err &&
|
|
32
|
+
(err as { status?: unknown }).status === 0
|
|
33
33
|
);
|
|
34
34
|
}
|
|
35
35
|
|
|
@@ -39,7 +39,11 @@ function isBrowserRuntime(): boolean {
|
|
|
39
39
|
|
|
40
40
|
export class ParallWs {
|
|
41
41
|
private ws: WebSocket | null = null;
|
|
42
|
-
private options: ParallWsOptions & {
|
|
42
|
+
private options: ParallWsOptions & {
|
|
43
|
+
reconnect: boolean;
|
|
44
|
+
reconnectInterval: number;
|
|
45
|
+
maxReconnectInterval: number;
|
|
46
|
+
};
|
|
43
47
|
private listeners = new Map<string, Set<WsEventHandler<WsEventType>>>();
|
|
44
48
|
private stateListeners = new Set<(state: WsConnectionState) => void>();
|
|
45
49
|
private heartbeatTimer: ReturnType<typeof setInterval> | null = null;
|
|
@@ -115,7 +119,11 @@ export class ParallWs {
|
|
|
115
119
|
ws.onclose = null;
|
|
116
120
|
ws.onopen = null;
|
|
117
121
|
ws.onerror = null;
|
|
118
|
-
try {
|
|
122
|
+
try {
|
|
123
|
+
ws.close();
|
|
124
|
+
} catch {
|
|
125
|
+
/* ignore */
|
|
126
|
+
}
|
|
119
127
|
// Only reconnect if this socket is still the active one.
|
|
120
128
|
// If connect() was called again, a newer socket owns the lifecycle.
|
|
121
129
|
if (ws !== this.ws) return;
|
|
@@ -271,7 +279,10 @@ export class ParallWs {
|
|
|
271
279
|
// event-loop stalls. Probe with a 5s timeout rather than force-
|
|
272
280
|
// reconnecting, so healthy connections that were merely timer-starved
|
|
273
281
|
// survive while genuinely dead sockets are caught quickly.
|
|
274
|
-
if (
|
|
282
|
+
if (
|
|
283
|
+
this.lastReceivedAt > 0 &&
|
|
284
|
+
Date.now() - this.lastReceivedAt > this.heartbeatIntervalMs * 1.5
|
|
285
|
+
) {
|
|
275
286
|
this.probeConnection();
|
|
276
287
|
return;
|
|
277
288
|
}
|
|
@@ -320,7 +331,11 @@ export class ParallWs {
|
|
|
320
331
|
this.ws.onopen = null;
|
|
321
332
|
this.ws.onerror = null;
|
|
322
333
|
this.ws.onmessage = null;
|
|
323
|
-
try {
|
|
334
|
+
try {
|
|
335
|
+
this.ws.close();
|
|
336
|
+
} catch {
|
|
337
|
+
/* ignore */
|
|
338
|
+
}
|
|
324
339
|
this.ws = null;
|
|
325
340
|
}
|
|
326
341
|
if (this.options.reconnect && !this.intentionalClose) {
|