@hypercerts-org/sdk-core 0.5.0-beta.0 → 0.6.0-beta.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.
Files changed (55) hide show
  1. package/dist/index.cjs +16 -12
  2. package/dist/index.cjs.map +1 -1
  3. package/dist/index.mjs +16 -12
  4. package/dist/index.mjs.map +1 -1
  5. package/package.json +8 -4
  6. package/.turbo/turbo-build.log +0 -40
  7. package/.turbo/turbo-test.log +0 -119
  8. package/CHANGELOG.md +0 -62
  9. package/eslint.config.mjs +0 -22
  10. package/rollup.config.js +0 -75
  11. package/src/auth/OAuthClient.ts +0 -497
  12. package/src/core/SDK.ts +0 -410
  13. package/src/core/config.ts +0 -243
  14. package/src/core/errors.ts +0 -257
  15. package/src/core/interfaces.ts +0 -324
  16. package/src/core/types.ts +0 -282
  17. package/src/errors.ts +0 -57
  18. package/src/index.ts +0 -107
  19. package/src/lexicons.ts +0 -64
  20. package/src/repository/BlobOperationsImpl.ts +0 -199
  21. package/src/repository/CollaboratorOperationsImpl.ts +0 -442
  22. package/src/repository/HypercertOperationsImpl.ts +0 -1146
  23. package/src/repository/LexiconRegistry.ts +0 -332
  24. package/src/repository/OrganizationOperationsImpl.ts +0 -282
  25. package/src/repository/ProfileOperationsImpl.ts +0 -281
  26. package/src/repository/RecordOperationsImpl.ts +0 -340
  27. package/src/repository/Repository.ts +0 -482
  28. package/src/repository/interfaces.ts +0 -909
  29. package/src/repository/types.ts +0 -111
  30. package/src/services/hypercerts/types.ts +0 -87
  31. package/src/storage/InMemorySessionStore.ts +0 -127
  32. package/src/storage/InMemoryStateStore.ts +0 -146
  33. package/src/storage.ts +0 -63
  34. package/src/testing/index.ts +0 -67
  35. package/src/testing/mocks.ts +0 -142
  36. package/src/testing/stores.ts +0 -285
  37. package/src/testing.ts +0 -64
  38. package/src/types.ts +0 -86
  39. package/tests/auth/OAuthClient.test.ts +0 -164
  40. package/tests/core/SDK.test.ts +0 -176
  41. package/tests/core/errors.test.ts +0 -81
  42. package/tests/repository/BlobOperationsImpl.test.ts +0 -155
  43. package/tests/repository/CollaboratorOperationsImpl.test.ts +0 -438
  44. package/tests/repository/HypercertOperationsImpl.test.ts +0 -652
  45. package/tests/repository/LexiconRegistry.test.ts +0 -192
  46. package/tests/repository/OrganizationOperationsImpl.test.ts +0 -240
  47. package/tests/repository/ProfileOperationsImpl.test.ts +0 -254
  48. package/tests/repository/RecordOperationsImpl.test.ts +0 -375
  49. package/tests/repository/Repository.test.ts +0 -149
  50. package/tests/utils/fixtures.ts +0 -117
  51. package/tests/utils/mocks.ts +0 -109
  52. package/tests/utils/repository-fixtures.ts +0 -78
  53. package/tsconfig.json +0 -11
  54. package/tsconfig.tsbuildinfo +0 -1
  55. package/vitest.config.ts +0 -30
