@livestore/sync-cf 0.4.0-dev.22 → 0.4.0-dev.23

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.
Files changed (78) hide show
  1. package/README.md +6 -7
  2. package/dist/.tsbuildinfo +1 -1
  3. package/dist/cf-worker/do/durable-object.d.ts.map +1 -1
  4. package/dist/cf-worker/do/durable-object.js +5 -5
  5. package/dist/cf-worker/do/durable-object.js.map +1 -1
  6. package/dist/cf-worker/do/layer.d.ts +1 -1
  7. package/dist/cf-worker/do/layer.d.ts.map +1 -1
  8. package/dist/cf-worker/do/layer.js +2 -2
  9. package/dist/cf-worker/do/layer.js.map +1 -1
  10. package/dist/cf-worker/do/pull.d.ts +2 -2
  11. package/dist/cf-worker/do/pull.d.ts.map +1 -1
  12. package/dist/cf-worker/do/pull.js +11 -5
  13. package/dist/cf-worker/do/pull.js.map +1 -1
  14. package/dist/cf-worker/do/push.d.ts +2 -2
  15. package/dist/cf-worker/do/push.d.ts.map +1 -1
  16. package/dist/cf-worker/do/push.js +16 -9
  17. package/dist/cf-worker/do/push.js.map +1 -1
  18. package/dist/cf-worker/do/sqlite.d.ts.map +1 -1
  19. package/dist/cf-worker/do/sqlite.js.map +1 -1
  20. package/dist/cf-worker/do/sync-storage.d.ts +1 -1
  21. package/dist/cf-worker/do/sync-storage.d.ts.map +1 -1
  22. package/dist/cf-worker/do/sync-storage.js +2 -1
  23. package/dist/cf-worker/do/sync-storage.js.map +1 -1
  24. package/dist/cf-worker/do/transport/do-rpc-server.d.ts.map +1 -1
  25. package/dist/cf-worker/do/transport/do-rpc-server.js +9 -5
  26. package/dist/cf-worker/do/transport/do-rpc-server.js.map +1 -1
  27. package/dist/cf-worker/do/transport/http-rpc-server.d.ts +1 -1
  28. package/dist/cf-worker/do/transport/http-rpc-server.d.ts.map +1 -1
  29. package/dist/cf-worker/do/transport/http-rpc-server.js +2 -2
  30. package/dist/cf-worker/do/transport/http-rpc-server.js.map +1 -1
  31. package/dist/cf-worker/do/transport/ws-rpc-server.d.ts.map +1 -1
  32. package/dist/cf-worker/do/transport/ws-rpc-server.js +7 -3
  33. package/dist/cf-worker/do/transport/ws-rpc-server.js.map +1 -1
  34. package/dist/cf-worker/shared.d.ts +7 -7
  35. package/dist/cf-worker/shared.d.ts.map +1 -1
  36. package/dist/cf-worker/worker.d.ts.map +1 -1
  37. package/dist/cf-worker/worker.js +7 -7
  38. package/dist/cf-worker/worker.js.map +1 -1
  39. package/dist/client/transport/do-rpc-client.d.ts.map +1 -1
  40. package/dist/client/transport/do-rpc-client.js +11 -7
  41. package/dist/client/transport/do-rpc-client.js.map +1 -1
  42. package/dist/client/transport/http-rpc-client.d.ts.map +1 -1
  43. package/dist/client/transport/http-rpc-client.js +10 -6
  44. package/dist/client/transport/http-rpc-client.js.map +1 -1
  45. package/dist/client/transport/ws-rpc-client.d.ts.map +1 -1
  46. package/dist/client/transport/ws-rpc-client.js +11 -11
  47. package/dist/client/transport/ws-rpc-client.js.map +1 -1
  48. package/dist/common/do-rpc-schema.d.ts +3 -3
  49. package/dist/common/do-rpc-schema.d.ts.map +1 -1
  50. package/dist/common/do-rpc-schema.js +3 -3
  51. package/dist/common/do-rpc-schema.js.map +1 -1
  52. package/dist/common/http-rpc-schema.d.ts +3 -3
  53. package/dist/common/http-rpc-schema.d.ts.map +1 -1
  54. package/dist/common/http-rpc-schema.js +3 -3
  55. package/dist/common/http-rpc-schema.js.map +1 -1
  56. package/dist/common/sync-message-types.d.ts +2 -2
  57. package/dist/common/ws-rpc-schema.d.ts +3 -3
  58. package/dist/common/ws-rpc-schema.d.ts.map +1 -1
  59. package/dist/common/ws-rpc-schema.js +3 -3
  60. package/dist/common/ws-rpc-schema.js.map +1 -1
  61. package/package.json +71 -13
  62. package/src/cf-worker/do/durable-object.ts +10 -8
  63. package/src/cf-worker/do/layer.ts +4 -3
  64. package/src/cf-worker/do/pull.ts +17 -6
  65. package/src/cf-worker/do/push.ts +20 -9
  66. package/src/cf-worker/do/sqlite.ts +1 -0
  67. package/src/cf-worker/do/sync-storage.ts +4 -2
  68. package/src/cf-worker/do/transport/do-rpc-server.ts +14 -5
  69. package/src/cf-worker/do/transport/http-rpc-server.ts +17 -17
  70. package/src/cf-worker/do/transport/ws-rpc-server.ts +13 -4
  71. package/src/cf-worker/shared.ts +3 -3
  72. package/src/cf-worker/worker.ts +17 -14
  73. package/src/client/transport/do-rpc-client.ts +20 -14
  74. package/src/client/transport/http-rpc-client.ts +19 -13
  75. package/src/client/transport/ws-rpc-client.ts +39 -36
  76. package/src/common/do-rpc-schema.ts +4 -3
  77. package/src/common/http-rpc-schema.ts +4 -3
  78. package/src/common/ws-rpc-schema.ts +4 -3
