@syncular/react 0.7.0 → 0.8.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/README.md +3 -0
- package/dist/client.d.ts +7 -1
- package/dist/client.js +3 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/use-commit-outcomes.d.ts +12 -0
- package/dist/use-commit-outcomes.js +17 -0
- package/package.json +4 -4
- package/src/client.ts +22 -0
- package/src/index.ts +4 -0
- package/src/use-commit-outcomes.ts +30 -0
package/README.md
CHANGED
|
@@ -164,6 +164,9 @@ not need a custom retention effect.
|
|
|
164
164
|
means an inbound pull/catch-up signal.
|
|
165
165
|
- `useConflicts()` observes conflicts and rejections only when that domain
|
|
166
166
|
changes.
|
|
167
|
+
- `useCommitOutcomes()` observes the durable newest-first final-outcome journal
|
|
168
|
+
from exact `outcomesChanged` batches. Resolve entries through
|
|
169
|
+
`useSyncClient().resolveCommitOutcome(...)`.
|
|
167
170
|
- `usePresence(scopeKey)` observes ephemeral realtime peers.
|
|
168
171
|
- `useSyncClient()` and `useReactiveStore()` expose the normalized low-level
|
|
169
172
|
surfaces for integrations.
|
package/dist/client.d.ts
CHANGED
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
* value → read it) and wraps every result in `Promise.resolve`, so a hook
|
|
12
12
|
* never has to care which core it holds.
|
|
13
13
|
*/
|
|
14
|
-
import type { ClientChangeListener, ConflictRecord, InvalidationListener, LeaseState, MutationInput, PresencePeer, QueryReadSpec, QuerySnapshot, RejectionRecord, SchemaFloor, SqlRow, SqlValue, SyncStatusSnapshot, WindowBase, WindowState } from '@syncular/client';
|
|
14
|
+
import type { ClientChangeListener, CommitOutcome, CommitOutcomeQuery, ConflictRecord, InvalidationListener, LeaseState, MutationInput, PresencePeer, QueryReadSpec, QuerySnapshot, RejectionRecord, ResolveCommitOutcomeInput, SchemaFloor, SqlRow, SqlValue, SyncStatusSnapshot, WindowBase, WindowState } from '@syncular/client';
|
|
15
15
|
/**
|
|
16
16
|
* The structural union of `SyncClient` and `SyncClientHandle`. Members that
|
|
17
17
|
* diverge are typed as "value or method, sync or promise"; {@link normalizeClient}
|
|
@@ -31,6 +31,9 @@ export interface SyncClientLike {
|
|
|
31
31
|
statusSnapshot(): SyncStatusSnapshot | Promise<SyncStatusSnapshot>;
|
|
32
32
|
conflicts: readonly ConflictRecord[] | (() => readonly ConflictRecord[] | Promise<readonly ConflictRecord[]>);
|
|
33
33
|
rejections: readonly RejectionRecord[] | (() => readonly RejectionRecord[] | Promise<readonly RejectionRecord[]>);
|
|
34
|
+
commitOutcome(clientCommitId: string): CommitOutcome | undefined | Promise<CommitOutcome | undefined>;
|
|
35
|
+
commitOutcomes(query?: CommitOutcomeQuery): readonly CommitOutcome[] | Promise<readonly CommitOutcome[]>;
|
|
36
|
+
resolveCommitOutcome(input: ResolveCommitOutcomeInput): CommitOutcome | Promise<CommitOutcome>;
|
|
34
37
|
schemaFloor: SchemaFloor | undefined | (() => SchemaFloor | undefined | Promise<SchemaFloor | undefined>);
|
|
35
38
|
leaseState: LeaseState | undefined | (() => LeaseState | undefined | Promise<LeaseState | undefined>);
|
|
36
39
|
upgrading: boolean | (() => boolean | Promise<boolean>);
|
|
@@ -57,6 +60,9 @@ export interface NormalizedClient {
|
|
|
57
60
|
statusSnapshot(): Promise<SyncStatusSnapshot>;
|
|
58
61
|
conflicts(): Promise<readonly ConflictRecord[]>;
|
|
59
62
|
rejections(): Promise<readonly RejectionRecord[]>;
|
|
63
|
+
commitOutcome(clientCommitId: string): Promise<CommitOutcome | undefined>;
|
|
64
|
+
commitOutcomes(query?: CommitOutcomeQuery): Promise<readonly CommitOutcome[]>;
|
|
65
|
+
resolveCommitOutcome(input: ResolveCommitOutcomeInput): Promise<CommitOutcome>;
|
|
60
66
|
schemaFloor(): Promise<SchemaFloor | undefined>;
|
|
61
67
|
leaseState(): Promise<LeaseState | undefined>;
|
|
62
68
|
upgrading(): Promise<boolean>;
|
package/dist/client.js
CHANGED
|
@@ -22,6 +22,9 @@ export function normalizeClient(client) {
|
|
|
22
22
|
statusSnapshot: () => Promise.resolve(client.statusSnapshot()),
|
|
23
23
|
conflicts: () => resolveMember(client, 'conflicts'),
|
|
24
24
|
rejections: () => resolveMember(client, 'rejections'),
|
|
25
|
+
commitOutcome: (clientCommitId) => Promise.resolve(client.commitOutcome(clientCommitId)),
|
|
26
|
+
commitOutcomes: (query) => Promise.resolve(client.commitOutcomes(query)),
|
|
27
|
+
resolveCommitOutcome: (input) => Promise.resolve(client.resolveCommitOutcome(input)),
|
|
25
28
|
schemaFloor: () => resolveMember(client, 'schemaFloor'),
|
|
26
29
|
leaseState: () => resolveMember(client, 'leaseState'),
|
|
27
30
|
upgrading: () => resolveMember(client, 'upgrading'),
|
package/dist/index.d.ts
CHANGED
|
@@ -13,6 +13,7 @@ export { inferTables } from './infer-tables.js';
|
|
|
13
13
|
export { SyncContext, SyncProvider, type SyncProviderProps, SyncStoreContext, } from './provider.js';
|
|
14
14
|
export { createSyncClientResource, isSyncClientResource, type SyncClientResource, type SyncClientResourceSnapshot, } from './resource.js';
|
|
15
15
|
export { useReactiveStore, useSyncClient } from './use-client.js';
|
|
16
|
+
export { type UseCommitOutcomesResult, useCommitOutcomes, } from './use-commit-outcomes.js';
|
|
16
17
|
export { type UseConflictsResult, useConflicts } from './use-conflicts.js';
|
|
17
18
|
export { type SyncTableDescriptor, type UseMutationOptions, type UseMutationResult, type UseTableMutationResult, useMutation, } from './use-mutation.js';
|
|
18
19
|
export { usePresence } from './use-presence.js';
|
package/dist/index.js
CHANGED
|
@@ -6,6 +6,7 @@ export { inferTables } from './infer-tables.js';
|
|
|
6
6
|
export { SyncContext, SyncProvider, SyncStoreContext, } from './provider.js';
|
|
7
7
|
export { createSyncClientResource, isSyncClientResource, } from './resource.js';
|
|
8
8
|
export { useReactiveStore, useSyncClient } from './use-client.js';
|
|
9
|
+
export { useCommitOutcomes, } from './use-commit-outcomes.js';
|
|
9
10
|
export { useConflicts } from './use-conflicts.js';
|
|
10
11
|
export { useMutation, } from './use-mutation.js';
|
|
11
12
|
export { usePresence } from './use-presence.js';
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { CommitOutcome } from '@syncular/client';
|
|
2
|
+
export interface UseCommitOutcomesResult {
|
|
3
|
+
readonly outcomes: readonly CommitOutcome[];
|
|
4
|
+
readonly isLoading: boolean;
|
|
5
|
+
readonly error: Error | undefined;
|
|
6
|
+
readonly refresh: () => void;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Durable newest-first commit history. It updates from the exact
|
|
10
|
+
* `outcomesChanged` transaction event, including resolution transitions.
|
|
11
|
+
*/
|
|
12
|
+
export declare function useCommitOutcomes(): UseCommitOutcomesResult;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { useCallback, useSyncExternalStore } from 'react';
|
|
2
|
+
import { useReactiveStore } from './use-client.js';
|
|
3
|
+
/**
|
|
4
|
+
* Durable newest-first commit history. It updates from the exact
|
|
5
|
+
* `outcomesChanged` transaction event, including resolution transitions.
|
|
6
|
+
*/
|
|
7
|
+
export function useCommitOutcomes() {
|
|
8
|
+
const entry = useReactiveStore().outcomes;
|
|
9
|
+
const snapshot = useSyncExternalStore(entry.subscribe, entry.getSnapshot, entry.getSnapshot);
|
|
10
|
+
const refresh = useCallback(() => entry.refresh(), [entry]);
|
|
11
|
+
return {
|
|
12
|
+
outcomes: snapshot.outcomes,
|
|
13
|
+
isLoading: snapshot.isLoading,
|
|
14
|
+
error: snapshot.error,
|
|
15
|
+
refresh,
|
|
16
|
+
};
|
|
17
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@syncular/react",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.8.0",
|
|
4
4
|
"description": "React hooks for Syncular offline-first sync",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"author": "Benjamin Kniffler",
|
|
@@ -48,15 +48,15 @@
|
|
|
48
48
|
"test": "bun test --preload ./test/setup.ts"
|
|
49
49
|
},
|
|
50
50
|
"dependencies": {
|
|
51
|
-
"@syncular/client": "0.
|
|
51
|
+
"@syncular/client": "0.8.0"
|
|
52
52
|
},
|
|
53
53
|
"peerDependencies": {
|
|
54
54
|
"react": ">=18.0.0"
|
|
55
55
|
},
|
|
56
56
|
"devDependencies": {
|
|
57
57
|
"@happy-dom/global-registrator": "^15.11.0",
|
|
58
|
-
"@syncular/core": "0.
|
|
59
|
-
"@syncular/server": "0.
|
|
58
|
+
"@syncular/core": "0.8.0",
|
|
59
|
+
"@syncular/server": "0.8.0",
|
|
60
60
|
"@testing-library/react": "^16.1.0",
|
|
61
61
|
"@types/react": "^18.3.0",
|
|
62
62
|
"react": "^18.3.1",
|
package/src/client.ts
CHANGED
|
@@ -13,6 +13,8 @@
|
|
|
13
13
|
*/
|
|
14
14
|
import type {
|
|
15
15
|
ClientChangeListener,
|
|
16
|
+
CommitOutcome,
|
|
17
|
+
CommitOutcomeQuery,
|
|
16
18
|
ConflictRecord,
|
|
17
19
|
InvalidationListener,
|
|
18
20
|
LeaseState,
|
|
@@ -21,6 +23,7 @@ import type {
|
|
|
21
23
|
QueryReadSpec,
|
|
22
24
|
QuerySnapshot,
|
|
23
25
|
RejectionRecord,
|
|
26
|
+
ResolveCommitOutcomeInput,
|
|
24
27
|
SchemaFloor,
|
|
25
28
|
SqlRow,
|
|
26
29
|
SqlValue,
|
|
@@ -60,6 +63,15 @@ export interface SyncClientLike {
|
|
|
60
63
|
rejections:
|
|
61
64
|
| readonly RejectionRecord[]
|
|
62
65
|
| (() => readonly RejectionRecord[] | Promise<readonly RejectionRecord[]>);
|
|
66
|
+
commitOutcome(
|
|
67
|
+
clientCommitId: string,
|
|
68
|
+
): CommitOutcome | undefined | Promise<CommitOutcome | undefined>;
|
|
69
|
+
commitOutcomes(
|
|
70
|
+
query?: CommitOutcomeQuery,
|
|
71
|
+
): readonly CommitOutcome[] | Promise<readonly CommitOutcome[]>;
|
|
72
|
+
resolveCommitOutcome(
|
|
73
|
+
input: ResolveCommitOutcomeInput,
|
|
74
|
+
): CommitOutcome | Promise<CommitOutcome>;
|
|
63
75
|
schemaFloor:
|
|
64
76
|
| SchemaFloor
|
|
65
77
|
| undefined
|
|
@@ -118,6 +130,11 @@ export interface NormalizedClient {
|
|
|
118
130
|
statusSnapshot(): Promise<SyncStatusSnapshot>;
|
|
119
131
|
conflicts(): Promise<readonly ConflictRecord[]>;
|
|
120
132
|
rejections(): Promise<readonly RejectionRecord[]>;
|
|
133
|
+
commitOutcome(clientCommitId: string): Promise<CommitOutcome | undefined>;
|
|
134
|
+
commitOutcomes(query?: CommitOutcomeQuery): Promise<readonly CommitOutcome[]>;
|
|
135
|
+
resolveCommitOutcome(
|
|
136
|
+
input: ResolveCommitOutcomeInput,
|
|
137
|
+
): Promise<CommitOutcome>;
|
|
121
138
|
schemaFloor(): Promise<SchemaFloor | undefined>;
|
|
122
139
|
leaseState(): Promise<LeaseState | undefined>;
|
|
123
140
|
upgrading(): Promise<boolean>;
|
|
@@ -145,6 +162,11 @@ export function normalizeClient(client: SyncClientLike): NormalizedClient {
|
|
|
145
162
|
statusSnapshot: () => Promise.resolve(client.statusSnapshot()),
|
|
146
163
|
conflicts: () => resolveMember(client, 'conflicts'),
|
|
147
164
|
rejections: () => resolveMember(client, 'rejections'),
|
|
165
|
+
commitOutcome: (clientCommitId) =>
|
|
166
|
+
Promise.resolve(client.commitOutcome(clientCommitId)),
|
|
167
|
+
commitOutcomes: (query) => Promise.resolve(client.commitOutcomes(query)),
|
|
168
|
+
resolveCommitOutcome: (input) =>
|
|
169
|
+
Promise.resolve(client.resolveCommitOutcome(input)),
|
|
148
170
|
schemaFloor: () => resolveMember(client, 'schemaFloor'),
|
|
149
171
|
leaseState: () => resolveMember(client, 'leaseState'),
|
|
150
172
|
upgrading: () => resolveMember(client, 'upgrading'),
|
package/src/index.ts
CHANGED
|
@@ -29,6 +29,10 @@ export {
|
|
|
29
29
|
type SyncClientResourceSnapshot,
|
|
30
30
|
} from './resource';
|
|
31
31
|
export { useReactiveStore, useSyncClient } from './use-client';
|
|
32
|
+
export {
|
|
33
|
+
type UseCommitOutcomesResult,
|
|
34
|
+
useCommitOutcomes,
|
|
35
|
+
} from './use-commit-outcomes';
|
|
32
36
|
export { type UseConflictsResult, useConflicts } from './use-conflicts';
|
|
33
37
|
export {
|
|
34
38
|
type SyncTableDescriptor,
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import type { CommitOutcome } from '@syncular/client';
|
|
2
|
+
import { useCallback, useSyncExternalStore } from 'react';
|
|
3
|
+
import { useReactiveStore } from './use-client';
|
|
4
|
+
|
|
5
|
+
export interface UseCommitOutcomesResult {
|
|
6
|
+
readonly outcomes: readonly CommitOutcome[];
|
|
7
|
+
readonly isLoading: boolean;
|
|
8
|
+
readonly error: Error | undefined;
|
|
9
|
+
readonly refresh: () => void;
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* Durable newest-first commit history. It updates from the exact
|
|
14
|
+
* `outcomesChanged` transaction event, including resolution transitions.
|
|
15
|
+
*/
|
|
16
|
+
export function useCommitOutcomes(): UseCommitOutcomesResult {
|
|
17
|
+
const entry = useReactiveStore().outcomes;
|
|
18
|
+
const snapshot = useSyncExternalStore(
|
|
19
|
+
entry.subscribe,
|
|
20
|
+
entry.getSnapshot,
|
|
21
|
+
entry.getSnapshot,
|
|
22
|
+
);
|
|
23
|
+
const refresh = useCallback(() => entry.refresh(), [entry]);
|
|
24
|
+
return {
|
|
25
|
+
outcomes: snapshot.outcomes,
|
|
26
|
+
isLoading: snapshot.isLoading,
|
|
27
|
+
error: snapshot.error,
|
|
28
|
+
refresh,
|
|
29
|
+
};
|
|
30
|
+
}
|