@@ -1,438 +0,0 @@
1
- import { describe, it, expect, vi, beforeEach } from "vitest";
2
- import { CollaboratorOperationsImpl } from "../../src/repository/CollaboratorOperationsImpl.js";
3
- import { NetworkError } from "../../src/core/errors.js";
4
-
5
- describe("CollaboratorOperationsImpl", () => {
6
- let mockSession: any;
7
- let collaboratorOps: CollaboratorOperationsImpl;
8
- const repoDid = "did:plc:testdid123";
9
- const serverUrl = "https://sds.example.com";
10
-
11
- beforeEach(() => {
12
- mockSession = {
13
- did: "did:plc:user123",
14
- sub: "did:plc:user123",
15
- fetchHandler: vi.fn(),
16
- };
17
-
18
- collaboratorOps = new CollaboratorOperationsImpl(mockSession, repoDid, serverUrl);
19
- });
20
-
21
- describe("grant", () => {
22
- it("should grant viewer access", async () => {
23
- mockSession.fetchHandler.mockResolvedValue({
24
- ok: true,
25
- json: async () => ({}),
26
- });
27
-
28
- await collaboratorOps.grant({ userDid: "did:plc:newuser", role: "viewer" });
29
-
30
- expect(mockSession.fetchHandler).toHaveBeenCalledWith(
31
- `${serverUrl}/xrpc/com.sds.repo.grantAccess`,
32
- expect.objectContaining({
33
- method: "POST",
34
- body: expect.stringContaining('"read":true'),
35
- }),
36
- );
37
-
38
- const body = JSON.parse(mockSession.fetchHandler.mock.calls[0][1].body);
39
- expect(body.permissions.read).toBe(true);
40
- expect(body.permissions.create).toBe(false);
41
- expect(body.permissions.update).toBe(false);
42
- expect(body.permissions.delete).toBe(false);
43
- });
44
-
45
- it("should grant editor access", async () => {
46
- mockSession.fetchHandler.mockResolvedValue({
47
- ok: true,
48
- json: async () => ({}),
49
- });
50
-
51
- await collaboratorOps.grant({ userDid: "did:plc:newuser", role: "editor" });
52
-
53
- const body = JSON.parse(mockSession.fetchHandler.mock.calls[0][1].body);
54
- expect(body.permissions.read).toBe(true);
55
- expect(body.permissions.create).toBe(true);
56
- expect(body.permissions.update).toBe(true);
57
- expect(body.permissions.delete).toBe(false);
58
- });
59
-
60
- it("should grant admin access", async () => {
61
- mockSession.fetchHandler.mockResolvedValue({
62
- ok: true,
63
- json: async () => ({}),
64
- });
65
-
66
- await collaboratorOps.grant({ userDid: "did:plc:newuser", role: "admin" });
67
-
68
- const body = JSON.parse(mockSession.fetchHandler.mock.calls[0][1].body);
69
- expect(body.permissions.admin).toBe(true);
70
- expect(body.permissions.delete).toBe(true);
71
- });
72
-
73
- it("should grant owner access", async () => {
74
- mockSession.fetchHandler.mockResolvedValue({
75
- ok: true,
76
- json: async () => ({}),
77
- });
78
-
79
- await collaboratorOps.grant({ userDid: "did:plc:newuser", role: "owner" });
80
-
81
- const body = JSON.parse(mockSession.fetchHandler.mock.calls[0][1].body);
82
- expect(body.permissions.owner).toBe(true);
83
- });
84
-
85
- it("should throw NetworkError on failure", async () => {
86
- mockSession.fetchHandler.mockResolvedValue({
87
- ok: false,
88
- statusText: "Forbidden",
89
- });
90
-
91
- await expect(collaboratorOps.grant({ userDid: "did:plc:newuser", role: "viewer" })).rejects.toThrow(NetworkError);
92
- });
93
- });
94
-
95
- describe("revoke", () => {
96
- it("should revoke access successfully", async () => {
97
- mockSession.fetchHandler.mockResolvedValue({
98
- ok: true,
99
- json: async () => ({}),
100
- });
101
-
102
- await collaboratorOps.revoke({ userDid: "did:plc:revokeduser" });
103
-
104
- expect(mockSession.fetchHandler).toHaveBeenCalledWith(
105
- `${serverUrl}/xrpc/com.sds.repo.revokeAccess`,
106
- expect.objectContaining({
107
- method: "POST",
108
- }),
109
- );
110
-
111
- const body = JSON.parse(mockSession.fetchHandler.mock.calls[0][1].body);
112
- expect(body.repo).toBe(repoDid);
113
- expect(body.userDid).toBe("did:plc:revokeduser");
114
- });
115
-
116
- it("should throw NetworkError on failure", async () => {
117
- mockSession.fetchHandler.mockResolvedValue({
118
- ok: false,
119
- statusText: "Not Found",
120
- });
121
-
122
- await expect(collaboratorOps.revoke({ userDid: "did:plc:user" })).rejects.toThrow(NetworkError);
123
- });
124
- });
125
-
126
- describe("list", () => {
127
- it("should list collaborators successfully", async () => {
128
- mockSession.fetchHandler.mockResolvedValue({
129
- ok: true,
130
- json: async () => ({
131
- collaborators: [
132
- {
133
- userDid: "did:plc:user1",
134
- permissions: ["read", "create", "update"],
135
- grantedBy: "did:plc:owner",
136
- grantedAt: "2024-01-01T00:00:00Z",
137
- },
138
- {
139
- userDid: "did:plc:user2",
140
- permissions: ["read"],
141
- grantedBy: "did:plc:owner",
142
- grantedAt: "2024-01-02T00:00:00Z",
143
- },
144
- ],
145
- }),
146
- });
147
-
148
- const result = await collaboratorOps.list();
149
-
150
- expect(result.collaborators).toHaveLength(2);
151
- expect(result.collaborators[0].userDid).toBe("did:plc:user1");
152
- expect(result.collaborators[0].role).toBe("editor");
153
- expect(result.collaborators[1].role).toBe("viewer");
154
- });
155
-
156
- it("should handle empty collaborators list", async () => {
157
- mockSession.fetchHandler.mockResolvedValue({
158
- ok: true,
159
- json: async () => ({ collaborators: [] }),
160
- });
161
-
162
- const result = await collaboratorOps.list();
163
-
164
- expect(result.collaborators).toHaveLength(0);
165
- });
166
-
167
- it("should correctly map permissions to roles", async () => {
168
- mockSession.fetchHandler.mockResolvedValue({
169
- ok: true,
170
- json: async () => ({
171
- collaborators: [
172
- {
173
- userDid: "did:plc:owner",
174
- permissions: ["read", "create", "update", "delete", "admin", "owner"],
175
- grantedBy: "did:plc:system",
176
- grantedAt: "2024-01-01T00:00:00Z",
177
- },
178
- {
179
- userDid: "did:plc:admin",
180
- permissions: ["read", "create", "update", "delete", "admin"],
181
- grantedBy: "did:plc:owner",
182
- grantedAt: "2024-01-01T00:00:00Z",
183
- },
184
- ],
185
- }),
186
- });
187
-
188
- const result = await collaboratorOps.list();
189
-
190
- expect(result.collaborators[0].role).toBe("owner");
191
- expect(result.collaborators[1].role).toBe("admin");
192
- });
193
-
194
- it("should throw NetworkError on failure", async () => {
195
- mockSession.fetchHandler.mockResolvedValue({
196
- ok: false,
197
- statusText: "Server Error",
198
- });
199
-
200
- await expect(collaboratorOps.list()).rejects.toThrow(NetworkError);
201
- });
202
- });
203
-
204
- describe("hasAccess", () => {
205
- it("should return true for active collaborator", async () => {
206
- mockSession.fetchHandler.mockResolvedValue({
207
- ok: true,
208
- json: async () => ({
209
- collaborators: [
210
- {
211
- userDid: "did:plc:activeuser",
212
- permissions: ["read"],
213
- grantedBy: "did:plc:owner",
214
- grantedAt: "2024-01-01T00:00:00Z",
215
- },
216
- ],
217
- }),
218
- });
219
-
220
- const result = await collaboratorOps.hasAccess("did:plc:activeuser");
221
-
222
- expect(result).toBe(true);
223
- });
224
-
225
- it("should return false for unknown user", async () => {
226
- mockSession.fetchHandler.mockResolvedValue({
227
- ok: true,
228
- json: async () => ({ collaborators: [] }),
229
- });
230
-
231
- const result = await collaboratorOps.hasAccess("did:plc:unknown");
232
-
233
- expect(result).toBe(false);
234
- });
235
-
236
- it("should return false for revoked user", async () => {
237
- mockSession.fetchHandler.mockResolvedValue({
238
- ok: true,
239
- json: async () => ({
240
- collaborators: [
241
- {
242
- userDid: "did:plc:revokeduser",
243
- permissions: ["read"],
244
- grantedBy: "did:plc:owner",
245
- grantedAt: "2024-01-01T00:00:00Z",
246
- revokedAt: "2024-02-01T00:00:00Z",
247
- },
248
- ],
249
- }),
250
- });
251
-
252
- const result = await collaboratorOps.hasAccess("did:plc:revokeduser");
253
-
254
- expect(result).toBe(false);
255
- });
256
-
257
- it("should return false on error", async () => {
258
- mockSession.fetchHandler.mockRejectedValue(new Error("Network error"));
259
-
260
- const result = await collaboratorOps.hasAccess("did:plc:user");
261
-
262
- expect(result).toBe(false);
263
- });
264
- });
265
-
266
- describe("getRole", () => {
267
- it("should return role for active collaborator", async () => {
268
- mockSession.fetchHandler.mockResolvedValue({
269
- ok: true,
270
- json: async () => ({
271
- collaborators: [
272
- {
273
- userDid: "did:plc:editor",
274
- permissions: ["read", "create", "update"],
275
- grantedBy: "did:plc:owner",
276
- grantedAt: "2024-01-01T00:00:00Z",
277
- },
278
- ],
279
- }),
280
- });
281
-
282
- const result = await collaboratorOps.getRole("did:plc:editor");
283
-
284
- expect(result).toBe("editor");
285
- });
286
-
287
- it("should return null for unknown user", async () => {
288
- mockSession.fetchHandler.mockResolvedValue({
289
- ok: true,
290
- json: async () => ({ collaborators: [] }),
291
- });
292
-
293
- const result = await collaboratorOps.getRole("did:plc:unknown");
294
-
295
- expect(result).toBeNull();
296
- });
297
-
298
- it("should return null for revoked user", async () => {
299
- mockSession.fetchHandler.mockResolvedValue({
300
- ok: true,
301
- json: async () => ({
302
- collaborators: [
303
- {
304
- userDid: "did:plc:revoked",
305
- permissions: ["read", "create", "update"],
306
- grantedBy: "did:plc:owner",
307
- grantedAt: "2024-01-01T00:00:00Z",
308
- revokedAt: "2024-02-01T00:00:00Z",
309
- },
310
- ],
311
- }),
312
- });
313
-
314
- const result = await collaboratorOps.getRole("did:plc:revoked");
315
-
316
- expect(result).toBeNull();
317
- });
318
- });
319
-
320
- describe("getPermissions", () => {
321
- it("should get current user permissions successfully", async () => {
322
- mockSession.fetchHandler.mockResolvedValue({
323
- ok: true,
324
- json: async () => ({
325
- permissions: {
326
- read: true,
327
- create: true,
328
- update: true,
329
- delete: false,
330
- admin: false,
331
- owner: false,
332
- },
333
- }),
334
- });
335
-
336
- const result = await collaboratorOps.getPermissions();
337
-
338
- expect(mockSession.fetchHandler).toHaveBeenCalledWith(
339
- `${serverUrl}/xrpc/com.sds.repo.getPermissions?repo=${encodeURIComponent(repoDid)}`,
340
- expect.objectContaining({
341
- method: "GET",
342
- }),
343
- );
344
-
345
- expect(result.read).toBe(true);
346
- expect(result.create).toBe(true);
347
- expect(result.update).toBe(true);
348
- expect(result.delete).toBe(false);
349
- expect(result.admin).toBe(false);
350
- expect(result.owner).toBe(false);
351
- });
352
-
353
- it("should handle owner permissions", async () => {
354
- mockSession.fetchHandler.mockResolvedValue({
355
- ok: true,
356
- json: async () => ({
357
- permissions: {
358
- read: true,
359
- create: true,
360
- update: true,
361
- delete: true,
362
- admin: true,
363
- owner: true,
364
- },
365
- }),
366
- });
367
-
368
- const result = await collaboratorOps.getPermissions();
369
-
370
- expect(result.owner).toBe(true);
371
- expect(result.admin).toBe(true);
372
- });
373
-
374
- it("should throw NetworkError on failure", async () => {
375
- mockSession.fetchHandler.mockResolvedValue({
376
- ok: false,
377
- statusText: "Forbidden",
378
- });
379
-
380
- await expect(collaboratorOps.getPermissions()).rejects.toThrow(NetworkError);
381
- });
382
- });
383
-
384
- describe("transferOwnership", () => {
385
- it("should transfer ownership successfully", async () => {
386
- mockSession.fetchHandler.mockResolvedValue({
387
- ok: true,
388
- json: async () => ({}),
389
- });
390
-
391
- await collaboratorOps.transferOwnership({ newOwnerDid: "did:plc:new-owner" });
392
-
393
- expect(mockSession.fetchHandler).toHaveBeenCalledWith(
394
- `${serverUrl}/xrpc/com.sds.repo.transferOwnership`,
395
- expect.objectContaining({
396
- method: "POST",
397
- }),
398
- );
399
-
400
- const body = JSON.parse(mockSession.fetchHandler.mock.calls[0][1].body);
401
- expect(body.repo).toBe(repoDid);
402
- expect(body.newOwner).toBe("did:plc:new-owner");
403
- });
404
-
405
- it("should throw NetworkError on failure", async () => {
406
- mockSession.fetchHandler.mockResolvedValue({
407
- ok: false,
408
- statusText: "Forbidden",
409
- });
410
-
411
- await expect(collaboratorOps.transferOwnership({ newOwnerDid: "did:plc:new-owner" })).rejects.toThrow(
412
- NetworkError,
413
- );
414
- });
415
-
416
- it("should throw NetworkError when not owner", async () => {
417
- mockSession.fetchHandler.mockResolvedValue({
418
- ok: false,
419
- statusText: "Forbidden: Only the owner can transfer ownership",
420
- });
421
-
422
- await expect(collaboratorOps.transferOwnership({ newOwnerDid: "did:plc:new-owner" })).rejects.toThrow(
423
- NetworkError,
424
- );
425
- });
426
-
427
- it("should throw NetworkError when new owner does not exist", async () => {
428
- mockSession.fetchHandler.mockResolvedValue({
429
- ok: false,
430
- statusText: "Not Found: New owner DID not found",
431
- });
432
-
433
- await expect(collaboratorOps.transferOwnership({ newOwnerDid: "did:plc:nonexistent" })).rejects.toThrow(
434
- NetworkError,
435
- );
436
- });
437
- });
438
- });