@@ -1,7 +1,9 @@
1
1
  import { env as importedEnv } from 'cloudflare:workers'
2
+
2
3
  import { UnknownError } from '@livestore/common'
3
4
  import type { HelperTypes } from '@livestore/common-cf'
4
5
  import { Effect, Schema } from '@livestore/utils/effect'
6
+
5
7
  import type { CfTypes, SearchParams } from '../common/mod.ts'
6
8
  import type { CfDeclare } from './mod.ts'
7
9
  import { type Env, type ForwardedHeaders, matchSyncRequest } from './shared.ts'
@@ -80,15 +82,16 @@ export const makeWorker = <
80
82
  fetch: async (request, env, _ctx) => {
81
83
  const url = new URL(request.url)
82
84
 
83
- const corsHeaders: CfTypes.HeadersInit = options.enableCORS
84
- ? {
85
- 'Access-Control-Allow-Origin': '*',
86
- 'Access-Control-Allow-Methods': 'GET, POST, OPTIONS',
87
- 'Access-Control-Allow-Headers': request.headers.get('Access-Control-Request-Headers') ?? '*',
88
- }
89
- : {}
85
+ const corsHeaders: CfTypes.HeadersInit =
86
+ options.enableCORS === true
87
+ ? {
88
+ 'Access-Control-Allow-Origin': '*',
89
+ 'Access-Control-Allow-Methods': 'GET, POST, OPTIONS',
90
+ 'Access-Control-Allow-Headers': request.headers.get('Access-Control-Request-Headers') ?? '*',
91
+ }
92
+ : {}
90
93
 
91
- if (request.method === 'OPTIONS' && options.enableCORS) {
94
+ if (request.method === 'OPTIONS' && options.enableCORS === true) {
92
95
  return new Response(null, {
93
96
  status: 204,
94
97
  headers: corsHeaders,
@@ -202,16 +205,16 @@ export const handleSyncRequest = <
202
205
  if (decodedEither._tag === 'Left') {
203
206
  const message = decodedEither.left.toString()
204
207
  console.error('Invalid payload (decode failed)', message)
205
- return new Response(message, { status: 400, headers })
208
+ return new Response(message, { status: 400, ...(headers !== undefined ? { headers } : {}) })
206
209
  }
207
210
 
208
211
  const result = yield* Effect.promise(async () =>
209
- validatePayload(decodedEither.right as TSyncPayload, { storeId, headers: requestHeaders }),
212
+ validatePayload(decodedEither.right, { storeId, headers: requestHeaders }),
210
213
  ).pipe(UnknownError.mapToUnknownError, Effect.either)
211
214
 
212
215
  if (result._tag === 'Left') {
213
216
  console.error('Invalid payload (validation failed)', result.left)
214
- return new Response(result.left.toString(), { status: 400, headers })
217
+ return new Response(result.left.toString(), { status: 400, ...(headers !== undefined ? { headers } : {}) })
215
218
  }
216
219
  } else {
217
220
  const result = yield* Effect.promise(async () =>
@@ -220,7 +223,7 @@ export const handleSyncRequest = <
220
223
 
221
224
  if (result._tag === 'Left') {
222
225
  console.error('Invalid payload (validation failed)', result.left)
223
- return new Response(result.left.toString(), { status: 400, headers })
226
+ return new Response(result.left.toString(), { status: 400, ...(headers !== undefined ? { headers } : {}) })
224
227
  }
225
228
  }
226
229
  }
@@ -232,7 +235,7 @@ export const handleSyncRequest = <
232
235
  `Failed dependency: Required Durable Object binding '${syncBackendBinding as string}' not available`,
233
236
  {
234
237
  status: 424,
235
- headers,
238
+ ...(headers !== undefined ? { headers } : {}),
236
239
  },
237
240
  )
238
241
  }
@@ -249,7 +252,7 @@ export const handleSyncRequest = <
249
252
  if (transport === 'ws' && (upgradeHeader === null || upgradeHeader !== 'websocket')) {
250
253
  return new Response('Durable Object expected Upgrade: websocket', {
251
254
  status: 426,
252
- headers,
255
+ ...(headers !== undefined ? { headers } : {}),
253
256
  })
254
257
  }
255
258
 
@@ -1,4 +1,4 @@
1
- import { InvalidPullError, InvalidPushError, SyncBackend, UnknownError } from '@livestore/common'
1
+ import { SyncBackend, UnknownError } from '@livestore/common'
2
2
  import { splitChunkBySize } from '@livestore/common/sync'
3
3
  import { type CfTypes, layerProtocolDurableObject } from '@livestore/common-cf'
4
4
  import { omit, shouldNeverHappen } from '@livestore/utils'
@@ -15,6 +15,7 @@ import {
15
15
  Stream,
16
16
  SubscriptionRef,
17
17
  } from '@livestore/utils/effect'
18
+
18
19
  import type { SyncBackendRpcInterface } from '../../cf-worker/shared.ts'
19
20
  import { MAX_DO_RPC_REQUEST_BYTES, MAX_PUSH_EVENTS_PER_REQUEST } from '../../common/constants.ts'
20
21
  import { SyncDoRpc } from '../../common/do-rpc-schema.ts'
@@ -73,9 +74,9 @@ export const makeDoRpcSync =
73
74
  })),
