bedrock-ts-sdk 0.0.2 → 0.0.4
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/index.d.mts +10 -10
- package/dist/index.d.ts +10 -10
- package/dist/index.js +143 -262
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +143 -262
- package/dist/index.mjs.map +1 -1
- package/package.json +4 -1
package/dist/index.mjs
CHANGED
|
@@ -116,24 +116,27 @@ var FileMetaEncryptedSchema = z.object({
|
|
|
116
116
|
// Encrypted filename
|
|
117
117
|
path: z.string(),
|
|
118
118
|
// Encrypted path
|
|
119
|
-
key:
|
|
120
|
-
// Encrypted AES key
|
|
121
|
-
iv:
|
|
122
|
-
// Encrypted IV
|
|
123
|
-
store_hash:
|
|
124
|
-
// Aleph STORE hash
|
|
119
|
+
key: z.string(),
|
|
120
|
+
// Encrypted AES key (ECIES encrypted)
|
|
121
|
+
iv: z.string(),
|
|
122
|
+
// Encrypted IV (ECIES encrypted)
|
|
123
|
+
store_hash: z.string(),
|
|
124
|
+
// Encrypted Aleph STORE hash
|
|
125
125
|
size: z.string(),
|
|
126
126
|
// Encrypted size
|
|
127
127
|
created_at: z.string(),
|
|
128
128
|
// Encrypted datetime
|
|
129
129
|
deleted_at: z.string().nullable(),
|
|
130
130
|
// Encrypted datetime or null
|
|
131
|
-
shared_keys: z.record(
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
131
|
+
shared_keys: z.record(
|
|
132
|
+
z.string(),
|
|
133
|
+
z.object({
|
|
134
|
+
key: z.string(),
|
|
135
|
+
// Encrypted key for recipient
|
|
136
|
+
iv: z.string()
|
|
137
|
+
// Encrypted IV for recipient
|
|
138
|
+
})
|
|
139
|
+
).default({})
|
|
137
140
|
});
|
|
138
141
|
var FileMetaSchema = z.object({
|
|
139
142
|
name: z.string(),
|
|
@@ -144,10 +147,13 @@ var FileMetaSchema = z.object({
|
|
|
144
147
|
size: z.number(),
|
|
145
148
|
created_at: DatetimeSchema,
|
|
146
149
|
deleted_at: DatetimeSchema.nullable(),
|
|
147
|
-
shared_keys: z.record(
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
150
|
+
shared_keys: z.record(
|
|
151
|
+
z.string(),
|
|
152
|
+
z.object({
|
|
153
|
+
key: HexString64Schema,
|
|
154
|
+
iv: HexString32Schema
|
|
155
|
+
})
|
|
156
|
+
).default({})
|
|
151
157
|
});
|
|
152
158
|
var PublicFileMetaSchema = z.object({
|
|
153
159
|
name: z.string(),
|
|
@@ -192,13 +198,15 @@ var FileEntriesAggregateSchema = z.object({
|
|
|
192
198
|
files: z.array(FileEntrySchema).default([])
|
|
193
199
|
});
|
|
194
200
|
var SecurityAggregateSchema = z.object({
|
|
195
|
-
authorizations: z.array(
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
201
|
+
authorizations: z.array(
|
|
202
|
+
z.object({
|
|
203
|
+
address: AddressSchema,
|
|
204
|
+
chain: z.string(),
|
|
205
|
+
channels: z.array(z.string()).optional(),
|
|
206
|
+
post_types: z.array(z.string()).optional(),
|
|
207
|
+
aggregate_keys: z.array(z.string()).optional()
|
|
208
|
+
})
|
|
209
|
+
)
|
|
202
210
|
});
|
|
203
211
|
|
|
204
212
|
// src/client/aleph-service.ts
|
|
@@ -522,7 +530,7 @@ var BedrockCore = class _BedrockCore {
|
|
|
522
530
|
* Get the main account's public key
|
|
523
531
|
*/
|
|
524
532
|
getPublicKey() {
|
|
525
|
-
return this.encryptionPrivateKey.publicKey.
|
|
533
|
+
return this.encryptionPrivateKey.publicKey.compressed.toString("hex");
|
|
526
534
|
}
|
|
527
535
|
/**
|
|
528
536
|
* Get the sub-account's private key (as hex string)
|
|
@@ -582,6 +590,9 @@ var BedrockCore = class _BedrockCore {
|
|
|
582
590
|
}
|
|
583
591
|
};
|
|
584
592
|
|
|
593
|
+
// src/services/file-service.ts
|
|
594
|
+
import { AlephHttpClient } from "@aleph-sdk/client";
|
|
595
|
+
|
|
585
596
|
// src/crypto/encryption.ts
|
|
586
597
|
import { encrypt as eciesEncrypt, decrypt as eciesDecrypt } from "eciesjs";
|
|
587
598
|
var CryptoUtils = class {
|
|
@@ -808,74 +819,33 @@ var EncryptionService = class {
|
|
|
808
819
|
// ============================================================================
|
|
809
820
|
static async encryptBrowser(data, key, iv) {
|
|
810
821
|
const crypto = CryptoUtils.getCrypto();
|
|
811
|
-
const cryptoKey = await crypto.subtle.importKey(
|
|
812
|
-
"raw",
|
|
813
|
-
key,
|
|
814
|
-
{ name: "AES-CBC" },
|
|
815
|
-
false,
|
|
816
|
-
["encrypt"]
|
|
817
|
-
);
|
|
822
|
+
const cryptoKey = await crypto.subtle.importKey("raw", key, { name: "AES-CBC" }, false, ["encrypt"]);
|
|
818
823
|
const dataBuffer = Buffer.from(data, "utf-8");
|
|
819
|
-
const encrypted = await crypto.subtle.encrypt(
|
|
820
|
-
{ name: "AES-CBC", iv },
|
|
821
|
-
cryptoKey,
|
|
822
|
-
dataBuffer
|
|
823
|
-
);
|
|
824
|
+
const encrypted = await crypto.subtle.encrypt({ name: "AES-CBC", iv }, cryptoKey, dataBuffer);
|
|
824
825
|
return CryptoUtils.bufferToHex(Buffer.from(encrypted));
|
|
825
826
|
}
|
|
826
827
|
static async decryptBrowser(encryptedData, key, iv) {
|
|
827
828
|
const crypto = CryptoUtils.getCrypto();
|
|
828
|
-
const cryptoKey = await crypto.subtle.importKey(
|
|
829
|
-
"raw",
|
|
830
|
-
key,
|
|
831
|
-
{ name: "AES-CBC" },
|
|
832
|
-
false,
|
|
833
|
-
["decrypt"]
|
|
834
|
-
);
|
|
829
|
+
const cryptoKey = await crypto.subtle.importKey("raw", key, { name: "AES-CBC" }, false, ["decrypt"]);
|
|
835
830
|
const encryptedBuffer = CryptoUtils.hexToBuffer(encryptedData);
|
|
836
|
-
const decrypted = await crypto.subtle.decrypt(
|
|
837
|
-
{ name: "AES-CBC", iv },
|
|
838
|
-
cryptoKey,
|
|
839
|
-
encryptedBuffer
|
|
840
|
-
);
|
|
831
|
+
const decrypted = await crypto.subtle.decrypt({ name: "AES-CBC", iv }, cryptoKey, encryptedBuffer);
|
|
841
832
|
return Buffer.from(decrypted).toString("utf-8");
|
|
842
833
|
}
|
|
843
834
|
static async encryptFileBrowser(buffer, key, iv) {
|
|
844
835
|
const crypto = CryptoUtils.getCrypto();
|
|
845
|
-
const cryptoKey = await crypto.subtle.importKey(
|
|
846
|
-
|
|
847
|
-
key,
|
|
848
|
-
{ name: "AES-CBC" },
|
|
849
|
-
false,
|
|
850
|
-
["encrypt"]
|
|
851
|
-
);
|
|
852
|
-
const encrypted = await crypto.subtle.encrypt(
|
|
853
|
-
{ name: "AES-CBC", iv },
|
|
854
|
-
cryptoKey,
|
|
855
|
-
buffer
|
|
856
|
-
);
|
|
836
|
+
const cryptoKey = await crypto.subtle.importKey("raw", key, { name: "AES-CBC" }, false, ["encrypt"]);
|
|
837
|
+
const encrypted = await crypto.subtle.encrypt({ name: "AES-CBC", iv }, cryptoKey, buffer);
|
|
857
838
|
return Buffer.from(encrypted);
|
|
858
839
|
}
|
|
859
840
|
static async decryptFileBrowser(buffer, key, iv) {
|
|
860
841
|
const crypto = CryptoUtils.getCrypto();
|
|
861
|
-
const cryptoKey = await crypto.subtle.importKey(
|
|
862
|
-
|
|
863
|
-
key,
|
|
864
|
-
{ name: "AES-CBC" },
|
|
865
|
-
false,
|
|
866
|
-
["decrypt"]
|
|
867
|
-
);
|
|
868
|
-
const decrypted = await crypto.subtle.decrypt(
|
|
869
|
-
{ name: "AES-CBC", iv },
|
|
870
|
-
cryptoKey,
|
|
871
|
-
buffer
|
|
872
|
-
);
|
|
842
|
+
const cryptoKey = await crypto.subtle.importKey("raw", key, { name: "AES-CBC" }, false, ["decrypt"]);
|
|
843
|
+
const decrypted = await crypto.subtle.decrypt({ name: "AES-CBC", iv }, cryptoKey, buffer);
|
|
873
844
|
return Buffer.from(decrypted);
|
|
874
845
|
}
|
|
875
846
|
};
|
|
876
847
|
|
|
877
848
|
// src/services/file-service.ts
|
|
878
|
-
import { AlephHttpClient } from "@aleph-sdk/client";
|
|
879
849
|
var FileService = class {
|
|
880
850
|
constructor(core) {
|
|
881
851
|
this.core = core;
|
|
@@ -886,10 +856,7 @@ var FileService = class {
|
|
|
886
856
|
async setup() {
|
|
887
857
|
const aleph = this.core.getAlephService();
|
|
888
858
|
try {
|
|
889
|
-
await aleph.fetchAggregate(
|
|
890
|
-
AGGREGATE_KEYS.FILE_ENTRIES,
|
|
891
|
-
FileEntriesAggregateSchema
|
|
892
|
-
);
|
|
859
|
+
await aleph.fetchAggregate(AGGREGATE_KEYS.FILE_ENTRIES, FileEntriesAggregateSchema);
|
|
893
860
|
} catch {
|
|
894
861
|
await aleph.createAggregate(AGGREGATE_KEYS.FILE_ENTRIES, { files: [] });
|
|
895
862
|
}
|
|
@@ -917,7 +884,7 @@ var FileService = class {
|
|
|
917
884
|
}
|
|
918
885
|
const encryptedContent = await EncryptionService.encryptFile(fileBuffer, key, iv);
|
|
919
886
|
const storeResult = await aleph.uploadFile(encryptedContent);
|
|
920
|
-
const fullPath = directoryPath ? `${directoryPath}
|
|
887
|
+
const fullPath = directoryPath ? `${directoryPath}${file.path}` : file.path;
|
|
921
888
|
const createdAt = (/* @__PURE__ */ new Date()).toISOString();
|
|
922
889
|
const fileMeta = {
|
|
923
890
|
name: file.name,
|
|
@@ -968,12 +935,14 @@ var FileService = class {
|
|
|
968
935
|
*/
|
|
969
936
|
async fetchFileEntries() {
|
|
970
937
|
const aleph = this.core.getAlephService();
|
|
938
|
+
const privateKey = this.core.getSubAccountPrivateKey();
|
|
971
939
|
try {
|
|
972
|
-
const aggregate = await aleph.fetchAggregate(
|
|
973
|
-
|
|
974
|
-
|
|
975
|
-
|
|
976
|
-
|
|
940
|
+
const aggregate = await aleph.fetchAggregate(AGGREGATE_KEYS.FILE_ENTRIES, FileEntriesAggregateSchema);
|
|
941
|
+
return aggregate.files.map(({ post_hash, path, shared_with }) => ({
|
|
942
|
+
post_hash,
|
|
943
|
+
path: EncryptionService.decryptEcies(path, privateKey),
|
|
944
|
+
shared_with
|
|
945
|
+
}));
|
|
977
946
|
} catch (error) {
|
|
978
947
|
throw new FileError(`Failed to fetch file entries: ${error.message}`);
|
|
979
948
|
}
|
|
@@ -1095,15 +1064,9 @@ var FileService = class {
|
|
|
1095
1064
|
const aleph = this.core.getAlephService();
|
|
1096
1065
|
try {
|
|
1097
1066
|
const files = await Promise.all(filePaths.map((path) => this.getFile(path)));
|
|
1098
|
-
await aleph.updateAggregate(
|
|
1099
|
-
|
|
1100
|
-
|
|
1101
|
-
async (aggregate) => ({
|
|
1102
|
-
files: aggregate.files.filter(
|
|
1103
|
-
(entry) => !files.some((f) => f.post_hash === entry.post_hash)
|
|
1104
|
-
)
|
|
1105
|
-
})
|
|
1106
|
-
);
|
|
1067
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.FILE_ENTRIES, FileEntriesAggregateSchema, async (aggregate) => ({
|
|
1068
|
+
files: aggregate.files.filter((entry) => !files.some((f) => f.post_hash === entry.post_hash))
|
|
1069
|
+
}));
|
|
1107
1070
|
const hashesToForget = files.flatMap((f) => [f.store_hash, f.post_hash]);
|
|
1108
1071
|
await aleph.deleteFiles(hashesToForget);
|
|
1109
1072
|
} catch (error) {
|
|
@@ -1133,15 +1096,11 @@ var FileService = class {
|
|
|
1133
1096
|
}
|
|
1134
1097
|
);
|
|
1135
1098
|
const newEncryptedPath = EncryptionService.encryptEcies(newPath, publicKey);
|
|
1136
|
-
await aleph.updateAggregate(
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
|
|
1141
|
-
(entry) => entry.post_hash === file.post_hash ? { ...entry, path: newEncryptedPath } : entry
|
|
1142
|
-
)
|
|
1143
|
-
})
|
|
1144
|
-
);
|
|
1099
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.FILE_ENTRIES, FileEntriesAggregateSchema, async (aggregate) => ({
|
|
1100
|
+
files: aggregate.files.map(
|
|
1101
|
+
(entry) => entry.post_hash === file.post_hash ? { ...entry, path: newEncryptedPath } : entry
|
|
1102
|
+
)
|
|
1103
|
+
}));
|
|
1145
1104
|
}
|
|
1146
1105
|
} catch (error) {
|
|
1147
1106
|
throw new FileError(`Failed to move files: ${error.message}`);
|
|
@@ -1156,11 +1115,13 @@ var FileService = class {
|
|
|
1156
1115
|
try {
|
|
1157
1116
|
const sourceFile = await this.getFile(sourcePath);
|
|
1158
1117
|
const content = await this.downloadFile(sourceFile);
|
|
1159
|
-
const [newFile] = await this.uploadFiles([
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1163
|
-
|
|
1118
|
+
const [newFile] = await this.uploadFiles([
|
|
1119
|
+
{
|
|
1120
|
+
name: newPath.split("/").pop() || newPath,
|
|
1121
|
+
path: newPath,
|
|
1122
|
+
content
|
|
1123
|
+
}
|
|
1124
|
+
]);
|
|
1164
1125
|
return newFile;
|
|
1165
1126
|
} catch (error) {
|
|
1166
1127
|
throw new FileError(`Failed to duplicate file: ${error.message}`);
|
|
@@ -1191,15 +1152,11 @@ var FileService = class {
|
|
|
1191
1152
|
return await this.encryptFileMeta(decryptedMeta);
|
|
1192
1153
|
}
|
|
1193
1154
|
);
|
|
1194
|
-
await aleph.updateAggregate(
|
|
1195
|
-
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
(entry) => entry.post_hash === file.post_hash ? { ...entry, shared_with: [.../* @__PURE__ */ new Set([...entry.shared_with, contactPublicKey])] } : entry
|
|
1200
|
-
)
|
|
1201
|
-
})
|
|
1202
|
-
);
|
|
1155
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.FILE_ENTRIES, FileEntriesAggregateSchema, async (aggregate) => ({
|
|
1156
|
+
files: aggregate.files.map(
|
|
1157
|
+
(entry) => entry.post_hash === file.post_hash ? { ...entry, shared_with: [.../* @__PURE__ */ new Set([...entry.shared_with, contactPublicKey])] } : entry
|
|
1158
|
+
)
|
|
1159
|
+
}));
|
|
1203
1160
|
} catch (error) {
|
|
1204
1161
|
throw new FileError(`Failed to share file: ${error.message}`);
|
|
1205
1162
|
}
|
|
@@ -1224,15 +1181,11 @@ var FileService = class {
|
|
|
1224
1181
|
return await this.encryptFileMeta(decryptedMeta);
|
|
1225
1182
|
}
|
|
1226
1183
|
);
|
|
1227
|
-
await aleph.updateAggregate(
|
|
1228
|
-
|
|
1229
|
-
|
|
1230
|
-
|
|
1231
|
-
|
|
1232
|
-
(entry) => entry.post_hash === file.post_hash ? { ...entry, shared_with: entry.shared_with.filter((pk) => pk !== contactPublicKey) } : entry
|
|
1233
|
-
)
|
|
1234
|
-
})
|
|
1235
|
-
);
|
|
1184
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.FILE_ENTRIES, FileEntriesAggregateSchema, async (aggregate) => ({
|
|
1185
|
+
files: aggregate.files.map(
|
|
1186
|
+
(entry) => entry.post_hash === file.post_hash ? { ...entry, shared_with: entry.shared_with.filter((pk) => pk !== contactPublicKey) } : entry
|
|
1187
|
+
)
|
|
1188
|
+
}));
|
|
1236
1189
|
} catch (error) {
|
|
1237
1190
|
throw new FileError(`Failed to unshare file: ${error.message}`);
|
|
1238
1191
|
}
|
|
@@ -1297,51 +1250,51 @@ var FileService = class {
|
|
|
1297
1250
|
// ============================================================================
|
|
1298
1251
|
async saveFileEntries(files) {
|
|
1299
1252
|
const aleph = this.core.getAlephService();
|
|
1300
|
-
|
|
1301
|
-
|
|
1302
|
-
|
|
1303
|
-
|
|
1304
|
-
|
|
1305
|
-
|
|
1306
|
-
|
|
1307
|
-
|
|
1308
|
-
|
|
1309
|
-
return { files: [...aggregate.files, ...newEntries] };
|
|
1310
|
-
}
|
|
1311
|
-
);
|
|
1253
|
+
const publicKey = this.core.getPublicKey();
|
|
1254
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.FILE_ENTRIES, FileEntriesAggregateSchema, async (aggregate) => {
|
|
1255
|
+
const newEntries = files.map((f) => ({
|
|
1256
|
+
path: EncryptionService.encryptEcies(f.path, publicKey),
|
|
1257
|
+
post_hash: f.post_hash,
|
|
1258
|
+
shared_with: f.shared_with || []
|
|
1259
|
+
}));
|
|
1260
|
+
return { files: [...aggregate.files, ...newEntries] };
|
|
1261
|
+
});
|
|
1312
1262
|
}
|
|
1313
1263
|
async encryptFileMeta(meta) {
|
|
1314
|
-
const key = this.core.getEncryptionKey();
|
|
1315
|
-
const iv = EncryptionService.generateIv();
|
|
1316
1264
|
const publicKey = this.core.getPublicKey();
|
|
1265
|
+
const fileKey = Buffer.from(meta.key, "hex");
|
|
1266
|
+
const fileIv = Buffer.from(meta.iv, "hex");
|
|
1317
1267
|
return {
|
|
1318
|
-
name: await EncryptionService.encrypt(meta.name,
|
|
1319
|
-
path: EncryptionService.
|
|
1268
|
+
name: await EncryptionService.encrypt(meta.name, fileKey, fileIv),
|
|
1269
|
+
path: await EncryptionService.encrypt(meta.path, fileKey, fileIv),
|
|
1320
1270
|
key: EncryptionService.encryptEcies(meta.key, publicKey),
|
|
1321
1271
|
iv: EncryptionService.encryptEcies(meta.iv, publicKey),
|
|
1322
|
-
store_hash: meta.store_hash,
|
|
1323
|
-
size: await EncryptionService.encrypt(meta.size.toString(),
|
|
1324
|
-
created_at: await EncryptionService.encrypt(meta.created_at,
|
|
1325
|
-
deleted_at:
|
|
1272
|
+
store_hash: await EncryptionService.encrypt(meta.store_hash, fileKey, fileIv),
|
|
1273
|
+
size: await EncryptionService.encrypt(meta.size.toString(), fileKey, fileIv),
|
|
1274
|
+
created_at: await EncryptionService.encrypt(meta.created_at, fileKey, fileIv),
|
|
1275
|
+
deleted_at: await EncryptionService.encrypt(meta.deleted_at ?? "null", fileKey, fileIv),
|
|
1326
1276
|
shared_keys: meta.shared_keys
|
|
1327
1277
|
};
|
|
1328
1278
|
}
|
|
1329
1279
|
async decryptFileMeta(encryptedMeta, privateKey) {
|
|
1330
|
-
const key = this.core.getEncryptionKey();
|
|
1331
|
-
const iv = EncryptionService.generateIv();
|
|
1332
1280
|
const privKey = privateKey || this.core.getSubAccountPrivateKey();
|
|
1333
1281
|
if (!privKey) {
|
|
1334
1282
|
throw new EncryptionError("Private key not available");
|
|
1335
1283
|
}
|
|
1284
|
+
const decryptedKey = EncryptionService.decryptEcies(encryptedMeta.key, privKey);
|
|
1285
|
+
const decryptedIv = EncryptionService.decryptEcies(encryptedMeta.iv, privKey);
|
|
1286
|
+
const fileKey = Buffer.from(decryptedKey, "hex");
|
|
1287
|
+
const fileIv = Buffer.from(decryptedIv, "hex");
|
|
1288
|
+
const decryptedDeletedAt = await EncryptionService.decrypt(encryptedMeta.deleted_at, fileKey, fileIv);
|
|
1336
1289
|
return {
|
|
1337
|
-
name: await EncryptionService.decrypt(encryptedMeta.name,
|
|
1338
|
-
path: EncryptionService.
|
|
1339
|
-
key:
|
|
1340
|
-
iv:
|
|
1341
|
-
store_hash: encryptedMeta.store_hash,
|
|
1342
|
-
size: parseInt(await EncryptionService.decrypt(encryptedMeta.size,
|
|
1343
|
-
created_at: await EncryptionService.decrypt(encryptedMeta.created_at,
|
|
1344
|
-
deleted_at:
|
|
1290
|
+
name: await EncryptionService.decrypt(encryptedMeta.name, fileKey, fileIv),
|
|
1291
|
+
path: await EncryptionService.decrypt(encryptedMeta.path, fileKey, fileIv),
|
|
1292
|
+
key: decryptedKey,
|
|
1293
|
+
iv: decryptedIv,
|
|
1294
|
+
store_hash: await EncryptionService.decrypt(encryptedMeta.store_hash, fileKey, fileIv),
|
|
1295
|
+
size: Number.parseInt(await EncryptionService.decrypt(encryptedMeta.size, fileKey, fileIv)),
|
|
1296
|
+
created_at: await EncryptionService.decrypt(encryptedMeta.created_at, fileKey, fileIv),
|
|
1297
|
+
deleted_at: decryptedDeletedAt === "null" ? null : decryptedDeletedAt,
|
|
1345
1298
|
shared_keys: encryptedMeta.shared_keys || {}
|
|
1346
1299
|
};
|
|
1347
1300
|
}
|
|
@@ -1359,10 +1312,7 @@ var ContactService = class {
|
|
|
1359
1312
|
async setup() {
|
|
1360
1313
|
const aleph = this.core.getAlephService();
|
|
1361
1314
|
try {
|
|
1362
|
-
await aleph.fetchAggregate(
|
|
1363
|
-
AGGREGATE_KEYS.CONTACTS,
|
|
1364
|
-
ContactsAggregateSchema
|
|
1365
|
-
);
|
|
1315
|
+
await aleph.fetchAggregate(AGGREGATE_KEYS.CONTACTS, ContactsAggregateSchema);
|
|
1366
1316
|
} catch {
|
|
1367
1317
|
await aleph.createAggregate(AGGREGATE_KEYS.CONTACTS, { contacts: [] });
|
|
1368
1318
|
}
|
|
@@ -1373,10 +1323,7 @@ var ContactService = class {
|
|
|
1373
1323
|
async listContacts() {
|
|
1374
1324
|
const aleph = this.core.getAlephService();
|
|
1375
1325
|
try {
|
|
1376
|
-
const aggregate = await aleph.fetchAggregate(
|
|
1377
|
-
AGGREGATE_KEYS.CONTACTS,
|
|
1378
|
-
ContactsAggregateSchema
|
|
1379
|
-
);
|
|
1326
|
+
const aggregate = await aleph.fetchAggregate(AGGREGATE_KEYS.CONTACTS, ContactsAggregateSchema);
|
|
1380
1327
|
return aggregate.contacts;
|
|
1381
1328
|
} catch (error) {
|
|
1382
1329
|
throw new ContactError(`Failed to fetch contacts: ${error.message}`);
|
|
@@ -1427,13 +1374,9 @@ var ContactService = class {
|
|
|
1427
1374
|
address,
|
|
1428
1375
|
public_key: publicKey
|
|
1429
1376
|
};
|
|
1430
|
-
await aleph.updateAggregate(
|
|
1431
|
-
|
|
1432
|
-
|
|
1433
|
-
async (aggregate) => ({
|
|
1434
|
-
contacts: [...aggregate.contacts, newContact]
|
|
1435
|
-
})
|
|
1436
|
-
);
|
|
1377
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.CONTACTS, ContactsAggregateSchema, async (aggregate) => ({
|
|
1378
|
+
contacts: [...aggregate.contacts, newContact]
|
|
1379
|
+
}));
|
|
1437
1380
|
return newContact;
|
|
1438
1381
|
} catch (error) {
|
|
1439
1382
|
if (error instanceof ContactError) {
|
|
@@ -1450,13 +1393,9 @@ var ContactService = class {
|
|
|
1450
1393
|
const aleph = this.core.getAlephService();
|
|
1451
1394
|
try {
|
|
1452
1395
|
await this.getContact(publicKey);
|
|
1453
|
-
await aleph.updateAggregate(
|
|
1454
|
-
|
|
1455
|
-
|
|
1456
|
-
async (aggregate) => ({
|
|
1457
|
-
contacts: aggregate.contacts.filter((c) => c.public_key !== publicKey)
|
|
1458
|
-
})
|
|
1459
|
-
);
|
|
1396
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.CONTACTS, ContactsAggregateSchema, async (aggregate) => ({
|
|
1397
|
+
contacts: aggregate.contacts.filter((c) => c.public_key !== publicKey)
|
|
1398
|
+
}));
|
|
1460
1399
|
} catch (error) {
|
|
1461
1400
|
if (error instanceof ContactError) {
|
|
1462
1401
|
throw error;
|
|
@@ -1477,15 +1416,9 @@ var ContactService = class {
|
|
|
1477
1416
|
...existingContact,
|
|
1478
1417
|
name: newName
|
|
1479
1418
|
};
|
|
1480
|
-
await aleph.updateAggregate(
|
|
1481
|
-
|
|
1482
|
-
|
|
1483
|
-
async (aggregate) => ({
|
|
1484
|
-
contacts: aggregate.contacts.map(
|
|
1485
|
-
(c) => c.public_key === publicKey ? updatedContact : c
|
|
1486
|
-
)
|
|
1487
|
-
})
|
|
1488
|
-
);
|
|
1419
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.CONTACTS, ContactsAggregateSchema, async (aggregate) => ({
|
|
1420
|
+
contacts: aggregate.contacts.map((c) => c.public_key === publicKey ? updatedContact : c)
|
|
1421
|
+
}));
|
|
1489
1422
|
return updatedContact;
|
|
1490
1423
|
} catch (error) {
|
|
1491
1424
|
if (error instanceof ContactError) {
|
|
@@ -1502,9 +1435,7 @@ var ContactService = class {
|
|
|
1502
1435
|
try {
|
|
1503
1436
|
await this.getContact(publicKey);
|
|
1504
1437
|
const entries = await this.fileService.fetchFileEntries();
|
|
1505
|
-
const sharedEntries = entries.filter(
|
|
1506
|
-
(entry) => entry.shared_with.includes(publicKey)
|
|
1507
|
-
);
|
|
1438
|
+
const sharedEntries = entries.filter((entry) => entry.shared_with.includes(publicKey));
|
|
1508
1439
|
const files = await this.fileService.fetchFilesMetaFromEntries(sharedEntries);
|
|
1509
1440
|
return files;
|
|
1510
1441
|
} catch (error) {
|
|
@@ -1527,9 +1458,7 @@ var ContactService = class {
|
|
|
1527
1458
|
contact.address
|
|
1528
1459
|
// Important: contact's address, not current user's
|
|
1529
1460
|
);
|
|
1530
|
-
const sharedEntries = contactEntries.files.filter(
|
|
1531
|
-
(entry) => entry.shared_with.includes(currentUserPublicKey)
|
|
1532
|
-
);
|
|
1461
|
+
const sharedEntries = contactEntries.files.filter((entry) => entry.shared_with.includes(currentUserPublicKey));
|
|
1533
1462
|
const files = await this.fileService.fetchFilesMetaFromEntries(
|
|
1534
1463
|
sharedEntries,
|
|
1535
1464
|
contact.address
|
|
@@ -1579,10 +1508,7 @@ var KnowledgeBaseService = class {
|
|
|
1579
1508
|
async setup() {
|
|
1580
1509
|
const aleph = this.core.getAlephService();
|
|
1581
1510
|
try {
|
|
1582
|
-
await aleph.fetchAggregate(
|
|
1583
|
-
AGGREGATE_KEYS.KNOWLEDGE_BASES,
|
|
1584
|
-
KnowledgeBasesAggregateSchema
|
|
1585
|
-
);
|
|
1511
|
+
await aleph.fetchAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, KnowledgeBasesAggregateSchema);
|
|
1586
1512
|
} catch {
|
|
1587
1513
|
await aleph.createAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, { knowledge_bases: [] });
|
|
1588
1514
|
}
|
|
@@ -1593,10 +1519,7 @@ var KnowledgeBaseService = class {
|
|
|
1593
1519
|
async listKnowledgeBases() {
|
|
1594
1520
|
const aleph = this.core.getAlephService();
|
|
1595
1521
|
try {
|
|
1596
|
-
const aggregate = await aleph.fetchAggregate(
|
|
1597
|
-
AGGREGATE_KEYS.KNOWLEDGE_BASES,
|
|
1598
|
-
KnowledgeBasesAggregateSchema
|
|
1599
|
-
);
|
|
1522
|
+
const aggregate = await aleph.fetchAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, KnowledgeBasesAggregateSchema);
|
|
1600
1523
|
return aggregate.knowledge_bases;
|
|
1601
1524
|
} catch (error) {
|
|
1602
1525
|
throw new KnowledgeBaseError(`Failed to fetch knowledge bases: ${error.message}`);
|
|
@@ -1634,13 +1557,9 @@ var KnowledgeBaseService = class {
|
|
|
1634
1557
|
created_at: now,
|
|
1635
1558
|
updated_at: now
|
|
1636
1559
|
};
|
|
1637
|
-
await aleph.updateAggregate(
|
|
1638
|
-
|
|
1639
|
-
|
|
1640
|
-
async (aggregate) => ({
|
|
1641
|
-
knowledge_bases: [...aggregate.knowledge_bases, newKb]
|
|
1642
|
-
})
|
|
1643
|
-
);
|
|
1560
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, KnowledgeBasesAggregateSchema, async (aggregate) => ({
|
|
1561
|
+
knowledge_bases: [...aggregate.knowledge_bases, newKb]
|
|
1562
|
+
}));
|
|
1644
1563
|
return newKb;
|
|
1645
1564
|
} catch (error) {
|
|
1646
1565
|
if (error instanceof KnowledgeBaseError) {
|
|
@@ -1657,13 +1576,9 @@ var KnowledgeBaseService = class {
|
|
|
1657
1576
|
const aleph = this.core.getAlephService();
|
|
1658
1577
|
try {
|
|
1659
1578
|
await this.getKnowledgeBase(name);
|
|
1660
|
-
await aleph.updateAggregate(
|
|
1661
|
-
|
|
1662
|
-
|
|
1663
|
-
async (aggregate) => ({
|
|
1664
|
-
knowledge_bases: aggregate.knowledge_bases.filter((k) => k.name !== name)
|
|
1665
|
-
})
|
|
1666
|
-
);
|
|
1579
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, KnowledgeBasesAggregateSchema, async (aggregate) => ({
|
|
1580
|
+
knowledge_bases: aggregate.knowledge_bases.filter((k) => k.name !== name)
|
|
1581
|
+
}));
|
|
1667
1582
|
} catch (error) {
|
|
1668
1583
|
if (error instanceof KnowledgeBaseError) {
|
|
1669
1584
|
throw error;
|
|
@@ -1689,15 +1604,9 @@ var KnowledgeBaseService = class {
|
|
|
1689
1604
|
name: newName,
|
|
1690
1605
|
updated_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
1691
1606
|
};
|
|
1692
|
-
await aleph.updateAggregate(
|
|
1693
|
-
|
|
1694
|
-
|
|
1695
|
-
async (aggregate) => ({
|
|
1696
|
-
knowledge_bases: aggregate.knowledge_bases.map(
|
|
1697
|
-
(k) => k.name === oldName ? updatedKb : k
|
|
1698
|
-
)
|
|
1699
|
-
})
|
|
1700
|
-
);
|
|
1607
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, KnowledgeBasesAggregateSchema, async (aggregate) => ({
|
|
1608
|
+
knowledge_bases: aggregate.knowledge_bases.map((k) => k.name === oldName ? updatedKb : k)
|
|
1609
|
+
}));
|
|
1701
1610
|
return updatedKb;
|
|
1702
1611
|
} catch (error) {
|
|
1703
1612
|
if (error instanceof KnowledgeBaseError) {
|
|
@@ -1720,15 +1629,9 @@ var KnowledgeBaseService = class {
|
|
|
1720
1629
|
file_paths: filePaths,
|
|
1721
1630
|
updated_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
1722
1631
|
};
|
|
1723
|
-
await aleph.updateAggregate(
|
|
1724
|
-
|
|
1725
|
-
|
|
1726
|
-
async (aggregate) => ({
|
|
1727
|
-
knowledge_bases: aggregate.knowledge_bases.map(
|
|
1728
|
-
(k) => k.name === name ? updatedKb : k
|
|
1729
|
-
)
|
|
1730
|
-
})
|
|
1731
|
-
);
|
|
1632
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, KnowledgeBasesAggregateSchema, async (aggregate) => ({
|
|
1633
|
+
knowledge_bases: aggregate.knowledge_bases.map((k) => k.name === name ? updatedKb : k)
|
|
1634
|
+
}));
|
|
1732
1635
|
return updatedKb;
|
|
1733
1636
|
} catch (error) {
|
|
1734
1637
|
if (error instanceof KnowledgeBaseError) {
|
|
@@ -1752,15 +1655,9 @@ var KnowledgeBaseService = class {
|
|
|
1752
1655
|
file_paths: updatedFilePaths,
|
|
1753
1656
|
updated_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
1754
1657
|
};
|
|
1755
|
-
await aleph.updateAggregate(
|
|
1756
|
-
|
|
1757
|
-
|
|
1758
|
-
async (aggregate) => ({
|
|
1759
|
-
knowledge_bases: aggregate.knowledge_bases.map(
|
|
1760
|
-
(k) => k.name === name ? updatedKb : k
|
|
1761
|
-
)
|
|
1762
|
-
})
|
|
1763
|
-
);
|
|
1658
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, KnowledgeBasesAggregateSchema, async (aggregate) => ({
|
|
1659
|
+
knowledge_bases: aggregate.knowledge_bases.map((k) => k.name === name ? updatedKb : k)
|
|
1660
|
+
}));
|
|
1764
1661
|
return updatedKb;
|
|
1765
1662
|
} catch (error) {
|
|
1766
1663
|
if (error instanceof KnowledgeBaseError) {
|
|
@@ -1778,23 +1675,15 @@ var KnowledgeBaseService = class {
|
|
|
1778
1675
|
const aleph = this.core.getAlephService();
|
|
1779
1676
|
try {
|
|
1780
1677
|
const existingKb = await this.getKnowledgeBase(name);
|
|
1781
|
-
const updatedFilePaths = existingKb.file_paths.filter(
|
|
1782
|
-
(path) => !filePaths.includes(path)
|
|
1783
|
-
);
|
|
1678
|
+
const updatedFilePaths = existingKb.file_paths.filter((path) => !filePaths.includes(path));
|
|
1784
1679
|
const updatedKb = {
|
|
1785
1680
|
...existingKb,
|
|
1786
1681
|
file_paths: updatedFilePaths,
|
|
1787
1682
|
updated_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
1788
1683
|
};
|
|
1789
|
-
await aleph.updateAggregate(
|
|
1790
|
-
|
|
1791
|
-
|
|
1792
|
-
async (aggregate) => ({
|
|
1793
|
-
knowledge_bases: aggregate.knowledge_bases.map(
|
|
1794
|
-
(k) => k.name === name ? updatedKb : k
|
|
1795
|
-
)
|
|
1796
|
-
})
|
|
1797
|
-
);
|
|
1684
|
+
await aleph.updateAggregate(AGGREGATE_KEYS.KNOWLEDGE_BASES, KnowledgeBasesAggregateSchema, async (aggregate) => ({
|
|
1685
|
+
knowledge_bases: aggregate.knowledge_bases.map((k) => k.name === name ? updatedKb : k)
|
|
1686
|
+
}));
|
|
1798
1687
|
return updatedKb;
|
|
1799
1688
|
} catch (error) {
|
|
1800
1689
|
if (error instanceof KnowledgeBaseError) {
|
|
@@ -1933,11 +1822,7 @@ var BedrockClient = class _BedrockClient {
|
|
|
1933
1822
|
* WARNING: This will delete all user data from Aleph
|
|
1934
1823
|
*/
|
|
1935
1824
|
async resetAllData() {
|
|
1936
|
-
await Promise.all([
|
|
1937
|
-
this.resetFiles(),
|
|
1938
|
-
this.resetContacts(),
|
|
1939
|
-
this.resetKnowledgeBases()
|
|
1940
|
-
]);
|
|
1825
|
+
await Promise.all([this.resetFiles(), this.resetContacts(), this.resetKnowledgeBases()]);
|
|
1941
1826
|
}
|
|
1942
1827
|
/**
|
|
1943
1828
|
* Reset all files
|
|
@@ -1970,11 +1855,7 @@ var BedrockClient = class _BedrockClient {
|
|
|
1970
1855
|
* Setup all services (create aggregates if they don't exist)
|
|
1971
1856
|
*/
|
|
1972
1857
|
async setup() {
|
|
1973
|
-
await Promise.all([
|
|
1974
|
-
this.files.setup(),
|
|
1975
|
-
this.contacts.setup(),
|
|
1976
|
-
this.knowledgeBases.setup()
|
|
1977
|
-
]);
|
|
1858
|
+
await Promise.all([this.files.setup(), this.contacts.setup(), this.knowledgeBases.setup()]);
|
|
1978
1859
|
}
|
|
1979
1860
|
};
|
|
1980
1861
|
|