@owlmeans/client-resource 0.1.1 → 0.1.3

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 CHANGED
@@ -1,6 +1,6 @@
1
1
  MIT License
2
2
 
3
- Copyright (c) 2024 OwlMeans Common — Fullstack typescript framework
3
+ Copyright (c) 2026 OwlMeans Common — Fullstack typescript framework
4
4
 
5
5
  Permission is hereby granted, free of charge, to any person obtaining a copy
6
6
  of this software and associated documentation files (the "Software"), to deal
package/README.md CHANGED
@@ -1,714 +1,68 @@
1
1
  # @owlmeans/client-resource
2
2
 
3
- Client-side resource management library for OwlMeans Common applications. This package provides a comprehensive data persistence and management system for React applications, with support for local database storage, CRUD operations, and seamless integration with the OwlMeans context system.
3
+ Client-side resource persistence layer browser key-value storage backed resource for the OwlMeans `Resource<T>` interface.
4
4
 
5
5
  ## Overview
6
6
 
7
- The `@owlmeans/client-resource` package extends the base `@owlmeans/resource` package with client-specific functionality. It provides:
8
-
9
- - **Local Database Integration**: Persistent data storage using client-side databases
10
- - **CRUD Operations**: Complete Create, Read, Update, Delete functionality
11
- - **Resource Management**: Structured data management with type safety
12
- - **Context Integration**: Seamless integration with OwlMeans context system
13
- - **List Management**: Efficient listing and pagination of records
14
- - **Data Integrity**: Built-in validation and error handling
15
- - **Storage Abstraction**: Database-agnostic storage interface
16
-
17
- This package is part of the OwlMeans resource management ecosystem:
18
- - **@owlmeans/resource**: Base resource interfaces and utilities
19
- - **@owlmeans/client-resource**: Client-side resource implementation *(this package)*
20
- - **@owlmeans/server-resource**: Server-side resource implementation
7
+ - `appendClientResource(context, alias)` registers a client-side resource under `alias` in the context
8
+ - `ClientResource<T>` — extends `Resource<T>` with `db` accessor and `erase()` method
9
+ - `ClientDbService` / `ClientDb` low-level key-value store interface (`get`, `set`, `has`, `del`)
10
+ - Used by `client-did`, `client-auth`, `web-flow`, and `web-db` to persist data in the browser
21
11
 
22
12
  ## Installation
23
13
 
24
14
  ```bash
25
- npm install @owlmeans/client-resource
15
+ bun add @owlmeans/client-resource
26
16
  ```
27
17
 
28
- ## Core Concepts
29
-
30
- ### Resources
31
- Resources represent collections of data with consistent CRUD operations. Each resource is backed by a client-side database and provides type-safe access to stored records.
32
-
33
- ### Client Database Service
34
- The underlying database service provides an abstraction over various client-side storage mechanisms (IndexedDB, localStorage, etc.).
35
-
36
- ### Record Management
37
- All data is stored as records with unique identifiers, supporting both automatic ID generation and custom IDs.
18
+ ## Usage
38
19
 
39
- ## API Reference
40
-
41
- ### Factory Functions
42
-
43
- #### `appendClientResource<C, T>(context: T, alias: string): T`
44
-
45
- Appends a client resource to the application context with the specified alias.
20
+ Register a client resource in context setup:
46
21
 
