@pixagram/lacerta-db 0.3.0 โ†’ 0.3.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.
Files changed (2) hide show
  1. package/package.json +2 -2
  2. package/readme.md +1046 -131
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pixagram/lacerta-db",
3
- "version": "0.3.0",
3
+ "version": "0.3.1",
4
4
  "description": "Lacerta-DB is a Javascript IndexedDB Database for Web Browsers. Simple, Fast, Secure.",
5
5
  "devDependencies": {
6
6
  "@babel/core": "^7.23.6",
@@ -37,7 +37,7 @@
37
37
  "license": "MIT",
38
38
  "repository": {
39
39
  "type": "git",
40
- "url": ""
40
+ "url": "https://github.com/pixagram-blockchain/LacertaDB"
41
41
  },
42
42
  "engines": {
43
43
  "node": ">=0.8.0"
package/readme.md CHANGED
@@ -1,207 +1,1122 @@
1
- LacertaDB (@pixagram/lacerta-db)
2
- LacertaDB is a Javascript IndexedDB Database for Web Browsers. Simple, Fast, Secure.
1
+ # LacertaDB
2
+ ![](https://github.com/pixagram-blockchain/LacertaDB/blob/main/logo.webp?raw=true)
3
+
4
+ > ๐ŸฆŽ **LacertaDB v4.0.3** - A powerful, feature-rich browser-based document database with encryption, compression, and advanced querying capabilities.
5
+
6
+ [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
7
+ [![Version](https://img.shields.io/badge/version-4.0.3-blue.svg)]()
8
+ [![Browser Compatible](https://img.shields.io/badge/browser-compatible-green.svg)]()
9
+
10
+ ## ๐Ÿ“š Table of Contents
11
+
12
+ - [โœจ Features](#-features)
13
+ - [๐Ÿš€ Quick Start](#-quick-start)
14
+ - [๐Ÿ“ฆ Installation](#-installation)
15
+ - [๐ŸŽฏ Basic Usage](#-basic-usage)
16
+ - [๐Ÿ”ง Core Concepts](#-core-concepts)
17
+ - [Database](#database)
18
+ - [Collections](#collections)
19
+ - [Documents](#documents)
20
+ - [๐Ÿ” Querying](#-querying)
21
+ - [Basic Queries](#basic-queries)
22
+ - [Advanced Queries](#advanced-queries)
23
+ - [Aggregation Pipeline](#aggregation-pipeline)
24
+ - [๐Ÿ” Security Features](#-security-features)
25
+ - [Encryption](#encryption)
26
+ - [Password Protection](#password-protection)
27
+ - [๐Ÿ“Ž Attachments](#-attachments)
28
+ - [โšก Performance](#-performance)
29
+ - [Compression](#compression)
30
+ - [Performance Monitoring](#performance-monitoring)
31
+ - [Query Caching](#query-caching)
32
+ - [๐Ÿ”„ Data Migration](#-data-migration)
33
+ - [๐Ÿ’พ Backup & Restore](#-backup--restore)
34
+ - [๐Ÿ› ๏ธ Advanced Features](#๏ธ-advanced-features)
35
+ - [Batch Operations](#batch-operations)
36
+ - [Event System](#event-system)
37
+ - [Quick Store](#quick-store)
38
+ - [๐Ÿ“Š Storage Management](#-storage-management)
39
+ - [๐ŸŽจ API Reference](#-api-reference)
40
+ - [๐Ÿ’ก Examples](#-examples)
41
+ - [๐Ÿ› Error Handling](#-error-handling)
42
+ - [๐Ÿ“ Best Practices](#-best-practices)
43
+ - [๐Ÿค Contributing](#-contributing)
44
+
45
+ ## โœจ Features
46
+
47
+ ๐ŸŽฏ **Core Features**
48
+ - ๐Ÿ“ **Document-based storage** using IndexedDB
49
+ - ๐Ÿ” **MongoDB-like query syntax** for familiar operations
50
+ - ๐Ÿ” **AES-256-GCM encryption** with PBKDF2 key derivation
51
+ - ๐Ÿ—œ๏ธ **Built-in compression** using CompressionStream API
52
+ - ๐Ÿ“Ž **File attachments** via Origin Private File System (OPFS)
53
+ - โšก **High performance** with async operations and caching
54
+
55
+ ๐Ÿš€ **Advanced Capabilities**
56
+ - ๐Ÿ“Š **Aggregation pipeline** for complex data processing
57
+ - ๐Ÿ”„ **Schema migration system** for version management
58
+ - ๐Ÿ“ˆ **Performance monitoring** with real-time metrics
59
+ - ๐ŸŽญ **Event-driven architecture** with hooks
60
+ - ๐Ÿ’พ **Import/Export functionality** with encryption support
61
+ - ๐Ÿ”ง **Batch operations** for efficient bulk processing
62
+
63
+ ## ๐Ÿš€ Quick Start
64
+
65
+ ```javascript
66
+ import { LacertaDB } from './lacertadb.js';
67
+
68
+ // Initialize LacertaDB
69
+ const lacerta = new LacertaDB();
70
+
71
+ // Get or create a database
72
+ const db = await lacerta.getDatabase('myApp');
73
+
74
+ // Create a collection
75
+ const users = await db.createCollection('users');
76
+
77
+ // Add a document
78
+ const userId = await users.add({
79
+ name: 'Alice Johnson',
80
+ email: 'alice@example.com',
81
+ age: 28,
82
+ tags: ['developer', 'javascript']
83
+ });
3
84
 
4
- LacertaDB offers a powerful, modern, and feature-rich interface for working with IndexedDB in the browser. It's designed as a document-oriented database, providing a developer-friendly API similar to MongoDB. It prioritizes security, performance, and advanced data handling capabilities right out of the box.
85
+ // Query documents
86
+ const results = await users.query({
87
+ age: { $gte: 25 },
88
+ tags: { $in: ['developer'] }
89
+ });
5
90
 
6
- โœจ Key Features
7
- Simple API: An intuitive and modern API that makes database operations straightforward.
91
+ console.log('Found users:', results);
92
+ ```
8
93
 
9
- Strong Encryption: Built-in AES-GCM encryption to secure sensitive documents with a password.
94
+ ## ๐Ÿ“ฆ Installation
10
95
 
11
- Efficient Compression: Automatic data compression using the Compression Streams API to save storage space.
96
+ ### NPM/Yarn Installation
12
97
 
13
- OPFS Attachments: Store large files like images or videos efficiently using the Origin Private File System (OPFS), linking them directly to your documents.
98
+ ```bash
99
+ npm install @pixagram/lacertadb
100
+ # or
101
+ yarn add @pixagram/lacertadb
102
+ ```
14
103
 
15
- Advanced Queries: A powerful MongoDB-like query engine with support for complex operators ($gt, $in, $regex, etc.) and logical combinations ($and, $or).
104
+ ### Browser Module
16
105
 
17
- Aggregation Pipeline: Perform complex data analysis and transformations directly in the database with a multi-stage aggregation pipeline ($match, $group, $sort, etc.).
106
+ ```html
107
+ <script type="module">
108
+ import { LacertaDB } from './lacertadb.js';
109
+ const lacerta = new LacertaDB();
110
+ </script>
111
+ ```
18
112
 
19
- High-Performance Serialization: Uses turboserial and turbobase64 instead of JSON for faster serialization and deserialization of data.
113
+ ### Dependencies
20
114
 
21
- Automatic Cleanup: Set storage limits and let the database automatically manage space by removing the oldest, non-permanent documents.
115
+ LacertaDB requires:
116
+ - `@pixagram/turboserial` - High-performance serialization
117
+ - `@pixagram/turbobase64` - Optimized Base64 encoding
22
118
 
23
- Full-Featured: Includes batch operations, query caching, metadata management, and a migration system to handle schema changes over time.
119
+ ## ๐ŸŽฏ Basic Usage
24
120
 
25
- ๐Ÿš€ Installation
26
- Install the package using your favorite package manager.
121
+ ### Creating a Database and Collection
27
122
 
28
- npm install @pixagram/lacerta-db
123
+ ```javascript
124
+ const lacerta = new LacertaDB();
125
+
126
+ // Create or get a database
127
+ const db = await lacerta.getDatabase('myDatabase');
128
+
129
+ // Create a collection with options
130
+ const products = await db.createCollection('products', {
131
+ compressed: true, // Enable compression by default
132
+ encrypted: false // Encryption disabled by default
133
+ });
134
+ ```
135
+
136
+ ### Adding Documents
137
+
138
+ ```javascript
139
+ // Simple document
140
+ await products.add({
141
+ name: 'Laptop',
142
+ price: 999.99,
143
+ inStock: true
144
+ });
145
+
146
+ // Document with options
147
+ await products.add(
148
+ {
149
+ name: 'Secure Document',
150
+ data: 'sensitive information'
151
+ },
152
+ {
153
+ id: 'custom-id-123', // Custom ID
154
+ encrypted: true, // Encrypt this document
155
+ password: 'secretPassword', // Encryption password
156
+ compressed: true, // Compress the document
157
+ permanent: true // Mark as permanent (won't be auto-deleted)
158
+ }
159
+ );
160
+ ```
161
+
162
+ ### Retrieving Documents
163
+
164
+ ```javascript
165
+ // Get by ID
166
+ const product = await products.get('custom-id-123', {
167
+ password: 'secretPassword' // Required for encrypted documents
168
+ });
29
169
 
30
- โšก Quick Start
31
- Here's how to get up and running with LacertaDB in just a few lines of code.
170
+ // Get all documents
171
+ const allProducts = await products.getAll();
32
172
 
33
- // Import the default instance
34
- import LacertaDB from '@pixagram/lacerta-db';
173
+ // Get with attachments
174
+ const withFiles = await products.get('doc-id', {
175
+ includeAttachments: true
176
+ });
177
+ ```
35
178
 
36
- async function main() {
37
- try {
38
- // 1. Get a database instance
39
- const db = await LacertaDB.getDatabase('my-app-db');
179
+ ## ๐Ÿ”ง Core Concepts
40
180
 
41
- // 2. Get or create a collection
42
- // Collections are created automatically on first access
43
- const users = await db.getCollection('users');
181
+ ### Database
44
182
 
45
- // 3. Add a new document
46
- const newUserId = await users.add({
47
- name: 'Alex',
48
- level: 10,
49
- joined: new Date()
50
- });
51
- console.log(`User created with ID: ${newUserId}`);
183
+ The database is the top-level container for your collections.
184
+
185
+ ```javascript
186
+ // Get existing or create new database
187
+ const db = await lacerta.getDatabase('appDB');
188
+
189
+ // List all collections
190
+ const collections = db.listCollections();
191
+
192
+ // Get database statistics
193
+ const stats = db.getStats();
194
+ console.log(`Total size: ${stats.totalSizeKB} KB`);
195
+ console.log(`Total documents: ${stats.totalDocuments}`);
196
+
197
+ // Configure database settings
198
+ db.updateSettings({
199
+ sizeLimitKB: 50000, // 50MB limit
200
+ bufferLimitKB: 40000, // Start cleanup at 40MB
201
+ freeSpaceEvery: 60000 // Run cleanup every minute
202
+ });
203
+ ```
52
204
 
53
- // 4. Get a document by its ID
54
- const user = await users.get(newUserId);
55
- console.log('Retrieved user:', user);
205
+ ### Collections
56
206
 
57
- // 5. Query for documents
58
- const highLevelUsers = await users.query({ level: { '$gt': 5 } });
59
- console.log('High-level users:', highLevelUsers);
207
+ Collections are containers for documents of similar type.
60
208
 
61
- } catch (error) {
62
- console.error('Database operation failed:', error);
209
+ ```javascript
210
+ // Create collection
211
+ const posts = await db.createCollection('posts');
212
+
213
+ // Get existing collection
214
+ const existingPosts = await db.getCollection('posts');
215
+
216
+ // Collection operations
217
+ await posts.clear(); // Remove all documents
218
+ await db.dropCollection('posts'); // Delete collection entirely
219
+
220
+ // Collection events
221
+ posts.on('afterAdd', (doc) => {
222
+ console.log('Document added:', doc._id);
223
+ });
224
+ ```
225
+
226
+ ### Documents
227
+
228
+ Documents are JavaScript objects with automatic metadata.
229
+
230
+ ```javascript
231
+ // Document structure
232
+ const doc = {
233
+ // User data
234
+ title: 'My Post',
235
+ content: 'Lorem ipsum...',
236
+
237
+ // Automatic metadata (added by LacertaDB)
238
+ _id: 'doc_1234567890_abc', // Auto-generated unique ID
239
+ _created: 1704067200000, // Creation timestamp
240
+ _modified: 1704067200000, // Last modification timestamp
241
+ _permanent: false, // Deletion protection flag
242
+ };
243
+ ```
244
+
245
+ ## ๐Ÿ” Querying
246
+
247
+ ### Basic Queries
248
+
249
+ ```javascript
250
+ // Find all documents matching criteria
251
+ const results = await users.query({
252
+ age: 30, // Exact match
253
+ 'address.city': 'New York' // Nested field
254
+ });
255
+
256
+ // With options
257
+ const paginatedResults = await users.query(
258
+ { status: 'active' },
259
+ {
260
+ sort: { createdAt: -1 }, // Sort descending
261
+ skip: 10, // Skip first 10
262
+ limit: 20, // Limit to 20 results
263
+ projection: { // Select fields
264
+ name: 1,
265
+ email: 1,
266
+ _id: 0
267
+ }
63
268
  }
64
- }
269
+ );
270
+ ```
65
271
 
66
- main();
272
+ ### Advanced Queries
67
273
 
68
- ๐Ÿ“– API Reference
69
- Database
70
- The Database object is your main entry point for managing collections.
274
+ LacertaDB supports MongoDB-style query operators:
71
275
 
72
- getDatabase(name)
73
- Retrieves a database instance. If it doesn't exist, it's created.
276
+ #### Comparison Operators
74
277
 
75
- const db = await LacertaDB.getDatabase('my-app-db');
278
+ ```javascript
279
+ // $eq, $ne, $gt, $gte, $lt, $lte
280
+ await products.query({
281
+ price: { $gte: 100, $lte: 500 }
282
+ });
76
283
 
77
- getCollection(name)
78
- Retrieves a collection from the database. If it doesn't exist, it's created.
284
+ // $in, $nin
285
+ await users.query({
286
+ role: { $in: ['admin', 'moderator'] }
287
+ });
288
+ ```
79
289
 
80
- const usersCollection = await db.getCollection('users');
290
+ #### Logical Operators
81
291
 
82
- dropCollection(name)
83
- Deletes a collection and all of its documents and attachments.
292
+ ```javascript
293
+ // $and
294
+ await products.query({
295
+ $and: [
296
+ { price: { $lt: 1000 } },
297
+ { category: 'electronics' }
298
+ ]
299
+ });
84
300
 
85
- await db.dropCollection('users');
301
+ // $or
302
+ await users.query({
303
+ $or: [
304
+ { age: { $gte: 65 } },
305
+ { status: 'premium' }
306
+ ]
307
+ });
86
308
 
87
- Collection
88
- The Collection object provides methods to interact with documents.
309
+ // $not
310
+ await products.query({
311
+ discontinued: { $not: { $eq: true } }
312
+ });
313
+ ```
89
314
 
90
- add(data, [options])
91
- Adds a new document to the collection.
315
+ #### Array Operators
92
316
 
93
- data (Object): The document data.
317
+ ```javascript
318
+ // $all - Array contains all values
319
+ await posts.query({
320
+ tags: { $all: ['javascript', 'database'] }
321
+ });
94
322
 
95
- options (Object, optional):
323
+ // $elemMatch - Element matching
324
+ await orders.query({
325
+ items: {
326
+ $elemMatch: {
327
+ product: 'laptop',
328
+ quantity: { $gte: 2 }
329
+ }
330
+ }
331
+ });
96
332
 
97
- encrypted (boolean): Set to true to encrypt the document.
333
+ // $size - Array length
334
+ await users.query({
335
+ hobbies: { $size: 3 }
336
+ });
337
+ ```
98
338
 
99
- password (string): Required if encrypted is true.
339
+ #### Text Search
100
340
 
101
- permanent (boolean): If true, the document won't be deleted by the auto-cleanup process.
341
+ ```javascript
342
+ // $regex - Regular expression
343
+ await users.query({
344
+ email: { $regex: '@company\\.com$' }
345
+ });
102
346
 
103
- attachments (Array): An array of file attachments.
347
+ // $text - Case-insensitive text search
348
+ await posts.query({
349
+ content: { $text: 'javascript' }
350
+ });
351
+ ```
352
+
353
+ ### Aggregation Pipeline
354
+
355
+ Powerful data processing with aggregation stages:
356
+
357
+ ```javascript
358
+ // Sales analysis pipeline
359
+ const salesReport = await orders.aggregate([
360
+ // Stage 1: Filter orders
361
+ { $match: { status: 'completed' } },
362
+
363
+ // Stage 2: Group by customer
364
+ {
365
+ $group: {
366
+ _id: '$customerId',
367
+ totalSpent: { $sum: '$amount' },
368
+ orderCount: { $count: {} },
369
+ avgOrderValue: { $avg: '$amount' }
370
+ }
371
+ },
372
+
373
+ // Stage 3: Sort by total spent
374
+ { $sort: { totalSpent: -1 } },
375
+
376
+ // Stage 4: Limit to top 10
377
+ { $limit: 10 },
378
+
379
+ // Stage 5: Project final shape
380
+ {
381
+ $project: {
382
+ customer: '$_id',
383
+ metrics: {
384
+ total: '$totalSpent',
385
+ orders: '$orderCount',
386
+ average: '$avgOrderValue'
387
+ }
388
+ }
389
+ }
390
+ ]);
391
+ ```
392
+
393
+ #### Lookup (Join) Operations
394
+
395
+ ```javascript
396
+ // Join with another collection
397
+ const ordersWithProducts = await orders.aggregate([
398
+ {
399
+ $lookup: {
400
+ from: 'products', // Foreign collection
401
+ localField: 'productId', // Field in orders
402
+ foreignField: '_id', // Field in products
403
+ as: 'productDetails' // Output array field
404
+ }
405
+ }
406
+ ]);
407
+ ```
408
+
409
+ ## ๐Ÿ” Security Features
410
+
411
+ ### Encryption
412
+
413
+ Documents can be individually encrypted with AES-256-GCM:
414
+
415
+ ```javascript
416
+ // Add encrypted document
417
+ await users.add(
418
+ {
419
+ ssn: '123-45-6789',
420
+ bankAccount: 'SECRET123',
421
+ salary: 75000
422
+ },
423
+ {
424
+ encrypted: true,
425
+ password: 'strong-password-here',
426
+ permanent: true // Protect from auto-deletion
427
+ }
428
+ );
104
429
 
105
- const userId = await users.add({ name: 'Zoe' }, { permanent: true });
430
+ // Retrieve encrypted document
431
+ const userData = await users.get('user-id', {
432
+ password: 'strong-password-here' // Required for decryption
433
+ });
106
434
 
107
- get(id, [options])
108
- Retrieves a single document by its _id.
435
+ // Update encrypted document
436
+ await users.update('user-id',
437
+ { salary: 80000 },
438
+ {
439
+ encrypted: true,
440
+ password: 'strong-password-here'
441
+ }
442
+ );
443
+ ```
109
444
 
110
- id (string): The document ID.
445
+ ### Password Protection
111
446
 
112
- options (Object, optional):
447
+ Secure your exports and backups:
113
448
 
114
- password (string): Required to decrypt an encrypted document.
449
+ ```javascript
450
+ // Export with encryption
451
+ const encryptedExport = await db.export('encrypted', 'export-password');
115
452
 
116
- includeAttachments (boolean): If true, retrieves file data from OPFS.
453
+ // Import encrypted data
454
+ await db.import(encryptedExport, 'encrypted', 'export-password');
117
455
 
118
- const user = await users.get(userId);
456
+ // Create encrypted backup
457
+ const backup = await lacerta.createBackup('backup-password');
119
458
 
120
- query(filter, [options])
121
- Finds documents matching the filter object.
459
+ // Restore from encrypted backup
460
+ await lacerta.restoreBackup(backup, 'backup-password');
461
+ ```
122
462
 
123
- filter (Object): A MongoDB-style query object.
463
+ ## ๐Ÿ“Ž Attachments
124
464
 
125
- options (Object, optional):
465
+ Store files using the Origin Private File System:
126
466
 
127
- sort (Object): Sort order (e.g., { level: -1 }).
467
+ ```javascript
468
+ // Prepare files
469
+ const file1 = new File(['content'], 'document.pdf', { type: 'application/pdf' });
470
+ const file2 = new Blob(['image data'], { type: 'image/png' });
128
471
 
129
- limit (number): Max number of documents to return.
472
+ // Add document with attachments
473
+ const docId = await documents.add(
474
+ { title: 'Report with Files' },
475
+ {
476
+ attachments: [
477
+ file1,
478
+ file2,
479
+ {
480
+ name: 'custom.txt',
481
+ type: 'text/plain',
482
+ data: new TextEncoder().encode('Custom file content')
483
+ }
484
+ ]
485
+ }
486
+ );
487
+
488
+ // Retrieve with attachments
489
+ const docWithFiles = await documents.get(docId, {
490
+ includeAttachments: true
491
+ });
130
492
 
131
- skip (number): Number of documents to skip.
493
+ // Access attachments
494
+ docWithFiles._attachments.forEach(attachment => {
495
+ console.log(`File: ${attachment.name} (${attachment.size} bytes)`);
496
+ // attachment.data is Uint8Array
497
+ });
498
+ ```
132
499
 
133
- const results = await users.query({ name: 'Alex' });
500
+ ## โšก Performance
134
501
 
135
- update(id, updates)
136
- Updates the data of a specific document.
502
+ ### Compression
137
503
 
138
- await users.update(userId, { level: 11 });
504
+ Reduce storage size with automatic compression:
139
505
 
140
- delete(id)
141
- Removes a document from the collection.
506
+ ```javascript
507
+ // Enable compression for all documents in collection
508
+ const compressedColl = await db.createCollection('largeDocs', {
509
+ compressed: true
510
+ });
142
511
 
143
- await users.delete(userId);
512
+ // Per-document compression
513
+ await collection.add(largeData, {
514
+ compressed: true // Uses DeflateStream compression
515
+ });
516
+ ```
144
517
 
145
- aggregate(pipeline)
146
- Processes documents through an aggregation pipeline.
518
+ ### Performance Monitoring
147
519
 
148
- const results = await users.aggregate([
149
- { '$match': { level: { '$gt': 5 } } },
150
- { '$group': { _id: null, averageLevel: { '$avg': '$level' } } }
151
- ]);
520
+ Track database performance metrics:
152
521
 
153
- ๐Ÿ› ๏ธ Advanced Usage
154
- Encryption ๐Ÿ”’
155
- To store sensitive data, simply set the encrypted flag and provide a password. LacertaDB handles the rest.
522
+ ```javascript
523
+ // Start monitoring
524
+ lacerta.performanceMonitor.startMonitoring();
156
525
 
157
- const secretData = { account: '123-456', secret: 'my-secret-key' };
526
+ // Perform operations...
158
527
 
159
- const docId = await db.collection('secrets').add(secretData, {
160
- encrypted: true,
161
- password: 'a-very-strong-password'
528
+ // Get performance stats
529
+ const stats = lacerta.performanceMonitor.getStats();
530
+ console.log(`Operations/sec: ${stats.opsPerSec}`);
531
+ console.log(`Avg latency: ${stats.avgLatency}ms`);
532
+ console.log(`Cache hit rate: ${stats.cacheHitRate}%`);
533
+ console.log(`Memory usage: ${stats.memoryUsageMB}MB`);
534
+
535
+ // Get optimization tips
536
+ const tips = lacerta.performanceMonitor.getOptimizationTips();
537
+ tips.forEach(tip => console.log(`๐Ÿ’ก ${tip}`));
538
+
539
+ // Stop monitoring
540
+ lacerta.performanceMonitor.stopMonitoring();
541
+ ```
542
+
543
+ ### Query Caching
544
+
545
+ Queries are automatically cached for 60 seconds:
546
+
547
+ ```javascript
548
+ // First query - hits database
549
+ const results1 = await users.query({ status: 'active' });
550
+
551
+ // Second identical query - served from cache
552
+ const results2 = await users.query({ status: 'active' });
553
+
554
+ // Clear cache manually if needed
555
+ users.clearCache();
556
+ ```
557
+
558
+ ## ๐Ÿ”„ Data Migration
559
+
560
+ Version your schema changes:
561
+
562
+ ```javascript
563
+ const migrationManager = new MigrationManager(db);
564
+
565
+ // Define migrations
566
+ migrationManager.addMigration({
567
+ version: '2.0.0',
568
+ name: 'Add user roles',
569
+ up: async (doc) => {
570
+ if (doc.type === 'user' && !doc.role) {
571
+ return { ...doc, role: 'standard' };
572
+ }
573
+ return doc;
574
+ },
575
+ down: async (doc) => {
576
+ if (doc.type === 'user') {
577
+ const { role, ...rest } = doc;
578
+ return rest;
579
+ }
580
+ return doc;
581
+ }
582
+ });
583
+
584
+ // Run migrations
585
+ await migrationManager.runMigrations('2.0.0');
586
+
587
+ // Rollback if needed
588
+ await migrationManager.rollback('1.0.0');
589
+ ```
590
+
591
+ ## ๐Ÿ’พ Backup & Restore
592
+
593
+ ### Database Export/Import
594
+
595
+ ```javascript
596
+ // Export single database
597
+ const exportData = await db.export('json');
598
+ // Save exportData to file or send to server
599
+
600
+ // Import data
601
+ const importResult = await db.import(exportData, 'json');
602
+ console.log(`Imported ${importResult.documents} documents`);
603
+
604
+ // Export with encryption
605
+ const secureExport = await db.export('encrypted', 'password123');
606
+ ```
607
+
608
+ ### Full System Backup
609
+
610
+ ```javascript
611
+ // Backup all databases
612
+ const systemBackup = await lacerta.createBackup();
613
+ // Optional: encrypt the backup
614
+ const encryptedBackup = await lacerta.createBackup('backup-password');
615
+
616
+ // Restore from backup
617
+ const restoreResult = await lacerta.restoreBackup(systemBackup);
618
+ console.log(`Restored: ${restoreResult.databases} databases`);
619
+ console.log(`Total documents: ${restoreResult.documents}`);
620
+ ```
621
+
622
+ ## ๐Ÿ› ๏ธ Advanced Features
623
+
624
+ ### Batch Operations
625
+
626
+ Efficient bulk operations with transaction support:
627
+
628
+ ```javascript
629
+ // Batch insert
630
+ const documents = [
631
+ { name: 'Doc 1', value: 100 },
632
+ { name: 'Doc 2', value: 200 },
633
+ { name: 'Doc 3', value: 300 }
634
+ ];
635
+
636
+ const results = await collection.batchAdd(documents, {
637
+ compressed: true,
638
+ encrypted: false
162
639
  });
163
640
 
164
- // You MUST provide the same password to retrieve it
165
- const retrieved = await db.collection('secrets').get(docId, {
166
- password: 'a-very-strong-password'
641
+ // Check results
642
+ results.forEach(result => {
643
+ if (result.success) {
644
+ console.log(`โœ… Added: ${result.id}`);
645
+ } else {
646
+ console.log(`โŒ Failed: ${result.error}`);
647
+ }
167
648
  });
168
649
 
169
- File Attachments ๐Ÿ“Ž
170
- You can attach files (like File objects or Uint8Array data) to a document. They are stored efficiently in the browser's Origin Private File System.
650
+ // Batch update
651
+ const updates = [
652
+ { id: 'doc1', data: { status: 'active' } },
653
+ { id: 'doc2', data: { status: 'inactive' } }
654
+ ];
655
+ await collection.batchUpdate(updates);
171
656
 
172
- // Create a sample file
173
- const fileContent = new TextEncoder().encode('This is the content of my file.');
174
- const attachment = {
175
- name: 'readme.txt',
176
- type: 'text/plain',
177
- data: fileContent
178
- };
657
+ // Batch delete
658
+ const idsToDelete = ['doc3', 'doc4', 'doc5'];
659
+ await collection.batchDelete(idsToDelete);
660
+ ```
661
+
662
+ ### Event System
663
+
664
+ React to database operations:
665
+
666
+ ```javascript
667
+ // Collection-level events
668
+ collection.on('beforeAdd', async (data) => {
669
+ console.log('Validating document...');
670
+ // Perform validation
671
+ });
672
+
673
+ collection.on('afterAdd', async (doc) => {
674
+ console.log(`Document ${doc._id} added`);
675
+ // Send notification, update cache, etc.
676
+ });
677
+
678
+ collection.on('beforeUpdate', async ({ docId, updates }) => {
679
+ console.log(`Updating ${docId}`);
680
+ });
681
+
682
+ collection.on('afterDelete', async (docId) => {
683
+ console.log(`Document ${docId} deleted`);
684
+ // Cleanup related data
685
+ });
686
+
687
+ // Remove event listener
688
+ const handler = (doc) => console.log(doc);
689
+ collection.on('afterAdd', handler);
690
+ collection.off('afterAdd', handler);
691
+ ```
692
+
693
+ ### Quick Store
694
+
695
+ Fast localStorage-based storage for small data:
696
+
697
+ ```javascript
698
+ // Access QuickStore
699
+ const quickStore = db.quickStore;
700
+
701
+ // Store data
702
+ quickStore.add('user-prefs', {
703
+ theme: 'dark',
704
+ language: 'en',
705
+ notifications: true
706
+ });
707
+
708
+ // Retrieve data
709
+ const prefs = quickStore.get('user-prefs');
710
+
711
+ // Update
712
+ quickStore.update('user-prefs', { theme: 'light' });
713
+
714
+ // Get all stored items
715
+ const allItems = quickStore.getAll();
716
+
717
+ // Clear QuickStore
718
+ quickStore.clear();
719
+ ```
720
+
721
+ ## ๐Ÿ“Š Storage Management
722
+
723
+ ### Size Limits and Auto-Cleanup
724
+
725
+ ```javascript
726
+ // Configure storage limits
727
+ db.updateSettings({
728
+ sizeLimitKB: 100000, // 100MB total limit
729
+ bufferLimitKB: 80000, // Start cleanup at 80MB
730
+ freeSpaceEvery: 30000 // Check every 30 seconds
731
+ });
732
+
733
+ // Manual cleanup
734
+ await collection.freeSpace();
735
+
736
+ // Mark documents as permanent
737
+ await collection.add(importantData, {
738
+ permanent: true // Won't be deleted during cleanup
739
+ });
740
+
741
+ // Check collection size
742
+ const stats = collection.metadata;
743
+ console.log(`Collection size: ${stats.sizeKB} KB`);
744
+ console.log(`Document count: ${stats.length}`);
745
+ ```
746
+
747
+ ### Storage Information
748
+
749
+ ```javascript
750
+ // Database statistics
751
+ const dbStats = db.getStats();
752
+ console.log(dbStats);
753
+ /* Output:
754
+ {
755
+ name: 'myDatabase',
756
+ totalSizeKB: 2457.3,
757
+ totalDocuments: 1250,
758
+ collections: [
759
+ {
760
+ name: 'users',
761
+ sizeKB: 1024.5,
762
+ documents: 500,
763
+ createdAt: '2024-01-01T00:00:00.000Z',
764
+ modifiedAt: '2024-01-15T10:30:00.000Z'
765
+ }
766
+ ]
767
+ }
768
+ */
769
+
770
+ // List all databases
771
+ const allDatabases = lacerta.listDatabases();
772
+ console.log('Available databases:', allDatabases);
773
+ ```
774
+
775
+ ## ๐ŸŽจ API Reference
776
+
777
+ ### LacertaDB Class
778
+
779
+ | Method | Description | Returns |
780
+ |--------|-------------|---------|
781
+ | `getDatabase(name)` | Get or create a database | `Promise<Database>` |
782
+ | `dropDatabase(name)` | Delete a database | `Promise<void>` |
783
+ | `listDatabases()` | List all database names | `Array<string>` |
784
+ | `createBackup(password?)` | Create full system backup | `Promise<string>` |
785
+ | `restoreBackup(data, password?)` | Restore from backup | `Promise<Object>` |
786
+
787
+ ### Database Class
788
+
789
+ | Method | Description | Returns |
790
+ |--------|-------------|---------|
791
+ | `createCollection(name, options?)` | Create new collection | `Promise<Collection>` |
792
+ | `getCollection(name)` | Get existing collection | `Promise<Collection>` |
793
+ | `dropCollection(name)` | Delete collection | `Promise<void>` |
794
+ | `listCollections()` | Get collection names | `Array<string>` |
795
+ | `getStats()` | Get database statistics | `Object` |
796
+ | `updateSettings(settings)` | Update configuration | `void` |
797
+ | `export(format, password?)` | Export database | `Promise<string>` |
798
+ | `import(data, format, password?)` | Import data | `Promise<Object>` |
799
+ | `clearAll()` | Delete all collections | `Promise<void>` |
800
+
801
+ ### Collection Class
802
+
803
+ | Method | Description | Returns |
804
+ |--------|-------------|---------|
805
+ | `add(data, options?)` | Add document | `Promise<string>` |
806
+ | `get(id, options?)` | Get document by ID | `Promise<Object>` |
807
+ | `getAll(options?)` | Get all documents | `Promise<Array>` |
808
+ | `update(id, updates, options?)` | Update document | `Promise<string>` |
809
+ | `delete(id)` | Delete document | `Promise<void>` |
810
+ | `query(filter, options?)` | Query documents | `Promise<Array>` |
811
+ | `aggregate(pipeline)` | Run aggregation | `Promise<Array>` |
812
+ | `batchAdd(documents, options?)` | Add multiple documents | `Promise<Array>` |
813
+ | `batchUpdate(updates, options?)` | Update multiple documents | `Promise<Array>` |
814
+ | `batchDelete(ids)` | Delete multiple documents | `Promise<Array>` |
815
+ | `clear()` | Remove all documents | `Promise<void>` |
816
+ | `on(event, callback)` | Add event listener | `void` |
817
+ | `off(event, callback)` | Remove event listener | `void` |
818
+ | `clearCache()` | Clear query cache | `void` |
819
+
820
+ ## ๐Ÿ’ก Examples
821
+
822
+ ### Todo Application
823
+
824
+ ```javascript
825
+ // Initialize
826
+ const lacerta = new LacertaDB();
827
+ const db = await lacerta.getDatabase('todoApp');
828
+ const todos = await db.createCollection('todos');
829
+
830
+ // Add todos
831
+ await todos.add({
832
+ title: 'Learn LacertaDB',
833
+ completed: false,
834
+ priority: 'high',
835
+ tags: ['learning', 'database'],
836
+ createdAt: Date.now()
837
+ });
838
+
839
+ // Query incomplete high-priority todos
840
+ const urgentTodos = await todos.query({
841
+ completed: false,
842
+ priority: 'high'
843
+ }, {
844
+ sort: { createdAt: -1 }
845
+ });
846
+
847
+ // Mark as complete
848
+ await todos.update(todoId, {
849
+ completed: true,
850
+ completedAt: Date.now()
851
+ });
179
852
 
180
- // Add a document with the attachment
181
- const reportId = await db.collection('reports').add(
182
- { title: 'Q3 Report' },
183
- { attachments: [attachment] }
853
+ // Get statistics
854
+ const stats = await todos.aggregate([
855
+ {
856
+ $group: {
857
+ _id: '$priority',
858
+ count: { $count: {} },
859
+ completed: {
860
+ $sum: { $cond: ['$completed', 1, 0] }
861
+ }
862
+ }
863
+ }
864
+ ]);
865
+ ```
866
+
867
+ ### E-Commerce Inventory
868
+
869
+ ```javascript
870
+ // Setup
871
+ const db = await lacerta.getDatabase('shop');
872
+ const products = await db.createCollection('products');
873
+ const orders = await db.createCollection('orders');
874
+
875
+ // Product with images
876
+ const productId = await products.add(
877
+ {
878
+ name: 'Wireless Mouse',
879
+ price: 29.99,
880
+ stock: 150,
881
+ category: 'electronics'
882
+ },
883
+ {
884
+ attachments: [productImage1, productImage2]
885
+ }
184
886
  );
185
887
 
186
- // Retrieve the document and its attachments
187
- const report = await db.collection('reports').get(reportId, {
188
- includeAttachments: true
888
+ // Complex inventory query
889
+ const lowStock = await products.query({
890
+ $and: [
891
+ { stock: { $lt: 20 } },
892
+ { category: { $in: ['electronics', 'accessories'] } }
893
+ ]
894
+ }, {
895
+ projection: { name: 1, stock: 1, price: 1 }
896
+ });
897
+
898
+ // Sales report with joins
899
+ const salesReport = await orders.aggregate([
900
+ { $match: { status: 'completed' } },
901
+ {
902
+ $lookup: {
903
+ from: 'products',
904
+ localField: 'productId',
905
+ foreignField: '_id',
906
+ as: 'product'
907
+ }
908
+ },
909
+ {
910
+ $group: {
911
+ _id: '$product.category',
912
+ revenue: { $sum: '$total' },
913
+ orderCount: { $count: {} }
914
+ }
915
+ },
916
+ { $sort: { revenue: -1 } }
917
+ ]);
918
+ ```
919
+
920
+ ### User Session Management
921
+
922
+ ```javascript
923
+ // Encrypted session storage
924
+ const sessions = await db.createCollection('sessions');
925
+
926
+ // Store session with encryption
927
+ await sessions.add(
928
+ {
929
+ userId: 'user123',
930
+ token: 'secret-session-token',
931
+ ipAddress: '192.168.1.1',
932
+ userAgent: navigator.userAgent,
933
+ expiresAt: Date.now() + (24 * 60 * 60 * 1000)
934
+ },
935
+ {
936
+ encrypted: true,
937
+ password: process.env.SESSION_KEY,
938
+ permanent: false
939
+ }
940
+ );
941
+
942
+ // Cleanup expired sessions
943
+ const now = Date.now();
944
+ const expired = await sessions.query({
945
+ expiresAt: { $lt: now }
946
+ });
947
+
948
+ await sessions.batchDelete(expired.map(s => s._id));
949
+ ```
950
+
951
+ ## ๐Ÿ› Error Handling
952
+
953
+ LacertaDB provides detailed error information:
954
+
955
+ ```javascript
956
+ try {
957
+ await collection.get('non-existent-id');
958
+ } catch (error) {
959
+ if (error instanceof LacertaDBError) {
960
+ console.error('Error:', error.message);
961
+ console.error('Code:', error.code);
962
+ console.error('Timestamp:', error.timestamp);
963
+
964
+ // Handle specific error codes
965
+ switch(error.code) {
966
+ case 'DOCUMENT_NOT_FOUND':
967
+ // Handle missing document
968
+ break;
969
+ case 'ENCRYPTION_FAILED':
970
+ // Handle encryption error
971
+ break;
972
+ case 'QUOTA_EXCEEDED':
973
+ // Handle storage limit
974
+ break;
975
+ }
976
+ }
977
+ }
978
+ ```
979
+
980
+ ### Common Error Codes
981
+
982
+ | Code | Description | Solution |
983
+ |------|-------------|----------|
984
+ | `DOCUMENT_NOT_FOUND` | Document ID doesn't exist | Check ID or use query |
985
+ | `COLLECTION_NOT_FOUND` | Collection doesn't exist | Create collection first |
986
+ | `ENCRYPTION_FAILED` | Encryption/decryption error | Check password |
987
+ | `COMPRESSION_FAILED` | Compression error | Check data format |
988
+ | `QUOTA_EXCEEDED` | Storage limit reached | Increase limit or cleanup |
989
+ | `INVALID_OPERATION` | Operation not allowed | Check document flags |
990
+ | `TRANSACTION_FAILED` | Database transaction error | Retry operation |
991
+
992
+ ## ๐Ÿ“ Best Practices
993
+
994
+ ### 1. ๐ŸŽฏ Design Your Schema
995
+
996
+ ```javascript
997
+ // Good: Consistent document structure
998
+ const userSchema = {
999
+ type: 'user',
1000
+ email: '',
1001
+ profile: {
1002
+ name: '',
1003
+ avatar: '',
1004
+ bio: ''
1005
+ },
1006
+ settings: {},
1007
+ metadata: {
1008
+ createdAt: Date.now(),
1009
+ lastLogin: null
1010
+ }
1011
+ };
1012
+ ```
1013
+
1014
+ ### 2. ๐Ÿ” Index Planning
1015
+
1016
+ ```javascript
1017
+ // Create indexes for frequently queried fields
1018
+ // (Indexes are automatically created for _id and _modified)
1019
+ // For custom indexes, use query patterns to identify needs
1020
+ ```
1021
+
1022
+ ### 3. ๐Ÿ” Security First
1023
+
1024
+ ```javascript
1025
+ // Always encrypt sensitive data
1026
+ const sensitiveOps = {
1027
+ encrypted: true,
1028
+ password: await generateSecurePassword(),
1029
+ permanent: true // Prevent accidental deletion
1030
+ };
1031
+ ```
1032
+
1033
+ ### 4. โšก Performance Optimization
1034
+
1035
+ ```javascript
1036
+ // Use batch operations for bulk actions
1037
+ await collection.batchAdd(largeDataset, {
1038
+ compressed: true // Compress large datasets
189
1039
  });
190
1040
 
191
- console.log(report.data._attachments[0].name); // "readme.txt"
192
- const content = new TextDecoder().decode(report.data._attachments[0].data);
193
- console.log(content); // "This is the content of my file."
1041
+ // Enable monitoring during development
1042
+ lacerta.performanceMonitor.startMonitoring();
1043
+ // ... test operations ...
1044
+ const tips = lacerta.performanceMonitor.getOptimizationTips();
1045
+ ```
1046
+
1047
+ ### 5. ๐Ÿงน Regular Maintenance
1048
+
1049
+ ```javascript
1050
+ // Set appropriate limits
1051
+ db.updateSettings({
1052
+ sizeLimitKB: 50000,
1053
+ bufferLimitKB: 40000,
1054
+ freeSpaceEvery: 300000 // 5 minutes
1055
+ });
1056
+
1057
+ // Regular backups
1058
+ const dailyBackup = async () => {
1059
+ const backup = await lacerta.createBackup('secure-password');
1060
+ await saveToCloud(backup);
1061
+ };
1062
+ setInterval(dailyBackup, 24 * 60 * 60 * 1000);
1063
+ ```
1064
+
1065
+ ### 6. ๐Ÿ“Š Monitor Usage
1066
+
1067
+ ```javascript
1068
+ // Track database growth
1069
+ const monitor = async () => {
1070
+ const stats = db.getStats();
1071
+ if (stats.totalSizeKB > 40000) {
1072
+ console.warn('Database size exceeds 40MB');
1073
+ // Trigger cleanup or alert
1074
+ }
1075
+ };
1076
+ ```
1077
+
1078
+ ## ๐Ÿค Contributing
1079
+
1080
+ We welcome contributions! Here's how you can help:
1081
+
1082
+ 1. ๐Ÿ› **Report Bugs**: Open an issue with reproduction steps
1083
+ 2. ๐Ÿ’ก **Suggest Features**: Share your ideas in discussions
1084
+ 3. ๐Ÿ“ **Improve Docs**: Fix typos or add examples
1085
+ 4. ๐Ÿ”ง **Submit PRs**: Fork, code, test, and submit
1086
+
1087
+ ### Development Setup
1088
+
1089
+ ```bash
1090
+ # Clone repository
1091
+ git clone https://github.com/pixagram-blockchain/LacertaDB.git
1092
+ cd LacertaDB
1093
+
1094
+ # Install dependencies
1095
+ npm install @pixagram/lacerta-db
1096
+
1097
+ # Run tests
1098
+ npm test
1099
+
1100
+ # Build
1101
+ npm run build
1102
+ ```
1103
+
1104
+ ## ๐Ÿ“„ License
1105
+
1106
+ MIT License - See [LICENSE](LICENSE) file for details
194
1107
 
195
- โš™๏ธ Serialization: TurboSerial
196
- A key performance feature of LacertaDB is its use of turboserial instead of JSON. This provides several advantages:
1108
+ ## ๐Ÿ™ Acknowledgments
197
1109
 
198
- โšก Speed: turboserial is significantly faster at serializing and deserializing complex JavaScript objects.
1110
+ - Built with โค๏ธ by the Pixagram team
1111
+ - Uses TurboSerial and TurboBase64 for high performance
1112
+ - Inspired by MongoDB's query language
1113
+ - Powered by modern browser APIs
199
1114
 
200
- ๐Ÿ“ฆ Efficiency: It produces a more compact binary output, especially when compression is enabled, saving storage space.
1115
+ ## ๐Ÿ“ฎ Support
201
1116
 
202
- ๐Ÿ”ฌ Type Support: It correctly handles more data types than JSON, including Date, Map, Set, BigInt, and typed arrays.
1117
+ - ๐Ÿ“ง Email: omnibus (at) pixagram.io
1118
+ - ๐Ÿ› Issues: [GitHub Issues](https://github.com/pixagram-blockchain/LacertaDB/issues)
203
1119
 
204
- All data stored in localStorage (like metadata) or passed to IndexedDB is processed through turboserial and turbobase64, ensuring top-tier performance.
1120
+ ---
205
1121
 
206
- ๐Ÿ“œ License
207
- LacertaDB is licensed under the MIT License.
1122
+ ๐ŸฆŽ LacertaDB - Fast, Secure, Browser-Native Database