74
75
  ),
75
76
  storeId,
76
- rpcContext: options?.live ? { callerContext: durableObjectContext } : undefined,
77
+ rpcContext: options?.live === true ? { callerContext: durableObjectContext } : undefined,
77
78
  }).pipe(
78
- options?.live
79
+ options?.live === true
79
80
  ? Stream.concatWithLastElement((res) =>
80
81
  Effect.gen(function* () {
81
82
  if (res._tag === 'None')
@@ -93,12 +94,16 @@ export const makeDoRpcSync =
93
94
  : identity,
94
95
  Stream.tap((res) => backendIdHelper.lazySet(res.backendId)),
95
96
  Stream.map((res) => omit(res, ['backendId'])),
96
- Stream.mapError((cause) => (cause._tag === 'InvalidPullError' ? cause : InvalidPullError.make({ cause }))),
97
+ Stream.mapError((cause) =>
98
+ cause._tag === 'UnknownError' || cause._tag === 'BackendIdMismatchError'
99
+ ? cause
100
+ : new UnknownError({ cause }),
101
+ ),
97
102
  Stream.withSpan('rpc-sync-client:pull'),
98
103
  )
99
104
 
100
- const push: SyncBackend.SyncBackend<{ createdAt: string }>['push'] = (batch) =>
101
- Effect.gen(function* () {
105
+ const push: SyncBackend.SyncBackend<{ createdAt: string }>['push'] = Effect.fn('rpc-sync-client:push')(
106
+ function* (batch) {
102
107
  if (batch.length === 0) {
103
108
  return
104
109
  }
@@ -114,19 +119,20 @@ export const makeDoRpcSync =
114
119
  backendId,
115
120
  }),
116
121
  }),
117
- Effect.mapError((cause) => new InvalidPushError({ cause: new UnknownError({ cause }) })),
122
+ Effect.mapError((cause) => new UnknownError({ cause })),
118
123
  )
119
124
 
120
125
  for (const chunk of Chunk.toReadonlyArray(batchChunks)) {
121
126
  const chunkArray = Chunk.toReadonlyArray(chunk)
122
127
  yield* rpcClient.SyncDoRpc.Push({ batch: chunkArray, storeId, backendId })
123
128
  }
124
- }).pipe(
125
- Effect.mapError((cause) =>
126
- cause._tag === 'InvalidPushError' ? cause : InvalidPushError.make({ cause: new UnknownError({ cause }) }),
127
- ),
128
- Effect.withSpan('rpc-sync-client:push'),
129
- )
129
+ },
130
+ Effect.mapError((cause) =>
131
+ cause._tag === 'UnknownError' || cause._tag === 'ServerAheadError' || cause._tag === 'BackendIdMismatchError'
132
+ ? cause
133
+ : new UnknownError({ cause }),
134
+ ),
135
+ )
130
136
 
