@secrecy/lib 1.77.0 → 1.78.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.
@@ -20,16 +20,17 @@ export class SecrecyCloudClient {
20
20
  const addDataToHistory = await this.#client.apiClient.cloud.addDataToHistory.mutate({
21
21
  dataId,
22
22
  nodeId,
23
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
23
24
  });
24
25
  const node = await apiNodeFullToInternalFull(addDataToHistory, this.#client.keyPairs);
25
26
  const data = node.history.find((d) => d.id === dataId);
26
27
  if (data !== undefined) {
27
- const othersIdentities = Object.entries(node.identities).filter(([id]) => id !== this.#client.uaIdentity.identityPubKey);
28
+ const othersIdentities = Object.entries(node.identities).filter(([id]) => id !== this.#client.currentIdentity.identityPubKey);
28
29
  const shares = othersIdentities.map(([publicKey]) => {
29
30
  return {
30
31
  pubKey: publicKey,
31
32
  key: data.key
32
- ? sodium.to_hex(encryptCryptoBox(sodium.from_hex(data.key), publicKey, this.#client.uaPrivateKey))
33
+ ? sodium.to_hex(encryptCryptoBox(sodium.from_hex(data.key), publicKey, this.#client.currentIdentityPrivateKey))
33
34
  : null,
34
35
  };
35
36
  });
@@ -37,6 +38,7 @@ export class SecrecyCloudClient {
37
38
  dataId: data.id,
38
39
  nodeId,
39
40
  users: shares,
41
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
40
42
  });
41
43
  }
42
44
  return internalNodeFullToNodeFull(node);
@@ -44,7 +46,7 @@ export class SecrecyCloudClient {
44
46
  async uploadData(opts) {
45
47
  return uploadData({
46
48
  ...opts,
47
- uaIdentity: this.#client.uaIdentity,
49
+ currentIdentity: this.#client.currentIdentity,
48
50
  keyPairs: this.#client.keyPairs,
49
51
  apiClient: this.#client.apiClient,
50
52
  });
@@ -60,21 +62,29 @@ export class SecrecyCloudClient {
60
62
  return await this.saveInCloud({ dataId: uploadedData.id, name, nodeId });
61
63
  }
62
64
  async deletedNodes() {
63
- const deletedNodes = await this.#client.apiClient.cloud.nodesDeleted.query({});
65
+ const deletedNodes = await this.#client.apiClient.cloud.nodesDeleted.query({
66
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
67
+ });
64
68
  return await Promise.all(deletedNodes.map(async (node) => await apiNodeToExternal(node, this.#client.keyPairs)));
65
69
  }
66
70
  async sharedNodes() {
67
- const nodesShared = await this.#client.apiClient.cloud.nodesShared.query({});
71
+ const nodesShared = await this.#client.apiClient.cloud.nodesShared.query({
72
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
73
+ });
68
74
  return await Promise.all(nodesShared.map(async (node) => await apiNodeToExternal(node, this.#client.keyPairs)));
69
75
  }
70
76
  async nodesSharedWithMe(type = 'FOLDER') {
71
- const nodesSharedWithMe = await this.#client.apiClient.cloud.nodesSharedWithMe.query({ type });
77
+ const nodesSharedWithMe = await this.#client.apiClient.cloud.nodesSharedWithMe.query({
78
+ type,
79
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
80
+ });
72
81
  return await Promise.all(nodesSharedWithMe.map(async (node) => await apiNodeToExternal(node, this.#client.keyPairs)));
73
82
  }
74
83
  async deleteNodeSharing({ nodeId, destPubKey, }) {
75
84
  const { isDeleted } = await this.#client.apiClient.cloud.deleteNodeSharing.mutate({
76
85
  nodeId,
77
86
  destPubKey,
87
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
78
88
  });
79
89
  return isDeleted;
80
90
  }
@@ -82,6 +92,7 @@ export class SecrecyCloudClient {
82
92
  const { isDeleted } = await this.#client.apiClient.cloud.leaveSharing.mutate({
83
93
  nodeId,
84
94
  fromPubKey,
95
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
85
96
  });
86
97
  return isDeleted;
87
98
  }
@@ -105,27 +116,32 @@ export class SecrecyCloudClient {
105
116
  nodeId,
106
117
  folderId: folderId ?? null,
107
118
  name,
119
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
108
120
  });
109
121
  return isDuplicated;
110
122
  }
111
123
  async deleteNodeCloudTrash({ ids }) {
112
- const { isDeleted } = await this.#client.apiClient.cloud.deleteNodeCloudTrash.mutate({ ids });
124
+ const { isDeleted } = await this.#client.apiClient.cloud.deleteNodeCloudTrash.mutate({
125
+ ids,
126
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
127
+ });
113
128
  return isDeleted;
114
129
  }
115
130
  async createFolder({ name, parentFolderId, }) {
116
131
  const { encryptedNameKey, encryptedName } = await generateAndEncryptNameAndKey({
117
132
  name,
118
- privateKey: this.#client.uaPrivateKey,
119
- publicKey: this.#client.uaIdentity.identityPubKey,
133
+ privateKey: this.#client.currentIdentityPrivateKey,
134
+ publicKey: this.#client.currentIdentity.identityPubKey,
120
135
  });
121
136
  const createdFolder = await this.#client.apiClient.cloud.createFolder.mutate({
122
137
  name: encryptedName,
123
138
  parentId: parentFolderId ?? null,
124
139
  nameKey: encryptedNameKey,
140
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
125
141
  });
126
142
  const folder = await apiNodeToExternalNodeFull(createdFolder, this.#client.keyPairs);
127
143
  if (folder.parent) {
128
- const othersIdentities = Object.entries(folder.parent.identities).filter(([id]) => id !== this.#client.uaIdentity.identityPubKey);
144
+ const othersIdentities = Object.entries(folder.parent.identities).filter(([id]) => id !== this.#client.currentIdentity.identityPubKey);
129
145
  // TODO: ??
130
146
  if (othersIdentities.length > 0) {
131
147
  await this.shareNode(othersIdentities.map(([identityPubKey, permissions]) => ({
@@ -145,17 +161,30 @@ export class SecrecyCloudClient {
145
161
  const node = await this.#client.apiClient.cloud.nodeFullById.query({
146
162
  id,
147
163
  deleted,
164
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
148
165
  });
149
166
  return await apiNodeToExternalNodeFull(node, this.#client.keyPairs);
150
167
  }
168
+ async nodes({ ids, deleted, }) {
169
+ const nodes = await this.#client.apiClient.cloud.nodeFullByIds.query({
170
+ ids,
171
+ deleted,
172
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
173
+ });
174
+ return await Promise.all(nodes.nodes.map((node) => apiNodeToExternalNodeFull(node, this.#client.keyPairs)));
175
+ }
151
176
  async dataMetadata({ id }) {
152
- const data = await this.#client.apiClient.cloud.dataById.query({ id });
177
+ const data = await this.#client.apiClient.cloud.dataById.query({
178
+ id,
179
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
180
+ });
153
181
  return apiDataToExternal(data, this.#client.keyPairs);
154
182
  }
155
183
  async shareNode(accesses, progress) {
156
184
  // TODO: Validate input
157
185
  const nodesMap = await this.#client.apiClient.cloud.shareNode.mutate({
158
186
  accesses,
187
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
159
188
  });
160
189
  const maxNodesBatchSize = 1000;
161
190
  const totalNodesToShare = Object.values(nodesMap).reduce((size, ids) => size + ids.length, 0);
@@ -235,6 +264,7 @@ export class SecrecyCloudClient {
235
264
  const subState = finishInput.length > 0
236
265
  ? await this.#client.apiClient.cloud.shareNodeFinish.mutate({
237
266
  accesses: finishInput,
267
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
238
268
  })
239
269
  : { isFinished: true, details: {} };
240
270
  const currentProgress = Math.min((index + 1) * maxNodesBatchSize, totalNodesToShare);
@@ -298,6 +328,7 @@ export class SecrecyCloudClient {
298
328
  id: nodeId,
299
329
  isFavorite: isFavorite ?? null,
300
330
  name,
331
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
301
332
  });
302
333
  return await apiNodeToExternalNodeFull(updateNode, this.#client.keyPairs);
303
334
  }
@@ -308,6 +339,7 @@ export class SecrecyCloudClient {
308
339
  }
309
340
  const dataContent = await this.#client.apiClient.cloud.dataContentById.query({
310
341
  id: dataId,
342
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
311
343
  });
312
344
  const totalBytes = Number(dataContent.sizeEncrypted ?? dataContent.size);
313
345
  const progressParts = {};
@@ -329,6 +361,7 @@ export class SecrecyCloudClient {
329
361
  }
330
362
  const missingContents = await this.#client.apiClient.cloud.dataContentByIds.query({
331
363
  ids: dataIds.filter((dataId) => !cachedData.some((datum) => datum.id === dataId)),
364
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
332
365
  });
333
366
  const allDataContents = [
334
367
  ...missingContents.map((data) => ({
@@ -358,28 +391,36 @@ export class SecrecyCloudClient {
358
391
  }));
359
392
  }
360
393
  async deleteNodes({ nodeIds, }) {
361
- return this.#client.apiClient.cloud.deleteNodes.mutate({ ids: nodeIds });
394
+ return this.#client.apiClient.cloud.deleteNodes.mutate({
395
+ ids: nodeIds,
396
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
397
+ });
362
398
  }
363
399
  async deleteData({ dataId, nodeId, }) {
364
400
  const { isDeleted } = await this.#client.apiClient.cloud.deleteData.mutate({
365
401
  dataId,
366
402
  nodeId,
403
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
367
404
  });
368
405
  return isDeleted;
369
406
  }
