@swarmdock/sdk 0.1.1 → 0.2.1
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 +128 -1
- package/dist/client.d.ts.map +1 -1
- package/dist/client.js +242 -1
- package/dist/client.js.map +1 -1
- package/dist/errors.d.ts +21 -0
- package/dist/errors.d.ts.map +1 -1
- package/dist/errors.js +50 -0
- package/dist/errors.js.map +1 -1
- package/dist/index.d.ts +4 -4
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2 -2
- package/dist/index.js.map +1 -1
- package/package.json +17 -9
- package/.turbo/turbo-build.log +0 -4
- package/.turbo/turbo-type-check.log +0 -4
- package/src/client.ts +0 -579
- package/src/errors.ts +0 -26
- package/src/index.ts +0 -32
- package/tsconfig.json +0 -8
package/dist/errors.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"errors.js","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"AAAA,MAAM,OAAO,cAAe,SAAQ,KAAK;IAC9B,MAAM,CAAS;IACf,IAAI,CAAS;IACb,OAAO,CAAW;IAE3B,YAAY,MAAc,EAAE,OAAe,EAAE,OAAiB;QAC5D,KAAK,CAAC,OAAO,CAAC,CAAC;QACf,IAAI,CAAC,IAAI,GAAG,gBAAgB,CAAC;QAC7B,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QACrB,IAAI,CAAC,IAAI,GAAG,cAAc,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC;QAChD,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;IACzB,CAAC;IAEO,MAAM,CAAC,YAAY,CAAC,MAAc;QACxC,QAAQ,MAAM,EAAE,CAAC;YACf,KAAK,GAAG,CAAC,CAAC,OAAO,aAAa,CAAC;YAC/B,KAAK,GAAG,CAAC,CAAC,OAAO,cAAc,CAAC;YAChC,KAAK,GAAG,CAAC,CAAC,OAAO,WAAW,CAAC;YAC7B,KAAK,GAAG,CAAC,CAAC,OAAO,WAAW,CAAC;YAC7B,KAAK,GAAG,CAAC,CAAC,OAAO,UAAU,CAAC;YAC5B,KAAK,GAAG,CAAC,CAAC,OAAO,cAAc,CAAC;YAChC,KAAK,GAAG,CAAC,CAAC,OAAO,gBAAgB,CAAC;YAClC,OAAO,CAAC,CAAC,OAAO,eAAe,CAAC;QAClC,CAAC;IACH,CAAC;CACF"}
|
|
1
|
+
{"version":3,"file":"errors.js","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
export { SwarmDockClient } from './client.js';
|
|
2
|
-
export type { SwarmDockClientOptions, RegisterParams, RegisterResult, BalanceResult, TransactionsResult, TaskListResult, TaskDetailResult, RatingsSummary, } from './client.js';
|
|
3
|
-
export { SwarmDockError } from './errors.js';
|
|
4
|
-
export type { Agent, AgentSkill, Task, TaskBid, EscrowTransaction, AgentRating, AATPayload, AgentCard, AgentCardSkill, SSEEvent, AgentUpdateInput, TaskCreateInput, TaskUpdateInput, TaskSubmitInput, TaskListQuery, BidCreateInput, RatingCreateInput, } from '@swarmdock/shared';
|
|
1
|
+
export { SwarmDockClient, SwarmDockAgent } from './client.js';
|
|
2
|
+
export type { SwarmDockClientOptions, RegisterParams, RegisterResult, BalanceResult, TransactionsResult, TaskListResult, TaskDetailResult, RatingsSummary, PortfolioResult, ReputationResult, TaskContext, TaskResult, TaskListing, SwarmDockAgentOptions, } from './client.js';
|
|
3
|
+
export { SwarmDockError, ValidationError, AuthenticationError, AuthorizationError, NotFoundError, ConflictError, RateLimitError, } from './errors.js';
|
|
4
|
+
export type { Agent, AgentSkill, Task, TaskBid, EscrowTransaction, AgentRating, Dispute, AATPayload, AgentCard, AgentCardSkill, PortfolioItem, StoredArtifactRef, SSEEvent, AgentUpdateInput, TaskCreateInput, TaskUpdateInput, TaskSubmitInput, TaskListQuery, BidCreateInput, RatingCreateInput, } from '@swarmdock/shared';
|
|
5
5
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAC9D,YAAY,EACV,sBAAsB,EACtB,cAAc,EACd,cAAc,EACd,aAAa,EACb,kBAAkB,EAClB,cAAc,EACd,gBAAgB,EAChB,cAAc,EACd,eAAe,EACf,gBAAgB,EAChB,WAAW,EACX,UAAU,EACV,WAAW,EACX,qBAAqB,GACtB,MAAM,aAAa,CAAC;AACrB,OAAO,EACL,cAAc,EACd,eAAe,EACf,mBAAmB,EACnB,kBAAkB,EAClB,aAAa,EACb,aAAa,EACb,cAAc,GACf,MAAM,aAAa,CAAC;AAErB,YAAY,EACV,KAAK,EACL,UAAU,EACV,IAAI,EACJ,OAAO,EACP,iBAAiB,EACjB,WAAW,EACX,OAAO,EACP,UAAU,EACV,SAAS,EACT,cAAc,EACd,aAAa,EACb,iBAAiB,EACjB,QAAQ,EACR,gBAAgB,EAChB,eAAe,EACf,eAAe,EACf,eAAe,EACf,aAAa,EACb,cAAc,EACd,iBAAiB,GAClB,MAAM,mBAAmB,CAAC"}
|
package/dist/index.js
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
export { SwarmDockClient } from './client.js';
|
|
2
|
-
export { SwarmDockError } from './errors.js';
|
|
1
|
+
export { SwarmDockClient, SwarmDockAgent } from './client.js';
|
|
2
|
+
export { SwarmDockError, ValidationError, AuthenticationError, AuthorizationError, NotFoundError, ConflictError, RateLimitError, } from './errors.js';
|
|
3
3
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,cAAc,EAAE,MAAM,aAAa,CAAC;AAiB9D,OAAO,EACL,cAAc,EACd,eAAe,EACf,mBAAmB,EACnB,kBAAkB,EAClB,aAAa,EACb,aAAa,EACb,cAAc,GACf,MAAM,aAAa,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,27 +1,35 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@swarmdock/sdk",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.2.1",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"main": "./dist/index.js",
|
|
6
6
|
"types": "./dist/index.d.ts",
|
|
7
|
+
"files": [
|
|
8
|
+
"dist"
|
|
9
|
+
],
|
|
7
10
|
"exports": {
|
|
8
11
|
".": {
|
|
9
12
|
"import": "./dist/index.js",
|
|
10
13
|
"types": "./dist/index.d.ts"
|
|
11
14
|
}
|
|
12
15
|
},
|
|
13
|
-
"scripts": {
|
|
14
|
-
"build": "tsc",
|
|
15
|
-
"dev": "tsc --watch",
|
|
16
|
-
"type-check": "tsc --noEmit"
|
|
17
|
-
},
|
|
18
16
|
"dependencies": {
|
|
19
|
-
"@
|
|
17
|
+
"@x402/evm": "^2.0.4",
|
|
18
|
+
"@x402/fetch": "^2.0.4",
|
|
20
19
|
"jose": "^6.0.0",
|
|
21
20
|
"tweetnacl": "^1.0.3",
|
|
22
|
-
"tweetnacl-util": "^0.15.1"
|
|
21
|
+
"tweetnacl-util": "^0.15.1",
|
|
22
|
+
"viem": "^2.37.4",
|
|
23
|
+
"@swarmdock/shared": "0.2.1"
|
|
23
24
|
},
|
|
24
25
|
"devDependencies": {
|
|
26
|
+
"tsx": "^4.20.6",
|
|
25
27
|
"typescript": "^5.8.0"
|
|
28
|
+
},
|
|
29
|
+
"scripts": {
|
|
30
|
+
"build": "tsc",
|
|
31
|
+
"dev": "tsc --watch",
|
|
32
|
+
"test": "node --import ./node_modules/tsx/dist/loader.mjs --test tests/**/*.test.ts",
|
|
33
|
+
"type-check": "tsc --noEmit"
|
|
26
34
|
}
|
|
27
|
-
}
|
|
35
|
+
}
|
package/.turbo/turbo-build.log
DELETED
package/src/client.ts
DELETED
|
@@ -1,579 +0,0 @@
|
|
|
1
|
-
import nacl from 'tweetnacl';
|
|
2
|
-
import tweetnaclUtil from 'tweetnacl-util';
|
|
3
|
-
const { encodeBase64, decodeBase64 } = tweetnaclUtil;
|
|
4
|
-
import type {
|
|
5
|
-
Agent,
|
|
6
|
-
Task,
|
|
7
|
-
TaskBid,
|
|
8
|
-
EscrowTransaction,
|
|
9
|
-
AgentRating,
|
|
10
|
-
AgentSkill,
|
|
11
|
-
SSEEvent,
|
|
12
|
-
AgentUpdateInput,
|
|
13
|
-
TaskCreateInput,
|
|
14
|
-
TaskSubmitInput,
|
|
15
|
-
BidCreateInput,
|
|
16
|
-
RatingCreateInput,
|
|
17
|
-
} from '@swarmdock/shared';
|
|
18
|
-
import { SwarmDockError } from './errors.js';
|
|
19
|
-
|
|
20
|
-
export interface SwarmDockClientOptions {
|
|
21
|
-
baseUrl: string;
|
|
22
|
-
privateKey?: string; // Ed25519 secret key, base64
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
export interface RegisterParams {
|
|
26
|
-
displayName: string;
|
|
27
|
-
description?: string;
|
|
28
|
-
framework?: string;
|
|
29
|
-
frameworkVersion?: string;
|
|
30
|
-
modelProvider?: string;
|
|
31
|
-
modelName?: string;
|
|
32
|
-
walletAddress: string;
|
|
33
|
-
skills?: Array<{
|
|
34
|
-
skillId: string;
|
|
35
|
-
skillName: string;
|
|
36
|
-
description: string;
|
|
37
|
-
category: string;
|
|
38
|
-
tags?: string[];
|
|
39
|
-
pricingModel?: string;
|
|
40
|
-
basePrice: string;
|
|
41
|
-
examplePrompts?: string[];
|
|
42
|
-
}>;
|
|
43
|
-
agentCardUrl?: string;
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
export interface RegisterResult {
|
|
47
|
-
token: string;
|
|
48
|
-
agent: {
|
|
49
|
-
id: string;
|
|
50
|
-
did: string;
|
|
51
|
-
displayName: string;
|
|
52
|
-
trustLevel: number;
|
|
53
|
-
status: string;
|
|
54
|
-
};
|
|
55
|
-
}
|
|
56
|
-
|
|
57
|
-
export interface BalanceResult {
|
|
58
|
-
agentId: string;
|
|
59
|
-
earned: string;
|
|
60
|
-
spent: string;
|
|
61
|
-
currency: string;
|
|
62
|
-
network: string;
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
export interface TransactionsResult {
|
|
66
|
-
transactions: EscrowTransaction[];
|
|
67
|
-
limit: number;
|
|
68
|
-
offset: number;
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
export interface TaskListResult {
|
|
72
|
-
tasks: Array<Task & { bidCount?: number }>;
|
|
73
|
-
limit: number;
|
|
74
|
-
offset: number;
|
|
75
|
-
total?: number;
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
type TaskListFilters = {
|
|
79
|
-
q?: string;
|
|
80
|
-
status?: string;
|
|
81
|
-
skills?: string;
|
|
82
|
-
budgetMin?: string;
|
|
83
|
-
budgetMax?: string;
|
|
84
|
-
requesterId?: string;
|
|
85
|
-
assigneeId?: string;
|
|
86
|
-
limit?: number;
|
|
87
|
-
offset?: number;
|
|
88
|
-
};
|
|
89
|
-
|
|
90
|
-
export interface TaskDetailResult extends Task {
|
|
91
|
-
requester?: {
|
|
92
|
-
id: string;
|
|
93
|
-
displayName: string;
|
|
94
|
-
trustLevel: number;
|
|
95
|
-
status: string;
|
|
96
|
-
} | null;
|
|
97
|
-
assignee?: {
|
|
98
|
-
id: string;
|
|
99
|
-
displayName: string;
|
|
100
|
-
trustLevel: number;
|
|
101
|
-
status: string;
|
|
102
|
-
} | null;
|
|
103
|
-
bids: Array<TaskBid & {
|
|
104
|
-
bidderDisplayName?: string | null;
|
|
105
|
-
bidder?: {
|
|
106
|
-
id: string;
|
|
107
|
-
displayName: string;
|
|
108
|
-
trustLevel: number;
|
|
109
|
-
status: string;
|
|
110
|
-
} | null;
|
|
111
|
-
}>;
|
|
112
|
-
bidCount: number;
|
|
113
|
-
}
|
|
114
|
-
|
|
115
|
-
export interface RatingsSummary {
|
|
116
|
-
ratings: AgentRating[];
|
|
117
|
-
averages: {
|
|
118
|
-
quality: number;
|
|
119
|
-
speed: number | null;
|
|
120
|
-
communication: number | null;
|
|
121
|
-
reliability: number | null;
|
|
122
|
-
} | null;
|
|
123
|
-
count: number;
|
|
124
|
-
}
|
|
125
|
-
|
|
126
|
-
type SSECallback = (event: SSEEvent) => void;
|
|
127
|
-
|
|
128
|
-
export class SwarmDockClient {
|
|
129
|
-
private readonly baseUrl: string;
|
|
130
|
-
private readonly secretKey: Uint8Array | null;
|
|
131
|
-
private readonly publicKeyBase64: string | null;
|
|
132
|
-
private token: string | null = null;
|
|
133
|
-
private agentId: string | null = null;
|
|
134
|
-
|
|
135
|
-
private sseAbortController: AbortController | null = null;
|
|
136
|
-
|
|
137
|
-
readonly profile: ProfileOperations;
|
|
138
|
-
readonly tasks: TaskOperations;
|
|
139
|
-
readonly events: EventOperations;
|
|
140
|
-
readonly payments: PaymentOperations;
|
|
141
|
-
|
|
142
|
-
constructor(options: SwarmDockClientOptions) {
|
|
143
|
-
this.baseUrl = options.baseUrl.replace(/\/+$/, '');
|
|
144
|
-
if (options.privateKey) {
|
|
145
|
-
this.secretKey = decodeBase64(options.privateKey);
|
|
146
|
-
const keyPair = nacl.sign.keyPair.fromSecretKey(this.secretKey);
|
|
147
|
-
this.publicKeyBase64 = encodeBase64(keyPair.publicKey);
|
|
148
|
-
} else {
|
|
149
|
-
this.secretKey = null;
|
|
150
|
-
this.publicKeyBase64 = null;
|
|
151
|
-
}
|
|
152
|
-
|
|
153
|
-
this.profile = new ProfileOperations(this);
|
|
154
|
-
this.tasks = new TaskOperations(this);
|
|
155
|
-
this.events = new EventOperations(this);
|
|
156
|
-
this.payments = new PaymentOperations(this);
|
|
157
|
-
}
|
|
158
|
-
|
|
159
|
-
async register(params: RegisterParams): Promise<RegisterResult> {
|
|
160
|
-
this.requireSigner();
|
|
161
|
-
|
|
162
|
-
const registerBody = {
|
|
163
|
-
publicKey: this.publicKeyBase64!,
|
|
164
|
-
displayName: params.displayName,
|
|
165
|
-
description: params.description,
|
|
166
|
-
framework: params.framework,
|
|
167
|
-
frameworkVersion: params.frameworkVersion,
|
|
168
|
-
modelProvider: params.modelProvider,
|
|
169
|
-
modelName: params.modelName,
|
|
170
|
-
walletAddress: params.walletAddress,
|
|
171
|
-
agentCardUrl: params.agentCardUrl,
|
|
172
|
-
skills: params.skills ?? [],
|
|
173
|
-
};
|
|
174
|
-
|
|
175
|
-
const registerRes = await this.fetch<{ agentId: string; challenge: string; expiresAt: string }>(
|
|
176
|
-
'/api/v1/agents/register',
|
|
177
|
-
{ method: 'POST', body: registerBody, auth: false },
|
|
178
|
-
);
|
|
179
|
-
|
|
180
|
-
const signature = this.sign(registerRes.challenge);
|
|
181
|
-
|
|
182
|
-
const verifyRes = await this.fetch<RegisterResult>(
|
|
183
|
-
'/api/v1/agents/verify',
|
|
184
|
-
{
|
|
185
|
-
method: 'POST',
|
|
186
|
-
body: {
|
|
187
|
-
publicKey: this.publicKeyBase64!,
|
|
188
|
-
challenge: registerRes.challenge,
|
|
189
|
-
signature,
|
|
190
|
-
},
|
|
191
|
-
auth: false,
|
|
192
|
-
},
|
|
193
|
-
);
|
|
194
|
-
|
|
195
|
-
this.token = verifyRes.token;
|
|
196
|
-
this.agentId = verifyRes.agent.id;
|
|
197
|
-
|
|
198
|
-
return verifyRes;
|
|
199
|
-
}
|
|
200
|
-
|
|
201
|
-
async authenticate(): Promise<void> {
|
|
202
|
-
if (this.token) {
|
|
203
|
-
return;
|
|
204
|
-
}
|
|
205
|
-
|
|
206
|
-
this.requireSigner();
|
|
207
|
-
|
|
208
|
-
const challengeRes = await this.fetch<{ challenge: string; expiresAt: string }>(
|
|
209
|
-
'/api/v1/agents/login/challenge',
|
|
210
|
-
{
|
|
211
|
-
method: 'POST',
|
|
212
|
-
body: { publicKey: this.publicKeyBase64! },
|
|
213
|
-
auth: false,
|
|
214
|
-
},
|
|
215
|
-
);
|
|
216
|
-
|
|
217
|
-
const verifyRes = await this.fetch<RegisterResult>(
|
|
218
|
-
'/api/v1/agents/login/verify',
|
|
219
|
-
{
|
|
220
|
-
method: 'POST',
|
|
221
|
-
body: {
|
|
222
|
-
publicKey: this.publicKeyBase64!,
|
|
223
|
-
challenge: challengeRes.challenge,
|
|
224
|
-
signature: this.sign(challengeRes.challenge),
|
|
225
|
-
},
|
|
226
|
-
auth: false,
|
|
227
|
-
},
|
|
228
|
-
);
|
|
229
|
-
|
|
230
|
-
this.token = verifyRes.token;
|
|
231
|
-
this.agentId = verifyRes.agent.id;
|
|
232
|
-
}
|
|
233
|
-
|
|
234
|
-
async heartbeat(): Promise<{ token: string }> {
|
|
235
|
-
await this.authenticate();
|
|
236
|
-
|
|
237
|
-
const res = await this.fetch<{ token: string; lastHeartbeat: string }>(
|
|
238
|
-
`/api/v1/agents/${this.agentId!}/heartbeat`,
|
|
239
|
-
{ method: 'POST' },
|
|
240
|
-
);
|
|
241
|
-
|
|
242
|
-
this.token = res.token;
|
|
243
|
-
return { token: res.token };
|
|
244
|
-
}
|
|
245
|
-
|
|
246
|
-
async rate(input: RatingCreateInput): Promise<AgentRating> {
|
|
247
|
-
return this.fetch<AgentRating>('/api/v1/ratings', {
|
|
248
|
-
method: 'POST',
|
|
249
|
-
body: input,
|
|
250
|
-
});
|
|
251
|
-
}
|
|
252
|
-
|
|
253
|
-
// -- Internal helpers exposed to sub-operation classes --
|
|
254
|
-
|
|
255
|
-
/** @internal */
|
|
256
|
-
async fetch<T>(path: string, options: FetchOptions = {}): Promise<T> {
|
|
257
|
-
const { method = 'GET', body, query, auth = true } = options;
|
|
258
|
-
|
|
259
|
-
let url = `${this.baseUrl}${path}`;
|
|
260
|
-
if (query) {
|
|
261
|
-
const params = new URLSearchParams();
|
|
262
|
-
for (const [key, value] of Object.entries(query)) {
|
|
263
|
-
if (value !== undefined && value !== null) {
|
|
264
|
-
params.set(key, String(value));
|
|
265
|
-
}
|
|
266
|
-
}
|
|
267
|
-
const qs = params.toString();
|
|
268
|
-
if (qs) url += `?${qs}`;
|
|
269
|
-
}
|
|
270
|
-
|
|
271
|
-
const headers: Record<string, string> = {
|
|
272
|
-
'Content-Type': 'application/json',
|
|
273
|
-
'Accept': 'application/json',
|
|
274
|
-
};
|
|
275
|
-
|
|
276
|
-
if (auth) {
|
|
277
|
-
await this.authenticate();
|
|
278
|
-
headers['Authorization'] = `Bearer ${this.token!}`;
|
|
279
|
-
}
|
|
280
|
-
|
|
281
|
-
const res = await globalThis.fetch(url, {
|
|
282
|
-
method,
|
|
283
|
-
headers,
|
|
284
|
-
body: body ? JSON.stringify(body) : undefined,
|
|
285
|
-
});
|
|
286
|
-
|
|
287
|
-
if (!res.ok) {
|
|
288
|
-
let errorData: { error?: string; details?: unknown } | undefined;
|
|
289
|
-
try {
|
|
290
|
-
errorData = await res.json() as { error?: string; details?: unknown };
|
|
291
|
-
} catch {
|
|
292
|
-
// Response may not be JSON
|
|
293
|
-
}
|
|
294
|
-
throw new SwarmDockError(
|
|
295
|
-
res.status,
|
|
296
|
-
errorData?.error ?? `Request failed: ${method} ${path}`,
|
|
297
|
-
errorData?.details,
|
|
298
|
-
);
|
|
299
|
-
}
|
|
300
|
-
|
|
301
|
-
return res.json() as Promise<T>;
|
|
302
|
-
}
|
|
303
|
-
|
|
304
|
-
/** @internal */
|
|
305
|
-
getAgentId(): string {
|
|
306
|
-
this.requireAuth();
|
|
307
|
-
return this.agentId!;
|
|
308
|
-
}
|
|
309
|
-
|
|
310
|
-
/** @internal */
|
|
311
|
-
getToken(): string {
|
|
312
|
-
this.requireAuth();
|
|
313
|
-
return this.token!;
|
|
314
|
-
}
|
|
315
|
-
|
|
316
|
-
/** @internal */
|
|
317
|
-
getBaseUrl(): string {
|
|
318
|
-
return this.baseUrl;
|
|
319
|
-
}
|
|
320
|
-
|
|
321
|
-
/** @internal */
|
|
322
|
-
setToken(token: string): void {
|
|
323
|
-
this.token = token;
|
|
324
|
-
}
|
|
325
|
-
|
|
326
|
-
/** @internal */
|
|
327
|
-
getSseAbortController(): AbortController | null {
|
|
328
|
-
return this.sseAbortController;
|
|
329
|
-
}
|
|
330
|
-
|
|
331
|
-
/** @internal */
|
|
332
|
-
setSseAbortController(controller: AbortController | null): void {
|
|
333
|
-
this.sseAbortController = controller;
|
|
334
|
-
}
|
|
335
|
-
|
|
336
|
-
private requireAuth(): void {
|
|
337
|
-
if (!this.token || !this.agentId) {
|
|
338
|
-
throw new SwarmDockError(401, 'Not authenticated. Call register() first.');
|
|
339
|
-
}
|
|
340
|
-
}
|
|
341
|
-
|
|
342
|
-
private requireSigner(): void {
|
|
343
|
-
if (!this.secretKey || !this.publicKeyBase64) {
|
|
344
|
-
throw new SwarmDockError(401, 'This operation requires an Ed25519 private key.');
|
|
345
|
-
}
|
|
346
|
-
}
|
|
347
|
-
|
|
348
|
-
private sign(message: string): string {
|
|
349
|
-
this.requireSigner();
|
|
350
|
-
const messageBytes = new TextEncoder().encode(message);
|
|
351
|
-
const signature = nacl.sign.detached(messageBytes, this.secretKey!);
|
|
352
|
-
return encodeBase64(signature);
|
|
353
|
-
}
|
|
354
|
-
}
|
|
355
|
-
|
|
356
|
-
interface FetchOptions {
|
|
357
|
-
method?: string;
|
|
358
|
-
body?: unknown;
|
|
359
|
-
query?: Record<string, string | number | undefined | null>;
|
|
360
|
-
auth?: boolean;
|
|
361
|
-
}
|
|
362
|
-
|
|
363
|
-
// -- Sub-operation classes --
|
|
364
|
-
|
|
365
|
-
class ProfileOperations {
|
|
366
|
-
constructor(private readonly client: SwarmDockClient) {}
|
|
367
|
-
|
|
368
|
-
async get(agentId?: string): Promise<Agent & { skills: AgentSkill[] }> {
|
|
369
|
-
if (!agentId) {
|
|
370
|
-
await this.client.authenticate();
|
|
371
|
-
}
|
|
372
|
-
const id = agentId ?? this.client.getAgentId();
|
|
373
|
-
return this.client.fetch(`/api/v1/agents/${id}`, { auth: false });
|
|
374
|
-
}
|
|
375
|
-
|
|
376
|
-
async update(fields: AgentUpdateInput): Promise<Agent> {
|
|
377
|
-
await this.client.authenticate();
|
|
378
|
-
const id = this.client.getAgentId();
|
|
379
|
-
return this.client.fetch(`/api/v1/agents/${id}`, {
|
|
380
|
-
method: 'PATCH',
|
|
381
|
-
body: fields,
|
|
382
|
-
});
|
|
383
|
-
}
|
|
384
|
-
|
|
385
|
-
async ratings(agentId?: string): Promise<RatingsSummary> {
|
|
386
|
-
if (!agentId) {
|
|
387
|
-
await this.client.authenticate();
|
|
388
|
-
}
|
|
389
|
-
const id = agentId ?? this.client.getAgentId();
|
|
390
|
-
return this.client.fetch(`/api/v1/agents/${id}/ratings`, { auth: false });
|
|
391
|
-
}
|
|
392
|
-
|
|
393
|
-
async match(params: { description: string; skills?: string[]; limit?: number }): Promise<{ matches: Agent[] }> {
|
|
394
|
-
return this.client.fetch('/api/v1/agents/match', { method: 'POST', body: params, auth: false });
|
|
395
|
-
}
|
|
396
|
-
}
|
|
397
|
-
|
|
398
|
-
class TaskOperations {
|
|
399
|
-
constructor(private readonly client: SwarmDockClient) {}
|
|
400
|
-
|
|
401
|
-
async list(filters?: TaskListFilters): Promise<TaskListResult> {
|
|
402
|
-
const query: Record<string, string | number | undefined | null> = {};
|
|
403
|
-
if (filters) {
|
|
404
|
-
if (filters.q) query.q = filters.q;
|
|
405
|
-
if (filters.status) query.status = filters.status;
|
|
406
|
-
if (filters.skills) query.skills = filters.skills;
|
|
407
|
-
if (filters.budgetMin) query.budgetMin = filters.budgetMin;
|
|
408
|
-
if (filters.budgetMax) query.budgetMax = filters.budgetMax;
|
|
409
|
-
if (filters.requesterId) query.requesterId = filters.requesterId;
|
|
410
|
-
if (filters.assigneeId) query.assigneeId = filters.assigneeId;
|
|
411
|
-
if (filters.limit !== undefined) query.limit = filters.limit;
|
|
412
|
-
if (filters.offset !== undefined) query.offset = filters.offset;
|
|
413
|
-
}
|
|
414
|
-
return this.client.fetch('/api/v1/tasks', { query, auth: false });
|
|
415
|
-
}
|
|
416
|
-
|
|
417
|
-
async create(input: TaskCreateInput): Promise<Task> {
|
|
418
|
-
return this.client.fetch('/api/v1/tasks', {
|
|
419
|
-
method: 'POST',
|
|
420
|
-
body: input,
|
|
421
|
-
});
|
|
422
|
-
}
|
|
423
|
-
|
|
424
|
-
async get(taskId: string): Promise<TaskDetailResult> {
|
|
425
|
-
return this.client.fetch(`/api/v1/tasks/${taskId}`, { auth: false });
|
|
426
|
-
}
|
|
427
|
-
|
|
428
|
-
async listBids(taskId: string): Promise<{ bids: TaskBid[] }> {
|
|
429
|
-
return this.client.fetch(`/api/v1/tasks/${taskId}/bids`, { auth: false });
|
|
430
|
-
}
|
|
431
|
-
|
|
432
|
-
async bid(taskId: string, input: BidCreateInput): Promise<TaskBid> {
|
|
433
|
-
return this.client.fetch(`/api/v1/tasks/${taskId}/bids`, {
|
|
434
|
-
method: 'POST',
|
|
435
|
-
body: input,
|
|
436
|
-
});
|
|
437
|
-
}
|
|
438
|
-
|
|
439
|
-
async acceptBid(taskId: string, bidId: string): Promise<{ task: Task; acceptedBid: TaskBid; escrow?: EscrowTransaction }> {
|
|
440
|
-
return this.client.fetch(`/api/v1/tasks/${taskId}/bids/${bidId}/accept`, {
|
|
441
|
-
method: 'POST',
|
|
442
|
-
});
|
|
443
|
-
}
|
|
444
|
-
|
|
445
|
-
async start(taskId: string): Promise<Task> {
|
|
446
|
-
return this.client.fetch(`/api/v1/tasks/${taskId}/start`, {
|
|
447
|
-
method: 'POST',
|
|
448
|
-
});
|
|
449
|
-
}
|
|
450
|
-
|
|
451
|
-
async submit(taskId: string, input: TaskSubmitInput): Promise<Task> {
|
|
452
|
-
return this.client.fetch(`/api/v1/tasks/${taskId}/submit`, {
|
|
453
|
-
method: 'POST',
|
|
454
|
-
body: input,
|
|
455
|
-
});
|
|
456
|
-
}
|
|
457
|
-
|
|
458
|
-
async approve(taskId: string): Promise<Task> {
|
|
459
|
-
return this.client.fetch(`/api/v1/tasks/${taskId}/approve`, {
|
|
460
|
-
method: 'POST',
|
|
461
|
-
});
|
|
462
|
-
}
|
|
463
|
-
|
|
464
|
-
async reject(taskId: string, reason?: string): Promise<Task> {
|
|
465
|
-
return this.client.fetch(`/api/v1/tasks/${taskId}/reject`, {
|
|
466
|
-
method: 'POST',
|
|
467
|
-
body: reason ? { reason } : undefined,
|
|
468
|
-
});
|
|
469
|
-
}
|
|
470
|
-
}
|
|
471
|
-
|
|
472
|
-
class EventOperations {
|
|
473
|
-
private callback: SSECallback | null = null;
|
|
474
|
-
|
|
475
|
-
constructor(private readonly client: SwarmDockClient) {}
|
|
476
|
-
|
|
477
|
-
subscribe(callback: SSECallback): void {
|
|
478
|
-
this.unsubscribe();
|
|
479
|
-
this.callback = callback;
|
|
480
|
-
|
|
481
|
-
const controller = new AbortController();
|
|
482
|
-
this.client.setSseAbortController(controller);
|
|
483
|
-
|
|
484
|
-
const url = `${this.client.getBaseUrl()}/api/v1/events`;
|
|
485
|
-
const token = this.client.getToken();
|
|
486
|
-
|
|
487
|
-
this.connectSSE(url, token, controller.signal);
|
|
488
|
-
}
|
|
489
|
-
|
|
490
|
-
unsubscribe(): void {
|
|
491
|
-
const controller = this.client.getSseAbortController();
|
|
492
|
-
if (controller) {
|
|
493
|
-
controller.abort();
|
|
494
|
-
this.client.setSseAbortController(null);
|
|
495
|
-
}
|
|
496
|
-
this.callback = null;
|
|
497
|
-
}
|
|
498
|
-
|
|
499
|
-
private async connectSSE(url: string, token: string, signal: AbortSignal): Promise<void> {
|
|
500
|
-
try {
|
|
501
|
-
const response = await globalThis.fetch(url, {
|
|
502
|
-
headers: {
|
|
503
|
-
'Authorization': `Bearer ${token}`,
|
|
504
|
-
'Accept': 'text/event-stream',
|
|
505
|
-
'Cache-Control': 'no-cache',
|
|
506
|
-
},
|
|
507
|
-
signal,
|
|
508
|
-
});
|
|
509
|
-
|
|
510
|
-
if (!response.ok) {
|
|
511
|
-
throw new SwarmDockError(response.status, 'Failed to connect to SSE stream');
|
|
512
|
-
}
|
|
513
|
-
|
|
514
|
-
const reader = response.body?.getReader();
|
|
515
|
-
if (!reader) {
|
|
516
|
-
throw new SwarmDockError(500, 'Response body is not readable');
|
|
517
|
-
}
|
|
518
|
-
|
|
519
|
-
const decoder = new TextDecoder();
|
|
520
|
-
let buffer = '';
|
|
521
|
-
|
|
522
|
-
while (!signal.aborted) {
|
|
523
|
-
const { done, value } = await reader.read();
|
|
524
|
-
if (done) break;
|
|
525
|
-
|
|
526
|
-
buffer += decoder.decode(value, { stream: true });
|
|
527
|
-
const lines = buffer.split('\n');
|
|
528
|
-
buffer = lines.pop() ?? '';
|
|
529
|
-
|
|
530
|
-
let currentEvent: string | null = null;
|
|
531
|
-
let currentData: string | null = null;
|
|
532
|
-
|
|
533
|
-
for (const line of lines) {
|
|
534
|
-
if (line.startsWith('event: ')) {
|
|
535
|
-
currentEvent = line.slice(7).trim();
|
|
536
|
-
} else if (line.startsWith('data: ')) {
|
|
537
|
-
currentData = line.slice(6).trim();
|
|
538
|
-
} else if (line === '' && currentEvent && currentData) {
|
|
539
|
-
if (this.callback) {
|
|
540
|
-
try {
|
|
541
|
-
const parsed = JSON.parse(currentData);
|
|
542
|
-
this.callback({
|
|
543
|
-
type: currentEvent,
|
|
544
|
-
data: parsed,
|
|
545
|
-
timestamp: (parsed as Record<string, unknown>).timestamp as string ?? new Date().toISOString(),
|
|
546
|
-
});
|
|
547
|
-
} catch {
|
|
548
|
-
// Skip malformed events
|
|
549
|
-
}
|
|
550
|
-
}
|
|
551
|
-
currentEvent = null;
|
|
552
|
-
currentData = null;
|
|
553
|
-
}
|
|
554
|
-
}
|
|
555
|
-
}
|
|
556
|
-
} catch (err) {
|
|
557
|
-
if (signal.aborted) return;
|
|
558
|
-
throw err;
|
|
559
|
-
}
|
|
560
|
-
}
|
|
561
|
-
}
|
|
562
|
-
|
|
563
|
-
class PaymentOperations {
|
|
564
|
-
constructor(private readonly client: SwarmDockClient) {}
|
|
565
|
-
|
|
566
|
-
async balance(): Promise<BalanceResult> {
|
|
567
|
-
await this.client.authenticate();
|
|
568
|
-
const id = this.client.getAgentId();
|
|
569
|
-
return this.client.fetch(`/api/v1/payments/agents/${id}/balance`);
|
|
570
|
-
}
|
|
571
|
-
|
|
572
|
-
async transactions(limit?: number, offset?: number): Promise<TransactionsResult> {
|
|
573
|
-
await this.client.authenticate();
|
|
574
|
-
const id = this.client.getAgentId();
|
|
575
|
-
return this.client.fetch(`/api/v1/payments/agents/${id}/transactions`, {
|
|
576
|
-
query: { limit: limit ?? undefined, offset: offset ?? undefined },
|
|
577
|
-
});
|
|
578
|
-
}
|
|
579
|
-
}
|
package/src/errors.ts
DELETED
|
@@ -1,26 +0,0 @@
|
|
|
1
|
-
export class SwarmDockError extends Error {
|
|
2
|
-
readonly status: number;
|
|
3
|
-
readonly code: string;
|
|
4
|
-
readonly details?: unknown;
|
|
5
|
-
|
|
6
|
-
constructor(status: number, message: string, details?: unknown) {
|
|
7
|
-
super(message);
|
|
8
|
-
this.name = 'SwarmDockError';
|
|
9
|
-
this.status = status;
|
|
10
|
-
this.code = SwarmDockError.statusToCode(status);
|
|
11
|
-
this.details = details;
|
|
12
|
-
}
|
|
13
|
-
|
|
14
|
-
private static statusToCode(status: number): string {
|
|
15
|
-
switch (status) {
|
|
16
|
-
case 400: return 'BAD_REQUEST';
|
|
17
|
-
case 401: return 'UNAUTHORIZED';
|
|
18
|
-
case 403: return 'FORBIDDEN';
|
|
19
|
-
case 404: return 'NOT_FOUND';
|
|
20
|
-
case 409: return 'CONFLICT';
|
|
21
|
-
case 429: return 'RATE_LIMITED';
|
|
22
|
-
case 500: return 'INTERNAL_ERROR';
|
|
23
|
-
default: return 'UNKNOWN_ERROR';
|
|
24
|
-
}
|
|
25
|
-
}
|
|
26
|
-
}
|