131
137
  const ping: SyncBackend.SyncBackend<{ createdAt: string }>['ping'] = rpcClient.SyncDoRpc.Ping({
132
138
  storeId,
@@ -170,7 +176,7 @@ export const makeDoRpcSync =
170
176
  export const handleSyncUpdateRpc = (payload: unknown) =>
171
177
  Effect.gen(function* () {
172
178
  const decodedPayload = yield* Schema.decodeUnknown(ResponseChunkEncoded)(payload)
173
- const decoded = yield* Schema.decodeUnknown(SyncMessage.PullResponse)(decodedPayload.values[0]!)
179
+ const decoded = yield* Schema.decodeUnknown(SyncMessage.PullResponse)(decodedPayload.values[0])
174
180
 
175
181
  const pullStreamMailbox = requestIdMailboxMap.get(decodedPayload.requestId)
176
182
 
@@ -1,4 +1,4 @@
1
- import { InvalidPullError, InvalidPushError, SyncBackend, UnknownError } from '@livestore/common'
1
+ import { SyncBackend, UnknownError } from '@livestore/common'
2
2
  import type { EventSequenceNumber } from '@livestore/common/schema'
3
3
  import { splitChunkBySize } from '@livestore/common/sync'
4
4
  import { omit } from '@livestore/utils'
@@ -19,6 +19,7 @@ import {
19
19
  SubscriptionRef,
20
20
  UrlParams,
21
21
  } from '@livestore/utils/effect'
22
+
22
23
  import { MAX_HTTP_REQUEST_BYTES, MAX_PUSH_EVENTS_PER_REQUEST } from '../../common/constants.ts'
23
24
  import { SyncHttpRpc } from '../../common/http-rpc-schema.ts'
24
25
  import { SearchParamsSchema } from '../../common/mod.ts'
@@ -134,7 +135,7 @@ export const makeHttpSync =
134
135
  payload,
135
136
  cursor: mapCursor(cursor),
136
137
  }).pipe(
137
- options?.live
138
+ options?.live === true
138
139
  ? // Phase 2: Simulate `live` pull by polling for new events
139
140
  Stream.concatWithLastElement((lastElement) => {
140
141
  const initialPhase2Cursor = lastElement.pipe(
@@ -166,14 +167,18 @@ export const makeHttpSync =
166
167
  : identity,
167
168
  Stream.tap((res) => backendIdHelper.lazySet(res.backendId)),
168
169
  Stream.map((res) => omit(res, ['backendId'])),
169
- Stream.mapError((cause) => (cause._tag === 'InvalidPullError' ? cause : InvalidPullError.make({ cause }))),
170
+ Stream.mapError((cause) =>
171
+ cause._tag === 'UnknownError' || cause._tag === 'BackendIdMismatchError'
172
+ ? cause
173
+ : new UnknownError({ cause }),
174
+ ),
170
175
  Stream.withSpan('http-sync-client:pull'),
171
176
  )
172
177
 
173
178
  const pushSemaphore = yield* Effect.makeSemaphore(1)
174
179
 
175
- const push: SyncBackend.SyncBackend<SyncMetadata>['push'] = (batch) =>
176
- Effect.gen(function* () {
180
+ const push: SyncBackend.SyncBackend<SyncMetadata>['push'] = Effect.fn('http-sync-client:push')(
181
+ function* (batch) {
177
182
  if (batch.length === 0) {
178
183
  return
179
184
  }
@@ -190,20 +195,21 @@ export const makeHttpSync =
190
195
  backendId,
191
196
  }),
192
197
  }),
193
- Effect.mapError((cause) => new InvalidPushError({ cause: new UnknownError({ cause }) })),
198
+ Effect.mapError((cause) => new UnknownError({ cause })),
194
199
  )
195
200
 
196
201
  for (const chunk of Chunk.toReadonlyArray(batchChunks)) {
197
202
  const chunkArray = Chunk.toReadonlyArray(chunk)
198
203
  yield* rpcClient.SyncHttpRpc.Push({ storeId, payload, batch: chunkArray, backendId })
199
204
  }
200
- }).pipe(
201
- pushSemaphore.withPermits(1),
202
- Effect.mapError((cause) =>
203
- cause._tag === 'InvalidPushError' ? cause : new InvalidPushError({ cause: new UnknownError({ cause }) }),
204
- ),
205
- Effect.withSpan('http-sync-client:push'),
206
- )
205
+ },
206
+ pushSemaphore.withPermits(1),
207
+ Effect.mapError((cause) =>
208
+ cause._tag === 'UnknownError' || cause._tag === 'ServerAheadError' || cause._tag === 'BackendIdMismatchError'
209
+ ? cause
210
+ : new UnknownError({ cause }),
211
+ ),
212
+ )
207
213
 