47
22
  ```typescript
48
23
  import { appendClientResource } from '@owlmeans/client-resource'
49
- import { makeClientContext } from '@owlmeans/client-context'
50
-
51
- const context = makeClientContext(config)
52
- appendClientResource(context, 'users')
53
-
54
- // Access the resource
55
- const userResource = context.resource<ClientResource<UserRecord>>('users')
56
- ```
57
-
58
- **Parameters:**
59
- - `context`: T - The client context to append the resource to
60
- - `alias`: string - Unique identifier for the resource
61
-
62
- **Returns:** Enhanced context with the registered resource
63
-
64
- ### Core Interfaces
65
-
66
- #### `ClientResource<T extends ResourceRecord>`
67
-
68
- Main interface for client-side resource management with full CRUD capabilities.
69
-
70
- ```typescript
71
- interface ClientResource<T extends ResourceRecord = ResourceRecord> extends Resource<T> {
72
- db?: ClientDb // Underlying database instance
73
- erase(): Promise<void> // Completely erase all data
74
-
75
- // Inherited from Resource:
76
- get(id: string): Promise<T> // Get record (throws if not found)
77
- load(id: string): Promise<T | null> // Load record (returns null if not found)
78
- list(criteria?, opts?): Promise<ListResult<T>> // List records with pagination
79
- create(record: Partial<T>): Promise<T> // Create new record
80
- update(record: Partial<T> & { id: string }): Promise<T> // Update existing record
81
- delete(id: string | T): Promise<T | null> // Delete record
82
- pick(id: string | T): Promise<T> // Remove and return record
83
- save(record: Partial<T>): Promise<T> // Save (create or update)
84
- }
85
- ```
86
-
87
- #### `ClientDbService`
88
-
89
- Service interface for managing client-side databases.
90
-
91
- ```typescript
92
- interface ClientDbService extends InitializedService {
93
- initialize(alias?: string): Promise<ClientDb> // Initialize database instance
94
- erase(): Promise<void> // Erase all databases
95
- }
96
- ```
97
-
98
- #### `ClientDb`
99
-
100
- Low-level database interface for direct storage operations.
101
-
102
- ```typescript
103
- interface ClientDb {
104
- get<T>(id: string): Promise<T> // Get value by ID
105
- set<T>(id: string, value: T): Promise<void> // Set value by ID
106
- has(id: string): Promise<boolean> // Check if ID exists
107
- del(id: string): Promise<boolean> // Delete by ID
108
- }
109
- ```
110
-
111
- ### Resource Methods Detailed Reference
112
-
113
- #### Data Retrieval Methods
114
-
115
- **`get(id: string): Promise<T>`**
116
- - **Purpose**: Retrieves a record by ID, throwing an error if not found
117
- - **Behavior**: Guaranteed to return a record or throw `UnknownRecordError`
118
- - **Usage**: When you know the record should exist
119
- - **Throws**: `UnknownRecordError` if record doesn't exist
120
-
121
- ```typescript
122
- const userResource = context.resource<ClientResource<UserRecord>>('users')
123
-
124
- try {
125
- const user = await userResource.get('user123')
126
- console.log('User found:', user.name)
127
- } catch (error) {
128
- console.error('User not found:', error.message)
129
- }
130
- ```
131
-
132
- **`load(id: string): Promise<T | null>`**
133
- - **Purpose**: Loads a record by ID, returning null if not found
134
- - **Behavior**: Safe retrieval that never throws for missing records
135
- - **Usage**: When you need to check if a record exists
136
- - **Returns**: Record object or null
137
-
138
- ```typescript
139
- const user = await userResource.load('user123')
140
- if (user) {
141
- console.log('User exists:', user.name)
142
- } else {
143
- console.log('User not found')
144
- }
145
- ```
146
24
 