370
407
  async deleteNode({ nodeId }) {
371
408
  const { isDeleted } = await this.#client.apiClient.cloud.deleteNode.mutate({
372
409
  id: nodeId,
410
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
373
411
  });
374
412
  return isDeleted;
375
413
  }
376
414
  async emptyTrash() {
377
- const { isCleaned } = await this.#client.apiClient.cloud.emptyNodeCloudTrash.mutate({});
415
+ const { isCleaned } = await this.#client.apiClient.cloud.emptyNodeCloudTrash.mutate({
416
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
417
+ });
378
418
  return isCleaned;
379
419
  }
380
420
  async recoverNode(id) {
381
421
  const { isRecovered } = await this.#client.apiClient.cloud.recoverNode.mutate({
382
422
  id,
423
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
383
424
  });
384
425
  return isRecovered;
385
426
  }
@@ -387,6 +428,7 @@ export class SecrecyCloudClient {
387
428
  const { isMoved } = await this.#client.apiClient.cloud.moveNodes.mutate({
388
429
  ids: nodeIds,
389
430
  parentId: parentNodeId ?? null,
431
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
390
432
  });
391
433
  return isMoved;
392
434
  }
@@ -429,7 +471,7 @@ export class SecrecyCloudClient {
429
471
  }
430
472
  const senderPubKey = await this.#client.app.userPublicKey(mail.sender.id);