208
214
  return SyncBackend.of({
209
215
  connect,
@@ -1,4 +1,4 @@
1
- import { InvalidPullError, InvalidPushError, IsOfflineError, SyncBackend, UnknownError } from '@livestore/common'
1
+ import { IsOfflineError, SyncBackend, UnknownError } from '@livestore/common'
2
2
  import type { LiveStoreEvent } from '@livestore/common/schema'
3
3
  import { splitChunkBySize } from '@livestore/common/sync'
4
4
  import { omit } from '@livestore/utils'
@@ -19,6 +19,7 @@ import {
19
19
  UrlParams,
20
20
  } from '@livestore/utils/effect'
21
21
  import type { WebSocket } from '@livestore/utils/effect/browser'
22
+
22
23
  import { MAX_PUSH_EVENTS_PER_REQUEST, MAX_WS_MESSAGE_BYTES } from '../../common/constants.ts'
23
24
  import { SearchParamsSchema } from '../../common/mod.ts'
24
25
  import type { SyncMetadata } from '../../common/sync-message-types.ts'
@@ -95,7 +96,10 @@ export const makeWsSync =
95
96
 
96
97
  const ProtocolLive = RpcClient.layerProtocolSocketWithIsConnected({
97
98
  isConnected,
98
- retryTransientErrors: Schedule.fixed(1000),
99
+ retryTransientErrors: Schedule.exponential('1 seconds').pipe(
100
+ Schedule.union(Schedule.fixed('30 seconds')),
101
+ Schedule.jittered,
102
+ ),
99
103
  pingSchedule: Schedule.once.pipe(Schedule.andThen(Schedule.fixed(pingInterval))),
100
104
  url: wsUrl,
101
105
  }).pipe(
@@ -138,55 +142,54 @@ export const makeWsSync =
138
142
  backendId: backendIdHelper.get().pipe(Option.getOrThrow),
139
143
  })),
