@oimdb/core 4.0.1 → 4.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -3,13 +3,183 @@
3
3
  All notable changes to `@oimdb/core` are recorded here. This file starts at 4.0.0; releases
4
4
  before it were not changelogged.
5
5
 
6
- ## 4.0.0 — unreleased
6
+ ## 4.2.0
7
+
8
+ ### Added
9
+
10
+ - `OIMDefaults` instance (`new OIMDefaults(options)`, `OIMDefaults.INSTANCE`), `TOIMDefaultsOptions`; option `defaults` on every factory.
11
+ - `releaseValue` option on `createOIMComputedService` and `createOIMSingleComputedService`; `TOIMComputedValueReleaser`.
12
+ - `createOIMSourceTrackingComputedService`, `createOIMSingleSourceTrackingComputedService`, `OIMSourceTrackingComputedService`, `OIMSingleSourceTrackingComputedService`, `TOIMSourceTrackingComputedSlot`, `TOIMSourceTrackingComputedContentSlot`, `TOIMSourceTrackingComputedDerive`, `TOIMSourceTrackingComputedDerivationOptions`, `OIMSlotContentSourceTrackingComputedService` (type), `TOIMComputedServiceFactoryOptions`.
13
+
14
+ ### Changed
15
+
16
+ - `createOIMSlotCollectionService`, `createOIMSingleSlotService`, `createOIMSlotContentEntityService`, `createOIMSlotCollectionIndexService`, `createOIMSlotCollectionSortedArrayIndexService`: no `db` argument.
17
+ - `createEffect`, `createAndRunEffect`, `subscribeEffect`: `(db, body, sourceSlots?, sourceComputeds?, sourceTrackingComputeds?)`.
18
+ - `closeBatch` throws when no batch is open.
19
+ - A slot written inside a batch is released only after the batch is delivered.
20
+ - Slot flag bit `32` is taken by the engine; a library's own bits start at `64`.
21
+ - `TOIMSlot.storeSlot` is required; a column slot carries its carrier's store slot.
22
+ - A last unhold inside a flush releases the slot at once, for every slot kind.
23
+ - `IOIMSlotContentService.releaseSlotContent(slot)` takes the slot only and throws on a held slot.
24
+ - `TOIMChannelClock.epoch` is an int32 that wraps; `oimIsRevisionAfter` compares epochs as `(epoch - sinceEpoch) | 0`.
25
+
26
+ ### Removed
27
+
28
+ - `OIMDefaults.STANDALONE_SLOT_OWNER`. Use `new OIMSlotOwner()`.
29
+ - `OIMDefaults` static fields and `OIMDefaultValue.setValue`. Use `new OIMDefaults({ … })` passed as `defaults`.
30
+ - `OIMDefaults.KEY_TREE_WALK_SCALAR`, `OIMDefaults.KEY_TREE_WALK_COMPOSITE`. Use `OIMScalarKeyTreeWalk.INSTANCE`, `OIMCompositeKeyTreeWalk.INSTANCE`.
31
+ - `OIMDefaults.ENTITY_SLOT_EMPTINESS`. Use `new OIMDefaults({ entitySlotEmptinessPolicy })`.
32
+ - `TOIMDBOptions.entityWriter`, `slotStamp`, `slotReleasePolicy`, `indexKeysService` and the same fields of `OIMDB`. Use `OIMDefaults`.
33
+
34
+ ### Renamed
35
+
36
+ - `TOIMSlotEditable` → `TOIMEditable`
37
+ - `OIMEffectService.createEffectImmediate` → `createAndRunEffect`
38
+ - `OIMEffectService.createEffectWithSourceTracking` → `createSourceTrackingEffect`
39
+ - `TOIMEffectBodyWithSourceTracking` → `TOIMSourceTrackingEffectBody`
40
+ - `OIMEffectSourceTracker` → `OIMSourceTracker`
41
+ - `IOIMContentChangeListener.onContentChangedMany` → `onManyContentsChanged`
42
+ - `createOIMEntityWriterInPlace` → `createOIMInPlaceEntityWriter`
43
+ - `createOIMEntityWriterReplacing` → `createOIMReplacingEntityWriter`
44
+ - `oimPatchEntityColumnsGuarded` → `oimGuardedPatchEntityColumns`
45
+ - `oimPatchEntityColumnGuarded` → `oimGuardedPatchEntityColumn`
46
+ - `oimPutEntityColumnsGuarded` → `oimGuardedPutEntityColumns`
47
+ - `TOIMSortColumn.column` → `columnName`
48
+ - `TOIMSlotStoreTree.root` → `rootCompositeKeyNode`
49
+ - `TOIMDerivation` → `TOIMComputedDerivation`
50
+ - `OIMContentChangeListenerService` → `OIMSlotContentChangeListenerService`
51
+ - `IOIMContentChangeListener` → `IOIMSlotContentChangeListener`
52
+
53
+ ## 4.1.0
54
+
55
+ Breaking: exports removed and renamed, `IOIMSlotOwner` has new required members.
56
+
57
+ ### Added
58
+
59
+ - `IOIMBucketMemberSlotsArrayService`: the members of an array bucket. `OIMBucketMemberSlotsArrayService`
60
+ (default) and `OIMBucketUniqueMemberSlotsArrayService`. Option `bucketMemberSlotsArrayService` on both
61
+ array buckets (`TOIMSlotContentArrayBucketServiceOptions`, `TOIMSlotContentSortedArrayBucketServiceOptions`).
62
+ - `slotSubscriptionListener` option: `IOIMSlotSubscriptionListener` (`onSlotFirstSubscribed`,
63
+ `onSlotLastUnsubscribed`), default `OIMNoSlotSubscriptionListener`.
64
+ - `OIMSlotReleaseWheel.markSlotReleaseDueNow(slot)`.
65
+ - `slotReleaseDueFramePolicy` on `OIMSlotAfterWriteReleasePolicy`: `OIMSlotReleaseAutoDueFramePolicy` (default),
66
+ `OIMSlotReleaseManualDueFramePolicy` (`openSlotReleaseDueFrame`, `closeSlotReleaseDueFrame`,
67
+ `writeInSlotReleaseDueFrame`).
68
+ - `OIMSlotWheel`, `OIMSlotReleaseWheel`, `OIMSlotRefetchWheel` (`scheduleSlotRefetchAt`), `IOIMSlotRefetchListener`,
69
+ `TOIMSlotWheelOptions`, `TOIMSlotReleaseWheelOptions`, `TOIMSlotRefetchWheelOptions`.
70
+ - `oimMintAfterWriteSlotReleaseWheel`, `oimMintAfterIdleSlotReleaseWheel`, `oimMintAfterUnholdSlotReleaseWheel`.
71
+ - `IOIMSlotOwner.unsafeMutateSlot(slot, mutateSlot)`.
72
+ - `openBatch`, `closeBatch`, `writeInBatch` on `OIMSlotCollectionService`. An index gets the batch in one
73
+ `onContentChangedMany` when the outermost batch closes. A flush inside a batch is allowed.
74
+ - `OIMSlotContentBucketService.getBucketMemberSlotsMissingFrom(bucketSlot, bucketMemberSlots)`.
75
+ - `storeSlot.slotService`; `TOIMStoreSlot` has a fourth type parameter.
76
+ - `TOIMSlotContentServiceKey`, `TOIMSlotContentServiceSlot`, `TOIMSlotContentServiceSingleSlot`,
77
+ `TOIMSlotContentServiceContent`, `TOIMSlotContentServicePatch`.
78
+ - `IOIMSlotContentService`, `IOIMKeyedSlotCreator`, `IOIMSingleSlotCreator`, `IOIMSlotFilingService`.
79
+ - `TOIMEntityContentSlot`, `TOIMBucketContentSlot`, `TOIMComputedContentSlot`.
80
+ - `OIMWritableSlotCollectionService.writeSlotContentByKey`, `OIMWritableSingleSlotService.writeSingleSlotContent`
81
+ and `clearSingleSlotContent`.
82
+ - `OIMSingleComputedService`, `createOIMSingleComputedService`, `TOIMComputedDerivationOptions`.
83
+ - `IOIMFlushSchedulerListener`.
84
+ - `OIMColumnSlotService`, as `columnSlotService` on `OIMSlotCollectionService` and `OIMSingleSlotService`.
85
+ - `OIMSlotContentComputedService` and `TOIMSlotContentComputedServiceOptions` as types.
86
+
87
+ ### Changed
88
+
89
+ - The release queue is a timing wheel; a slot's place on it is a bit of `slot.slotFlags`.
90
+ - Release wheels on `db.collectorSlot` are created on first use.
91
+ - A single write files the slot, then tells the index. Nothing is rolled back if the index throws.
92
+ - Under a synchronous `channelScheduler` one write can run several frames.
93
+ - `releaseSlotContent` throws inside a flush when the slot has content.
94
+ - Single slots have the same shape as keyed ones (`key` and `indexKeys` are `undefined`).
95
+
96
+ ### Renamed
97
+
98
+ - `OIMSlotContentBucketServiceArrayBased` → `OIMSlotContentArrayBucketService`
99
+ - `OIMSlotContentBucketServiceArrayDriven` → `OIMSlotContentPositionalArrayBucketService`
100
+ - `OIMSlotContentBucketServiceSortedArrayDriven` → `OIMSlotContentSortedArrayBucketService`
101
+ - `OIMSlotContentBucketServiceSetDriven` → `OIMSlotContentSetBucketService`
102
+ - `TOIMSlotContentBucketServiceSortedArrayDrivenOptions` → `TOIMSlotContentSortedArrayBucketServiceOptions`
103
+ - `OIMSlotReleasePolicyAfterWrite` → `OIMSlotAfterWriteReleasePolicy`
104
+ - `OIMSlotReleasePolicyAfterIdle` → `OIMSlotAfterIdleReleasePolicy`
105
+ - `OIMSlotReleasePolicyAfterUnhold` → `OIMSlotAfterUnholdReleasePolicy`
106
+ - `OIMSlotReleasePolicyAtEmpty` → `OIMSlotAtEmptyReleasePolicy`
107
+ - `OIMSlotReleasePolicyAtUnhold` → `OIMSlotAtUnholdReleasePolicy`
108
+ - `OIMSlotReleasePolicyEarliest` → `OIMSlotEarliestReleasePolicy`
109
+ - `OIMSlotReleasePolicyNever` → `OIMSlotNeverReleasePolicy`
110
+ - `TOIMSlotReleasePolicyAfterWriteOptions` → `TOIMSlotAfterWriteReleasePolicyOptions`
111
+ - `TOIMSlotReleasePolicyAfterIdleOptions` → `TOIMSlotAfterIdleReleasePolicyOptions`
112
+ - `TOIMSlotReleasePolicyAfterUnholdOptions` → `TOIMSlotAfterUnholdReleasePolicyOptions`
113
+ - `OIMErrorPolicyThrowAtOnce` → `OIMThrowAtOnceErrorPolicy`
114
+ - `OIMErrorPolicyLogAndContinue` → `OIMLogAndContinueErrorPolicy`
115
+ - `TOIMErrorPolicyLogAndContinueOptions` → `TOIMLogAndContinueErrorPolicyOptions`
116
+ - `OIMSlotStoreServiceMapDriven` → `OIMSlotMapStoreService`
117
+ - `OIMSlotStoreServiceTreeDriven` → `OIMSlotTreeStoreService`
118
+ - `OIMSlotStoreServiceSingleSlotDriven` → `OIMSingleSlotStoreService`
119
+ - `OIMIndexKeysServiceAppending` → `OIMAppendingIndexKeysService`
120
+ - `OIMIndexKeysServiceReclaiming` → `OIMReclaimingIndexKeysService`
121
+ - `OIMColumnOwnerPushDriven` → `OIMPushColumnSlotOwner`
122
+ - `OIMColumnOwnerPullDriven` → `OIMPullColumnSlotOwner`
123
+ - `OIMColumnOwner` → `OIMColumnSlotOwner`
124
+ - `TOIMColumnOwnerOptions` → `TOIMColumnSlotOwnerOptions`
125
+ - `OIMComputedServiceSorted` → `OIMSortedComputedService`
126
+ - `OIMComputedServiceBucketMemo` → `OIMBucketMemoComputedService`
127
+ - `TOIMComputedServiceSortedOptions` → `TOIMSortedComputedServiceOptions`
128
+ - `TOIMComputedServiceBucketMemoOptions` → `TOIMBucketMemoComputedServiceOptions`
129
+ - `createOIMComputedServiceSorted` → `createOIMSortedComputedService`
130
+ - `createOIMComputedServiceBucketMemo` → `createOIMBucketMemoComputedService`
131
+ - `OIMKeyTreeWalkComposite` → `OIMCompositeKeyTreeWalk`
132
+ - `OIMKeyTreeWalkScalar` → `OIMScalarKeyTreeWalk`
133
+ - `TOIMEntityInsertStrategy` → `TOIMEntityInserter`
134
+ - `OIMStoreSlotListenerNone` → `OIMNoStoreSlotListener`
135
+ - `IOIMSlotEmptiness` → `IOIMSlotEmptinessPolicy`
136
+ - `OIMIndexService` → `OIMSlotCollectionIndexService`
137
+ - `createOIMIndexService` → `createOIMSlotCollectionIndexService`
138
+ - `TOIMIndexServiceFactoryOptions` → `TOIMSlotCollectionIndexServiceFactoryOptions`
139
+ - `TOIMIndexServiceOptions` → `TOIMSlotCollectionIndexServiceOptions`
140
+ - `TOIMIndexServiceStoreSlot` → `TOIMSlotCollectionIndexServiceStoreSlot`
141
+ - `OIMIndexServiceSortedArrayDriven` → `OIMSlotCollectionSortedArrayIndexService`
142
+ - `createOIMIndexServiceSortedArrayDriven` → `createOIMSlotCollectionSortedArrayIndexService`
143
+
144
+ ### Removed
145
+
146
+ - `createOIMEntityService`, `createOIMSingleEntityService`, `createOIMBucketService`,
147
+ `createOIMSingleBucketService`, `createOIMIndexServiceByCompositeKey`, `TOIMBucketCollectionFactoryArguments`,
148
+ `TOIMSlotContentEntityServiceFactoryOptions`. Use `createOIMSlotCollectionService(db, { slotContentService })`
149
+ or `createOIMSingleSlotService(db, { slotContentService })`; an array key needs `slotStoreService`.
150
+ - `IOIMSlotContentStrategy`, `IOIMSlotContentFlushStrategy`. Use `IOIMSlotContentService`.
151
+ - `OIMSlotColumnService`, and the column doors on the collection and single services. Use their `columnSlotService` (`OIMColumnSlotService`): `getColumn`, `holdColumn`, `getAnyColumn`, `holdAnyColumn`, `getColumnGroup`, `holdColumnGroup`, `unholdColumn`.
152
+ - `TOIMBucketSlotsSortedArrayStore`, `TOIMBucketSlotsArrayUniqueStore`. Use `TOIMBucketSlotsArrayStore`.
153
+ - `OIMReleaseSlotCollectorService`, `OIMReleaseSlotCollectorServiceAfterWrite`,
154
+ `OIMReleaseSlotCollectorServiceAfterIdle`, `OIMReleaseSlotCollectorServiceAfterUnhold`,
155
+ `OIMReleaseSlotQueueService`, `TOIMReleaseSlotCollectorSlot`, `createOIMReleaseSlotCollectorSlot`, and the
156
+ `…ReleaseSlotCollectorSlot` fields of `TOIMCollectorSlot`. Use the release wheels.
157
+ - `IOIMBucketArrayMembership`, `OIMBucketArrayMembershipNonUnique`, `OIMBucketArrayMembershipUnique`, option
158
+ `bucketArrayMembership`. Use `bucketMemberSlotsArrayService`.
159
+ - `upsertEntities`, `insertEntities`, `fillEntities`, `clearAllEntities`, `deleteEntities` and their errors.
160
+ Loop single writes inside `writeInBatch`.
161
+ - Subframes: `openSubframe`, `closeSubframe`, `isSubframeOpen`, `listChangedStoreSlot`,
162
+ `IOIMSubframeCloseListener` and their fields. Use a batch.
163
+ - `fillSlotContent` on `IOIMSlotContentWriter` and the content services.
164
+
165
+ ## 4.0.1
166
+
167
+ Speed, with no change to the API.
168
+
169
+ - `OIMSlotOwnerService.isAnyColumnReferenced` looks only at the slot's own column slots.
170
+ - `OIMColumnOwner.mintColumnGroupSlot` skips rebuilding the key of a group already registered by the
171
+ same object.
172
+ - `oimMergeRootSlots` drops duplicate roots with a linear scan up to 16 roots and a `Set` above.
173
+ - `OIMIndexService.updateIndexKeysForSlots` groups only under buckets it minted.
174
+ - `OIMSlotContentEntityService.fillEachEntity` detects a repeated key by the store's size when the
175
+ store started empty.
176
+
177
+ ## 4.0.0
7
178
 