431
473
  const dataKey = attachment.key
432
- ? decryptCryptoBox(sodium.from_hex(attachment.key), senderPubKey, this.#client.uaPrivateKey)
474
+ ? decryptCryptoBox(sodium.from_hex(attachment.key), senderPubKey, this.#client.currentIdentityPrivateKey)
433
475
  : null;
434
476
  key = dataKey !== null ? sodium.to_hex(dataKey) : null;
435
477
  }
@@ -441,12 +483,12 @@ export class SecrecyCloudClient {
441
483
  key = data.key;
442
484
  }
443
485
  key = key
444
- ? sodium.to_hex(encryptCryptoBox(sodium.from_hex(key), this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey))
486
+ ? sodium.to_hex(encryptCryptoBox(sodium.from_hex(key), this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey))
445
487
  : null;
446
488
  const { encryptedNameKey, encryptedName } = await generateAndEncryptNameAndKey({
447
489
  name,
448
- privateKey: this.#client.uaPrivateKey,
449
- publicKey: this.#client.uaIdentity.identityPubKey,
490
+ privateKey: this.#client.currentIdentityPrivateKey,
491
+ publicKey: this.#client.currentIdentity.identityPubKey,
450
492
  });
451
493
  const saveInCloud = await this.#client.apiClient.cloud.saveInCloud.mutate({
452
494
  dataId,
@@ -454,10 +496,11 @@ export class SecrecyCloudClient {
454
496
  nodeId: nodeId ?? null,
455
497
  fileName: encryptedName,
456
498
  nameKey: encryptedNameKey,
499
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
457
500
  });
