@oimdb/core 4.0.1 → 4.1.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,136 @@
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.1.0
7
+
8
+ Breaking: exports removed and renamed, `IOIMSlotOwner` has new required members.
9
+
10
+ ### Added
11
+
12
+ - `IOIMBucketMemberSlotsArrayService`: the members of an array bucket. `OIMBucketMemberSlotsArrayService`
13
+ (default) and `OIMBucketUniqueMemberSlotsArrayService`. Option `bucketMemberSlotsArrayService` on both
14
+ array buckets (`TOIMSlotContentArrayBucketServiceOptions`, `TOIMSlotContentSortedArrayBucketServiceOptions`).
15
+ - `slotSubscriptionListener` option: `IOIMSlotSubscriptionListener` (`onSlotFirstSubscribed`,
16
+ `onSlotLastUnsubscribed`), default `OIMNoSlotSubscriptionListener`.
17
+ - `OIMSlotReleaseWheel.markSlotReleaseDueNow(slot)`.
18
+ - `slotReleaseDueFramePolicy` on `OIMSlotAfterWriteReleasePolicy`: `OIMSlotReleaseAutoDueFramePolicy` (default),
19
+ `OIMSlotReleaseManualDueFramePolicy` (`openSlotReleaseDueFrame`, `closeSlotReleaseDueFrame`,
20
+ `writeInSlotReleaseDueFrame`).
21
+ - `OIMSlotWheel`, `OIMSlotReleaseWheel`, `OIMSlotRefetchWheel` (`scheduleSlotRefetchAt`), `IOIMSlotRefetchListener`,
22
+ `TOIMSlotWheelOptions`, `TOIMSlotReleaseWheelOptions`, `TOIMSlotRefetchWheelOptions`.
23
+ - `oimMintAfterWriteSlotReleaseWheel`, `oimMintAfterIdleSlotReleaseWheel`, `oimMintAfterUnholdSlotReleaseWheel`.
24
+ - `IOIMSlotOwner.unsafeMutateSlot(slot, mutateSlot)`.
25
+ - `openBatch`, `closeBatch`, `writeInBatch` on `OIMSlotCollectionService`. An index gets the batch in one
26
+ `onContentChangedMany` when the outermost batch closes. A flush inside a batch is allowed.
27
+ - `OIMSlotContentBucketService.getBucketMemberSlotsMissingFrom(bucketSlot, bucketMemberSlots)`.
28
+ - `storeSlot.slotService`; `TOIMStoreSlot` has a fourth type parameter.
29
+ - `TOIMSlotContentServiceKey`, `TOIMSlotContentServiceSlot`, `TOIMSlotContentServiceSingleSlot`,
30
+ `TOIMSlotContentServiceContent`, `TOIMSlotContentServicePatch`.
31
+ - `IOIMSlotContentService`, `IOIMKeyedSlotCreator`, `IOIMSingleSlotCreator`, `IOIMSlotFilingService`.
32
+ - `TOIMEntityContentSlot`, `TOIMBucketContentSlot`, `TOIMComputedContentSlot`.
33
+ - `OIMWritableSlotCollectionService.writeSlotContentByKey`, `OIMWritableSingleSlotService.writeSingleSlotContent`
34
+ and `clearSingleSlotContent`.
35
+ - `OIMSingleComputedService`, `createOIMSingleComputedService`, `TOIMComputedDerivationOptions`.
36
+ - `IOIMFlushSchedulerListener`.
37
+ - `OIMColumnSlotService`, as `columnSlotService` on `OIMSlotCollectionService` and `OIMSingleSlotService`.
38
+ - `OIMSlotContentComputedService` and `TOIMSlotContentComputedServiceOptions` as types.
39
+
40
+ ### Changed
41
+
42
+ - The release queue is a timing wheel; a slot's place on it is a bit of `slot.slotFlags`.
43
+ - Release wheels on `db.collectorSlot` are created on first use.
44
+ - A single write files the slot, then tells the index. Nothing is rolled back if the index throws.
45
+ - Under a synchronous `channelScheduler` one write can run several frames.
46
+ - `releaseSlotContent` throws inside a flush when the slot has content.
47
+ - Single slots have the same shape as keyed ones (`key` and `indexKeys` are `undefined`).
48
+
49
+ ### Renamed
50
+
51
+ - `OIMSlotContentBucketServiceArrayBased` → `OIMSlotContentArrayBucketService`
52
+ - `OIMSlotContentBucketServiceArrayDriven` → `OIMSlotContentPositionalArrayBucketService`
53
+ - `OIMSlotContentBucketServiceSortedArrayDriven` → `OIMSlotContentSortedArrayBucketService`
54
+ - `OIMSlotContentBucketServiceSetDriven` → `OIMSlotContentSetBucketService`
55
+ - `TOIMSlotContentBucketServiceSortedArrayDrivenOptions` → `TOIMSlotContentSortedArrayBucketServiceOptions`
56
+ - `OIMSlotReleasePolicyAfterWrite` → `OIMSlotAfterWriteReleasePolicy`
57
+ - `OIMSlotReleasePolicyAfterIdle` → `OIMSlotAfterIdleReleasePolicy`
58
+ - `OIMSlotReleasePolicyAfterUnhold` → `OIMSlotAfterUnholdReleasePolicy`
59
+ - `OIMSlotReleasePolicyAtEmpty` → `OIMSlotAtEmptyReleasePolicy`
60
+ - `OIMSlotReleasePolicyAtUnhold` → `OIMSlotAtUnholdReleasePolicy`
61
+ - `OIMSlotReleasePolicyEarliest` → `OIMSlotEarliestReleasePolicy`
62
+ - `OIMSlotReleasePolicyNever` → `OIMSlotNeverReleasePolicy`
63
+ - `TOIMSlotReleasePolicyAfterWriteOptions` → `TOIMSlotAfterWriteReleasePolicyOptions`
64
+ - `TOIMSlotReleasePolicyAfterIdleOptions` → `TOIMSlotAfterIdleReleasePolicyOptions`
65
+ - `TOIMSlotReleasePolicyAfterUnholdOptions` → `TOIMSlotAfterUnholdReleasePolicyOptions`
66
+ - `OIMErrorPolicyThrowAtOnce` → `OIMThrowAtOnceErrorPolicy`
67
+ - `OIMErrorPolicyLogAndContinue` → `OIMLogAndContinueErrorPolicy`
68
+ - `TOIMErrorPolicyLogAndContinueOptions` → `TOIMLogAndContinueErrorPolicyOptions`
69
+ - `OIMSlotStoreServiceMapDriven` → `OIMSlotMapStoreService`
70
+ - `OIMSlotStoreServiceTreeDriven` → `OIMSlotTreeStoreService`
71
+ - `OIMSlotStoreServiceSingleSlotDriven` → `OIMSingleSlotStoreService`
72
+ - `OIMIndexKeysServiceAppending` → `OIMAppendingIndexKeysService`
73
+ - `OIMIndexKeysServiceReclaiming` → `OIMReclaimingIndexKeysService`
74
+ - `OIMColumnOwnerPushDriven` → `OIMPushColumnSlotOwner`
75
+ - `OIMColumnOwnerPullDriven` → `OIMPullColumnSlotOwner`
76
+ - `OIMColumnOwner` → `OIMColumnSlotOwner`
77
+ - `TOIMColumnOwnerOptions` → `TOIMColumnSlotOwnerOptions`
78
+ - `OIMComputedServiceSorted` → `OIMSortedComputedService`
79
+ - `OIMComputedServiceBucketMemo` → `OIMBucketMemoComputedService`
80
+ - `TOIMComputedServiceSortedOptions` → `TOIMSortedComputedServiceOptions`
81
+ - `TOIMComputedServiceBucketMemoOptions` → `TOIMBucketMemoComputedServiceOptions`
82
+ - `createOIMComputedServiceSorted` → `createOIMSortedComputedService`
83
+ - `createOIMComputedServiceBucketMemo` → `createOIMBucketMemoComputedService`
84
+ - `OIMKeyTreeWalkComposite` → `OIMCompositeKeyTreeWalk`
85
+ - `OIMKeyTreeWalkScalar` → `OIMScalarKeyTreeWalk`
86
+ - `TOIMEntityInsertStrategy` → `TOIMEntityInserter`
87
+ - `OIMStoreSlotListenerNone` → `OIMNoStoreSlotListener`
88
+ - `IOIMSlotEmptiness` → `IOIMSlotEmptinessPolicy`
89
+ - `OIMIndexService` → `OIMSlotCollectionIndexService`
90
+ - `createOIMIndexService` → `createOIMSlotCollectionIndexService`
91
+ - `TOIMIndexServiceFactoryOptions` → `TOIMSlotCollectionIndexServiceFactoryOptions`
92
+ - `TOIMIndexServiceOptions` → `TOIMSlotCollectionIndexServiceOptions`
93
+ - `TOIMIndexServiceStoreSlot` → `TOIMSlotCollectionIndexServiceStoreSlot`
94
+ - `OIMIndexServiceSortedArrayDriven` → `OIMSlotCollectionSortedArrayIndexService`
95
+ - `createOIMIndexServiceSortedArrayDriven` → `createOIMSlotCollectionSortedArrayIndexService`
96
+
97
+ ### Removed
98
+
99
+ - `createOIMEntityService`, `createOIMSingleEntityService`, `createOIMBucketService`,
100
+ `createOIMSingleBucketService`, `createOIMIndexServiceByCompositeKey`, `TOIMBucketCollectionFactoryArguments`,
101
+ `TOIMSlotContentEntityServiceFactoryOptions`. Use `createOIMSlotCollectionService(db, { slotContentService })`
102
+ or `createOIMSingleSlotService(db, { slotContentService })`; an array key needs `slotStoreService`.
103
+ - `IOIMSlotContentStrategy`, `IOIMSlotContentFlushStrategy`. Use `IOIMSlotContentService`.
104
+ - `OIMSlotColumnService`, and the column doors on the collection and single services. Use their `columnSlotService` (`OIMColumnSlotService`): `getColumn`, `holdColumn`, `getAnyColumn`, `holdAnyColumn`, `getColumnGroup`, `holdColumnGroup`, `unholdColumn`.
105
+ - `TOIMBucketSlotsSortedArrayStore`, `TOIMBucketSlotsArrayUniqueStore`. Use `TOIMBucketSlotsArrayStore`.
106
+ - `OIMReleaseSlotCollectorService`, `OIMReleaseSlotCollectorServiceAfterWrite`,
107
+ `OIMReleaseSlotCollectorServiceAfterIdle`, `OIMReleaseSlotCollectorServiceAfterUnhold`,
108
+ `OIMReleaseSlotQueueService`, `TOIMReleaseSlotCollectorSlot`, `createOIMReleaseSlotCollectorSlot`, and the
109
+ `…ReleaseSlotCollectorSlot` fields of `TOIMCollectorSlot`. Use the release wheels.
110
+ - `IOIMBucketArrayMembership`, `OIMBucketArrayMembershipNonUnique`, `OIMBucketArrayMembershipUnique`, option
111
+ `bucketArrayMembership`. Use `bucketMemberSlotsArrayService`.
112
+ - `upsertEntities`, `insertEntities`, `fillEntities`, `clearAllEntities`, `deleteEntities` and their errors.
113
+ Loop single writes inside `writeInBatch`.
114
+ - Subframes: `openSubframe`, `closeSubframe`, `isSubframeOpen`, `listChangedStoreSlot`,
115
+ `IOIMSubframeCloseListener` and their fields. Use a batch.
116
+ - `fillSlotContent` on `IOIMSlotContentWriter` and the content services.
117
+
118
+ ## 4.0.1
119
+
120
+ Speed, with no change to the API.
121
+
122
+ - `OIMSlotOwnerService.isAnyColumnReferenced` looks only at the slot's own column slots.
123
+ - `OIMColumnOwner.mintColumnGroupSlot` skips rebuilding the key of a group already registered by the
124
+ same object.
125
+ - `oimMergeRootSlots` drops duplicate roots with a linear scan up to 16 roots and a `Set` above.
126
+ - `OIMIndexService.updateIndexKeysForSlots` groups only under buckets it minted.
127
+ - `OIMSlotContentEntityService.fillEachEntity` detects a repeated key by the store's size when the
128
+ store started empty.
129
+
130
+ ## 4.0.0
7
131
 