147
- **`list(criteria?, opts?): Promise<ListResult<T>>`**
148
- - **Purpose**: Lists records with optional filtering and pagination
149
- - **Behavior**: Efficiently paginates through large datasets
150
- - **Usage**: For displaying lists of data with optional filtering
151
- - **Returns**: Object with `items` array and `pager` information
152
-
153
- ```typescript
154
- // List all users
155
- const allUsers = await userResource.list()
156
-
157
- // List with pagination
158
- const pagedUsers = await userResource.list({}, {
159
- pager: { page: 0, size: 10 }
160
- })
161
-
162
- // List with filtering
163
- const activeUsers = await userResource.list({
164
- status: 'active'
165
- })
166
-
167
- // Combined filtering and pagination
168
- const result = await userResource.list(
169
- { role: 'admin' },
170
- { pager: { page: 1, size: 5 } }
171
- )
172
-
173
- console.log('Users:', result.items)
174
- console.log('Total:', result.pager.total)
175
- ```
176
-
177
- #### Data Modification Methods
178
-
179
- **`create(record: Partial<T>): Promise<T>`**
180
- - **Purpose**: Creates a new record with automatic ID generation
181
- - **Behavior**: Generates unique ID if not provided, validates uniqueness
182
- - **Usage**: For creating new records
183
- - **Throws**: `RecordExists` if ID already exists
184
- - **Returns**: Created record with generated/validated ID
185
-
186
- ```typescript
187
- const newUser = await userResource.create({
188
- name: 'John Doe',
189
- email: 'john@example.com',
190
- role: 'user'
191
- })
192
- console.log('Created user with ID:', newUser.id)
193
- ```
194
-
195
- **`update(record: Partial<T> & { id: string }): Promise<T>`**
196
- - **Purpose**: Updates an existing record with partial data
197
- - **Behavior**: Merges provided data with existing record
198
- - **Usage**: For modifying existing records
199
- - **Throws**: `UnknownRecordError` if record doesn't exist
200
- - **Returns**: Updated record
201
-
202
- ```typescript
203
- const updatedUser = await userResource.update({
204
- id: 'user123',
205
- name: 'Jane Doe',
206
- lastLogin: new Date()
207
- })
208
- ```
209
-
210
- **`save(record: Partial<T>): Promise<T>`**
211
- - **Purpose**: Smart save that creates or updates based on existence
212
- - **Behavior**: Creates if ID is missing or record doesn't exist, updates otherwise
213
- - **Usage**: When you want create-or-update semantics
214
- - **Returns**: Saved record
215
-
216
- ```typescript
217
- // Will create if user doesn't exist
218
- const user1 = await userResource.save({
219
- name: 'New User',
220
- email: 'new@example.com'
221
- })
222
-
223
- // Will update if user exists
224
- const user2 = await userResource.save({
225
- id: 'existing-user',
226
- name: 'Updated Name'
227
- })
25
+ appendClientResource(context, 'my-resource')
228
26
  ```
229
27
 
230
- **`delete(id: string | T): Promise<T | null>`**
231
- - **Purpose**: Deletes a record by ID or record object
232
- - **Behavior**: Removes record and updates internal lists
233
- - **Usage**: For permanent record removal
234
- - **Returns**: Deleted record or null if not found
28
+ Use the resource via the context:
235
29
 
236
30
  ```typescript
237
- // Delete by ID
238
- const deletedUser = await userResource.delete('user123')
31
+ import type { ClientResource } from '@owlmeans/client-resource'
239
32
 
240
- // Delete by record
241
- const userToDelete = await userResource.load('user456')
242
- if (userToDelete) {
243
- await userResource.delete(userToDelete)
244
- }
33
+ const res = context.resource<ClientResource<MyRecord>>('my-resource')
34
+ await res.save({ id: 'key', ...data })
35
+ const record = await res.load('key')
36
+ await res.erase() // clear all stored data
245
37
  ```
246
38
 
247
- **`pick(id: string | T): Promise<T>`**
248
- - **Purpose**: Removes and returns a record atomically
249
- - **Behavior**: Combines delete operation with return of the deleted record
250
- - **Usage**: When you need to extract a record from storage
251
- - **Throws**: `UnknownRecordError` if record doesn't exist
252
- - **Returns**: Picked record
39
+ ## API
253
40
 
254
- ```typescript
255
- try {
256
- const pickedUser = await userResource.pick('user123')
257
- console.log('Picked user:', pickedUser.name)
258
- // User is now removed from storage
259
- } catch (error) {
260
- console.error('User not found for picking')
261
- }
262
- ```
41
+ ### `appendClientResource<C, T>(context, alias): T`
263
42
 
264
- **`erase(): Promise<void>`**
265
- - **Purpose**: Completely erases all data in the resource
266
- - **Behavior**: Removes all records and resets the resource to empty state
267
- - **Usage**: For data cleanup or reset operations
268
- - **Warning**: This operation is irreversible
43
+ Appends a client resource with the given `alias` to `context`. Returns the context for chaining.
269
44
 
270
- ```typescript
271
- // Completely clear all user data
272
- await userResource.erase()
273
- console.log('All user data erased')
274
- ```
45
+ ### `ClientResource<T>`
275
46
 