458
501
  const node = await apiNodeToExternalNodeFull(saveInCloud, this.#client.keyPairs);
459
502
  if (node.parent) {
460
- const othersIdentities = Object.entries(node.parent.identities).filter(([id]) => id !== this.#client.uaIdentity.identityPubKey);
503
+ const othersIdentities = Object.entries(node.parent.identities).filter(([id]) => id !== this.#client.currentIdentity.identityPubKey);
461
504
  // TODO: ??
462
505
  if (othersIdentities.length > 0) {
463
506
  await this.shareNode(othersIdentities.map(([identityPubKey, permissions]) => ({
@@ -508,6 +551,7 @@ export class SecrecyCloudClient {
508
551
  const fetchedNodes = missingNodeIds.length > 0
509
552
  ? await this.#client.apiClient.cloud.nodesForEncryption.query({
510
553
  ids: missingNodeIds,
554
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
511
555
  })
512
556
  : [];
513
557
  const diff = missingNodeIds.filter((id) => !fetchedNodes.some((node) => node.id === id));
@@ -532,10 +576,10 @@ export class SecrecyCloudClient {
532
576
  }
533
577
  nodesMappedUsers[pubKey].push({
534
578
  id: node.id,
535
- nameKey: sodium.to_hex(encryptCryptoBox(sodium.from_hex(node.access.nameKey), pubKey, this.#client.uaPrivateKey)),
579
+ nameKey: sodium.to_hex(encryptCryptoBox(sodium.from_hex(node.access.nameKey), pubKey, this.#client.currentIdentityPrivateKey)),
536
580
  data: node.history.map((f) => ({
537
581
  id: f.id,
538
- key: sodium.to_hex(encryptCryptoBox(sodium.from_hex(f.key), pubKey, this.#client.uaPrivateKey)),
582
+ key: sodium.to_hex(encryptCryptoBox(sodium.from_hex(f.key), pubKey, this.#client.currentIdentityPrivateKey)),
539
583
  })),
540
584
  });
541
585
  }
@@ -575,7 +619,10 @@ export class SecrecyCloudClient {
575
619
  return this.#client.apiClient.cloud.dataLinks.query(input);
576
620
  }
577
621
  checkAccesses(input) {
578
- return this.#client.apiClient.cloud.checkAccesses.query(input);
622
+ return this.#client.apiClient.cloud.checkAccesses.query({
623
+ ...input,
624
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
625
+ });
579
626
  }
580
627
  createPublicDataLink(input) {
581
628
  if (input.expireAt && input.expireAt <= new Date()) {
@@ -609,7 +656,7 @@ export class SecrecyCloudClient {
609
656
  ? dataContent.senderPublicKey
610
657
  : dataContent.type === 'cloud' || dataContent.type === 'lite'
611
658
  ? dataContent.sharedByPublicKey
612
- : this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey)
659
+ : this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey)
613
660
  : null;
614
661
  const src = key
615
662
  ? await decrypt(key, encryptedContent, progressDecrypt, signal)
@@ -12,21 +12,25 @@ export class SecrecyGroupClient {
12
12
  const opts = {
13
13
  pubKey: input.pubKey,
14
14
  role: input.role,
15
- fromPubKey: this.#client.uaIdentity.identityPubKey,
16
15
  id: input.id,
17
- encPriv: sodium.to_hex(encryptCryptoBox(sodium.from_hex(groupIdentity.identityPubKey), input.pubKey, this.#client.uaPrivateKey)),
16
+ encPriv: sodium.to_hex(encryptCryptoBox(sodium.from_hex(groupIdentity.identityPubKey), input.pubKey, this.#client.currentIdentityPrivateKey)),
18
17
  };
19
- return this.#client.apiClient.group.addMember.mutate(opts);
18
+ return this.#client.apiClient.group.addMember.mutate({
19
+ ...opts,
20
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
21
+ });
20
22
  }
21
23
  async create(input) {
22
24
  const keyPair = generateCryptoBoxKeyPair();
23
25
  const opts = {
24
26
  name: input.name,
25
- fromPubKey: this.#client.uaIdentity.identityPubKey,
26
27
  pubKey: keyPair.publicKey,
27
- encPriv: sodium.to_hex(encryptCryptoBox(sodium.from_hex(keyPair.privateKey), this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey)),
28
+ encPriv: sodium.to_hex(encryptCryptoBox(sodium.from_hex(keyPair.privateKey), this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey)),
28
29
  };
29
- return this.#client.apiClient.group.create.mutate(opts);
30
+ return this.#client.apiClient.group.create.mutate({
31
+ ...opts,
32
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
33
+ });
30
34
  }
31
35
  async deleteMember(input) {
32
36
  return this.#client.apiClient.group.deleteMember.mutate(input);
@@ -16,12 +16,14 @@ export class SecrecyMailClient {
16
16
  async recover({ mailId }) {
17
17
  const { isRecovered } = await this.#client.apiClient.mail.recover.mutate({
18
18
  id: mailId,
19
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
19
20
  });
20
21
  return isRecovered;
21
22
  }
22
23
  async deletedMails({ mailType, }) {
23
24
  const deletedMails = await this.#client.apiClient.mail.deleted.query({
24
25
  type: mailType,
26
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
25
27
  });
26
28
  return await Promise.all(deletedMails.map(async (mail) => await convertInternalMailToExternal({
27
29
  mail,
@@ -73,7 +75,7 @@ export class SecrecyMailClient {
73
75
  throw new Error(`File ${f.name} (${f.id}) does not exists`);
74
76
  }
75
77
  }
76
- f.name = sodium.to_hex(encryptCryptoBox(sodium.from_string(f.name), this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey));
78
+ f.name = sodium.to_hex(encryptCryptoBox(sodium.from_string(f.name), this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey));
77
79
  }
78
80
  }
79
81
  const updateDraftMail = await this.#client.apiClient.mail.updateDraft.mutate({
@@ -81,14 +83,15 @@ export class SecrecyMailClient {
81
83
  recipients: recipients ?? null,
82
84
  replyToId: replyToId ?? null,
83
85
  body: body !== undefined
84
- ? sodium.to_hex(encryptCryptoBox(sodium.from_string(body), this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey))
86
+ ? sodium.to_hex(encryptCryptoBox(sodium.from_string(body), this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey))
85
87
  : null,
86
88
  subject: subject !== undefined
87
- ? sodium.to_hex(encryptCryptoBox(sodium.from_string(subject), this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey))
89
+ ? sodium.to_hex(encryptCryptoBox(sodium.from_string(subject), this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey))
88
90
  : null,
89
91
  senderFiles: senderFiles ?? null,
90
92
  hash,
91
93
  hashKey,
94
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
92
95
  });
93
96
  return (await convertInternalMailToExternal({
94
97
  mail: updateDraftMail,
@@ -104,16 +107,20 @@ export class SecrecyMailClient {
104
107
  async deleteTrash({ ids }) {
105
108
  const { isDeleted } = await this.#client.apiClient.mail.deleteTrash.mutate({
106
109
  ids,
110
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
107
111
  });
108
112
  return isDeleted;
109
113
  }
110
114
  async emptyTrash() {
111
- const { isDeleted } = await this.#client.apiClient.mail.emptyTrash.mutate({});
115
+ const { isDeleted } = await this.#client.apiClient.mail.emptyTrash.mutate({
116
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
117
+ });
112
118
  return isDeleted;
113
119
  }
114
120
  async delete({ mailId }) {
115
121
  const { isDeleted } = await this.#client.apiClient.mail.delete.mutate({
116
122
  id: mailId,
123
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
117
124
  });
118
125
  return isDeleted;
119
126
  }
@@ -201,17 +208,18 @@ export class SecrecyMailClient {
201
208
  }
202
209
  senderFiles.push({
203
210
  id: data.id,
204
- name: sodium.to_hex(encryptCryptoBox(sodium.from_string(f.name), this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey)),
211
+ name: sodium.to_hex(encryptCryptoBox(sodium.from_string(f.name), this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey)),
205
212
  });
206
213
  }
207
214
  const createDraftMail = await this.#client.apiClient.mail.createDraft.mutate({
208
215
  recipients,
209
216
  replyToId,
210
- body: sodium.to_hex(encryptCryptoBox(sodium.from_string(body), this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey)),
211
- subject: sodium.to_hex(encryptCryptoBox(sodium.from_string(subject), this.#client.uaIdentity.identityPubKey, this.#client.uaPrivateKey)),
217
+ body: sodium.to_hex(encryptCryptoBox(sodium.from_string(body), this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey)),
218
+ subject: sodium.to_hex(encryptCryptoBox(sodium.from_string(subject), this.#client.currentIdentity.identityPubKey, this.#client.currentIdentityPrivateKey)),
212
219
  senderFiles,
213
220
  hash,
214
221
  hashKey,
222
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
215
223
  });
216
224
  return (await convertInternalMailToExternal({
217
225
  mail: createDraftMail,
@@ -221,17 +229,22 @@ export class SecrecyMailClient {
221
229
  async read({ mailId }) {
222
230
  const { isRead } = await this.#client.apiClient.mail.read.mutate({
223
231
  id: mailId,
232
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
224
233
  });
225
234
  return isRead;
226
235
  }
227
236
  async unread({ mailId }) {
228
237
  const { isUnread } = await this.#client.apiClient.mail.unread.mutate({
229
238
  id: mailId,
239
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
230
240
  });
231
241
  return isUnread;
232
242
  }
233
243
  async receivedMails(input) {
234
- const receivedMails = await this.#client.apiClient.mail.received.query(input);
244
+ const receivedMails = await this.#client.apiClient.mail.received.query({
245
+ ...input,
246
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
247
+ });
235
248
  return await Promise.all(receivedMails.map(async (mail) => (await convertInternalMailToExternal({
236
249
  mail,
237
250
  keyPairs: this.#client.keyPairs,
@@ -252,7 +265,9 @@ export class SecrecyMailClient {
252
265
  }))));
253
266
  }
254
267
  async unreadReceivedMailsCount() {
255
- const unreadReceivedMailsCount = await this.#client.apiClient.mail.unreadReceivedCount.query({});
268
+ const unreadReceivedMailsCount = await this.#client.apiClient.mail.unreadReceivedCount.query({
269
+ fromIdentityPubKey: this.#client.currentIdentity.identityPubKey,
270
+ });
256
271
  return unreadReceivedMailsCount;
257
272
  }
258
273
  _eachUser = async (data, subject, body, idOrMail) => {
@@ -272,17 +287,17 @@ export class SecrecyMailClient {
272
287
  const key = dataInHistory.key;
273
288
  attachments.push({
274
289
  dataId: f.id,
275
- name: sodium.to_hex(encryptCryptoBox(sodium.from_string(f.name), pubKey, this.#client.uaPrivateKey)),
290
+ name: sodium.to_hex(encryptCryptoBox(sodium.from_string(f.name), pubKey, this.#client.currentIdentityPrivateKey)),
276
291
  key: key
277
- ? sodium.to_hex(encryptCryptoBox(sodium.from_hex(key), pubKey, this.#client.uaPrivateKey))
292
+ ? sodium.to_hex(encryptCryptoBox(sodium.from_hex(key), pubKey, this.#client.currentIdentityPrivateKey))
278
293
  : null,
279
294
  });
280
295
  }
281
296
  return {
282
297
  // recipientId: userId,
283
298
  recipientPubKey: pubKey,
284
- body: sodium.to_hex(encryptCryptoBox(sodium.from_string(body), pubKey, this.#client.uaPrivateKey)),
285
- subject: sodium.to_hex(encryptCryptoBox(sodium.from_string(subject), pubKey, this.#client.uaPrivateKey)),
299
+ body: sodium.to_hex(encryptCryptoBox(sodium.from_string(body), pubKey, this.#client.currentIdentityPrivateKey)),
300
+ subject: sodium.to_hex(encryptCryptoBox(sodium.from_string(subject), pubKey, this.#client.currentIdentityPrivateKey)),
286
301
  attachments,
287
302
  };
288
303
  };
@@ -15,6 +15,7 @@ import { SecrecyIdentityClient } from './SecrecyIdentityClient.js';
15
15
  export class SecrecyClient extends BaseClient {
16
16
  #groupIdentities;
17
17
  #uaIdentity;
18
+ #currentGroupIdentity = null;
18
19
  #keyPairs;
19
20
  cloud;
20
21
  mail;
@@ -61,6 +62,16 @@ export class SecrecyClient extends BaseClient {
61
62
  this.group = new SecrecyGroupClient(this);
62
63
  this.identity = new SecrecyIdentityClient(this);
63
64
  }
65
+ get currentIdentity() {
66
+ return this.#currentGroupIdentity ?? this.#uaIdentity;
67
+ }
68
+ get currentIdentityPrivateKey() {
69
+ return this.getPrivateKey(this.currentIdentity.identityPubKey);
70
+ }
71
+ set currentGroup(groupId) {
72
+ this.#currentGroupIdentity =
73
+ this.#groupIdentities.find((g) => g.groupId === groupId) ?? null;
74
+ }
64
75
  get publicKey() {
65
76
  return this.#uaIdentity.identityPubKey;
66
77
  }
@@ -11,6 +11,7 @@ export const groupSchema = z.object({
11
11
  groupId: z.string(),
12
12
  groupRole: z.enum(['ADMIN', 'MEMBER']),
13
13
  sharedByPubKey: z.string(),
14
+ sharedToPubKey: z.string(),
14
15
  groupOwnerPubKey: z.string(),
15
16
  });
16
17
  export const accessIdentitySchema = z.discriminatedUnion('kind', [
@@ -11,11 +11,11 @@ import { promiseAllLimit } from '../utils/promise.js';
11
11
  import { encryptDataAndKey } from '../crypto/domain.js';
12
12
  import { derivePassword, generatePassword } from '../crypto/helpers.js';
13
13
  import { decryptCryptoBox, encryptSecretBox } from '../crypto/index.js';
14
- export async function uploadData({ storageType, data, password, forcePassword = false, encrypted = true, encryptProgress, uploadProgress, signal, meta, uaIdentity, keyPairs, apiClient, }) {
14
+ export async function uploadData({ storageType, data, password, forcePassword = false, encrypted = true, encryptProgress, uploadProgress, signal, meta, currentIdentity, keyPairs, apiClient, }) {
15
15
  if (!encrypted && (password || forcePassword)) {
16
16
  throw new Error('Cannot share unencrypted data with a password!');
17
17
  }
18
- if (encrypted && !password && !forcePassword && !uaIdentity) {
18
+ if (encrypted && !password && !forcePassword && !currentIdentity) {
19
19
  throw new Error('Cannot share encrypted data without a password!');
20
20
  }
21
21
  apiClient ??= getTrpcGuestClient();
@@ -37,7 +37,7 @@ export async function uploadData({ storageType, data, password, forcePassword =
37
37
  if (storageType === 'lite' && dataBuffer.byteLength > kiloToBytes(1024)) {
38
38
  throw new Error('The data is too big for lite upload!');
39
39
  }
40
- if (!uaIdentity && storageType === 'cold') {
40
+ if (!currentIdentity && storageType === 'cold') {
41
41
  throw new Error('Cold storage is only for logged users!');
42
42
  }
43
43
  const compressed = encrypted ? compress(dataBuffer) : dataBuffer;
@@ -45,7 +45,7 @@ export async function uploadData({ storageType, data, password, forcePassword =
45
45
  ? await encryptDataAndKey({
46
46
  data: compressed,
47
47
  progress: encryptProgress,
48
- uaIdentity,
48
+ currentIdentity,
49
49
  keyPairs,
50
50
  signal,
51
51
  })
@@ -74,7 +74,7 @@ export async function uploadData({ storageType, data, password, forcePassword =
74
74
  key = dataKey;
75
75
  }
76
76
  else {
77
- if (!uaIdentity) {
77
+ if (!currentIdentity) {
78
78
  throw new Error('Unable to encrypt data without keyPair!');
79
79
  }
80
80
  if (!data.key) {
@@ -10,10 +10,10 @@ import { concatenate } from '../utils/array.js';
10
10
  * If a string is provided as keypair, it should be considered as guest with password case.
11
11
  * If keypair is not provided, then we generate a key to be used as password for guest too.
12
12
  */
13
- export async function encryptDataAndKey({ data, uaIdentity, keyPairs, progress, signal, }) {
13
+ export async function encryptDataAndKey({ data, currentIdentity, keyPairs, progress, signal, }) {
14
14
  const dataKey = secretStreamKeygen();
15
15
  const { data: encryptedData, md5: md5Data, md5Encrypted, } = await encrypt(dataKey, data, progress, signal);
16
- if (!uaIdentity || !keyPairs) {
16
+ if (!currentIdentity || !keyPairs) {
17
17
  return {
18
18
  encryptedData,
19
19
  dataKey,
@@ -21,11 +21,11 @@ export async function encryptDataAndKey({ data, uaIdentity, keyPairs, progress,
21
21
  md5Encrypted,
22
22
  };
23
23
  }
24
- const priv = keyPairs[uaIdentity.identityPubKey];
24
+ const priv = keyPairs[currentIdentity.identityPubKey];
25
25
  if (!priv) {
26
26
  throw new Error('No private key found for user app identity');
27
27
  }
28
- const encDataKey = encryptCryptoBox(dataKey, uaIdentity.identityPubKey, priv);
28
+ const encDataKey = encryptCryptoBox(dataKey, currentIdentity.identityPubKey, priv);
29
29
  return {
30
30
  encryptedDataKey: encDataKey,
31
31
  encryptedData,
@@ -52,6 +52,10 @@ export declare class SecrecyCloudClient {
52
52
  id?: string | null | undefined;
53
53
  deleted?: boolean | null | undefined;
54
54
  }): Promise<NodeFull>;
55
+ nodes({ ids, deleted, }: {
56
+ ids: string[];
57
+ deleted?: boolean | null | undefined;
58
+ }): Promise<NodeFull[]>;
55
59
  dataMetadata({ id }: {
56
60
  id: string;
57
61
  }): Promise<DataMetadata>;
@@ -124,7 +128,7 @@ export declare class SecrecyCloudClient {
124
128
  createdByOrgId: string | null;
125
129
  createdByAppId: string | null;
126
130
  }[]>;
127
- checkAccesses(input: RouterInputs['cloud']['checkAccesses']): Promise<{
131
+ checkAccesses(input: Omit<RouterInputs['cloud']['checkAccesses'], 'fromIdentityPubKey'>): Promise<{
128
132
  isMatching: true;
129
133
  } | {
130
134
  isMatching: false;
@@ -33,7 +33,7 @@ export declare class SecrecyMailClient {
33
33
  unread({ mailId }: {
34
34
  mailId: string;
35
35
  }): Promise<boolean>;
36
- receivedMails(input: RouterInputs['mail']['received']): Promise<ReceivedMail[]>;
36
+ receivedMails(input: Omit<RouterInputs['mail']['received'], 'fromIdentityPubKey'>): Promise<ReceivedMail[]>;
37
37
  sentMails(input: RouterInputs['mail']['sent']): Promise<SentMail[]>;
38
38
  draftMails(input: RouterInputs['mail']['draft']): Promise<DraftMail[]>;
39
39
  unreadReceivedMailsCount(): Promise<number>;
@@ -37,6 +37,9 @@ export declare class SecrecyClient extends BaseClient {
37
37
  group: SecrecyGroupClient;
38
38
  identity: SecrecyIdentityClient;
39
39
  constructor(opts: SecrecyClientOptions);
40
+ get currentIdentity(): Readonly<AccessIdentity>;
41
+ get currentIdentityPrivateKey(): string;
42
+ set currentGroup(groupId: string | null);
40
43
  get publicKey(): string;
41
44
  get apiClient(): Readonly<ApiClient>;
42
45
  get keyPairs(): Readonly<Record<string, string>>;
@@ -14,6 +14,7 @@ export declare const groupSchema: z.ZodObject<{
14
14
  MEMBER: "MEMBER";
15
15
  }>;
16
16
  sharedByPubKey: z.ZodString;
17
+ sharedToPubKey: z.ZodString;
17
18
  groupOwnerPubKey: z.ZodString;
18
19
  }, z.core.$strip>;
19
20
  export declare const accessIdentitySchema: z.ZodDiscriminatedUnion<[z.ZodObject<{
@@ -30,6 +31,7 @@ export declare const accessIdentitySchema: z.ZodDiscriminatedUnion<[z.ZodObject<
30
31
  MEMBER: "MEMBER";
31
32
  }>;
32
33
  sharedByPubKey: z.ZodString;
34
+ sharedToPubKey: z.ZodString;
33
35
  groupOwnerPubKey: z.ZodString;
34
36
  }, z.core.$strip>], "kind">;
35
37
  export type AccessIdentity = z.infer<typeof accessIdentitySchema>;
@@ -19,6 +19,7 @@ export declare const secrecyUserApp: z.ZodReadonly<z.ZodObject<{
19
19
  MEMBER: "MEMBER";
20
20
  }>;
21
21
  sharedByPubKey: z.ZodString;
22
+ sharedToPubKey: z.ZodString;
22
23
  groupOwnerPubKey: z.ZodString;
23
24
  }, z.core.$strip>], "kind">>;
24
25
  keyPairs: z.ZodRecord<z.ZodString, z.ZodString>;