@sovant/sdk 1.0.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/LICENSE +21 -0
- package/README.md +370 -0
- package/dist/index.d.mts +369 -0
- package/dist/index.d.ts +369 -0
- package/dist/index.js +463 -0
- package/dist/index.mjs +430 -0
- package/package.json +56 -0
package/dist/index.mjs
ADDED
|
@@ -0,0 +1,430 @@
|
|
|
1
|
+
// src/errors.ts
|
|
2
|
+
var SovantError = class extends Error {
|
|
3
|
+
constructor(message, statusCode, details) {
|
|
4
|
+
super(message);
|
|
5
|
+
this.name = "SovantError";
|
|
6
|
+
this.statusCode = statusCode;
|
|
7
|
+
this.details = details;
|
|
8
|
+
}
|
|
9
|
+
};
|
|
10
|
+
var AuthenticationError = class extends SovantError {
|
|
11
|
+
constructor(message = "Authentication failed") {
|
|
12
|
+
super(message, 401);
|
|
13
|
+
this.name = "AuthenticationError";
|
|
14
|
+
}
|
|
15
|
+
};
|
|
16
|
+
var RateLimitError = class extends SovantError {
|
|
17
|
+
constructor(message = "Rate limit exceeded", retryAfter) {
|
|
18
|
+
super(message, 429);
|
|
19
|
+
this.name = "RateLimitError";
|
|
20
|
+
this.retryAfter = retryAfter;
|
|
21
|
+
}
|
|
22
|
+
};
|
|
23
|
+
var ValidationError = class extends SovantError {
|
|
24
|
+
constructor(message = "Validation failed", errors) {
|
|
25
|
+
super(message, 400);
|
|
26
|
+
this.name = "ValidationError";
|
|
27
|
+
this.errors = errors;
|
|
28
|
+
}
|
|
29
|
+
};
|
|
30
|
+
var NotFoundError = class extends SovantError {
|
|
31
|
+
constructor(message = "Resource not found") {
|
|
32
|
+
super(message, 404);
|
|
33
|
+
this.name = "NotFoundError";
|
|
34
|
+
}
|
|
35
|
+
};
|
|
36
|
+
var NetworkError = class extends SovantError {
|
|
37
|
+
constructor(message = "Network request failed") {
|
|
38
|
+
super(message);
|
|
39
|
+
this.name = "NetworkError";
|
|
40
|
+
}
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
// src/client.ts
|
|
44
|
+
var BaseClient = class {
|
|
45
|
+
constructor(config) {
|
|
46
|
+
this.config = {
|
|
47
|
+
apiKey: config.apiKey,
|
|
48
|
+
baseUrl: config.baseUrl || "https://api.sovant.ai/v1",
|
|
49
|
+
timeout: config.timeout || 3e4,
|
|
50
|
+
maxRetries: config.maxRetries || 3,
|
|
51
|
+
retryDelay: config.retryDelay || 1e3
|
|
52
|
+
};
|
|
53
|
+
if (!this.config.apiKey) {
|
|
54
|
+
throw new AuthenticationError("API key is required");
|
|
55
|
+
}
|
|
56
|
+
if (!this.config.baseUrl.startsWith("https://")) {
|
|
57
|
+
throw new SovantError("API base URL must use HTTPS for security");
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
async request(method, path, data, retryCount = 0) {
|
|
61
|
+
const url = `${this.config.baseUrl}${path}`;
|
|
62
|
+
const controller = new AbortController();
|
|
63
|
+
const timeoutId = setTimeout(() => controller.abort(), this.config.timeout);
|
|
64
|
+
try {
|
|
65
|
+
const response = await fetch(url, {
|
|
66
|
+
method,
|
|
67
|
+
headers: {
|
|
68
|
+
Authorization: `Bearer ${this.config.apiKey}`,
|
|
69
|
+
"Content-Type": "application/json",
|
|
70
|
+
"X-SDK-Version": "1.0.0",
|
|
71
|
+
"X-SDK-Language": "javascript"
|
|
72
|
+
},
|
|
73
|
+
body: data ? JSON.stringify(data) : void 0,
|
|
74
|
+
signal: controller.signal
|
|
75
|
+
});
|
|
76
|
+
clearTimeout(timeoutId);
|
|
77
|
+
if (!response.ok) {
|
|
78
|
+
await this.handleErrorResponse(response);
|
|
79
|
+
}
|
|
80
|
+
const responseData = await response.json();
|
|
81
|
+
return responseData;
|
|
82
|
+
} catch (error) {
|
|
83
|
+
clearTimeout(timeoutId);
|
|
84
|
+
if (error instanceof SovantError) {
|
|
85
|
+
throw error;
|
|
86
|
+
}
|
|
87
|
+
if (error instanceof Error) {
|
|
88
|
+
if (error.name === "AbortError") {
|
|
89
|
+
throw new NetworkError("Request timeout");
|
|
90
|
+
}
|
|
91
|
+
if (retryCount < this.config.maxRetries) {
|
|
92
|
+
await this.delay(this.config.retryDelay * Math.pow(2, retryCount));
|
|
93
|
+
return this.request(method, path, data, retryCount + 1);
|
|
94
|
+
}
|
|
95
|
+
throw new NetworkError(error.message);
|
|
96
|
+
}
|
|
97
|
+
throw new SovantError("Unknown error occurred");
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
async handleErrorResponse(response) {
|
|
101
|
+
let errorData;
|
|
102
|
+
try {
|
|
103
|
+
errorData = await response.json();
|
|
104
|
+
} catch {
|
|
105
|
+
errorData = {
|
|
106
|
+
error: "unknown_error",
|
|
107
|
+
message: `HTTP ${response.status} ${response.statusText}`,
|
|
108
|
+
status_code: response.status
|
|
109
|
+
};
|
|
110
|
+
}
|
|
111
|
+
switch (response.status) {
|
|
112
|
+
case 401:
|
|
113
|
+
throw new AuthenticationError(errorData.message);
|
|
114
|
+
case 404:
|
|
115
|
+
throw new NotFoundError(errorData.message);
|
|
116
|
+
case 429:
|
|
117
|
+
const retryAfter = response.headers.get("Retry-After");
|
|
118
|
+
throw new RateLimitError(
|
|
119
|
+
errorData.message,
|
|
120
|
+
retryAfter ? parseInt(retryAfter, 10) : void 0
|
|
121
|
+
);
|
|
122
|
+
case 400:
|
|
123
|
+
case 422:
|
|
124
|
+
throw new ValidationError(errorData.message, errorData.details);
|
|
125
|
+
default:
|
|
126
|
+
throw new SovantError(
|
|
127
|
+
errorData.message,
|
|
128
|
+
response.status,
|
|
129
|
+
errorData.details
|
|
130
|
+
);
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
delay(ms) {
|
|
134
|
+
return new Promise((resolve) => setTimeout(resolve, ms));
|
|
135
|
+
}
|
|
136
|
+
buildQueryString(params) {
|
|
137
|
+
const searchParams = new URLSearchParams();
|
|
138
|
+
Object.entries(params).forEach(([key, value]) => {
|
|
139
|
+
if (value !== void 0 && value !== null) {
|
|
140
|
+
if (Array.isArray(value)) {
|
|
141
|
+
value.forEach((v) => searchParams.append(key, String(v)));
|
|
142
|
+
} else {
|
|
143
|
+
searchParams.append(key, String(value));
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
});
|
|
147
|
+
const queryString = searchParams.toString();
|
|
148
|
+
return queryString ? `?${queryString}` : "";
|
|
149
|
+
}
|
|
150
|
+
};
|
|
151
|
+
|
|
152
|
+
// src/resources/memories.ts
|
|
153
|
+
var Memories = class extends BaseClient {
|
|
154
|
+
/**
|
|
155
|
+
* Create a new memory
|
|
156
|
+
*/
|
|
157
|
+
async create(data) {
|
|
158
|
+
return this.request("POST", "/memory", data);
|
|
159
|
+
}
|
|
160
|
+
/**
|
|
161
|
+
* Get a memory by ID
|
|
162
|
+
*/
|
|
163
|
+
async get(id) {
|
|
164
|
+
return this.request("GET", `/memory/${id}`);
|
|
165
|
+
}
|
|
166
|
+
/**
|
|
167
|
+
* Update a memory
|
|
168
|
+
*/
|
|
169
|
+
async update(id, data) {
|
|
170
|
+
return this.request("PUT", `/memory/${id}`, data);
|
|
171
|
+
}
|
|
172
|
+
/**
|
|
173
|
+
* Delete a memory
|
|
174
|
+
*/
|
|
175
|
+
async delete(id) {
|
|
176
|
+
await this.request("DELETE", `/memory/${id}`);
|
|
177
|
+
}
|
|
178
|
+
/**
|
|
179
|
+
* List memories with pagination
|
|
180
|
+
*/
|
|
181
|
+
async list(options) {
|
|
182
|
+
const queryString = this.buildQueryString(options || {});
|
|
183
|
+
return this.request(
|
|
184
|
+
"GET",
|
|
185
|
+
`/memory${queryString}`
|
|
186
|
+
);
|
|
187
|
+
}
|
|
188
|
+
/**
|
|
189
|
+
* Search memories
|
|
190
|
+
*/
|
|
191
|
+
async search(options) {
|
|
192
|
+
const queryString = this.buildQueryString({
|
|
193
|
+
q: options.query,
|
|
194
|
+
limit: options.limit,
|
|
195
|
+
offset: options.offset,
|
|
196
|
+
type: options.type,
|
|
197
|
+
tags: options.tags,
|
|
198
|
+
created_after: options.created_after,
|
|
199
|
+
created_before: options.created_before,
|
|
200
|
+
search_type: options.search_type,
|
|
201
|
+
include_archived: options.include_archived,
|
|
202
|
+
sort_by: options.sort_by,
|
|
203
|
+
sort_order: options.sort_order
|
|
204
|
+
});
|
|
205
|
+
const response = await this.request(
|
|
206
|
+
"GET",
|
|
207
|
+
`/memory/search${queryString}`
|
|
208
|
+
);
|
|
209
|
+
return response.results;
|
|
210
|
+
}
|
|
211
|
+
/**
|
|
212
|
+
* Batch create memories
|
|
213
|
+
*/
|
|
214
|
+
async createBatch(memories) {
|
|
215
|
+
return this.request("POST", "/memory/batch", {
|
|
216
|
+
memories
|
|
217
|
+
});
|
|
218
|
+
}
|
|
219
|
+
/**
|
|
220
|
+
* Batch delete memories
|
|
221
|
+
*/
|
|
222
|
+
async deleteBatch(ids) {
|
|
223
|
+
return this.request("POST", "/memory/batch/delete", {
|
|
224
|
+
ids
|
|
225
|
+
});
|
|
226
|
+
}
|
|
227
|
+
/**
|
|
228
|
+
* Get memory insights and analytics
|
|
229
|
+
*/
|
|
230
|
+
async getInsights(options) {
|
|
231
|
+
const queryString = this.buildQueryString(options || {});
|
|
232
|
+
return this.request("GET", `/memory/insights${queryString}`);
|
|
233
|
+
}
|
|
234
|
+
/**
|
|
235
|
+
* Archive a memory
|
|
236
|
+
*/
|
|
237
|
+
async archive(id) {
|
|
238
|
+
return this.update(id, { is_archived: true });
|
|
239
|
+
}
|
|
240
|
+
/**
|
|
241
|
+
* Unarchive a memory
|
|
242
|
+
*/
|
|
243
|
+
async unarchive(id) {
|
|
244
|
+
return this.update(id, { is_archived: false });
|
|
245
|
+
}
|
|
246
|
+
/**
|
|
247
|
+
* Pin a memory
|
|
248
|
+
*/
|
|
249
|
+
async pin(id) {
|
|
250
|
+
return this.update(id, { is_pinned: true });
|
|
251
|
+
}
|
|
252
|
+
/**
|
|
253
|
+
* Unpin a memory
|
|
254
|
+
*/
|
|
255
|
+
async unpin(id) {
|
|
256
|
+
return this.update(id, { is_pinned: false });
|
|
257
|
+
}
|
|
258
|
+
/**
|
|
259
|
+
* Get related memories
|
|
260
|
+
*/
|
|
261
|
+
async getRelated(id, options) {
|
|
262
|
+
const queryString = this.buildQueryString(options || {});
|
|
263
|
+
const response = await this.request(
|
|
264
|
+
"GET",
|
|
265
|
+
`/memory/${id}/related${queryString}`
|
|
266
|
+
);
|
|
267
|
+
return response.results;
|
|
268
|
+
}
|
|
269
|
+
};
|
|
270
|
+
|
|
271
|
+
// src/resources/threads.ts
|
|
272
|
+
var Threads = class extends BaseClient {
|
|
273
|
+
/**
|
|
274
|
+
* Create a new thread
|
|
275
|
+
*/
|
|
276
|
+
async create(data) {
|
|
277
|
+
return this.request("POST", "/threads", data);
|
|
278
|
+
}
|
|
279
|
+
/**
|
|
280
|
+
* Get a thread by ID
|
|
281
|
+
*/
|
|
282
|
+
async get(id, includeMemories = false) {
|
|
283
|
+
const queryString = includeMemories ? "?include_memories=true" : "";
|
|
284
|
+
return this.request(
|
|
285
|
+
"GET",
|
|
286
|
+
`/threads/${id}${queryString}`
|
|
287
|
+
);
|
|
288
|
+
}
|
|
289
|
+
/**
|
|
290
|
+
* Update a thread
|
|
291
|
+
*/
|
|
292
|
+
async update(id, data) {
|
|
293
|
+
return this.request("PUT", `/threads/${id}`, data);
|
|
294
|
+
}
|
|
295
|
+
/**
|
|
296
|
+
* Delete a thread
|
|
297
|
+
*/
|
|
298
|
+
async delete(id, deleteMemories = false) {
|
|
299
|
+
const queryString = deleteMemories ? "?delete_memories=true" : "";
|
|
300
|
+
await this.request("DELETE", `/threads/${id}${queryString}`);
|
|
301
|
+
}
|
|
302
|
+
/**
|
|
303
|
+
* List threads with pagination
|
|
304
|
+
*/
|
|
305
|
+
async list(options) {
|
|
306
|
+
const queryString = this.buildQueryString(options || {});
|
|
307
|
+
return this.request(
|
|
308
|
+
"GET",
|
|
309
|
+
`/threads${queryString}`
|
|
310
|
+
);
|
|
311
|
+
}
|
|
312
|
+
/**
|
|
313
|
+
* Add memories to a thread
|
|
314
|
+
*/
|
|
315
|
+
async addMemories(id, memoryIds) {
|
|
316
|
+
return this.request("POST", `/threads/${id}/memories`, {
|
|
317
|
+
add: memoryIds
|
|
318
|
+
});
|
|
319
|
+
}
|
|
320
|
+
/**
|
|
321
|
+
* Remove memories from a thread
|
|
322
|
+
*/
|
|
323
|
+
async removeMemories(id, memoryIds) {
|
|
324
|
+
return this.request("POST", `/threads/${id}/memories`, {
|
|
325
|
+
remove: memoryIds
|
|
326
|
+
});
|
|
327
|
+
}
|
|
328
|
+
/**
|
|
329
|
+
* Get memories in a thread
|
|
330
|
+
*/
|
|
331
|
+
async getMemories(id, options) {
|
|
332
|
+
const queryString = this.buildQueryString(options || {});
|
|
333
|
+
return this.request(
|
|
334
|
+
"GET",
|
|
335
|
+
`/threads/${id}/memories${queryString}`
|
|
336
|
+
);
|
|
337
|
+
}
|
|
338
|
+
/**
|
|
339
|
+
* Get thread statistics
|
|
340
|
+
*/
|
|
341
|
+
async getStats(id) {
|
|
342
|
+
return this.request("GET", `/threads/${id}/stats`);
|
|
343
|
+
}
|
|
344
|
+
/**
|
|
345
|
+
* Archive a thread
|
|
346
|
+
*/
|
|
347
|
+
async archive(id) {
|
|
348
|
+
return this.update(id, { status: "archived" });
|
|
349
|
+
}
|
|
350
|
+
/**
|
|
351
|
+
* Unarchive a thread
|
|
352
|
+
*/
|
|
353
|
+
async unarchive(id) {
|
|
354
|
+
return this.update(id, { status: "active" });
|
|
355
|
+
}
|
|
356
|
+
/**
|
|
357
|
+
* Complete a thread
|
|
358
|
+
*/
|
|
359
|
+
async complete(id) {
|
|
360
|
+
return this.update(id, { status: "completed" });
|
|
361
|
+
}
|
|
362
|
+
/**
|
|
363
|
+
* Search threads
|
|
364
|
+
*/
|
|
365
|
+
async search(options) {
|
|
366
|
+
const queryString = this.buildQueryString({
|
|
367
|
+
q: options.query,
|
|
368
|
+
limit: options.limit,
|
|
369
|
+
offset: options.offset,
|
|
370
|
+
status: options.status,
|
|
371
|
+
tags: options.tags
|
|
372
|
+
});
|
|
373
|
+
return this.request(
|
|
374
|
+
"GET",
|
|
375
|
+
`/threads/search${queryString}`
|
|
376
|
+
);
|
|
377
|
+
}
|
|
378
|
+
/**
|
|
379
|
+
* Merge multiple threads into one
|
|
380
|
+
*/
|
|
381
|
+
async merge(targetId, sourceIds) {
|
|
382
|
+
return this.request("POST", `/threads/${targetId}/merge`, {
|
|
383
|
+
source_thread_ids: sourceIds
|
|
384
|
+
});
|
|
385
|
+
}
|
|
386
|
+
/**
|
|
387
|
+
* Clone a thread
|
|
388
|
+
*/
|
|
389
|
+
async clone(id, options) {
|
|
390
|
+
return this.request("POST", `/threads/${id}/clone`, options);
|
|
391
|
+
}
|
|
392
|
+
};
|
|
393
|
+
|
|
394
|
+
// src/index.ts
|
|
395
|
+
var SovantClient = class {
|
|
396
|
+
constructor(apiKeyOrConfig) {
|
|
397
|
+
if (typeof apiKeyOrConfig === "string") {
|
|
398
|
+
this.config = { apiKey: apiKeyOrConfig };
|
|
399
|
+
} else {
|
|
400
|
+
this.config = apiKeyOrConfig;
|
|
401
|
+
}
|
|
402
|
+
this.memories = new Memories(this.config);
|
|
403
|
+
this.threads = new Threads(this.config);
|
|
404
|
+
}
|
|
405
|
+
/**
|
|
406
|
+
* Test API connection
|
|
407
|
+
*/
|
|
408
|
+
async ping() {
|
|
409
|
+
const client = new BaseClient(this.config);
|
|
410
|
+
return client.request("GET", "/health");
|
|
411
|
+
}
|
|
412
|
+
/**
|
|
413
|
+
* Get current API usage and quota
|
|
414
|
+
*/
|
|
415
|
+
async getUsage() {
|
|
416
|
+
const client = new BaseClient(this.config);
|
|
417
|
+
return client.request("GET", "/usage");
|
|
418
|
+
}
|
|
419
|
+
};
|
|
420
|
+
var index_default = SovantClient;
|
|
421
|
+
export {
|
|
422
|
+
AuthenticationError,
|
|
423
|
+
NetworkError,
|
|
424
|
+
NotFoundError,
|
|
425
|
+
RateLimitError,
|
|
426
|
+
SovantClient,
|
|
427
|
+
SovantError,
|
|
428
|
+
ValidationError,
|
|
429
|
+
index_default as default
|
|
430
|
+
};
|
package/package.json
ADDED
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@sovant/sdk",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "Official JavaScript/TypeScript SDK for Sovant Memory API",
|
|
5
|
+
"main": "dist/index.js",
|
|
6
|
+
"module": "dist/index.mjs",
|
|
7
|
+
"types": "dist/index.d.ts",
|
|
8
|
+
"files": [
|
|
9
|
+
"dist",
|
|
10
|
+
"README.md",
|
|
11
|
+
"LICENSE"
|
|
12
|
+
],
|
|
13
|
+
"scripts": {
|
|
14
|
+
"build": "tsup src/index.ts --format cjs,esm --dts --clean",
|
|
15
|
+
"dev": "tsup src/index.ts --format cjs,esm --dts --watch",
|
|
16
|
+
"test": "jest",
|
|
17
|
+
"lint": "eslint src --ext ts",
|
|
18
|
+
"prepublishOnly": "npm run build"
|
|
19
|
+
},
|
|
20
|
+
"keywords": [
|
|
21
|
+
"sovant",
|
|
22
|
+
"memory",
|
|
23
|
+
"api",
|
|
24
|
+
"ai",
|
|
25
|
+
"sdk",
|
|
26
|
+
"typescript",
|
|
27
|
+
"javascript"
|
|
28
|
+
],
|
|
29
|
+
"author": "Sovant AI",
|
|
30
|
+
"license": "MIT",
|
|
31
|
+
"repository": {
|
|
32
|
+
"type": "git",
|
|
33
|
+
"url": "git+https://github.com/sovant-ai/javascript-sdk.git"
|
|
34
|
+
},
|
|
35
|
+
"bugs": {
|
|
36
|
+
"url": "https://github.com/sovant-ai/javascript-sdk/issues"
|
|
37
|
+
},
|
|
38
|
+
"homepage": "https://sovant.ai",
|
|
39
|
+
"devDependencies": {
|
|
40
|
+
"@types/jest": "^29.5.12",
|
|
41
|
+
"@types/node": "^20.11.0",
|
|
42
|
+
"@typescript-eslint/eslint-plugin": "^6.18.1",
|
|
43
|
+
"@typescript-eslint/parser": "^6.18.1",
|
|
44
|
+
"eslint": "^8.56.0",
|
|
45
|
+
"jest": "^29.7.0",
|
|
46
|
+
"ts-jest": "^29.1.1",
|
|
47
|
+
"tsup": "^8.0.1",
|
|
48
|
+
"typescript": "^5.3.3"
|
|
49
|
+
},
|
|
50
|
+
"engines": {
|
|
51
|
+
"node": ">=14.0.0"
|
|
52
|
+
},
|
|
53
|
+
"publishConfig": {
|
|
54
|
+
"access": "public"
|
|
55
|
+
}
|
|
56
|
+
}
|