8
132
  A ground-up rewrite, not an incremental version: **nothing from the 3.x public API survives
9
133
  unchanged.** There is no port table. The exported surface is `src/index.ts`, enumerated in the
10
134
  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.
135
+ is rather than as a diff.
13
136
 
14
137
  ### The two changes everything else follows from
15
138
 
@@ -17,36 +140,36 @@ published.
17
140
  key to a slot once (`getSlotByKey`, `holdSlotByKey`) and works through that slot afterwards.
18
141
  `updateEntity` takes a slot; `updateEntityByKey` / `deleteEntityByKey` say the lookup in their
19
142
  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
143
+ - **A god-object runtime → stateless services over slots.** Writes and reads are methods of the
144
+ service that owns the slot; delivery is `OIMChannelService`'s; `OIMDB` is a root that builds
22
145
  collections with its defaults and drives `flush()`.
23
146
 
24
147
  ### What the engine is made of
25
148
 
26
149
  - **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`.
150
+ computed — and only its owner mutates it. `OIMSlotOwnerService` owns a collection's slots and
151
+ decides when an unheld one goes, through an injected `IOIMSlotReleasePolicy` (`AtEmpty` by
152
+ default, plus `AtUnhold`, `AfterUnhold`, `AfterWrite`, `AfterIdle`, `Never` and `Earliest`).
153
+ - **Entities.** `createOIMEntityService` for a keyed collection, `createOIMSingleEntityService` for
154
+ one record. The writer is a fork chosen at construction: `createOIMEntityWriterInPlace` or
155
+ `createOIMEntityWriterReplacing`, each with an insert strategy (`oimInsertEntityWithCopy`,
156
+ `oimInsertEntityWithoutCopy`, `oimInsertEntityWithSanitizedCopy`).
157
+ - **Columns.** `OIMColumnOwner` owns column slots on any slot, so an effect can wait on one
158
+ column of one entity (`holdColumn`, `holdColumnGroup`).
159
+ - **Buckets and indexes.** `createOIMBucketService` holds slots the caller files;
160
+ `createOIMIndexService` files an entity collection's slots by `keyOf`. How a bucket holds its slots
161
+ is a fork: `OIMSlotContentBucketServiceSetDriven`, `OIMSlotContentBucketServiceArrayDriven` or
162
+ `OIMSlotContentBucketServiceSortedArrayDriven`. Positional edits record a command script through
163
+ `OIMBucketCommands`.
164
+ - **Computeds.** A computed is a `TOIMComputedSlot` created and read only by its service —
165
+ `createOIMComputedService`, `createOIMComputedServiceSorted` or `createOIMComputedServiceBucketMemo` —
166
+ over named sources. It is pulled: a read refreshes it against the channel clock.
167
+ - **Delivery.** `OIMChannelService` coalesces a frame's writes and `OIMEffectService` runs each
168
+ effect once per frame over its root slots and source computeds; `subscribeAfterEachFrame`,
169
+ `subscribeAfterEachFlush` and `subscribeOnceAfterFrame` run after it. Errors go through an
170
+ `IOIMErrorPolicy`.
48
171
  - **Keys.** A composite key is a chain descended one segment at a time
49
- (`OIMSlotStoreServiceTreeDriven` with `OIMScalarKeyTreeWalk` or `OIMCompositeKeyTreeWalk`), so
172
+ (`OIMSlotStoreServiceTreeDriven` with `OIMKeyTreeWalkScalar` or `OIMKeyTreeWalkComposite`), so
50
173
  nothing is encoded.
51
174
 
52
175
  ### Removed from 3.x
@@ -74,10 +197,9 @@ published.
74
197
 
75
198
  ### Companion packages
76
199
 
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`,
200
+ - `@oimdb/react`: `OIMDBProvider` / `useOIMDB`, with `useOIMValue`, `useOIMEntity`, `useOIMField`,
201
+ `useOIMBucketSlots`, `useOIMBucketSlotsByKey`, `useOIMSlotsByKeys` and the computed hooks.
202
+ - `@oimdb/persist`: `OIMPersistor` with `OIMPersistResourceSnapshot` and `OIMPersistResourceRecords`.
203
+ - `@oimdb/exodra`: `exoBinding`, `exoSource`, `exoCombine`, `exoFollowKey`, `exoRows`, `exoList`,
82
204
  `exoDerivedList`, `exoPositionalList`.
83
205
  - `@oimdb/async`: deprecated outright, exports nothing.