140
144
  ),
141
- live: options?.live ?? false,
145
+ live: options?.live === true,
142
146
  }).pipe(
143
147
  Stream.tap((res) => backendIdHelper.lazySet(res.backendId)),
144
148
  Stream.map((res) => omit(res, ['backendId'])),
145
149
  Stream.mapError((cause) =>
146
- cause._tag === 'RpcClientError' && Socket.isSocketError(cause.cause)
150
+ cause._tag === 'RpcClientError' && Socket.isSocketError(cause.cause) === true
147
151
  ? new IsOfflineError({ cause: cause.cause })
148
- : cause._tag === 'InvalidPullError'
152
+ : cause._tag === 'UnknownError' || cause._tag === 'BackendIdMismatchError'
149
153
  ? cause
150
- : InvalidPullError.make({ cause }),
154
+ : new UnknownError({ cause }),
151
155
  ),
152
156
  Stream.withSpan('pull'),
153
157
  ),
154
158
 
155
- push: (batch) =>
156
- Effect.gen(function* () {
157
- if (batch.length === 0) return
159
+ push: Effect.fn('push')(function* (batch) {
160
+ if (batch.length === 0) return
158
161
 
159
- const encodePayload = (batch: ReadonlyArray<LiveStoreEvent.Global.Encoded>) => ({
162
+ const encodePayload = (batch: ReadonlyArray<LiveStoreEvent.Global.Encoded>) => ({
163
+ storeId,
164
+ payload,
165
+ batch,
166
+ backendId: backendIdHelper.get(),
167
+ })
168
+
169
+ const chunksChunk = yield* Chunk.fromIterable(batch).pipe(
170
+ splitChunkBySize({
171
+ maxItems: MAX_PUSH_EVENTS_PER_REQUEST,
172
+ maxBytes: MAX_WS_MESSAGE_BYTES,
173
+ encode: encodePayload,
174
+ }),
175
+ Effect.mapError((cause) => new UnknownError({ cause })),
176
+ )
177
+
178
+ for (const sub of chunksChunk) {
179
+ yield* rpcClient.SyncWsRpc.Push({
160
180
  storeId,
161
181
  payload,
162
- batch,
182
+ batch: Chunk.toReadonlyArray(sub),
163
183
  backendId: backendIdHelper.get(),
164
- })
165
-
166
- const chunksChunk = yield* Chunk.fromIterable(batch).pipe(
167
- splitChunkBySize({
168
- maxItems: MAX_PUSH_EVENTS_PER_REQUEST,
169
- maxBytes: MAX_WS_MESSAGE_BYTES,
170
- encode: encodePayload,
171
- }),
172
- Effect.mapError((cause) => new InvalidPushError({ cause: new UnknownError({ cause }) })),
184
+ }).pipe(
185
+ Effect.mapError((cause) =>
186
+ cause._tag === 'UnknownError' || cause._tag === 'ServerAheadError' || cause._tag === 'BackendIdMismatchError'
187
+ ? cause
188
+ : new UnknownError({ cause }),
189
+ ),
173
190
  )
174
-
175
- for (const sub of chunksChunk) {
176
- yield* rpcClient.SyncWsRpc.Push({
177
- storeId,
178
- payload,
179
- batch: Chunk.toReadonlyArray(sub),
180
- backendId: backendIdHelper.get(),
181
- }).pipe(
182
- Effect.mapError((cause) =>
183
- cause._tag === 'InvalidPushError'
184
- ? cause
185
- : new InvalidPushError({ cause: new UnknownError({ cause }) }),
186
- ),
187
- )
188
- }
189
- }).pipe(Effect.withSpan('push')),
191
+ }
192
+ }),
190
193
  ping,
191
194
  metadata: {
192
195
  name: '@livestore/cf-sync',
@@ -1,5 +1,6 @@
1
- import { InvalidPullError, InvalidPushError } from '@livestore/common'
1
+ import { BackendIdMismatchError, ServerAheadError, UnknownError } from '@livestore/common'
2
2
  import { Rpc, RpcGroup, Schema } from '@livestore/utils/effect'
3
+
3
4
  import * as SyncMessage from './sync-message-types.ts'
4
5
 
5
6
  const commonPayloadFields = {
@@ -34,7 +35,7 @@ export class SyncDoRpc extends RpcGroup.make(
34
35
  rpcRequestId: Schema.String,
35
36
  ...SyncMessage.PullResponse.fields,
36
37
  }),
37
- error: InvalidPullError,
38
+ error: Schema.Union(UnknownError, BackendIdMismatchError),
38
39
  stream: true,
39
40
  }),
