bedrock-ts-sdk 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 Bedrock.im
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,539 @@
1
+ # Bedrock SDK
2
+
3
+ TypeScript SDK for [Bedrock](https://bedrock.im) - decentralized cloud storage powered by [Aleph](https://aleph.im).
4
+
5
+ ## Features
6
+
7
+ - 🔐 **End-to-end encryption** - All files and metadata encrypted with AES-256-CBC + ECIES
8
+ - 🌐 **Universal** - Works in Node.js and browser environments
9
+ - 📁 **File management** - Upload, download, move, delete (soft/hard), share files
10
+ - 🔗 **Public sharing** - Share files publicly without authentication
11
+ - 👥 **Contact management** - Manage contacts and share files securely
12
+ - 🧠 **Knowledge bases** - Organize files into collections
13
+ - 💳 **Credit tracking** - Monitor usage credits and transaction history
14
+ - ⚡ **Decentralized** - Built on Aleph network, no central server
15
+ - 🔑 **Wallet integration** - MetaMask, Rabby, WalletConnect, or private key
16
+ - 📦 **TypeScript** - Full type safety with TypeScript
17
+
18
+ ## Installation
19
+
20
+ ```bash
21
+ npm install bedrock-ts-sdk
22
+ ```
23
+
24
+ ## Quick Start
25
+
26
+ ### Node.js
27
+
28
+ ```typescript
29
+ import { BedrockClient } from 'bedrock-ts-sdk';
30
+
31
+ // Initialize from private key
32
+ const client = await BedrockClient.fromPrivateKey('0x...');
33
+
34
+ // Upload a file
35
+ const files = await client.files.uploadFiles([{
36
+ name: 'hello.txt',
37
+ path: 'documents/hello.txt',
38
+ content: Buffer.from('Hello, Bedrock!'),
39
+ }]);
40
+
41
+ // List all files
42
+ const allFiles = await client.files.listFiles();
43
+ console.log('Files:', allFiles);
44
+
45
+ // Download a file
46
+ const content = await client.files.downloadFile(allFiles[0]);
47
+ console.log('Content:', content.toString());
48
+ ```
49
+
50
+ ### Browser with MetaMask
51
+
52
+ ```typescript
53
+ import { BedrockClient, BEDROCK_MESSAGE } from 'bedrock-ts-sdk';
54
+
55
+ // Request signature from MetaMask
56
+ const accounts = await window.ethereum.request({
57
+ method: 'eth_requestAccounts'
58
+ });
59
+ const signature = await window.ethereum.request({
60
+ method: 'personal_sign',
61
+ params: [BEDROCK_MESSAGE, accounts[0]],
62
+ });
63
+
64
+ // Initialize client with signature
65
+ const client = await BedrockClient.fromSignature(
66
+ signature,
67
+ window.ethereum
68
+ );
69
+
70
+ // Upload a file from user input
71
+ const fileInput = document.querySelector('input[type="file"]');
72
+ const file = fileInput.files[0];
73
+ const buffer = Buffer.from(await file.arrayBuffer());
74
+
75
+ await client.files.uploadFiles([{
76
+ name: file.name,
77
+ path: `uploads/${file.name}`,
78
+ content: buffer,
79
+ }]);
80
+ ```
81
+
82
+ ## API Reference
83
+
84
+ ### Initialization
85
+
86
+ #### `BedrockClient.fromPrivateKey(privateKey, config?)`
87
+
88
+ Create client from Ethereum private key.
89
+
90
+ ```typescript
91
+ const client = await BedrockClient.fromPrivateKey('0xabc123...');
92
+ ```
93
+
94
+ #### `BedrockClient.fromProvider(provider, config?)`
95
+
96
+ Create client from wallet provider (MetaMask, WalletConnect, etc.).
97
+
98
+ ```typescript
99
+ const client = await BedrockClient.fromProvider(window.ethereum);
100
+ ```
101
+
102
+ #### `BedrockClient.fromSignature(signatureHash, provider, config?)`
103
+
104
+ Create client from wallet signature (recommended for web apps).
105
+
106
+ ```typescript
107
+ // User signs message with wallet
108
+ const signature = await wallet.signMessage({ message: 'Bedrock.im' });
109
+ const client = await BedrockClient.fromSignature(
110
+ signature,
111
+ window.ethereum,
112
+ { apiServer: 'https://api2.aleph.im' }
113
+ );
114
+ ```
115
+
116
+ ### File Operations
117
+
118
+ #### Upload Files
119
+
120
+ ```typescript
121
+ const files = await client.files.uploadFiles([
122
+ {
123
+ name: 'document.pdf',
124
+ path: 'documents/document.pdf',
125
+ content: fileBuffer, // Buffer or File
126
+ },
127
+ {
128
+ name: 'image.jpg',
129
+ path: 'images/image.jpg',
130
+ content: imageBuffer,
131
+ },
132
+ ]);
133
+ ```
134
+
135
+ #### List Files
136
+
137
+ ```typescript
138
+ // List all non-deleted files
139
+ const files = await client.files.listFiles();
140
+
141
+ // Include soft-deleted files
142
+ const allFiles = await client.files.listFiles(true);
143
+ ```
144
+
145
+ #### Get File by Path
146
+
147
+ ```typescript
148
+ const file = await client.files.getFile('documents/document.pdf');
149
+ console.log(file.name, file.size, file.created_at);
150
+ ```
151
+
152
+ #### Download File
153
+
154
+ ```typescript
155
+ const file = await client.files.getFile('documents/document.pdf');
156
+ const content = await client.files.downloadFile(file);
157
+
158
+ // Save to disk (Node.js)
159
+ fs.writeFileSync('downloaded.pdf', content);
160
+
161
+ // Create download link (Browser)
162
+ const blob = new Blob([content]);
163
+ const url = URL.createObjectURL(blob);
164
+ ```
165
+
166
+ #### Move/Rename Files
167
+
168
+ ```typescript
169
+ await client.files.moveFiles([
170
+ { oldPath: 'old/path.txt', newPath: 'new/path.txt' },
171
+ { oldPath: 'doc.pdf', newPath: 'documents/doc.pdf' },
172
+ ]);
173
+ ```
174
+
175
+ #### Duplicate File
176
+
177
+ ```typescript
178
+ await client.files.duplicateFile('original.txt', 'copy.txt');
179
+ ```
180
+
181
+ #### Soft Delete (Trash)
182
+
183
+ ```typescript
184
+ // Move to trash
185
+ await client.files.softDeleteFiles(['path/to/file.txt']);
186
+
187
+ // Restore from trash
188
+ await client.files.restoreFiles(['path/to/file.txt']);
189
+ ```
190
+
191
+ #### Hard Delete (Permanent)
192
+
193
+ ```typescript
194
+ // WARNING: This permanently removes files from Aleph network
195
+ await client.files.hardDeleteFiles(['path/to/file.txt']);
196
+ ```
197
+
198
+ #### Share Files
199
+
200
+ ```typescript
201
+ // Share with a contact
202
+ await client.files.shareFile('document.pdf', contactPublicKey);
203
+
204
+ // Unshare
205
+ await client.files.unshareFile('document.pdf', contactPublicKey);
206
+ ```
207
+
208
+ #### Public File Sharing
209
+
210
+ ```typescript
211
+ // Share file publicly (anyone can access without authentication)
212
+ const file = await client.files.getFile('document.pdf');
213
+ const publicHash = await client.files.shareFilePublicly(file, 'username');
214
+
215
+ console.log(`Share this link: https://app.bedrock.im/public/${publicHash}`);
216
+
217
+ // Fetch public file metadata (static method - no auth needed)
218
+ import { FileService } from 'bedrock-ts-sdk';
219
+ const metadata = await FileService.fetchPublicFileMeta(publicHash);
220
+ console.log(metadata.name, metadata.size, metadata.username);
221
+
222
+ // Download public file (static method - no auth needed)
223
+ const content = await FileService.downloadPublicFile(metadata.store_hash);
224
+ ```
225
+
226
+ ### Contact Operations
227
+
228
+ #### Add Contact
229
+
230
+ ```typescript
231
+ const contact = await client.contacts.addContact(
232
+ 'Alice', // Name
233
+ '0x742d35Cc6634C0532925a3b844Bc9e7595f0bEb1', // Address
234
+ 'public_key_hex' // Public key
235
+ );
236
+ ```
237
+
238
+ #### List Contacts
239
+
240
+ ```typescript
241
+ const contacts = await client.contacts.listContacts();
242
+ contacts.forEach(c => {
243
+ console.log(c.name, c.address, c.public_key);
244
+ });
245
+ ```
246
+
247
+ #### Get Contact
248
+
249
+ ```typescript
250
+ // By public key
251
+ const contact = await client.contacts.getContact(publicKey);
252
+
253
+ // By address
254
+ const contact = await client.contacts.getContactByAddress('0x...');
255
+ ```
256
+
257
+ #### Update Contact
258
+
259
+ ```typescript
260
+ await client.contacts.updateContactName(publicKey, 'Alice Smith');
261
+ ```
262
+
263
+ #### Remove Contact
264
+
265
+ ```typescript
266
+ await client.contacts.removeContact(publicKey);
267
+ ```
268
+
269
+ #### Share Files with Contact
270
+
271
+ ```typescript
272
+ // Share
273
+ await client.contacts.shareFileWithContact('file.pdf', publicKey);
274
+
275
+ // Get files you shared with a contact
276
+ const sharedFiles = await client.contacts.getSharedFiles(publicKey);
277
+
278
+ // Get files a contact shared with you
279
+ const receivedFiles = await client.contacts.fetchFilesSharedByContact(publicKey);
280
+
281
+ // Unshare
282
+ await client.contacts.unshareFileWithContact('file.pdf', publicKey);
283
+ ```
284
+
285
+ ### Knowledge Base Operations
286
+
287
+ #### Create Knowledge Base
288
+
289
+ ```typescript
290
+ const kb = await client.knowledgeBases.createKnowledgeBase('My Documents');
291
+
292
+ // With initial files
293
+ const kb = await client.knowledgeBases.createKnowledgeBase(
294
+ 'Research Papers',
295
+ ['paper1.pdf', 'paper2.pdf']
296
+ );
297
+ ```
298
+
299
+ #### List Knowledge Bases
300
+
301
+ ```typescript
302
+ const kbs = await client.knowledgeBases.listKnowledgeBases();
303
+ kbs.forEach(kb => {
304
+ console.log(kb.name, kb.file_paths.length);
305
+ });
306
+ ```
307
+
308
+ #### Get Knowledge Base
309
+
310
+ ```typescript
311
+ const kb = await client.knowledgeBases.getKnowledgeBase('My Documents');
312
+ ```
313
+
314
+ #### Rename Knowledge Base
315
+
316
+ ```typescript
317
+ await client.knowledgeBases.renameKnowledgeBase('Old Name', 'New Name');
318
+ ```
319
+
320
+ #### Manage Files in Knowledge Base
321
+
322
+ ```typescript
323
+ // Set files (replaces all)
324
+ await client.knowledgeBases.setFiles('My KB', ['file1.txt', 'file2.txt']);
325
+
326
+ // Add files
327
+ await client.knowledgeBases.addFiles('My KB', ['file3.txt']);
328
+
329
+ // Remove files
330
+ await client.knowledgeBases.removeFiles('My KB', ['file1.txt']);
331
+
332
+ // Clear all files
333
+ await client.knowledgeBases.clearFiles('My KB');
334
+ ```
335
+
336
+ #### Delete Knowledge Base
337
+
338
+ ```typescript
339
+ await client.knowledgeBases.deleteKnowledgeBase('My Documents');
340
+ ```
341
+
342
+ ### Credit Operations
343
+
344
+ The credit system is backend-managed (read-only from SDK).
345
+
346
+ #### Get Credit Balance
347
+
348
+ ```typescript
349
+ const credits = await client.credits.getCreditBalance();
350
+
351
+ console.log('Balance:', credits.balance);
352
+ console.log('Transactions:', credits.transactions);
353
+
354
+ // Transaction history
355
+ credits.transactions.forEach(tx => {
356
+ console.log(tx.type, tx.amount, tx.description, tx.timestamp);
357
+ });
358
+ ```
359
+
360
+ **Note:** Credits are managed by the backend. Users cannot modify their balance via the SDK. The backend maintains a credit aggregate with user balances and transaction history.
361
+
362
+ ### Utility Methods
363
+
364
+ #### Get Account Info
365
+
366
+ ```typescript
367
+ const mainAddress = client.getMainAddress();
368
+ const subAddress = client.getSubAddress();
369
+ const publicKey = client.getPublicKey();
370
+ const encryptionKey = client.getEncryptionKey();
371
+ ```
372
+
373
+ #### Reset Data
374
+
375
+ ```typescript
376
+ // WARNING: These operations permanently delete data
377
+
378
+ // Reset all data
379
+ await client.resetAllData();
380
+
381
+ // Reset specific data types
382
+ await client.resetFiles();
383
+ await client.resetContacts();
384
+ await client.resetKnowledgeBases();
385
+ ```
386
+
387
+ ## Architecture
388
+
389
+ ### Encryption
390
+
391
+ Bedrock uses a dual encryption approach:
392
+
393
+ 1. **File content**: Encrypted with AES-256-CBC using random key/IV
394
+ 2. **File paths**: Encrypted with ECIES using user's public key
395
+ 3. **Metadata**: Encrypted with AES-256-CBC using signature-derived key
396
+ 4. **Shared keys**: Encrypted with ECIES using recipient's public key
397
+
398
+ ### Sub-accounts
399
+
400
+ - Main account signs a message to generate a signature
401
+ - Signature is used to derive encryption key and sub-account
402
+ - Sub-account is authorized via Aleph security aggregate
403
+ - All operations use the sub-account for better security
404
+
405
+ ### Aleph Storage
406
+
407
+ - **STORE**: Binary file content (encrypted)
408
+ - **POST**: File metadata (encrypted)
409
+ - **AGGREGATE**: File index, contacts, knowledge bases
410
+ - **FORGET**: Delete messages from network
411
+
412
+ ## Configuration
413
+
414
+ ```typescript
415
+ const client = await BedrockClient.fromPrivateKey(privateKey, {
416
+ channel: 'MY_CUSTOM_CHANNEL', // Default: 'bedrock'
417
+ apiServer: 'https://api2.aleph.im', // Default: 'https://api2.aleph.im'
418
+ });
419
+ ```
420
+
421
+ **Configuration Options:**
422
+ - `channel`: Aleph channel for data isolation (default: `'bedrock'`)
423
+ - `apiServer`: Aleph API server URL (default: `'https://api2.aleph.im'`)
424
+
425
+ ## Development
426
+
427
+ ### Setup
428
+
429
+ ```bash
430
+ # Install dependencies
431
+ npm install
432
+
433
+ # Build
434
+ npm run build
435
+
436
+ # Watch mode
437
+ npm run dev
438
+
439
+ # Run tests
440
+ npm test
441
+
442
+ # Type check
443
+ npm run typecheck
444
+ ```
445
+
446
+ ### Project Structure
447
+
448
+ ```
449
+ bedrock-sdk/
450
+ ├── src/
451
+ │ ├── bedrock-client.ts # Main client interface
452
+ │ ├── client/ # Core client & Aleph service
453
+ │ ├── services/ # File, Contact, KB services
454
+ │ ├── crypto/ # Encryption utilities
455
+ │ ├── types/ # TypeScript types & schemas
456
+ │ └── index.ts # Public API exports
457
+ ├── tests/ # Unit tests
458
+ ├── examples/ # Usage examples
459
+ └── package.json
460
+ ```
461
+
462
+ ## Examples
463
+
464
+ See the [examples/](./examples) directory:
465
+
466
+ - [basic-usage.ts](./examples/basic-usage.ts) - Complete Node.js example
467
+ - [browser-usage.html](./examples/browser-usage.html) - Interactive browser demo
468
+
469
+ ## Error Handling
470
+
471
+ The SDK provides typed errors:
472
+
473
+ ```typescript
474
+ import {
475
+ BedrockError,
476
+ AuthenticationError,
477
+ EncryptionError,
478
+ FileError,
479
+ FileNotFoundError,
480
+ ContactError,
481
+ KnowledgeBaseError,
482
+ CreditError,
483
+ NetworkError,
484
+ ValidationError,
485
+ } from 'bedrock-ts-sdk';
486
+
487
+ try {
488
+ await client.files.getFile('nonexistent.txt');
489
+ } catch (error) {
490
+ if (error instanceof FileNotFoundError) {
491
+ console.log('File not found:', error.message);
492
+ } else if (error instanceof NetworkError) {
493
+ console.log('Network error:', error.message);
494
+ } else if (error instanceof CreditError) {
495
+ console.log('Credit operation failed:', error.message);
496
+ }
497
+ }
498
+ ```
499
+
500
+ ## Browser Compatibility
501
+
502
+ The SDK works in modern browsers with:
503
+
504
+ - WebCrypto API (for encryption)
505
+ - BigInt support
506
+ - ES2020+ features
507
+
508
+ Tested on:
509
+ - Chrome 90+
510
+ - Firefox 90+
511
+ - Safari 14+
512
+ - Edge 90+
513
+
514
+ ## Security Considerations
515
+
516
+ - Private keys are never sent over the network
517
+ - All file content is encrypted before upload
518
+ - File paths are encrypted to hide folder structure
519
+ - Metadata is encrypted with signature-derived key
520
+ - Use HTTPS/secure connections in production
521
+ - Keep private keys secure and never commit them
522
+
523
+ ## License
524
+
525
+ MIT
526
+
527
+ ## Contributing
528
+
529
+ Contributions welcome! Please open an issue or PR.
530
+
531
+ ## Support
532
+
533
+ - Documentation: [https://docs.bedrock.im](https://docs.bedrock.im)
534
+ - Issues: [GitHub Issues](https://github.com/bedrock-im/bedrock-sdk/issues)
535
+ - Aleph Docs: [https://docs.aleph.cloud](https://docs.aleph.cloud)
536
+
537
+ ## Acknowledgments
538
+
539
+ Built on [Aleph](https://aleph.cloud) decentralized network.