@smthrs/notifications 1.0.0-rc.7 → 1.0.0-rc.9
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/README.md +3 -1
- package/dist/cjs/NotificationQueue.d.ts +2 -1
- package/dist/cjs/NotificationQueue.d.ts.map +1 -1
- package/dist/cjs/NotificationQueue.js +9 -10
- package/dist/cjs/NotificationQueue.js.map +2 -2
- package/dist/cjs/Projection.d.ts +4 -1
- package/dist/cjs/Projection.d.ts.map +1 -1
- package/dist/cjs/Projection.js +2 -3
- package/dist/cjs/Projection.js.map +2 -2
- package/dist/cjs/internal/replay.d.ts +22 -0
- package/dist/cjs/internal/replay.d.ts.map +1 -0
- package/dist/cjs/internal/replay.js +46 -0
- package/dist/cjs/internal/replay.js.map +7 -0
- package/dist/esm/NotificationQueue.d.ts +2 -1
- package/dist/esm/NotificationQueue.d.ts.map +1 -1
- package/dist/esm/NotificationQueue.js +11 -12
- package/dist/esm/NotificationQueue.js.map +1 -1
- package/dist/esm/Projection.d.ts +4 -1
- package/dist/esm/Projection.d.ts.map +1 -1
- package/dist/esm/Projection.js +6 -2
- package/dist/esm/Projection.js.map +1 -1
- package/dist/esm/internal/replay.d.ts +22 -0
- package/dist/esm/internal/replay.d.ts.map +1 -0
- package/dist/esm/internal/replay.js +31 -0
- package/dist/esm/internal/replay.js.map +1 -0
- package/docs/README.md +3 -1
- package/docs/api.md +12 -8
- package/docs/installation.md +5 -1
- package/docs/quickstart.md +1 -1
- package/package.json +5 -5
- package/src/NotificationQueue.ts +15 -16
- package/src/Projection.ts +6 -4
- package/src/internal/replay.ts +39 -0
package/src/Projection.ts
CHANGED
|
@@ -7,6 +7,7 @@
|
|
|
7
7
|
import { Projection as JournalProjection } from "@smthrs/journal"
|
|
8
8
|
import * as Effect from "effect/Effect"
|
|
9
9
|
import * as Option from "effect/Option"
|
|
10
|
+
import * as Replay from "./internal/replay.ts"
|
|
10
11
|
import * as NotificationEvent from "./NotificationEvent.ts"
|
|
11
12
|
import * as NotificationState from "./NotificationState.ts"
|
|
12
13
|
|
|
@@ -18,7 +19,10 @@ import * as NotificationState from "./NotificationState.ts"
|
|
|
18
19
|
* `NotificationState.applyAdmission` applies the decision each record already
|
|
19
20
|
* committed, and an admitted record is retained however many are pending. A
|
|
20
21
|
* composition built with `NotificationQueue.layerWith` above the default
|
|
21
|
-
* replays every admission it wrote.
|
|
22
|
+
* replays every admission it wrote. A versioned edit of a steer that is still
|
|
23
|
+
* pending replaces that item in place, exactly as the queue's own fold reads
|
|
24
|
+
* it, so an edited steer projects as one pending item rather than one per
|
|
25
|
+
* version.
|
|
22
26
|
*
|
|
23
27
|
* The projected `capacity` is `NotificationState.defaultCapacity` because the
|
|
24
28
|
* initial state has to start somewhere and no journal record carries the bound
|
|
@@ -37,9 +41,7 @@ export const derive = JournalProjection.make({
|
|
|
37
41
|
|
|
38
42
|
const event = decoded.value
|
|
39
43
|
if (NotificationEvent.isAdmitted(event)) {
|
|
40
|
-
return Effect.succeed(
|
|
41
|
-
NotificationState.applyAdmission(state, event.notification, entry.seq, event.decision)
|
|
42
|
-
)
|
|
44
|
+
return Effect.succeed(Replay.applyAdmitted(state, event, entry.seq))
|
|
43
45
|
}
|
|
44
46
|
return Effect.succeed(NotificationState.applyPromoted(state, event.ids))
|
|
45
47
|
}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The one replay rule for an admission record, shared by the queue's fold and
|
|
3
|
+
* the journal projection so the two read the same history to the same state.
|
|
4
|
+
*
|
|
5
|
+
* @private
|
|
6
|
+
* @since 1.0.0
|
|
7
|
+
*/
|
|
8
|
+
|
|
9
|
+
import type * as NotificationEvent from "../NotificationEvent.ts"
|
|
10
|
+
import * as NotificationState from "../NotificationState.ts"
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* Applies one committed admission record to the state so far.
|
|
14
|
+
*
|
|
15
|
+
* A versioned record whose id is still pending is an edit: it replaces that
|
|
16
|
+
* item in place and keeps its original sequence, so the edit is delivered at
|
|
17
|
+
* the cutoff the first version was admitted under. Every other record applies
|
|
18
|
+
* the decision it committed.
|
|
19
|
+
*
|
|
20
|
+
* @private
|
|
21
|
+
* @since 1.0.0
|
|
22
|
+
*/
|
|
23
|
+
export const applyAdmitted = (
|
|
24
|
+
state: NotificationState.State,
|
|
25
|
+
event: NotificationEvent.Admitted,
|
|
26
|
+
seq: number
|
|
27
|
+
): NotificationState.State => {
|
|
28
|
+
if (event.version !== undefined && state.items.some((item) => item.notification.id === event.notification.id)) {
|
|
29
|
+
return Object.freeze({
|
|
30
|
+
...state,
|
|
31
|
+
items: Object.freeze(state.items.map((item) =>
|
|
32
|
+
item.notification.id === event.notification.id
|
|
33
|
+
? Object.freeze({ notification: event.notification, seq: item.seq })
|
|
34
|
+
: item
|
|
35
|
+
))
|
|
36
|
+
})
|
|
37
|
+
}
|
|
38
|
+
return NotificationState.applyAdmission(state, event.notification, seq, event.decision)
|
|
39
|
+
}
|