40
41
  Rpc.make('SyncDoRpc.Push', {
@@ -43,7 +44,7 @@ export class SyncDoRpc extends RpcGroup.make(
43
44
  ...commonPayloadFields,
44
45
  },
45
46
  success: SyncMessage.PushAck,
46
- error: InvalidPushError,
47
+ error: Schema.Union(UnknownError, ServerAheadError, BackendIdMismatchError),
47
48
  }),
48
49
  Rpc.make('SyncDoRpc.Ping', {
49
50
  payload: {
@@ -1,5 +1,6 @@
1
- import { InvalidPullError, InvalidPushError, UnknownError } from '@livestore/common'
1
+ import { BackendIdMismatchError, ServerAheadError, UnknownError } from '@livestore/common'
2
2
  import { Rpc, RpcGroup, Schema } from '@livestore/utils/effect'
3
+
3
4
  import * as SyncMessage from './sync-message-types.ts'
4
5
 
5
6
  /**
@@ -17,7 +18,7 @@ export class SyncHttpRpc extends RpcGroup.make(
17
18
  ...SyncMessage.PullRequest.fields,
18
19
  }),
19
20
  success: SyncMessage.PullResponse,
20
- error: InvalidPullError,
21
+ error: Schema.Union(UnknownError, BackendIdMismatchError),
21
22
  stream: true,
22
23
  }),
23
24
  Rpc.make('SyncHttpRpc.Push', {
@@ -27,7 +28,7 @@ export class SyncHttpRpc extends RpcGroup.make(
27
28
  ...SyncMessage.PushRequest.fields,
28
29
  }),
29
30
  success: SyncMessage.PushAck,
30
- error: InvalidPushError,
31
+ error: Schema.Union(UnknownError, ServerAheadError, BackendIdMismatchError),
31
32
  }),
32
33
  Rpc.make('SyncHttpRpc.Ping', {
33
34
  payload: Schema.Struct({
@@ -1,5 +1,6 @@
1
- import { InvalidPullError, InvalidPushError } from '@livestore/common'
1
+ import { BackendIdMismatchError, ServerAheadError, UnknownError } from '@livestore/common'
2
2
  import { Rpc, RpcGroup, Schema } from '@livestore/utils/effect'
3
+
3
4
  import * as SyncMessage from './sync-message-types.ts'
4
5
 
5
6
  /**
@@ -19,7 +20,7 @@ export class SyncWsRpc extends RpcGroup.make(
19
20
  ...SyncMessage.PullRequest.fields,
20
21
  }),
21
22
  success: SyncMessage.PullResponse,
22
- error: InvalidPullError,
23
+ error: Schema.Union(UnknownError, BackendIdMismatchError),
23
24
  stream: true,
24
25
  }),
25
26
  Rpc.make('SyncWsRpc.Push', {
@@ -29,7 +30,7 @@ export class SyncWsRpc extends RpcGroup.make(
29
30
  ...SyncMessage.PushRequest.fields,
30
31
  }),
31
32
  success: SyncMessage.PushAck,
32
- error: InvalidPushError,
33
+ error: Schema.Union(UnknownError, ServerAheadError, BackendIdMismatchError),
33
34
  }),
34
35
  // Ping <> Pong is handled by DO WS auto-response
35
36
  // TODO add admin RPCs