8
179
  A ground-up rewrite, not an incremental version: **nothing from the 3.x public API survives
9
180
  unchanged.** There is no port table. The exported surface is `src/index.ts`, enumerated in the
10
181
  README's export reference, and [the documentation](https://oimdb.org/docs/) describes it as it
11
- is rather than as a diff. `npm install @oimdb/core` does not give you this engine until 4.0.0 is
12
- published.
182
+ is rather than as a diff.
13
183
 
14
184
  ### The two changes everything else follows from
15
185
 
@@ -17,36 +187,36 @@ published.
17
187
  key to a slot once (`getSlotByKey`, `holdSlotByKey`) and works through that slot afterwards.
18
188
  `updateEntity` takes a slot; `updateEntityByKey` / `deleteEntityByKey` say the lookup in their
19
189
  names.
20
- - **A god-object runtime → an operation lives on its subject.** Writes and reads are methods on
21
- the collection that owns the slot; delivery is `OIMChannel`'s; `OIMDB` is a root that builds
190
+ - **A god-object runtime → stateless services over slots.** Writes and reads are methods of the
191
+ service that owns the slot; delivery is `OIMChannelService`'s; `OIMDB` is a root that builds
22
192
  collections with its defaults and drives `flush()`.
23
193
 
24
194
  ### What the engine is made of