276
- ### Database Configuration
47
+ Extends `Resource<T>` with:
48
+ - `db?: ClientDb` — underlying key-value store
49
+ - `erase(): Promise<void>` — wipe all stored records
277
50
 
278
- Resources can be configured through the context configuration:
51
+ ### `ClientDb`
279
52
 
280
- ```typescript
281
- const context = makeClientContext({
282
- service: 'my-app',
283
- // ... other config
284
- dbs: [
285
- {
286
- alias: 'users',
287
- service: 'client-db',
288
- schema: 'app-users',
289
- host: []
290
- },
291
- {
292
- alias: 'settings',
293
- service: 'client-db',
294
- schema: 'app-settings',
295
- host: []
296
- }
297
- ]
298
- })
299
- ```
53
+ Low-level browser storage interface:
54
+ - `get<T>(id): Promise<T>`
55
+ - `set<T>(id, value): Promise<void>`
56
+ - `has(id): Promise<boolean>`
57
+ - `del(id): Promise<boolean>`
300
58
 
301
59
  ### Constants
302
60
 
303
- #### `DEFAULT_DB_ALIAS`
304
- Default database service alias (`'client-db'`).
305
-
306
- #### `LIST_KEY`
307
- Internal key used for maintaining record lists (`'_list'`).
308
-
309
- ## Usage Examples
310
-
311
- ### Basic Resource Setup
312
-
313
- ```typescript
314
- import { appendClientResource } from '@owlmeans/client-resource'
315
- import { makeClientContext } from '@owlmeans/client-context'
316
-
317
- interface UserRecord extends ResourceRecord {
318
- id: string
319
- name: string
320
- email: string
321
- role: 'admin' | 'user'
322
- createdAt: Date
323
- lastLogin?: Date
324
- }
325
-
326
- // Create context and add resource
327
- const context = makeClientContext(config)
328
- appendClientResource(context, 'users')
329
-
330
- // Initialize context
331
- await context.configure().init()
332
-
333
- // Access the resource
334
- const userResource = context.resource<ClientResource<UserRecord>>('users')
335
- ```
336
-
337
- ### Complete CRUD Operations
338
-
339
- ```typescript
340
- // Create a new user
341
- const newUser = await userResource.create({
342
- name: 'Alice Johnson',
343
- email: 'alice@example.com',
344
- role: 'user',
345
- createdAt: new Date()
346
- })
347
- console.log('Created user:', newUser.id)
348
-
349
- // Load a user
350
- const user = await userResource.load(newUser.id)
351
- if (user) {
352
- console.log('User found:', user.name)
353
- }
354
-
355
- // Update the user
356
- const updatedUser = await userResource.update({
357
- id: newUser.id,
358
- lastLogin: new Date(),
359
- role: 'admin'
360
- })
361
-
362
- // List users with pagination
363
- const userList = await userResource.list({}, {
364
- pager: { page: 0, size: 10 }
365
- })
366
- console.log('Users:', userList.items.length)
367
- console.log('Total users:', userList.pager.total)
368
-
369
- // Delete the user
370
- const deletedUser = await userResource.delete(newUser.id)
371
- console.log('Deleted user:', deletedUser?.name)
372
- ```
373
-
374
- ### Advanced Filtering and Pagination
375
-
376
- ```typescript
377
- interface ProductRecord extends ResourceRecord {
378
- id: string
379
- name: string
380
- category: string
381
- price: number
382
- inStock: boolean
383
- }
384
-
385
- const productResource = context.resource<ClientResource<ProductRecord>>('products')
386
-
387
- // Filter by category
388
- const electronics = await productResource.list({
389
- category: 'electronics'
390
- })
391
-
392
- // Filter by availability
393
- const availableProducts = await productResource.list({
394
- inStock: true
395
- })
396
-
397
- // Paginated results
398
- let page = 0
399
- const pageSize = 20
400
- let hasMore = true
401
-
402
- while (hasMore) {
403
- const result = await productResource.list({}, {
404
- pager: { page, size: pageSize }
405
- })
406
-
407
- console.log(`Page ${page + 1}:`, result.items.length)
408
-
409
- hasMore = (page + 1) * pageSize < result.pager.total
410
- page++
411
- }
412
- ```
413
-
414
- ### Error Handling
415
-
416
- ```typescript
417
- import { RecordExists, UnknownRecordError, ResourceError } from '@owlmeans/resource'
418
-
419
- try {
420
- // Attempt to create user with specific ID
421
- const user = await userResource.create({
422
- id: 'specific-id',
423
- name: 'Test User',
424
- email: 'test@example.com'
425
- })
426
- } catch (error) {
427
- if (error instanceof RecordExists) {
428
- console.error('User with this ID already exists')
429
- } else if (error instanceof ResourceError) {
430
- console.error('Resource error:', error.message)
431
- }
432
- }
433
-
434
- try {
435
- // Attempt to get non-existent user
436
- const user = await userResource.get('non-existent-id')
437
- } catch (error) {
438
- if (error instanceof UnknownRecordError) {
439
- console.error('User not found')
440
- }
441
- }
442
- ```
443
-
444
- ### Multiple Resources Management
445
-
446
- ```typescript
447
- interface UserRecord extends ResourceRecord {
448
- id: string
449
- name: string
450
- email: string
451
- }
452
-
453
- interface PostRecord extends ResourceRecord {
454
- id: string
455
- title: string
456
- content: string
457
- authorId: string
458
- publishedAt: Date
459
- }
460
-
461
- // Setup multiple resources
462
- const context = makeClientContext(config)
463
- appendClientResource(context, 'users')
464
- appendClientResource(context, 'posts')
465
-
466
- await context.configure().init()
467
-
468
- const userResource = context.resource<ClientResource<UserRecord>>('users')
469
- const postResource = context.resource<ClientResource<PostRecord>>('posts')
470
-
471
- // Create user and posts
472
- const author = await userResource.create({
473
- name: 'John Doe',
474
- email: 'john@example.com'
475
- })
476
-
477
- const post1 = await postResource.create({
478
- title: 'First Post',
479
- content: 'Hello world!',
480
- authorId: author.id,
481
- publishedAt: new Date()
482
- })
483
-
484
- const post2 = await postResource.create({
485
- title: 'Second Post',
486
- content: 'More content here',
487
- authorId: author.id,
488
- publishedAt: new Date()
489
- })
490
-
491
- // Find posts by author
492
- const authorPosts = await postResource.list({
493
- authorId: author.id
494
- })
495
- console.log(`${author.name} has ${authorPosts.items.length} posts`)
496
- ```
497
-
498
- ### Resource with Custom Database Configuration
499
-
500
- ```typescript
501
- const context = makeClientContext({
502
- service: 'advanced-app',
503
- // ... other config
504
- dbs: [
505
- {
506
- alias: 'user-data',
507
- service: 'indexed-db-service',
508
- schema: 'users-v2',
509
- host: []
510
- },
511
- {
512
- alias: 'cache-data',
513
- service: 'memory-db-service',
514
- schema: 'temp-cache',
515
- host: []
516
- }
517
- ]
518
- })
519
-
520
- // Resources will use the configured database services
521
- appendClientResource(context, 'user-data')
522
- appendClientResource(context, 'cache-data')
523
- ```
524
-
525
- ### Reactive Resource Updates
526
-
527
- ```typescript
528
- import { useState, useEffect } from 'react'
529
- import { useContext } from '@owlmeans/client'
530
-
531
- function UserList() {
532
- const context = useContext()
533
- const [users, setUsers] = useState([])
534
-
535
- useEffect(() => {
536
- const loadUsers = async () => {
537
- const userResource = context.resource('users')
538
- const result = await userResource.list()
539
- setUsers(result.items)
540
- }
541
-
542
- loadUsers()
543
- }, [])
544
-
545
- const addUser = async (userData) => {
546
- const userResource = context.resource('users')
547
- const newUser = await userResource.create(userData)
548
- setUsers(prev => [...prev, newUser])
549
- }
550
-
551
- const deleteUser = async (userId) => {
552
- const userResource = context.resource('users')
553
- await userResource.delete(userId)
554
- setUsers(prev => prev.filter(u => u.id !== userId))
555
- }
556
-
557
- return (
558
- <div>
559
- {users.map(user => (
560
- <div key={user.id}>
561
- {user.name}
562
- <button onClick={() => deleteUser(user.id)}>Delete</button>
563
- </div>
564
- ))}
565
- </div>
566
- )
567
- }
568
- ```
569
-
570
- ### Data Migration and Cleanup
571
-
572
- ```typescript
573
- // Migration helper
574
- const migrateUserData = async () => {
575
- const userResource = context.resource<ClientResource<UserRecord>>('users')
576
- const users = await userResource.list()
577
-
578
- for (const user of users.items) {
579
- if (!user.createdAt) {
580
- await userResource.update({
581
- id: user.id,
582
- createdAt: new Date()
583
- })
584
- }
585
- }
586
- }
587
-
588
- // Cleanup old data
589
- const cleanupOldUsers = async () => {
590
- const userResource = context.resource<ClientResource<UserRecord>>('users')
591
- const users = await userResource.list()
592
-
593
- const oneYearAgo = new Date()
594
- oneYearAgo.setFullYear(oneYearAgo.getFullYear() - 1)
595
-
596
- for (const user of users.items) {
597
- if (user.lastLogin && user.lastLogin < oneYearAgo) {
598
- await userResource.delete(user.id)
599
- console.log('Deleted inactive user:', user.name)
600
- }
601
- }
602
- }
603
-
604
- // Complete resource reset
605
- const resetAllData = async () => {
606
- const userResource = context.resource('users')
607
- const postResource = context.resource('posts')
608
-
609
- await Promise.all([
610
- userResource.erase(),
611
- postResource.erase()
612
- ])
613
-
614
- console.log('All data erased')
615
- }
616
- ```
617
-
618
- ## Error Handling
619
-
620
- The package integrates with the OwlMeans error system and may throw the following errors:
621
-
622
- ### `ResourceError`
623
- General resource operation errors.
624
-
625
- ### `UnknownRecordError`
626
- Thrown when attempting to access a record that doesn't exist.
627
-
628
- ### `RecordExists`
629
- Thrown when attempting to create a record with an ID that already exists.
630
-
631
- ```typescript
632
- import { ResourceError, UnknownRecordError, RecordExists } from '@owlmeans/resource'
633
-
634
- const handleResourceOperation = async () => {
635
- try {
636
- await userResource.create({ id: 'existing-id', name: 'Test' })
637
- } catch (error) {
638
- if (error instanceof RecordExists) {
639
- console.error('Record already exists')
640
- } else if (error instanceof UnknownRecordError) {
641
- console.error('Record not found')
642
- } else if (error instanceof ResourceError) {
643
- console.error('Resource error:', error.message)
644
- }
645
- }
646
- }
647
- ```
648
-
649
- ## Performance Considerations
650
-
651
- 1. **Pagination**: Use pagination for large datasets to avoid memory issues
652
- 2. **Indexing**: Consider database indexing for frequently queried fields
653
- 3. **Batch Operations**: Group related operations together when possible
654
- 4. **Memory Management**: Use `pick()` instead of `get()` + `delete()` when extracting data
655
- 5. **Database Choice**: Choose appropriate database service based on data size and usage patterns
656
-
657
- ## Integration with Other Packages
658
-
659
- ### Client Context Integration
660
- ```typescript
661
- import { makeClientContext } from '@owlmeans/client-context'
662
- import { appendClientResource } from '@owlmeans/client-resource'
663
-
664
- const context = makeClientContext(config)
665
- appendClientResource(context, 'users')
666
- ```
667
-
668
- ### Authentication Integration
669
- ```typescript
670
- import { appendClientResource } from '@owlmeans/client-resource'
671
- import { AUTH_RESOURCE } from '@owlmeans/client-auth'
672
-
673
- // Setup authentication resource
674
- appendClientResource(context, AUTH_RESOURCE)
675
- ```
676
-
677
- ### Database Service Integration
678
- ```typescript
679
- import { WebDbService } from '@owlmeans/web-db'
680
- import { appendClientResource } from '@owlmeans/client-resource'
681
-
682
- // Register database service first
683
- context.registerService(webDbService)
684
-
685
- // Then add resources that use it
686
- appendClientResource(context, 'users')
687
- ```
688
-
689
- ## Best Practices
690
-
691
- 1. **Type Safety**: Always use TypeScript interfaces for your records
692
- 2. **Resource Naming**: Use descriptive names for resource aliases
693
- 3. **Error Handling**: Implement comprehensive error handling for all operations
694
- 4. **Data Validation**: Validate data before storing in resources
695
- 5. **Memory Management**: Use pagination for large datasets
696
- 6. **Consistent IDs**: Use consistent ID generation strategies
697
- 7. **Database Configuration**: Configure appropriate database services for your use case
698
-
699
- ## Dependencies
700
-
701
- This package depends on:
702
- - `@owlmeans/resource` - Base resource interfaces and utilities
703
- - `@owlmeans/client-context` - Client context management
704
- - `@owlmeans/context` - Core context system
705
- - `@noble/hashes` - Cryptographic utilities for ID generation
706
- - `@scure/base` - Base encoding for ID generation
61
+ - `DEFAULT_DB_ALIAS` — `'client-db'` — default alias for the underlying DB service
62
+ - `LIST_KEY` `'_list'` — key used to store the record index
707
63
 
