@polymorfa/store 0.1.0-dev.20260922094209
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 +21 -0
- package/README.md +326 -0
- package/dist/backend.d.ts +89 -0
- package/dist/backend.d.ts.map +1 -0
- package/dist/backend.js +341 -0
- package/dist/backend.js.map +1 -0
- package/dist/conversation-source.d.ts +28 -0
- package/dist/conversation-source.d.ts.map +1 -0
- package/dist/conversation-source.js +160 -0
- package/dist/conversation-source.js.map +1 -0
- package/dist/inbox-source.d.ts +19 -0
- package/dist/inbox-source.d.ts.map +1 -0
- package/dist/inbox-source.js +90 -0
- package/dist/inbox-source.js.map +1 -0
- package/dist/index.d.ts +7 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +7 -0
- package/dist/index.js.map +1 -0
- package/dist/react.d.ts +13 -0
- package/dist/react.d.ts.map +1 -0
- package/dist/react.js +45 -0
- package/dist/react.js.map +1 -0
- package/dist/reducers.d.ts +48 -0
- package/dist/reducers.d.ts.map +1 -0
- package/dist/reducers.js +821 -0
- package/dist/reducers.js.map +1 -0
- package/dist/sources.d.ts +170 -0
- package/dist/sources.d.ts.map +1 -0
- package/dist/sources.js +510 -0
- package/dist/sources.js.map +1 -0
- package/dist/store.d.ts +168 -0
- package/dist/store.d.ts.map +1 -0
- package/dist/store.js +619 -0
- package/dist/store.js.map +1 -0
- package/dist/types.d.ts +212 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +13 -0
- package/dist/types.js.map +1 -0
- package/package.json +54 -0
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import { createStoreConversationSource } from "./conversation-source.js";
|
|
2
|
+
/**
|
|
3
|
+
* An `<Inbox/>` source that renders from the local store first, fills gaps
|
|
4
|
+
* from your backend and follows store changes, so the list and open
|
|
5
|
+
* conversations update as events are ingested.
|
|
6
|
+
*/
|
|
7
|
+
export function createStoreInboxSource(store, options) {
|
|
8
|
+
const { backend } = options;
|
|
9
|
+
const limit = options.limit ?? 200;
|
|
10
|
+
return {
|
|
11
|
+
async listConversations(cursor, signal) {
|
|
12
|
+
if (cursor !== undefined)
|
|
13
|
+
return backend.listConversations(cursor, signal);
|
|
14
|
+
const rows = (await store.conversations.list({ limit })).filter((row) => row.deleted !== true);
|
|
15
|
+
if (rows.length === 0)
|
|
16
|
+
return backend.listConversations(undefined, signal);
|
|
17
|
+
const contacts = await Promise.all(rows.map((row) => store.contacts.get(row.id)));
|
|
18
|
+
return {
|
|
19
|
+
conversations: rows.map((row, index) => toInboxConversation(row, contacts[index])),
|
|
20
|
+
};
|
|
21
|
+
},
|
|
22
|
+
conversation(conversation) {
|
|
23
|
+
const remote = backend.conversation(conversation);
|
|
24
|
+
return createStoreConversationSource(store, {
|
|
25
|
+
conversationId: conversation.id,
|
|
26
|
+
load: (cursor, signal) => remote.load(cursor, signal),
|
|
27
|
+
send: (message, signal) => remote.send(message, signal),
|
|
28
|
+
...(conversation.session === undefined
|
|
29
|
+
? {}
|
|
30
|
+
: { session: conversation.session }),
|
|
31
|
+
...(options.onError === undefined ? {} : { onError: options.onError }),
|
|
32
|
+
});
|
|
33
|
+
},
|
|
34
|
+
...(backend.contact === undefined
|
|
35
|
+
? {}
|
|
36
|
+
: {
|
|
37
|
+
contact: (conversation, signal) => backend.contact(conversation, signal),
|
|
38
|
+
}),
|
|
39
|
+
subscribe(listener) {
|
|
40
|
+
return store.subscribe("conversations", (change) => {
|
|
41
|
+
for (const id of change.deleted)
|
|
42
|
+
listener({ type: "remove", conversationId: id });
|
|
43
|
+
if (change.keys.length === 0)
|
|
44
|
+
return;
|
|
45
|
+
void Promise.all(change.keys.map(async (id) => {
|
|
46
|
+
const [row, contact] = await Promise.all([
|
|
47
|
+
store.conversations.get(id),
|
|
48
|
+
store.contacts.get(id),
|
|
49
|
+
]);
|
|
50
|
+
if (row === undefined || row.deleted === true)
|
|
51
|
+
return;
|
|
52
|
+
listener({
|
|
53
|
+
type: "conversation",
|
|
54
|
+
conversation: toInboxConversation(row, contact),
|
|
55
|
+
});
|
|
56
|
+
})).catch((error) => options.onError?.(error));
|
|
57
|
+
});
|
|
58
|
+
},
|
|
59
|
+
close() {
|
|
60
|
+
backend.close?.();
|
|
61
|
+
},
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
function toInboxConversation(row, contact) {
|
|
65
|
+
const name = row.name ??
|
|
66
|
+
contact?.fullName ??
|
|
67
|
+
contact?.businessName ??
|
|
68
|
+
contact?.pushName ??
|
|
69
|
+
undefined;
|
|
70
|
+
return {
|
|
71
|
+
id: row.id,
|
|
72
|
+
...(row.session === undefined ? {} : { session: row.session }),
|
|
73
|
+
...(name === undefined ? {} : { name }),
|
|
74
|
+
...(contact?.phoneNumber === undefined
|
|
75
|
+
? {}
|
|
76
|
+
: { phoneNumber: contact.phoneNumber }),
|
|
77
|
+
...(row.lastMessage === undefined
|
|
78
|
+
? {}
|
|
79
|
+
: {
|
|
80
|
+
lastMessage: {
|
|
81
|
+
text: row.lastMessage.text,
|
|
82
|
+
createdAt: row.lastMessage.createdAt,
|
|
83
|
+
direction: row.lastMessage.fromMe ? "outbound" : "inbound",
|
|
84
|
+
},
|
|
85
|
+
}),
|
|
86
|
+
lastActivity: row.lastActivity,
|
|
87
|
+
unreadCount: row.unreadCount,
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
//# sourceMappingURL=inbox-source.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"inbox-source.js","sourceRoot":"","sources":["../src/inbox-source.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
export { DATA_STORE_NAMES, type Checkpoint, type ConversationReferenceView, type ConversationSummaryMessage, type DataStoreName, type IdentityReferenceView, type PolymorfaEvent, type StoreChange, type StoreChangeListener, type StoreName, type StoreRowMap, type StoredAttachment, type StoredCall, type StoredCallParticipant, type StoredCallState, type StoredContact, type StoredConversation, type StoredEvent, type StoredLabel, type StoredMessage, type StoredMessageStatus, type StoredPresence, type StoredRow, type StoredSession, type StoredTemplate, } from "./types.js";
|
|
2
|
+
export { DEFAULT_RETENTION, SENSITIVE_FIELDS, createPolymorfaStore, type BroadcastChannelLike, type EventListQuery, type IngestResult, type ListOptions, type MessageInput, type MessageListQuery, type PolymorfaStore, type PolymorfaStoreOptions, type RedactRule, type RetentionOptions, type RetentionRule, type SealContext, type StoreMode, type StoreReader, type StoreUsage, } from "./store.js";
|
|
3
|
+
export { BUILT_IN_REDUCERS, type ReducerContext, type StoreReducer, } from "./reducers.js";
|
|
4
|
+
export { DEFAULT_SSE_EVENT_TYPES, DEFAULT_SSE_MAX_LINE_LENGTH, MIN_EVENT_STREAM_RETRY_MS, SseParser, connectEventSource, eventsFromFrame, fromEventSource, fromEventStream, fromIterable, fromWebSocket, readProjectStreamFrame, type ConnectEventSourceOptions, type EventSourceConnection, type EventSourceLike, type FromEventSourceOptions, type FromEventStreamOptions, type IterableEventSource, type LiveEventListener, type LiveEventMeta, type LiveEventSource, type LiveEventSubscribeOptions, type ProjectStreamFrame, type SseFrame, type WebSocketLike, } from "./sources.js";
|
|
5
|
+
export { createStoreConversationSource, toConversationMessage, type StoreConversationSourceOptions, } from "./conversation-source.js";
|
|
6
|
+
export { createStoreInboxSource, type StoreInboxSourceOptions, } from "./inbox-source.js";
|
|
7
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,gBAAgB,EAChB,KAAK,UAAU,EACf,KAAK,yBAAyB,EAC9B,KAAK,0BAA0B,EAC/B,KAAK,aAAa,EAClB,KAAK,qBAAqB,EAC1B,KAAK,cAAc,EACnB,KAAK,WAAW,EAChB,KAAK,mBAAmB,EACxB,KAAK,SAAS,EACd,KAAK,WAAW,EAChB,KAAK,gBAAgB,EACrB,KAAK,UAAU,EACf,KAAK,qBAAqB,EAC1B,KAAK,eAAe,EACpB,KAAK,aAAa,EAClB,KAAK,kBAAkB,EACvB,KAAK,WAAW,EAChB,KAAK,WAAW,EAChB,KAAK,aAAa,EAClB,KAAK,mBAAmB,EACxB,KAAK,cAAc,EACnB,KAAK,SAAS,EACd,KAAK,aAAa,EAClB,KAAK,cAAc,GACpB,MAAM,YAAY,CAAC;AACpB,OAAO,EACL,iBAAiB,EACjB,gBAAgB,EAChB,oBAAoB,EACpB,KAAK,oBAAoB,EACzB,KAAK,cAAc,EACnB,KAAK,YAAY,EACjB,KAAK,WAAW,EAChB,KAAK,YAAY,EACjB,KAAK,gBAAgB,EACrB,KAAK,cAAc,EACnB,KAAK,qBAAqB,EAC1B,KAAK,UAAU,EACf,KAAK,gBAAgB,EACrB,KAAK,aAAa,EAClB,KAAK,WAAW,EAChB,KAAK,SAAS,EACd,KAAK,WAAW,EAChB,KAAK,UAAU,GAChB,MAAM,YAAY,CAAC;AACpB,OAAO,EACL,iBAAiB,EACjB,KAAK,cAAc,EACnB,KAAK,YAAY,GAClB,MAAM,eAAe,CAAC;AACvB,OAAO,EACL,uBAAuB,EACvB,2BAA2B,EAC3B,yBAAyB,EACzB,SAAS,EACT,kBAAkB,EAClB,eAAe,EACf,eAAe,EACf,eAAe,EACf,YAAY,EACZ,aAAa,EACb,sBAAsB,EACtB,KAAK,yBAAyB,EAC9B,KAAK,qBAAqB,EAC1B,KAAK,eAAe,EACpB,KAAK,sBAAsB,EAC3B,KAAK,sBAAsB,EAC3B,KAAK,mBAAmB,EACxB,KAAK,iBAAiB,EACtB,KAAK,aAAa,EAClB,KAAK,eAAe,EACpB,KAAK,yBAAyB,EAC9B,KAAK,kBAAkB,EACvB,KAAK,QAAQ,EACb,KAAK,aAAa,GACnB,MAAM,cAAc,CAAC;AACtB,OAAO,EACL,6BAA6B,EAC7B,qBAAqB,EACrB,KAAK,8BAA8B,GACpC,MAAM,0BAA0B,CAAC;AAClC,OAAO,EACL,sBAAsB,EACtB,KAAK,uBAAuB,GAC7B,MAAM,mBAAmB,CAAC"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
export { DATA_STORE_NAMES, } from "./types.js";
|
|
2
|
+
export { DEFAULT_RETENTION, SENSITIVE_FIELDS, createPolymorfaStore, } from "./store.js";
|
|
3
|
+
export { BUILT_IN_REDUCERS, } from "./reducers.js";
|
|
4
|
+
export { DEFAULT_SSE_EVENT_TYPES, DEFAULT_SSE_MAX_LINE_LENGTH, MIN_EVENT_STREAM_RETRY_MS, SseParser, connectEventSource, eventsFromFrame, fromEventSource, fromEventStream, fromIterable, fromWebSocket, readProjectStreamFrame, } from "./sources.js";
|
|
5
|
+
export { createStoreConversationSource, toConversationMessage, } from "./conversation-source.js";
|
|
6
|
+
export { createStoreInboxSource, } from "./inbox-source.js";
|
|
7
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,gBAAgB,GAyBjB,MAAM,YAAY,CAAC;AACpB,OAAO,EACL,iBAAiB,EACjB,gBAAgB,EAChB,oBAAoB,GAgBrB,MAAM,YAAY,CAAC;AACpB,OAAO,EACL,iBAAiB,GAGlB,MAAM,eAAe,CAAC;AACvB,OAAO,EACL,uBAAuB,EACvB,2BAA2B,EAC3B,yBAAyB,EACzB,SAAS,EACT,kBAAkB,EAClB,eAAe,EACf,eAAe,EACf,eAAe,EACf,YAAY,EACZ,aAAa,EACb,sBAAsB,GAcvB,MAAM,cAAc,CAAC;AACtB,OAAO,EACL,6BAA6B,EAC7B,qBAAqB,GAEtB,MAAM,0BAA0B,CAAC;AAClC,OAAO,EACL,sBAAsB,GAEvB,MAAM,mBAAmB,CAAC"}
|
package/dist/react.d.ts
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { PolymorfaStore } from "./store.js";
|
|
2
|
+
import type { DataStoreName } from "./types.js";
|
|
3
|
+
export interface PolymorfaStoreQueryState<T> {
|
|
4
|
+
readonly data: T | undefined;
|
|
5
|
+
readonly error: unknown;
|
|
6
|
+
readonly loading: boolean;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Runs `query` and runs it again whenever one of `stores` changes, in this
|
|
10
|
+
* tab or another. Pass a stable `key` that identifies the query inputs.
|
|
11
|
+
*/
|
|
12
|
+
export declare function usePolymorfaStoreQuery<T>(store: PolymorfaStore | undefined, stores: DataStoreName | readonly DataStoreName[], query: (store: PolymorfaStore) => Promise<T>, key?: string): PolymorfaStoreQueryState<T>;
|
|
13
|
+
//# sourceMappingURL=react.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"react.d.ts","sourceRoot":"","sources":["../src/react.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AACjD,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,YAAY,CAAC;AAEhD,MAAM,WAAW,wBAAwB,CAAC,CAAC;IACzC,QAAQ,CAAC,IAAI,EAAE,CAAC,GAAG,SAAS,CAAC;IAC7B,QAAQ,CAAC,KAAK,EAAE,OAAO,CAAC;IACxB,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC;CAC3B;AAED;;;GAGG;AACH,wBAAgB,sBAAsB,CAAC,CAAC,EACtC,KAAK,EAAE,cAAc,GAAG,SAAS,EACjC,MAAM,EAAE,aAAa,GAAG,SAAS,aAAa,EAAE,EAChD,KAAK,EAAE,CAAC,KAAK,EAAE,cAAc,KAAK,OAAO,CAAC,CAAC,CAAC,EAC5C,GAAG,GAAE,MAAW,GACf,wBAAwB,CAAC,CAAC,CAAC,CA0C7B"}
|
package/dist/react.js
ADDED
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
import { useEffect, useRef, useState } from "react";
|
|
2
|
+
/**
|
|
3
|
+
* Runs `query` and runs it again whenever one of `stores` changes, in this
|
|
4
|
+
* tab or another. Pass a stable `key` that identifies the query inputs.
|
|
5
|
+
*/
|
|
6
|
+
export function usePolymorfaStoreQuery(store, stores, query, key = "") {
|
|
7
|
+
const [state, setState] = useState({
|
|
8
|
+
data: undefined,
|
|
9
|
+
error: undefined,
|
|
10
|
+
loading: store !== undefined,
|
|
11
|
+
});
|
|
12
|
+
const latestQuery = useRef(query);
|
|
13
|
+
latestQuery.current = query;
|
|
14
|
+
const names = (typeof stores === "string" ? [stores] : stores).join(",");
|
|
15
|
+
useEffect(() => {
|
|
16
|
+
if (store === undefined) {
|
|
17
|
+
setState({ data: undefined, error: undefined, loading: false });
|
|
18
|
+
return;
|
|
19
|
+
}
|
|
20
|
+
let active = true;
|
|
21
|
+
let generation = 0;
|
|
22
|
+
const run = () => {
|
|
23
|
+
const current = (generation += 1);
|
|
24
|
+
setState((previous) => ({ ...previous, loading: true }));
|
|
25
|
+
latestQuery.current(store).then((data) => {
|
|
26
|
+
if (active && current === generation)
|
|
27
|
+
setState({ data, error: undefined, loading: false });
|
|
28
|
+
}, (error) => {
|
|
29
|
+
if (active && current === generation)
|
|
30
|
+
setState((previous) => ({ ...previous, error, loading: false }));
|
|
31
|
+
});
|
|
32
|
+
};
|
|
33
|
+
run();
|
|
34
|
+
const unsubscribes = names
|
|
35
|
+
.split(",")
|
|
36
|
+
.map((name) => store.subscribe(name, run));
|
|
37
|
+
return () => {
|
|
38
|
+
active = false;
|
|
39
|
+
for (const unsubscribe of unsubscribes)
|
|
40
|
+
unsubscribe();
|
|
41
|
+
};
|
|
42
|
+
}, [store, names, key]);
|
|
43
|
+
return state;
|
|
44
|
+
}
|
|
45
|
+
//# sourceMappingURL=react.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"react.js","sourceRoot":"","sources":["../src/react.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAC;AAWpD;;;GAGG;AACH,MAAM,UAAU,sBAAsB,CACpC,KAAiC,EACjC,MAAgD,EAChD,KAA4C,EAC5C,MAAc,EAAE;IAEhB,MAAM,CAAC,KAAK,EAAE,QAAQ,CAAC,GAAG,QAAQ,CAA8B;QAC9D,IAAI,EAAE,SAAS;QACf,KAAK,EAAE,SAAS;QAChB,OAAO,EAAE,KAAK,KAAK,SAAS;KAC7B,CAAC,CAAC;IACH,MAAM,WAAW,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC;IAClC,WAAW,CAAC,OAAO,GAAG,KAAK,CAAC;IAC5B,MAAM,KAAK,GAAG,CAAC,OAAO,MAAM,KAAK,QAAQ,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IAEzE,SAAS,CAAC,GAAG,EAAE;QACb,IAAI,KAAK,KAAK,SAAS,EAAE,CAAC;YACxB,QAAQ,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,KAAK,EAAE,SAAS,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC,CAAC;YAChE,OAAO;QACT,CAAC;QACD,IAAI,MAAM,GAAG,IAAI,CAAC;QAClB,IAAI,UAAU,GAAG,CAAC,CAAC;QACnB,MAAM,GAAG,GAAG,GAAG,EAAE;YACf,MAAM,OAAO,GAAG,CAAC,UAAU,IAAI,CAAC,CAAC,CAAC;YAClC,QAAQ,CAAC,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC,EAAE,GAAG,QAAQ,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC;YACzD,WAAW,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,IAAI,CAC7B,CAAC,IAAI,EAAE,EAAE;gBACP,IAAI,MAAM,IAAI,OAAO,KAAK,UAAU;oBAClC,QAAQ,CAAC,EAAE,IAAI,EAAE,KAAK,EAAE,SAAS,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC,CAAC;YACzD,CAAC,EACD,CAAC,KAAc,EAAE,EAAE;gBACjB,IAAI,MAAM,IAAI,OAAO,KAAK,UAAU;oBAClC,QAAQ,CAAC,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC,EAAE,GAAG,QAAQ,EAAE,KAAK,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC;YACrE,CAAC,CACF,CAAC;QACJ,CAAC,CAAC;QACF,GAAG,EAAE,CAAC;QACN,MAAM,YAAY,GAAG,KAAK;aACvB,KAAK,CAAC,GAAG,CAAC;aACV,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,KAAK,CAAC,SAAS,CAAC,IAAqB,EAAE,GAAG,CAAC,CAAC,CAAC;QAC9D,OAAO,GAAG,EAAE;YACV,MAAM,GAAG,KAAK,CAAC;YACf,KAAK,MAAM,WAAW,IAAI,YAAY;gBAAE,WAAW,EAAE,CAAC;QACxD,CAAC,CAAC;IACJ,CAAC,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,GAAG,CAAC,CAAC,CAAC;IAExB,OAAO,KAAK,CAAC;AACf,CAAC"}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import type { DataStoreName, PolymorfaEvent, StoreRowMap, StoredMessage, StoredMessageStatus, StoredRow } from "./types.js";
|
|
2
|
+
/** The write surface a reducer sees. Writes commit with the whole batch. */
|
|
3
|
+
export interface ReducerContext {
|
|
4
|
+
/** Event time in epoch milliseconds. */
|
|
5
|
+
readonly time: number;
|
|
6
|
+
get<S extends DataStoreName>(store: S, id: string): Promise<StoreRowMap[S] | undefined>;
|
|
7
|
+
put<S extends DataStoreName>(store: S, row: StoreRowMap[S]): void;
|
|
8
|
+
delete(store: DataStoreName, id: string): void;
|
|
9
|
+
/** Deletes every message in a conversation. */
|
|
10
|
+
deleteConversationMessages(conversationId: string): void;
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* Applies one event. Return `false` when the event was not filed anywhere,
|
|
14
|
+
* so the store keeps it in `custom`.
|
|
15
|
+
*/
|
|
16
|
+
export type StoreReducer = (event: PolymorfaEvent, context: ReducerContext) => void | boolean | Promise<void | boolean>;
|
|
17
|
+
/** Row keys a reducer is likely to read, fetched in one transaction. */
|
|
18
|
+
export type KeyHints = readonly (readonly [DataStoreName, string])[];
|
|
19
|
+
/** `T` with every possibly-undefined field made optional instead. */
|
|
20
|
+
export type Defined<T> = {
|
|
21
|
+
[K in keyof T as undefined extends T[K] ? never : K]: T[K];
|
|
22
|
+
} & {
|
|
23
|
+
[K in keyof T as undefined extends T[K] ? K : never]?: Exclude<T[K], undefined>;
|
|
24
|
+
};
|
|
25
|
+
/** Drops `undefined` values so rows stay valid under exact optional types. */
|
|
26
|
+
export declare function pick<T extends object>(value: T): Defined<T>;
|
|
27
|
+
/** Payload times are Unix seconds or milliseconds; returns milliseconds. */
|
|
28
|
+
export declare function payloadTime(value: unknown): number | undefined;
|
|
29
|
+
/**
|
|
30
|
+
* Copies each defined field of `patch` onto `row` unless the row already
|
|
31
|
+
* holds a newer value for that field.
|
|
32
|
+
*/
|
|
33
|
+
export declare function applyFields<T extends StoredRow>(row: T, patch: Partial<T>, time: number): T;
|
|
34
|
+
/** Status only moves forward, whatever order acknowledgements arrive in. */
|
|
35
|
+
export declare function advanceStatus(current: StoredMessageStatus, next: StoredMessageStatus): StoredMessageStatus;
|
|
36
|
+
/** Upserts message content and updates the conversation summary. */
|
|
37
|
+
export declare function upsertMessage(context: ReducerContext, patch: Partial<StoredMessage> & {
|
|
38
|
+
readonly id: string;
|
|
39
|
+
readonly conversationId: string;
|
|
40
|
+
readonly session: string;
|
|
41
|
+
}, time: number, options: {
|
|
42
|
+
readonly content: boolean;
|
|
43
|
+
readonly status?: StoredMessageStatus;
|
|
44
|
+
}): Promise<void>;
|
|
45
|
+
export declare const BUILT_IN_REDUCERS: Readonly<Record<string, StoreReducer>>;
|
|
46
|
+
/** Keys the built-in reducers read, so a batch can load them together. */
|
|
47
|
+
export declare function keyHints(event: PolymorfaEvent): KeyHints;
|
|
48
|
+
//# sourceMappingURL=reducers.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"reducers.d.ts","sourceRoot":"","sources":["../src/reducers.ts"],"names":[],"mappings":"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"}
|