25
195
 
26
196
  - **Slots and their owners.** Every observable thing is a slot — an entity, a column, a bucket, a
27
- computed — and only its owner mutates it. `OIMSlotAggregate` is the base every collection
28
- extends; `OIMSlotReleaseOwner` decides when an unheld slot goes, through an injected
29
- `IOIMSlotReleasePolicy` (`AtEmpty` by default, plus `AtUnhold`, `AfterUnhold`, `AfterWrite`,
30
- `AfterIdle`, `Never` and `Earliest`).
31
- - **Entities.** `OIMEntityCollection` (silent) and `OIMChannelledEntityCollection` (wakes the
32
- channel), `OIMSingleEntity` for one record. The writer is a fork chosen at construction:
33
- `createOIMEntityWriterInPlace` or `createOIMEntityWriterReplacing`, each taking
34
- `copyingWriterStrategy` (default) or `asHandedWriterStrategy`.
35
- - **Columns.** `OIMColumnOwner` owns column slots on any aggregate, so an effect can wait on one
36
- column of one entity (`holdColumn`, `channel.effectOnColumn`).
37
- - **Buckets and indexes.** `OIMBucketCollection` holds slots the caller files;
38
- `OIMIndex` files an entity collection's slots by `keyOf`. How a bucket holds its slots is a fork:
39
- `OIMBucketSlotsServiceSetDriven` or `OIMBucketSlotsServiceArrayDriven`. Positional edits record
40
- a command script through `OIMBucketCommands`.
41
- - **Computeds.** A computed is a `TOIMComputedSlot` created and read only by its owner —
42
- `OIMSingleComputed` or `OIMComputedCollection` — over named sources. It is pulled: a read
43
- refreshes it against the channel clock. `OIMComputedCollectionSorted` is the shipped order over
44
- an index, re-sorted only when a member's sort column changes.
45
- - **Delivery.** `OIMChannel` coalesces a frame's writes and runs each `OIMEffect` once per frame
46
- over its root slots and source computeds; `subscribeAfterEachFrame`, `subscribeAfterEachFlush`
47
- and `subscribeOnceAfterFrame` run after it. Errors go through an `IOIMErrorPolicy`.
197
+ computed — and only its owner mutates it. `OIMSlotOwnerService` owns a collection's slots and
198
+ decides when an unheld one goes, through an injected `IOIMSlotReleasePolicy` (`AtEmpty` by
199
+ default, plus `AtUnhold`, `AfterUnhold`, `AfterWrite`, `AfterIdle`, `Never` and `Earliest`).
200
+ - **Entities.** `createOIMEntityService` for a keyed collection, `createOIMSingleEntityService` for
201
+ one record. The writer is a fork chosen at construction: `createOIMEntityWriterInPlace` or
202
+ `createOIMEntityWriterReplacing`, each with an insert strategy (`oimInsertEntityWithCopy`,
203
+ `oimInsertEntityWithoutCopy`, `oimInsertEntityWithSanitizedCopy`).
204
+ - **Columns.** `OIMColumnOwner` owns column slots on any slot, so an effect can wait on one
205
+ column of one entity (`holdColumn`, `holdColumnGroup`).
206
+ - **Buckets and indexes.** `createOIMBucketService` holds slots the caller files;
207
+ `createOIMIndexService` files an entity collection's slots by `keyOf`. How a bucket holds its slots
208
+ is a fork: `OIMSlotContentBucketServiceSetDriven`, `OIMSlotContentBucketServiceArrayDriven` or
209
+ `OIMSlotContentBucketServiceSortedArrayDriven`. Positional edits record a command script through
210
+ `OIMBucketCommands`.
211
+ - **Computeds.** A computed is a `TOIMComputedSlot` created and read only by its service —
212
+ `createOIMComputedService`, `createOIMComputedServiceSorted` or `createOIMComputedServiceBucketMemo` —
213
+ over named sources. It is pulled: a read refreshes it against the channel clock.
214
+ - **Delivery.** `OIMChannelService` coalesces a frame's writes and `OIMEffectService` runs each
215
+ effect once per frame over its root slots and source computeds; `subscribeAfterEachFrame`,
216
+ `subscribeAfterEachFlush` and `subscribeOnceAfterFrame` run after it. Errors go through an
217
+ `IOIMErrorPolicy`.
48
218
  - **Keys.** A composite key is a chain descended one segment at a time