708
64
  ## Related Packages
709
65
 
710
- - [`@owlmeans/resource`](../resource) - Base resource interfaces
711
- - [`@owlmeans/client-context`](../client-context) - Client context management
712
- - [`@owlmeans/web-db`](../web-db) - Web database implementation
713
- - [`@owlmeans/server-resource`](../server-resource) - Server-side resources
714
- - [`@owlmeans/client-auth`](../client-auth) - Authentication with resource storage
66
+ - [`@owlmeans/resource`](../resource) `Resource<T>`, `ResourceRecord` base interfaces
67
+ - [`@owlmeans/web-db`](../web-db) — IndexedDB-backed implementation of `ClientDbService`
68
+ - [`@owlmeans/client-did`](../client-did) uses `appendClientResource` to persist DID keys
package/package.json CHANGED
@@ -1,6 +1,7 @@
1
1
  {
2
2
  "name": "@owlmeans/client-resource",
3
- "version": "0.1.1",
3
+ "version": "0.1.3",
4
+ "license": "MIT",
4
5
  "type": "module",
5
6
  "scripts": {
6
7
  "build": "tsc -b",
@@ -21,14 +22,15 @@
21
22
  },
22
23
  "dependencies": {
23
24
  "@noble/hashes": "^1.5.0",
24
- "@owlmeans/client-context": "^0.1.1",
25
- "@owlmeans/context": "^0.1.1",
26
- "@owlmeans/resource": "^0.1.1",
25
+ "@owlmeans/client-context": "^0.1.3",
26
+ "@owlmeans/context": "^0.1.3",
27
+ "@owlmeans/resource": "^0.1.3",
27
28
  "@scure/base": "^1.1.9"
28
29
  },
29
30
  "devDependencies": {
31
+ "@owlmeans/dep-config": "workspace:*",
30
32
  "nodemon": "^3.1.11",
31
- "typescript": "^5.8.3"
33
+ "typescript": "^6.0.2"
32
34
  },
33
35
  "publishConfig": {
34
36
  "access": "public"
package/tsconfig.json CHANGED
@@ -1,15 +1,10 @@
1
1
  {
2
2
  "extends": [
3
- "../tsconfig.default.json"
3
+ "@owlmeans/dep-config/tsconfig.base.json"
4
4
  ],
5
5
  "compilerOptions": {
6
- "rootDir": "./src/", /* Specify the root folder within your source files. */
7
- "outDir": "./build/", /* Specify an output folder for all emitted files. */
8
- "moduleResolution": "Bundler",
6
+ "rootDir": "./src/",
7
+ "outDir": "./build/"
9
8
  },
10
- "exclude": [
11
- "./dist/**/*",
12
- "./build/**/*",
13
- "./*.ts"
14
- ]
15
- }
9
+ "exclude": ["./dist/**/*", "./build/**/*", "./*.ts"]
10
+ }