49
- (`OIMSlotStoreServiceTreeDriven` with `OIMScalarKeyTreeWalk` or `OIMCompositeKeyTreeWalk`), so
219
+ (`OIMSlotStoreServiceTreeDriven` with `OIMKeyTreeWalkScalar` or `OIMKeyTreeWalkComposite`), so
50
220
  nothing is encoded.
51
221
 
52
222
  ### Removed from 3.x
@@ -74,10 +244,9 @@ published.
74
244
 
75
245
  ### Companion packages
76
246
 
77
- - `@oimdb/react`: `useOIMValue`, `useOIMEntity`, `useOIMField`, `useOIMBucketSlots`,
78
- `useOIMBucketSlotsByKey`, `useOIMSlotsByKeys`, with `OIMChannelProvider` / `useOIMChannel`.
79
- - `@oimdb/persist`: `OIMPersistor` and `OIMPersistResource` over `createBucketSourceAdapter`,
80
- `createCollectionSourceAdapter` and `createSingleEntitySourceAdapter`.
81
- - `@oimdb/exodra`: `exoBinding`, `exoSource`, `exoCombine`, `exoFollowKey`, `exoRows`,
247
+ - `@oimdb/react`: `OIMDBProvider` / `useOIMDB`, with `useOIMValue`, `useOIMEntity`, `useOIMField`,
248
+ `useOIMBucketSlots`, `useOIMBucketSlotsByKey`, `useOIMSlotsByKeys` and the computed hooks.
249
+ - `@oimdb/persist`: `OIMPersistor` with `OIMPersistResourceSnapshot` and `OIMPersistResourceRecords`.
250
+ - `@oimdb/exodra`: `exoBinding`, `exoSource`, `exoCombine`, `exoFollowKey`, `exoRows`, `exoList`,
82
251
  `exoDerivedList`, `exoPositionalList`.
83
252
  - `@oimdb/async`: deprecated outright, exports nothing.