@rocicorp/zero 1.11.0-canary.4 → 1.11.0-canary.40

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 (1015) hide show
  1. package/out/analyze-query/src/analyze-cli.js +4 -4
  2. package/out/analyze-query/src/analyze-cli.js.map +1 -1
  3. package/out/analyze-query/src/bin-analyze.js +13 -12
  4. package/out/analyze-query/src/bin-analyze.js.map +1 -1
  5. package/out/analyze-query/src/bin-transform.js +1 -1
  6. package/out/analyze-query/src/bin-transform.js.map +1 -1
  7. package/out/ast-to-zql/src/ast-to-zql.d.ts +8 -1
  8. package/out/ast-to-zql/src/ast-to-zql.d.ts.map +1 -1
  9. package/out/ast-to-zql/src/ast-to-zql.js +25 -25
  10. package/out/ast-to-zql/src/ast-to-zql.js.map +1 -1
  11. package/out/otel/src/log-options.d.ts +16 -0
  12. package/out/otel/src/log-options.d.ts.map +1 -1
  13. package/out/otel/src/log-options.js +60 -6
  14. package/out/otel/src/log-options.js.map +1 -1
  15. package/out/replicache/src/bg-interval.d.ts +2 -1
  16. package/out/replicache/src/bg-interval.d.ts.map +1 -1
  17. package/out/replicache/src/bg-interval.js +13 -4
  18. package/out/replicache/src/bg-interval.js.map +1 -1
  19. package/out/replicache/src/btree/node.d.ts.map +1 -1
  20. package/out/replicache/src/btree/node.js +3 -6
  21. package/out/replicache/src/btree/node.js.map +1 -1
  22. package/out/replicache/src/dag/gc.d.ts.map +1 -1
  23. package/out/replicache/src/dag/gc.js +8 -11
  24. package/out/replicache/src/dag/gc.js.map +1 -1
  25. package/out/replicache/src/dag/invalid-ref-count-error.d.ts +12 -0
  26. package/out/replicache/src/dag/invalid-ref-count-error.d.ts.map +1 -0
  27. package/out/replicache/src/dag/invalid-ref-count-error.js +19 -0
  28. package/out/replicache/src/dag/invalid-ref-count-error.js.map +1 -0
  29. package/out/replicache/src/dag/lazy-store.d.ts +17 -4
  30. package/out/replicache/src/dag/lazy-store.d.ts.map +1 -1
  31. package/out/replicache/src/dag/lazy-store.js +35 -9
  32. package/out/replicache/src/dag/lazy-store.js.map +1 -1
  33. package/out/replicache/src/dag/store-impl.d.ts +12 -2
  34. package/out/replicache/src/dag/store-impl.d.ts.map +1 -1
  35. package/out/replicache/src/dag/store-impl.js +29 -9
  36. package/out/replicache/src/dag/store-impl.js.map +1 -1
  37. package/out/replicache/src/db/rebase.d.ts +14 -2
  38. package/out/replicache/src/db/rebase.d.ts.map +1 -1
  39. package/out/replicache/src/db/rebase.js +27 -5
  40. package/out/replicache/src/db/rebase.js.map +1 -1
  41. package/out/replicache/src/get-kv-store-provider.d.ts +1 -1
  42. package/out/replicache/src/get-kv-store-provider.d.ts.map +1 -1
  43. package/out/replicache/src/get-kv-store-provider.js +4 -4
  44. package/out/replicache/src/get-kv-store-provider.js.map +1 -1
  45. package/out/replicache/src/kv/expo-sqlite/store.d.ts.map +1 -1
  46. package/out/replicache/src/kv/expo-sqlite/store.js +28 -5
  47. package/out/replicache/src/kv/expo-sqlite/store.js.map +1 -1
  48. package/out/replicache/src/kv/idb-store.d.ts +18 -0
  49. package/out/replicache/src/kv/idb-store.d.ts.map +1 -1
  50. package/out/replicache/src/kv/idb-store.js +30 -2
  51. package/out/replicache/src/kv/idb-store.js.map +1 -1
  52. package/out/replicache/src/kv/mem-fallback-store.d.ts +54 -0
  53. package/out/replicache/src/kv/mem-fallback-store.d.ts.map +1 -0
  54. package/out/replicache/src/kv/mem-fallback-store.js +177 -0
  55. package/out/replicache/src/kv/mem-fallback-store.js.map +1 -0
  56. package/out/replicache/src/kv/mem-store.d.ts +1 -0
  57. package/out/replicache/src/kv/mem-store.d.ts.map +1 -1
  58. package/out/replicache/src/kv/mem-store.js +3 -0
  59. package/out/replicache/src/kv/mem-store.js.map +1 -1
  60. package/out/replicache/src/kv/op-sqlite/store.d.ts.map +1 -1
  61. package/out/replicache/src/kv/op-sqlite/store.js +4 -4
  62. package/out/replicache/src/kv/op-sqlite/store.js.map +1 -1
  63. package/out/replicache/src/kv/sqlite-store.d.ts +22 -1
  64. package/out/replicache/src/kv/sqlite-store.d.ts.map +1 -1
  65. package/out/replicache/src/kv/sqlite-store.js +159 -14
  66. package/out/replicache/src/kv/sqlite-store.js.map +1 -1
  67. package/out/replicache/src/kv/store.d.ts +6 -0
  68. package/out/replicache/src/kv/store.d.ts.map +1 -1
  69. package/out/replicache/src/new-client-channel.js.map +1 -1
  70. package/out/replicache/src/persist/client-gc.d.ts +2 -1
  71. package/out/replicache/src/persist/client-gc.d.ts.map +1 -1
  72. package/out/replicache/src/persist/client-gc.js +2 -2
  73. package/out/replicache/src/persist/client-gc.js.map +1 -1
  74. package/out/replicache/src/persist/client-group-gc.d.ts +2 -1
  75. package/out/replicache/src/persist/client-group-gc.d.ts.map +1 -1
  76. package/out/replicache/src/persist/client-group-gc.js +2 -2
  77. package/out/replicache/src/persist/client-group-gc.js.map +1 -1
  78. package/out/replicache/src/persist/clients.d.ts +2 -2
  79. package/out/replicache/src/persist/collect-idb-databases.d.ts +28 -8
  80. package/out/replicache/src/persist/collect-idb-databases.d.ts.map +1 -1
  81. package/out/replicache/src/persist/collect-idb-databases.js +97 -20
  82. package/out/replicache/src/persist/collect-idb-databases.js.map +1 -1
  83. package/out/replicache/src/persist/heartbeat.d.ts +2 -1
  84. package/out/replicache/src/persist/heartbeat.d.ts.map +1 -1
  85. package/out/replicache/src/persist/heartbeat.js +2 -2
  86. package/out/replicache/src/persist/heartbeat.js.map +1 -1
  87. package/out/replicache/src/persist/idb-databases-store-db-name.js +1 -1
  88. package/out/replicache/src/persist/idb-databases-store-db-name.js.map +1 -1
  89. package/out/replicache/src/persist/persist.d.ts.map +1 -1
  90. package/out/replicache/src/persist/persist.js +18 -8
  91. package/out/replicache/src/persist/persist.js.map +1 -1
  92. package/out/replicache/src/persist/refresh.js +6 -2
  93. package/out/replicache/src/persist/refresh.js.map +1 -1
  94. package/out/replicache/src/replicache-impl.d.ts +85 -3
  95. package/out/replicache/src/replicache-impl.d.ts.map +1 -1
  96. package/out/replicache/src/replicache-impl.js +321 -29
  97. package/out/replicache/src/replicache-impl.js.map +1 -1
  98. package/out/replicache/src/replicache-options.d.ts +9 -0
  99. package/out/replicache/src/replicache-options.d.ts.map +1 -1
  100. package/out/replicache/src/storage-failure.d.ts +37 -0
  101. package/out/replicache/src/storage-failure.d.ts.map +1 -0
  102. package/out/replicache/src/storage-failure.js +31 -0
  103. package/out/replicache/src/storage-failure.js.map +1 -0
  104. package/out/shared/src/arrays.d.ts +5 -0
  105. package/out/shared/src/arrays.d.ts.map +1 -1
  106. package/out/shared/src/arrays.js +8 -10
  107. package/out/shared/src/arrays.js.map +1 -1
  108. package/out/shared/src/centroid.d.ts +0 -1
  109. package/out/shared/src/centroid.d.ts.map +1 -1
  110. package/out/shared/src/centroid.js +1 -4
  111. package/out/shared/src/centroid.js.map +1 -1
  112. package/out/shared/src/error.d.ts +11 -0
  113. package/out/shared/src/error.d.ts.map +1 -1
  114. package/out/shared/src/error.js +35 -1
  115. package/out/shared/src/error.js.map +1 -1
  116. package/out/shared/src/hash.d.ts.map +1 -1
  117. package/out/shared/src/hash.js +32 -7
  118. package/out/shared/src/hash.js.map +1 -1
  119. package/out/shared/src/iterables.d.ts +2 -0
  120. package/out/shared/src/iterables.d.ts.map +1 -1
  121. package/out/shared/src/iterables.js +18 -1
  122. package/out/shared/src/iterables.js.map +1 -1
  123. package/out/shared/src/map.d.ts +24 -2
  124. package/out/shared/src/map.d.ts.map +1 -1
  125. package/out/shared/src/map.js +18 -4
  126. package/out/shared/src/map.js.map +1 -1
  127. package/out/shared/src/options-types.d.ts +2 -2
  128. package/out/shared/src/options.d.ts.map +1 -1
  129. package/out/shared/src/options.js +10 -7
  130. package/out/shared/src/options.js.map +1 -1
  131. package/out/shared/src/random-values.js +12 -1
  132. package/out/shared/src/random-values.js.map +1 -1
  133. package/out/shared/src/ring-buffer.d.ts +10 -0
  134. package/out/shared/src/ring-buffer.d.ts.map +1 -1
  135. package/out/shared/src/ring-buffer.js +26 -1
  136. package/out/shared/src/ring-buffer.js.map +1 -1
  137. package/out/shared/src/tdigest.d.ts +10 -0
  138. package/out/shared/src/tdigest.d.ts.map +1 -1
  139. package/out/shared/src/tdigest.js +147 -63
  140. package/out/shared/src/tdigest.js.map +1 -1
  141. package/out/shared/src/valita.d.ts +88 -0
  142. package/out/shared/src/valita.d.ts.map +1 -1
  143. package/out/shared/src/valita.js +141 -23
  144. package/out/shared/src/valita.js.map +1 -1
  145. package/out/z2s/src/compiler.d.ts.map +1 -1
  146. package/out/z2s/src/compiler.js +10 -6
  147. package/out/z2s/src/compiler.js.map +1 -1
  148. package/out/z2s/src/sql.d.ts.map +1 -1
  149. package/out/z2s/src/sql.js +9 -5
  150. package/out/z2s/src/sql.js.map +1 -1
  151. package/out/zero/package.js +5 -6
  152. package/out/zero/package.js.map +1 -1
  153. package/out/zero/src/zero.js +2 -1
  154. package/out/zero-cache/src/auth/write-authorizer.d.ts.map +1 -1
  155. package/out/zero-cache/src/auth/write-authorizer.js +1 -0
  156. package/out/zero-cache/src/auth/write-authorizer.js.map +1 -1
  157. package/out/zero-cache/src/config/normalize.d.ts +1 -0
  158. package/out/zero-cache/src/config/normalize.d.ts.map +1 -1
  159. package/out/zero-cache/src/config/normalize.js +46 -4
  160. package/out/zero-cache/src/config/normalize.js.map +1 -1
  161. package/out/zero-cache/src/config/zero-config.d.ts +146 -24
  162. package/out/zero-cache/src/config/zero-config.d.ts.map +1 -1
  163. package/out/zero-cache/src/config/zero-config.js +494 -158
  164. package/out/zero-cache/src/config/zero-config.js.map +1 -1
  165. package/out/zero-cache/src/custom/fetch.d.ts +1 -1
  166. package/out/zero-cache/src/custom/fetch.d.ts.map +1 -1
  167. package/out/zero-cache/src/custom/fetch.js.map +1 -1
  168. package/out/zero-cache/src/db/lite-tables.d.ts.map +1 -1
  169. package/out/zero-cache/src/db/lite-tables.js +3 -4
  170. package/out/zero-cache/src/db/lite-tables.js.map +1 -1
  171. package/out/zero-cache/src/db/migration-lite.d.ts.map +1 -1
  172. package/out/zero-cache/src/db/migration-lite.js +5 -3
  173. package/out/zero-cache/src/db/migration-lite.js.map +1 -1
  174. package/out/zero-cache/src/observability/events.js +4 -1
  175. package/out/zero-cache/src/observability/events.js.map +1 -1
  176. package/out/zero-cache/src/observability/log-throttle.d.ts +44 -0
  177. package/out/zero-cache/src/observability/log-throttle.d.ts.map +1 -0
  178. package/out/zero-cache/src/observability/log-throttle.js +76 -0
  179. package/out/zero-cache/src/observability/log-throttle.js.map +1 -0
  180. package/out/zero-cache/src/observability/metrics.d.ts.map +1 -1
  181. package/out/zero-cache/src/observability/metrics.js +2 -7
  182. package/out/zero-cache/src/observability/metrics.js.map +1 -1
  183. package/out/zero-cache/src/scripts/permissions.d.ts +16 -0
  184. package/out/zero-cache/src/scripts/permissions.d.ts.map +1 -1
  185. package/out/zero-cache/src/scripts/permissions.js +3 -3
  186. package/out/zero-cache/src/scripts/permissions.js.map +1 -1
  187. package/out/zero-cache/src/server/change-streamer.d.ts.map +1 -1
  188. package/out/zero-cache/src/server/change-streamer.js +123 -87
  189. package/out/zero-cache/src/server/change-streamer.js.map +1 -1
  190. package/out/zero-cache/src/server/inspector-delegate.d.ts +28 -2
  191. package/out/zero-cache/src/server/inspector-delegate.d.ts.map +1 -1
  192. package/out/zero-cache/src/server/inspector-delegate.js +37 -17
  193. package/out/zero-cache/src/server/inspector-delegate.js.map +1 -1
  194. package/out/zero-cache/src/server/main.d.ts.map +1 -1
  195. package/out/zero-cache/src/server/main.js +13 -2
  196. package/out/zero-cache/src/server/main.js.map +1 -1
  197. package/out/zero-cache/src/server/mutator.js +2 -0
  198. package/out/zero-cache/src/server/mutator.js.map +1 -1
  199. package/out/zero-cache/src/server/reaper.d.ts.map +1 -1
  200. package/out/zero-cache/src/server/reaper.js +2 -0
  201. package/out/zero-cache/src/server/reaper.js.map +1 -1
  202. package/out/zero-cache/src/server/replicator.d.ts +7 -0
  203. package/out/zero-cache/src/server/replicator.d.ts.map +1 -1
  204. package/out/zero-cache/src/server/replicator.js +103 -22
  205. package/out/zero-cache/src/server/replicator.js.map +1 -1
  206. package/out/zero-cache/src/server/runner/run-worker.d.ts.map +1 -1
  207. package/out/zero-cache/src/server/runner/run-worker.js +12 -6
  208. package/out/zero-cache/src/server/runner/run-worker.js.map +1 -1
  209. package/out/zero-cache/src/server/runner/zero-dispatcher.d.ts.map +1 -1
  210. package/out/zero-cache/src/server/runner/zero-dispatcher.js +5 -0
  211. package/out/zero-cache/src/server/runner/zero-dispatcher.js.map +1 -1
  212. package/out/zero-cache/src/server/slot-keeper.d.ts +26 -0
  213. package/out/zero-cache/src/server/slot-keeper.d.ts.map +1 -0
  214. package/out/zero-cache/src/server/slot-keeper.js +181 -0
  215. package/out/zero-cache/src/server/slot-keeper.js.map +1 -0
  216. package/out/zero-cache/src/server/syncer-assigner.d.ts +14 -0
  217. package/out/zero-cache/src/server/syncer-assigner.d.ts.map +1 -0
  218. package/out/zero-cache/src/server/syncer-assigner.js +72 -0
  219. package/out/zero-cache/src/server/syncer-assigner.js.map +1 -0
  220. package/out/zero-cache/src/server/syncer.d.ts.map +1 -1
  221. package/out/zero-cache/src/server/syncer.js +40 -2
  222. package/out/zero-cache/src/server/syncer.js.map +1 -1
  223. package/out/zero-cache/src/server/worker-dispatcher.d.ts.map +1 -1
  224. package/out/zero-cache/src/server/worker-dispatcher.js +21 -4
  225. package/out/zero-cache/src/server/worker-dispatcher.js.map +1 -1
  226. package/out/zero-cache/src/server/worker-urls.d.ts +1 -0
  227. package/out/zero-cache/src/server/worker-urls.d.ts.map +1 -1
  228. package/out/zero-cache/src/server/worker-urls.js +2 -1
  229. package/out/zero-cache/src/server/worker-urls.js.map +1 -1
  230. package/out/zero-cache/src/services/analyze.d.ts.map +1 -1
  231. package/out/zero-cache/src/services/analyze.js +11 -9
  232. package/out/zero-cache/src/services/analyze.js.map +1 -1
  233. package/out/zero-cache/src/services/change-source/common/backfill-manager.d.ts.map +1 -1
  234. package/out/zero-cache/src/services/change-source/common/backfill-manager.js +198 -24
  235. package/out/zero-cache/src/services/change-source/common/backfill-manager.js.map +1 -1
  236. package/out/zero-cache/src/services/change-source/common/change-stream-multiplexer.d.ts.map +1 -1
  237. package/out/zero-cache/src/services/change-source/common/change-stream-multiplexer.js +16 -4
  238. package/out/zero-cache/src/services/change-source/common/change-stream-multiplexer.js.map +1 -1
  239. package/out/zero-cache/src/services/change-source/common/init-cleanup.d.ts +24 -0
  240. package/out/zero-cache/src/services/change-source/common/init-cleanup.d.ts.map +1 -0
  241. package/out/zero-cache/src/services/change-source/common/init-cleanup.js +44 -0
  242. package/out/zero-cache/src/services/change-source/common/init-cleanup.js.map +1 -0
  243. package/out/zero-cache/src/services/change-source/common/replica-restore.d.ts +82 -2
  244. package/out/zero-cache/src/services/change-source/common/replica-restore.d.ts.map +1 -1
  245. package/out/zero-cache/src/services/change-source/common/replica-restore.js +21 -10
  246. package/out/zero-cache/src/services/change-source/common/replica-restore.js.map +1 -1
  247. package/out/zero-cache/src/services/change-source/common/replica-schema.d.ts +1 -0
  248. package/out/zero-cache/src/services/change-source/common/replica-schema.d.ts.map +1 -1
  249. package/out/zero-cache/src/services/change-source/common/replica-schema.js +15 -3
  250. package/out/zero-cache/src/services/change-source/common/replica-schema.js.map +1 -1
  251. package/out/zero-cache/src/services/change-source/custom/change-source.d.ts +1 -1
  252. package/out/zero-cache/src/services/change-source/custom/change-source.d.ts.map +1 -1
  253. package/out/zero-cache/src/services/change-source/custom/change-source.js +7 -3
  254. package/out/zero-cache/src/services/change-source/custom/change-source.js.map +1 -1
  255. package/out/zero-cache/src/services/change-source/pg/backfill-stream.d.ts +9 -0
  256. package/out/zero-cache/src/services/change-source/pg/backfill-stream.d.ts.map +1 -1
  257. package/out/zero-cache/src/services/change-source/pg/backfill-stream.js +207 -20
  258. package/out/zero-cache/src/services/change-source/pg/backfill-stream.js.map +1 -1
  259. package/out/zero-cache/src/services/change-source/pg/change-source-init.d.ts +65 -0
  260. package/out/zero-cache/src/services/change-source/pg/change-source-init.d.ts.map +1 -0
  261. package/out/zero-cache/src/services/change-source/pg/change-source-init.js +312 -0
  262. package/out/zero-cache/src/services/change-source/pg/change-source-init.js.map +1 -0
  263. package/out/zero-cache/src/services/change-source/pg/change-source.d.ts +31 -18
  264. package/out/zero-cache/src/services/change-source/pg/change-source.d.ts.map +1 -1
  265. package/out/zero-cache/src/services/change-source/pg/change-source.js +132 -157
  266. package/out/zero-cache/src/services/change-source/pg/change-source.js.map +1 -1
  267. package/out/zero-cache/src/services/change-source/pg/initial-sync.d.ts +44 -2
  268. package/out/zero-cache/src/services/change-source/pg/initial-sync.d.ts.map +1 -1
  269. package/out/zero-cache/src/services/change-source/pg/initial-sync.js +60 -23
  270. package/out/zero-cache/src/services/change-source/pg/initial-sync.js.map +1 -1
  271. package/out/zero-cache/src/services/change-source/pg/logical-replication/stream.d.ts +66 -1
  272. package/out/zero-cache/src/services/change-source/pg/logical-replication/stream.d.ts.map +1 -1
  273. package/out/zero-cache/src/services/change-source/pg/logical-replication/stream.js +207 -24
  274. package/out/zero-cache/src/services/change-source/pg/logical-replication/stream.js.map +1 -1
  275. package/out/zero-cache/src/services/change-source/pg/replication-slot-cleanup-monitor.d.ts +16 -0
  276. package/out/zero-cache/src/services/change-source/pg/replication-slot-cleanup-monitor.d.ts.map +1 -0
  277. package/out/zero-cache/src/services/change-source/pg/replication-slot-cleanup-monitor.js +113 -0
  278. package/out/zero-cache/src/services/change-source/pg/replication-slot-cleanup-monitor.js.map +1 -0
  279. package/out/zero-cache/src/services/change-source/pg/replication-slots.d.ts +66 -21
  280. package/out/zero-cache/src/services/change-source/pg/replication-slots.d.ts.map +1 -1
  281. package/out/zero-cache/src/services/change-source/pg/replication-slots.js +274 -68
  282. package/out/zero-cache/src/services/change-source/pg/replication-slots.js.map +1 -1
  283. package/out/zero-cache/src/services/change-source/pg/schema/index-predicate.d.ts.map +1 -1
  284. package/out/zero-cache/src/services/change-source/pg/schema/index-predicate.js +68 -8
  285. package/out/zero-cache/src/services/change-source/pg/schema/index-predicate.js.map +1 -1
  286. package/out/zero-cache/src/services/change-source/pg/schema/init.d.ts.map +1 -1
  287. package/out/zero-cache/src/services/change-source/pg/schema/init.js +46 -1
  288. package/out/zero-cache/src/services/change-source/pg/schema/init.js.map +1 -1
  289. package/out/zero-cache/src/services/change-source/pg/schema/replica-stage-enum.d.ts +10 -0
  290. package/out/zero-cache/src/services/change-source/pg/schema/replica-stage-enum.d.ts.map +1 -0
  291. package/out/zero-cache/src/services/change-source/pg/schema/replica-stage-enum.js +6 -0
  292. package/out/zero-cache/src/services/change-source/pg/schema/replica-stage-enum.js.map +1 -0
  293. package/out/zero-cache/src/services/change-source/pg/schema/shard.d.ts +68 -27
  294. package/out/zero-cache/src/services/change-source/pg/schema/shard.d.ts.map +1 -1
  295. package/out/zero-cache/src/services/change-source/pg/schema/shard.js +116 -35
  296. package/out/zero-cache/src/services/change-source/pg/schema/shard.js.map +1 -1
  297. package/out/zero-cache/src/services/change-source/protocol/backfill-progress.d.ts +68 -0
  298. package/out/zero-cache/src/services/change-source/protocol/backfill-progress.d.ts.map +1 -0
  299. package/out/zero-cache/src/services/change-source/protocol/backfill-progress.js +141 -0
  300. package/out/zero-cache/src/services/change-source/protocol/backfill-progress.js.map +1 -0
  301. package/out/zero-cache/src/services/change-source/protocol/current/data.d.ts +45 -2
  302. package/out/zero-cache/src/services/change-source/protocol/current/data.d.ts.map +1 -1
  303. package/out/zero-cache/src/services/change-source/protocol/current/data.js +10 -1
  304. package/out/zero-cache/src/services/change-source/protocol/current/data.js.map +1 -1
  305. package/out/zero-cache/src/services/change-source/protocol/current/downstream.d.ts +60 -3
  306. package/out/zero-cache/src/services/change-source/protocol/current/downstream.d.ts.map +1 -1
  307. package/out/zero-cache/src/services/change-source/protocol/current/upstream.d.ts +23 -10
  308. package/out/zero-cache/src/services/change-source/protocol/current/upstream.d.ts.map +1 -1
  309. package/out/zero-cache/src/services/change-source/protocol/current/upstream.js +17 -7
  310. package/out/zero-cache/src/services/change-source/protocol/current/upstream.js.map +1 -1
  311. package/out/zero-cache/src/services/change-source/protocol/current.js +2 -1
  312. package/out/zero-cache/src/services/change-streamer/backfill-state-tracker.d.ts +72 -0
  313. package/out/zero-cache/src/services/change-streamer/backfill-state-tracker.d.ts.map +1 -0
  314. package/out/zero-cache/src/services/change-streamer/backfill-state-tracker.js +162 -0
  315. package/out/zero-cache/src/services/change-streamer/backfill-state-tracker.js.map +1 -0
  316. package/out/zero-cache/src/services/change-streamer/backfill-state.d.ts +50 -0
  317. package/out/zero-cache/src/services/change-streamer/backfill-state.d.ts.map +1 -0
  318. package/out/zero-cache/src/services/change-streamer/backfill-state.js +268 -0
  319. package/out/zero-cache/src/services/change-streamer/backfill-state.js.map +1 -0
  320. package/out/zero-cache/src/services/change-streamer/backup-cleanup-monitor-factory.d.ts.map +1 -1
  321. package/out/zero-cache/src/services/change-streamer/backup-cleanup-monitor-factory.js +6 -17
  322. package/out/zero-cache/src/services/change-streamer/backup-cleanup-monitor-factory.js.map +1 -1
  323. package/out/zero-cache/src/services/change-streamer/backup-monitor.d.ts.map +1 -1
  324. package/out/zero-cache/src/services/change-streamer/backup-monitor.js +59 -8
  325. package/out/zero-cache/src/services/change-streamer/backup-monitor.js.map +1 -1
  326. package/out/zero-cache/src/services/change-streamer/broadcast.d.ts +8 -2
  327. package/out/zero-cache/src/services/change-streamer/broadcast.d.ts.map +1 -1
  328. package/out/zero-cache/src/services/change-streamer/broadcast.js +24 -4
  329. package/out/zero-cache/src/services/change-streamer/broadcast.js.map +1 -1
  330. package/out/zero-cache/src/services/change-streamer/change-log-codec.d.ts +19 -4
  331. package/out/zero-cache/src/services/change-streamer/change-log-codec.d.ts.map +1 -1
  332. package/out/zero-cache/src/services/change-streamer/change-log-codec.js +28 -8
  333. package/out/zero-cache/src/services/change-streamer/change-log-codec.js.map +1 -1
  334. package/out/zero-cache/src/services/change-streamer/change-log-initializer.d.ts +17 -0
  335. package/out/zero-cache/src/services/change-streamer/change-log-initializer.d.ts.map +1 -1
  336. package/out/zero-cache/src/services/change-streamer/change-log-initializer.js +44 -1
  337. package/out/zero-cache/src/services/change-streamer/change-log-initializer.js.map +1 -1
  338. package/out/zero-cache/src/services/change-streamer/change-streamer-http.d.ts +54 -6
  339. package/out/zero-cache/src/services/change-streamer/change-streamer-http.d.ts.map +1 -1
  340. package/out/zero-cache/src/services/change-streamer/change-streamer-http.js +145 -35
  341. package/out/zero-cache/src/services/change-streamer/change-streamer-http.js.map +1 -1
  342. package/out/zero-cache/src/services/change-streamer/change-streamer-service.d.ts +36 -0
  343. package/out/zero-cache/src/services/change-streamer/change-streamer-service.d.ts.map +1 -1
  344. package/out/zero-cache/src/services/change-streamer/change-streamer-service.js +252 -111
  345. package/out/zero-cache/src/services/change-streamer/change-streamer-service.js.map +1 -1
  346. package/out/zero-cache/src/services/change-streamer/change-streamer.d.ts +161 -17
  347. package/out/zero-cache/src/services/change-streamer/change-streamer.d.ts.map +1 -1
  348. package/out/zero-cache/src/services/change-streamer/change-streamer.js +33 -2
  349. package/out/zero-cache/src/services/change-streamer/change-streamer.js.map +1 -1
  350. package/out/zero-cache/src/services/change-streamer/drain-tracker.d.ts +24 -0
  351. package/out/zero-cache/src/services/change-streamer/drain-tracker.d.ts.map +1 -0
  352. package/out/zero-cache/src/services/change-streamer/drain-tracker.js +67 -0
  353. package/out/zero-cache/src/services/change-streamer/drain-tracker.js.map +1 -0
  354. package/out/zero-cache/src/services/change-streamer/forwarder.d.ts +3 -3
  355. package/out/zero-cache/src/services/change-streamer/forwarder.d.ts.map +1 -1
  356. package/out/zero-cache/src/services/change-streamer/forwarder.js +36 -5
  357. package/out/zero-cache/src/services/change-streamer/forwarder.js.map +1 -1
  358. package/out/zero-cache/src/services/change-streamer/litestream-sync-requester.d.ts +53 -0
  359. package/out/zero-cache/src/services/change-streamer/litestream-sync-requester.d.ts.map +1 -0
  360. package/out/zero-cache/src/services/change-streamer/litestream-sync-requester.js +156 -0
  361. package/out/zero-cache/src/services/change-streamer/litestream-sync-requester.js.map +1 -0
  362. package/out/zero-cache/src/services/change-streamer/restore-admission.d.ts +243 -0
  363. package/out/zero-cache/src/services/change-streamer/restore-admission.d.ts.map +1 -0
  364. package/out/zero-cache/src/services/change-streamer/restore-admission.js +317 -0
  365. package/out/zero-cache/src/services/change-streamer/restore-admission.js.map +1 -0
  366. package/out/zero-cache/src/services/change-streamer/schema/tables.d.ts +58 -1
  367. package/out/zero-cache/src/services/change-streamer/schema/tables.d.ts.map +1 -1
  368. package/out/zero-cache/src/services/change-streamer/schema/tables.js +107 -16
  369. package/out/zero-cache/src/services/change-streamer/schema/tables.js.map +1 -1
  370. package/out/zero-cache/src/services/change-streamer/snapshot-message.d.ts +92 -0
  371. package/out/zero-cache/src/services/change-streamer/snapshot-message.d.ts.map +1 -0
  372. package/out/zero-cache/src/services/change-streamer/snapshot-message.js +42 -0
  373. package/out/zero-cache/src/services/change-streamer/snapshot-message.js.map +1 -0
  374. package/out/zero-cache/src/services/change-streamer/snapshot-reservations.d.ts +14 -2
  375. package/out/zero-cache/src/services/change-streamer/snapshot-reservations.d.ts.map +1 -1
  376. package/out/zero-cache/src/services/change-streamer/snapshot-reservations.js +23 -10
  377. package/out/zero-cache/src/services/change-streamer/snapshot-reservations.js.map +1 -1
  378. package/out/zero-cache/src/services/change-streamer/snapshot.d.ts +7 -69
  379. package/out/zero-cache/src/services/change-streamer/snapshot.d.ts.map +1 -1
  380. package/out/zero-cache/src/services/change-streamer/snapshot.js +21 -53
  381. package/out/zero-cache/src/services/change-streamer/snapshot.js.map +1 -1
  382. package/out/zero-cache/src/services/change-streamer/sqlite-change-log-writer.d.ts +6 -1
  383. package/out/zero-cache/src/services/change-streamer/sqlite-change-log-writer.d.ts.map +1 -1
  384. package/out/zero-cache/src/services/change-streamer/sqlite-change-log-writer.js +27 -9
  385. package/out/zero-cache/src/services/change-streamer/sqlite-change-log-writer.js.map +1 -1
  386. package/out/zero-cache/src/services/change-streamer/storer.d.ts +95 -4
  387. package/out/zero-cache/src/services/change-streamer/storer.d.ts.map +1 -1
  388. package/out/zero-cache/src/services/change-streamer/storer.js +294 -84
  389. package/out/zero-cache/src/services/change-streamer/storer.js.map +1 -1
  390. package/out/zero-cache/src/services/change-streamer/subscribe.d.ts +485 -0
  391. package/out/zero-cache/src/services/change-streamer/subscribe.d.ts.map +1 -0
  392. package/out/zero-cache/src/services/change-streamer/subscribe.js +93 -0
  393. package/out/zero-cache/src/services/change-streamer/subscribe.js.map +1 -0
  394. package/out/zero-cache/src/services/change-streamer/subscriber.d.ts +80 -2
  395. package/out/zero-cache/src/services/change-streamer/subscriber.d.ts.map +1 -1
  396. package/out/zero-cache/src/services/change-streamer/subscriber.js +157 -20
  397. package/out/zero-cache/src/services/change-streamer/subscriber.js.map +1 -1
  398. package/out/zero-cache/src/services/change-streamer/upstream-acker.d.ts +19 -1
  399. package/out/zero-cache/src/services/change-streamer/upstream-acker.d.ts.map +1 -1
  400. package/out/zero-cache/src/services/change-streamer/upstream-acker.js +23 -3
  401. package/out/zero-cache/src/services/change-streamer/upstream-acker.js.map +1 -1
  402. package/out/zero-cache/src/services/http-service.d.ts +7 -1
  403. package/out/zero-cache/src/services/http-service.d.ts.map +1 -1
  404. package/out/zero-cache/src/services/http-service.js +14 -2
  405. package/out/zero-cache/src/services/http-service.js.map +1 -1
  406. package/out/zero-cache/src/services/life-cycle.d.ts +68 -2
  407. package/out/zero-cache/src/services/life-cycle.d.ts.map +1 -1
  408. package/out/zero-cache/src/services/life-cycle.js +155 -19
  409. package/out/zero-cache/src/services/life-cycle.js.map +1 -1
  410. package/out/zero-cache/src/services/litestream/commands.d.ts +35 -3
  411. package/out/zero-cache/src/services/litestream/commands.d.ts.map +1 -1
  412. package/out/zero-cache/src/services/litestream/commands.js +137 -35
  413. package/out/zero-cache/src/services/litestream/commands.js.map +1 -1
  414. package/out/zero-cache/src/services/litestream/config-v5.yml +6 -7
  415. package/out/zero-cache/src/services/litestream/litestream-checkpointer.js +51 -24
  416. package/out/zero-cache/src/services/litestream/litestream-checkpointer.js.map +1 -1
  417. package/out/zero-cache/src/services/litestream/litestream-controller.d.ts +10 -2
  418. package/out/zero-cache/src/services/litestream/litestream-controller.d.ts.map +1 -1
  419. package/out/zero-cache/src/services/litestream/litestream-controller.js +3 -2
  420. package/out/zero-cache/src/services/litestream/litestream-controller.js.map +1 -1
  421. package/out/zero-cache/src/services/litestream/restore-progress.d.ts +24 -0
  422. package/out/zero-cache/src/services/litestream/restore-progress.d.ts.map +1 -0
  423. package/out/zero-cache/src/services/litestream/restore-progress.js +91 -0
  424. package/out/zero-cache/src/services/litestream/restore-progress.js.map +1 -0
  425. package/out/zero-cache/src/services/mutagen/mutagen.d.ts +5 -0
  426. package/out/zero-cache/src/services/mutagen/mutagen.d.ts.map +1 -1
  427. package/out/zero-cache/src/services/mutagen/mutagen.js +7 -1
  428. package/out/zero-cache/src/services/mutagen/mutagen.js.map +1 -1
  429. package/out/zero-cache/src/services/mutagen/pusher.d.ts.map +1 -1
  430. package/out/zero-cache/src/services/mutagen/pusher.js +5 -6
  431. package/out/zero-cache/src/services/mutagen/pusher.js.map +1 -1
  432. package/out/zero-cache/src/services/plannerz.d.ts +163 -0
  433. package/out/zero-cache/src/services/plannerz.d.ts.map +1 -0
  434. package/out/zero-cache/src/services/plannerz.js +267 -0
  435. package/out/zero-cache/src/services/plannerz.js.map +1 -0
  436. package/out/zero-cache/src/services/profz.d.ts +30 -0
  437. package/out/zero-cache/src/services/profz.d.ts.map +1 -0
  438. package/out/zero-cache/src/services/profz.js +163 -0
  439. package/out/zero-cache/src/services/profz.js.map +1 -0
  440. package/out/zero-cache/src/services/replicator/change-log-cookies.js +1 -1
  441. package/out/zero-cache/src/services/replicator/change-log-cookies.js.map +1 -1
  442. package/out/zero-cache/src/services/replicator/change-log-stream-writer.d.ts +5 -4
  443. package/out/zero-cache/src/services/replicator/change-log-stream-writer.d.ts.map +1 -1
  444. package/out/zero-cache/src/services/replicator/change-log-stream-writer.js +20 -22
  445. package/out/zero-cache/src/services/replicator/change-log-stream-writer.js.map +1 -1
  446. package/out/zero-cache/src/services/replicator/change-processor.d.ts.map +1 -1
  447. package/out/zero-cache/src/services/replicator/change-processor.js +51 -5
  448. package/out/zero-cache/src/services/replicator/change-processor.js.map +1 -1
  449. package/out/zero-cache/src/services/replicator/drain-handler.d.ts +74 -0
  450. package/out/zero-cache/src/services/replicator/drain-handler.d.ts.map +1 -0
  451. package/out/zero-cache/src/services/replicator/drain-handler.js +185 -0
  452. package/out/zero-cache/src/services/replicator/drain-handler.js.map +1 -0
  453. package/out/zero-cache/src/services/replicator/incremental-sync.d.ts +6 -2
  454. package/out/zero-cache/src/services/replicator/incremental-sync.d.ts.map +1 -1
  455. package/out/zero-cache/src/services/replicator/incremental-sync.js +114 -28
  456. package/out/zero-cache/src/services/replicator/incremental-sync.js.map +1 -1
  457. package/out/zero-cache/src/services/replicator/replication-status.d.ts +35 -1
  458. package/out/zero-cache/src/services/replicator/replication-status.d.ts.map +1 -1
  459. package/out/zero-cache/src/services/replicator/replication-status.js +99 -8
  460. package/out/zero-cache/src/services/replicator/replication-status.js.map +1 -1
  461. package/out/zero-cache/src/services/replicator/replicator.d.ts +5 -1
  462. package/out/zero-cache/src/services/replicator/replicator.d.ts.map +1 -1
  463. package/out/zero-cache/src/services/replicator/replicator.js +5 -2
  464. package/out/zero-cache/src/services/replicator/replicator.js.map +1 -1
  465. package/out/zero-cache/src/services/replicator/reporter/recorder.d.ts +16 -1
  466. package/out/zero-cache/src/services/replicator/reporter/recorder.d.ts.map +1 -1
  467. package/out/zero-cache/src/services/replicator/reporter/recorder.js +70 -27
  468. package/out/zero-cache/src/services/replicator/reporter/recorder.js.map +1 -1
  469. package/out/zero-cache/src/services/replicator/schema/backfilling.d.ts +23 -2
  470. package/out/zero-cache/src/services/replicator/schema/backfilling.d.ts.map +1 -1
  471. package/out/zero-cache/src/services/replicator/schema/backfilling.js +54 -2
  472. package/out/zero-cache/src/services/replicator/schema/backfilling.js.map +1 -1
  473. package/out/zero-cache/src/services/replicator/sqlite-change-log-observability.d.ts +6 -6
  474. package/out/zero-cache/src/services/replicator/sqlite-change-log-observability.d.ts.map +1 -1
  475. package/out/zero-cache/src/services/replicator/sqlite-change-log-observability.js +19 -14
  476. package/out/zero-cache/src/services/replicator/sqlite-change-log-observability.js.map +1 -1
  477. package/out/zero-cache/src/services/replicator/write-worker-client.d.ts +11 -3
  478. package/out/zero-cache/src/services/replicator/write-worker-client.d.ts.map +1 -1
  479. package/out/zero-cache/src/services/replicator/write-worker-client.js.map +1 -1
  480. package/out/zero-cache/src/services/replicator/write-worker.js +5 -1
  481. package/out/zero-cache/src/services/replicator/write-worker.js.map +1 -1
  482. package/out/zero-cache/src/services/run-ast.d.ts +12 -0
  483. package/out/zero-cache/src/services/run-ast.d.ts.map +1 -1
  484. package/out/zero-cache/src/services/run-ast.js +42 -22
  485. package/out/zero-cache/src/services/run-ast.js.map +1 -1
  486. package/out/zero-cache/src/services/runner.d.ts +2 -1
  487. package/out/zero-cache/src/services/runner.d.ts.map +1 -1
  488. package/out/zero-cache/src/services/runner.js +10 -2
  489. package/out/zero-cache/src/services/runner.js.map +1 -1
  490. package/out/zero-cache/src/services/statz.d.ts +4 -0
  491. package/out/zero-cache/src/services/statz.d.ts.map +1 -1
  492. package/out/zero-cache/src/services/statz.js +22 -5
  493. package/out/zero-cache/src/services/statz.js.map +1 -1
  494. package/out/zero-cache/src/services/view-syncer/advancement-metrics.d.ts +26 -0
  495. package/out/zero-cache/src/services/view-syncer/advancement-metrics.d.ts.map +1 -0
  496. package/out/zero-cache/src/services/view-syncer/advancement-metrics.js +26 -0
  497. package/out/zero-cache/src/services/view-syncer/advancement-metrics.js.map +1 -0
  498. package/out/zero-cache/src/services/view-syncer/batch-pacer.d.ts +79 -0
  499. package/out/zero-cache/src/services/view-syncer/batch-pacer.d.ts.map +1 -0
  500. package/out/zero-cache/src/services/view-syncer/batch-pacer.js +249 -0
  501. package/out/zero-cache/src/services/view-syncer/batch-pacer.js.map +1 -0
  502. package/out/zero-cache/src/services/view-syncer/client-handler.d.ts +19 -2
  503. package/out/zero-cache/src/services/view-syncer/client-handler.d.ts.map +1 -1
  504. package/out/zero-cache/src/services/view-syncer/client-handler.js +42 -30
  505. package/out/zero-cache/src/services/view-syncer/client-handler.js.map +1 -1
  506. package/out/zero-cache/src/services/view-syncer/cvr-store.d.ts +27 -2
  507. package/out/zero-cache/src/services/view-syncer/cvr-store.d.ts.map +1 -1
  508. package/out/zero-cache/src/services/view-syncer/cvr-store.js +86 -21
  509. package/out/zero-cache/src/services/view-syncer/cvr-store.js.map +1 -1
  510. package/out/zero-cache/src/services/view-syncer/cvr.d.ts +75 -12
  511. package/out/zero-cache/src/services/view-syncer/cvr.d.ts.map +1 -1
  512. package/out/zero-cache/src/services/view-syncer/cvr.js +234 -43
  513. package/out/zero-cache/src/services/view-syncer/cvr.js.map +1 -1
  514. package/out/zero-cache/src/services/view-syncer/deferred-writes-budget.d.ts +81 -0
  515. package/out/zero-cache/src/services/view-syncer/deferred-writes-budget.d.ts.map +1 -0
  516. package/out/zero-cache/src/services/view-syncer/deferred-writes-budget.js +128 -0
  517. package/out/zero-cache/src/services/view-syncer/deferred-writes-budget.js.map +1 -0
  518. package/out/zero-cache/src/services/view-syncer/drain-coordinator.d.ts +14 -1
  519. package/out/zero-cache/src/services/view-syncer/drain-coordinator.d.ts.map +1 -1
  520. package/out/zero-cache/src/services/view-syncer/drain-coordinator.js +30 -4
  521. package/out/zero-cache/src/services/view-syncer/drain-coordinator.js.map +1 -1
  522. package/out/zero-cache/src/services/view-syncer/hydration-circuit-breaker.d.ts +51 -0
  523. package/out/zero-cache/src/services/view-syncer/hydration-circuit-breaker.d.ts.map +1 -0
  524. package/out/zero-cache/src/services/view-syncer/hydration-circuit-breaker.js +78 -0
  525. package/out/zero-cache/src/services/view-syncer/hydration-circuit-breaker.js.map +1 -0
  526. package/out/zero-cache/src/services/view-syncer/inspect-handler.d.ts +12 -2
  527. package/out/zero-cache/src/services/view-syncer/inspect-handler.d.ts.map +1 -1
  528. package/out/zero-cache/src/services/view-syncer/inspect-handler.js +29 -5
  529. package/out/zero-cache/src/services/view-syncer/inspect-handler.js.map +1 -1
  530. package/out/zero-cache/src/services/view-syncer/pipeline-driver.d.ts +165 -9
  531. package/out/zero-cache/src/services/view-syncer/pipeline-driver.d.ts.map +1 -1
  532. package/out/zero-cache/src/services/view-syncer/pipeline-driver.js +953 -209
  533. package/out/zero-cache/src/services/view-syncer/pipeline-driver.js.map +1 -1
  534. package/out/zero-cache/src/services/view-syncer/plan-warnings.d.ts +7 -0
  535. package/out/zero-cache/src/services/view-syncer/plan-warnings.d.ts.map +1 -0
  536. package/out/zero-cache/src/services/view-syncer/plan-warnings.js +35 -0
  537. package/out/zero-cache/src/services/view-syncer/plan-warnings.js.map +1 -0
  538. package/out/zero-cache/src/services/view-syncer/push-cost.d.ts +132 -0
  539. package/out/zero-cache/src/services/view-syncer/push-cost.d.ts.map +1 -0
  540. package/out/zero-cache/src/services/view-syncer/push-cost.js +164 -0
  541. package/out/zero-cache/src/services/view-syncer/push-cost.js.map +1 -0
  542. package/out/zero-cache/src/services/view-syncer/push-cutoff.d.ts +55 -0
  543. package/out/zero-cache/src/services/view-syncer/push-cutoff.d.ts.map +1 -0
  544. package/out/zero-cache/src/services/view-syncer/push-cutoff.js +56 -0
  545. package/out/zero-cache/src/services/view-syncer/push-cutoff.js.map +1 -0
  546. package/out/zero-cache/src/services/view-syncer/query-covering.d.ts.map +1 -1
  547. package/out/zero-cache/src/services/view-syncer/query-covering.js +2 -6
  548. package/out/zero-cache/src/services/view-syncer/query-covering.js.map +1 -1
  549. package/out/zero-cache/src/services/view-syncer/query-shape.d.ts +25 -0
  550. package/out/zero-cache/src/services/view-syncer/query-shape.d.ts.map +1 -0
  551. package/out/zero-cache/src/services/view-syncer/query-shape.js +28 -0
  552. package/out/zero-cache/src/services/view-syncer/query-shape.js.map +1 -0
  553. package/out/zero-cache/src/services/view-syncer/query-stats.d.ts +89 -0
  554. package/out/zero-cache/src/services/view-syncer/query-stats.d.ts.map +1 -0
  555. package/out/zero-cache/src/services/view-syncer/query-stats.js +233 -0
  556. package/out/zero-cache/src/services/view-syncer/query-stats.js.map +1 -0
  557. package/out/zero-cache/src/services/view-syncer/schema/types.d.ts +2 -107
  558. package/out/zero-cache/src/services/view-syncer/schema/types.d.ts.map +1 -1
  559. package/out/zero-cache/src/services/view-syncer/schema/types.js +5 -20
  560. package/out/zero-cache/src/services/view-syncer/schema/types.js.map +1 -1
  561. package/out/zero-cache/src/services/view-syncer/snapshot-row-cache.d.ts +95 -0
  562. package/out/zero-cache/src/services/view-syncer/snapshot-row-cache.d.ts.map +1 -0
  563. package/out/zero-cache/src/services/view-syncer/snapshot-row-cache.js +155 -0
  564. package/out/zero-cache/src/services/view-syncer/snapshot-row-cache.js.map +1 -0
  565. package/out/zero-cache/src/services/view-syncer/snapshotter.d.ts +229 -16
  566. package/out/zero-cache/src/services/view-syncer/snapshotter.d.ts.map +1 -1
  567. package/out/zero-cache/src/services/view-syncer/snapshotter.js +455 -43
  568. package/out/zero-cache/src/services/view-syncer/snapshotter.js.map +1 -1
  569. package/out/zero-cache/src/services/view-syncer/view-syncer.d.ts +8 -2
  570. package/out/zero-cache/src/services/view-syncer/view-syncer.d.ts.map +1 -1
  571. package/out/zero-cache/src/services/view-syncer/view-syncer.js +788 -71
  572. package/out/zero-cache/src/services/view-syncer/view-syncer.js.map +1 -1
  573. package/out/zero-cache/src/types/pg-data-type.d.ts +2 -0
  574. package/out/zero-cache/src/types/pg-data-type.d.ts.map +1 -1
  575. package/out/zero-cache/src/types/pg-data-type.js +6 -1
  576. package/out/zero-cache/src/types/pg-data-type.js.map +1 -1
  577. package/out/zero-cache/src/types/pg.d.ts.map +1 -1
  578. package/out/zero-cache/src/types/pg.js +2 -2
  579. package/out/zero-cache/src/types/pg.js.map +1 -1
  580. package/out/zero-cache/src/types/processes.d.ts +50 -0
  581. package/out/zero-cache/src/types/processes.d.ts.map +1 -1
  582. package/out/zero-cache/src/types/processes.js +43 -4
  583. package/out/zero-cache/src/types/processes.js.map +1 -1
  584. package/out/zero-cache/src/types/profiler.d.ts +12 -0
  585. package/out/zero-cache/src/types/profiler.d.ts.map +1 -1
  586. package/out/zero-cache/src/types/profiler.js +46 -1
  587. package/out/zero-cache/src/types/profiler.js.map +1 -1
  588. package/out/zero-cache/src/types/row-key.d.ts +1 -15
  589. package/out/zero-cache/src/types/row-key.d.ts.map +1 -1
  590. package/out/zero-cache/src/types/row-key.js +6 -8
  591. package/out/zero-cache/src/types/row-key.js.map +1 -1
  592. package/out/zero-cache/src/types/streams.d.ts +49 -7
  593. package/out/zero-cache/src/types/streams.d.ts.map +1 -1
  594. package/out/zero-cache/src/types/streams.js +190 -58
  595. package/out/zero-cache/src/types/streams.js.map +1 -1
  596. package/out/zero-cache/src/types/subscription.d.ts +15 -0
  597. package/out/zero-cache/src/types/subscription.d.ts.map +1 -1
  598. package/out/zero-cache/src/types/subscription.js +123 -31
  599. package/out/zero-cache/src/types/subscription.js.map +1 -1
  600. package/out/zero-cache/src/types/websocket-handoff.d.ts +1 -1
  601. package/out/zero-cache/src/types/websocket-handoff.d.ts.map +1 -1
  602. package/out/zero-cache/src/types/websocket-handoff.js +18 -9
  603. package/out/zero-cache/src/types/websocket-handoff.js.map +1 -1
  604. package/out/zero-cache/src/types/ws.d.ts.map +1 -1
  605. package/out/zero-cache/src/types/ws.js +1 -16
  606. package/out/zero-cache/src/types/ws.js.map +1 -1
  607. package/out/zero-cache/src/workers/connect-params.d.ts +1 -0
  608. package/out/zero-cache/src/workers/connect-params.d.ts.map +1 -1
  609. package/out/zero-cache/src/workers/connect-params.js.map +1 -1
  610. package/out/zero-cache/src/workers/connection.d.ts +2 -1
  611. package/out/zero-cache/src/workers/connection.d.ts.map +1 -1
  612. package/out/zero-cache/src/workers/connection.js +9 -1
  613. package/out/zero-cache/src/workers/connection.js.map +1 -1
  614. package/out/zero-cache/src/workers/replicator.d.ts.map +1 -1
  615. package/out/zero-cache/src/workers/replicator.js +24 -7
  616. package/out/zero-cache/src/workers/replicator.js.map +1 -1
  617. package/out/zero-cache/src/workers/syncer-ws-message-handler.d.ts.map +1 -1
  618. package/out/zero-cache/src/workers/syncer-ws-message-handler.js +21 -16
  619. package/out/zero-cache/src/workers/syncer-ws-message-handler.js.map +1 -1
  620. package/out/zero-cache/src/workers/syncer.d.ts.map +1 -1
  621. package/out/zero-cache/src/workers/syncer.js +55 -4
  622. package/out/zero-cache/src/workers/syncer.js.map +1 -1
  623. package/out/zero-client/src/client/active-clients-manager.d.ts.map +1 -1
  624. package/out/zero-client/src/client/active-clients-manager.js +4 -1
  625. package/out/zero-client/src/client/active-clients-manager.js.map +1 -1
  626. package/out/zero-client/src/client/connection-manager.d.ts +20 -0
  627. package/out/zero-client/src/client/connection-manager.d.ts.map +1 -1
  628. package/out/zero-client/src/client/connection-manager.js +77 -13
  629. package/out/zero-client/src/client/connection-manager.js.map +1 -1
  630. package/out/zero-client/src/client/connection-status-enum.d.ts +2 -0
  631. package/out/zero-client/src/client/connection-status-enum.d.ts.map +1 -1
  632. package/out/zero-client/src/client/connection-status-enum.js +3 -1
  633. package/out/zero-client/src/client/connection-status-enum.js.map +1 -1
  634. package/out/zero-client/src/client/connection.d.ts +6 -0
  635. package/out/zero-client/src/client/connection.d.ts.map +1 -1
  636. package/out/zero-client/src/client/connection.js +2 -1
  637. package/out/zero-client/src/client/connection.js.map +1 -1
  638. package/out/zero-client/src/client/context.d.ts +23 -13
  639. package/out/zero-client/src/client/context.d.ts.map +1 -1
  640. package/out/zero-client/src/client/context.js +94 -26
  641. package/out/zero-client/src/client/context.js.map +1 -1
  642. package/out/zero-client/src/client/crud-impl.d.ts.map +1 -1
  643. package/out/zero-client/src/client/crud-impl.js +1 -1
  644. package/out/zero-client/src/client/crud-impl.js.map +1 -1
  645. package/out/zero-client/src/client/custom.d.ts +5 -4
  646. package/out/zero-client/src/client/custom.d.ts.map +1 -1
  647. package/out/zero-client/src/client/custom.js +3 -3
  648. package/out/zero-client/src/client/custom.js.map +1 -1
  649. package/out/zero-client/src/client/inspector/lazy-inspector.js +1 -1
  650. package/out/zero-client/src/client/ivm-branch.d.ts.map +1 -1
  651. package/out/zero-client/src/client/ivm-branch.js +20 -3
  652. package/out/zero-client/src/client/ivm-branch.js.map +1 -1
  653. package/out/zero-client/src/client/keys.d.ts.map +1 -1
  654. package/out/zero-client/src/client/keys.js +19 -1
  655. package/out/zero-client/src/client/keys.js.map +1 -1
  656. package/out/zero-client/src/client/make-mutate-property.d.ts +1 -1
  657. package/out/zero-client/src/client/make-mutate-property.d.ts.map +1 -1
  658. package/out/zero-client/src/client/make-mutate-property.js.map +1 -1
  659. package/out/zero-client/src/client/make-replicache-mutators.d.ts.map +1 -1
  660. package/out/zero-client/src/client/make-replicache-mutators.js +1 -1
  661. package/out/zero-client/src/client/make-replicache-mutators.js.map +1 -1
  662. package/out/zero-client/src/client/mutation-tracker.d.ts +2 -2
  663. package/out/zero-client/src/client/mutation-tracker.d.ts.map +1 -1
  664. package/out/zero-client/src/client/mutation-tracker.js +3 -7
  665. package/out/zero-client/src/client/mutation-tracker.js.map +1 -1
  666. package/out/zero-client/src/client/mutator-proxy.d.ts.map +1 -1
  667. package/out/zero-client/src/client/mutator-proxy.js +9 -4
  668. package/out/zero-client/src/client/mutator-proxy.js.map +1 -1
  669. package/out/zero-client/src/client/options.d.ts +33 -0
  670. package/out/zero-client/src/client/options.d.ts.map +1 -1
  671. package/out/zero-client/src/client/options.js.map +1 -1
  672. package/out/zero-client/src/client/query-manager.d.ts +9 -0
  673. package/out/zero-client/src/client/query-manager.d.ts.map +1 -1
  674. package/out/zero-client/src/client/query-manager.js +47 -14
  675. package/out/zero-client/src/client/query-manager.js.map +1 -1
  676. package/out/zero-client/src/client/reload-error-handler.js +2 -2
  677. package/out/zero-client/src/client/reload-error-handler.js.map +1 -1
  678. package/out/zero-client/src/client/storage-version.d.ts +23 -0
  679. package/out/zero-client/src/client/storage-version.d.ts.map +1 -0
  680. package/out/zero-client/src/client/version.js +1 -1
  681. package/out/zero-client/src/client/zero-rep.d.ts +1 -0
  682. package/out/zero-client/src/client/zero-rep.d.ts.map +1 -1
  683. package/out/zero-client/src/client/zero-rep.js +8 -6
  684. package/out/zero-client/src/client/zero-rep.js.map +1 -1
  685. package/out/zero-client/src/client/zero.d.ts +18 -3
  686. package/out/zero-client/src/client/zero.d.ts.map +1 -1
  687. package/out/zero-client/src/client/zero.js +86 -48
  688. package/out/zero-client/src/client/zero.js.map +1 -1
  689. package/out/zero-client/src/mod.d.ts +2 -1
  690. package/out/zero-client/src/mod.d.ts.map +1 -1
  691. package/out/zero-client/src/mod.js +1 -0
  692. package/out/zero-client/src/types/query-result.d.ts +2 -0
  693. package/out/zero-client/src/types/query-result.d.ts.map +1 -1
  694. package/out/zero-events/src/status.d.ts +64 -0
  695. package/out/zero-events/src/status.d.ts.map +1 -1
  696. package/out/zero-protocol/src/analyze-query-result.d.ts +12 -12
  697. package/out/zero-protocol/src/analyze-query-result.d.ts.map +1 -1
  698. package/out/zero-protocol/src/analyze-query-result.js +3 -3
  699. package/out/zero-protocol/src/analyze-query-result.js.map +1 -1
  700. package/out/zero-protocol/src/ast.d.ts +24 -0
  701. package/out/zero-protocol/src/ast.d.ts.map +1 -1
  702. package/out/zero-protocol/src/ast.js +39 -16
  703. package/out/zero-protocol/src/ast.js.map +1 -1
  704. package/out/zero-protocol/src/down.d.ts +36 -36
  705. package/out/zero-protocol/src/inspect-down.d.ts +31 -31
  706. package/out/zero-protocol/src/inspect-up.d.ts +158 -61
  707. package/out/zero-protocol/src/inspect-up.d.ts.map +1 -1
  708. package/out/zero-protocol/src/inspect-up.js +12 -6
  709. package/out/zero-protocol/src/inspect-up.js.map +1 -1
  710. package/out/zero-protocol/src/protocol-version.d.ts +4 -1
  711. package/out/zero-protocol/src/protocol-version.d.ts.map +1 -1
  712. package/out/zero-protocol/src/protocol-version.js.map +1 -1
  713. package/out/zero-protocol/src/queries-patch.js +2 -2
  714. package/out/zero-protocol/src/queries-patch.js.map +1 -1
  715. package/out/zero-protocol/src/query-hash.d.ts.map +1 -1
  716. package/out/zero-protocol/src/query-hash.js +2 -5
  717. package/out/zero-protocol/src/query-hash.js.map +1 -1
  718. package/out/zero-protocol/src/up.d.ts +766 -256
  719. package/out/zero-protocol/src/up.d.ts.map +1 -1
  720. package/out/zero-protocol/src/up.js +25 -3
  721. package/out/zero-protocol/src/up.js.map +1 -1
  722. package/out/zero-react/src/use-query.d.ts +5 -4
  723. package/out/zero-react/src/use-query.d.ts.map +1 -1
  724. package/out/zero-react/src/use-query.js +75 -8
  725. package/out/zero-react/src/use-query.js.map +1 -1
  726. package/out/zero-react/src/zero.js +1 -0
  727. package/out/zero-server/src/adapters/drizzle.d.ts +16 -4
  728. package/out/zero-server/src/adapters/drizzle.d.ts.map +1 -1
  729. package/out/zero-server/src/adapters/drizzle.js +19 -11
  730. package/out/zero-server/src/adapters/drizzle.js.map +1 -1
  731. package/out/zero-server/src/adapters/kysely.d.ts +6 -3
  732. package/out/zero-server/src/adapters/kysely.d.ts.map +1 -1
  733. package/out/zero-server/src/adapters/kysely.js +16 -6
  734. package/out/zero-server/src/adapters/kysely.js.map +1 -1
  735. package/out/zero-server/src/adapters/pg.d.ts +7 -2
  736. package/out/zero-server/src/adapters/pg.d.ts.map +1 -1
  737. package/out/zero-server/src/adapters/pg.js +34 -10
  738. package/out/zero-server/src/adapters/pg.js.map +1 -1
  739. package/out/zero-server/src/adapters/postgresjs.d.ts +4 -2
  740. package/out/zero-server/src/adapters/postgresjs.d.ts.map +1 -1
  741. package/out/zero-server/src/adapters/postgresjs.js +15 -5
  742. package/out/zero-server/src/adapters/postgresjs.js.map +1 -1
  743. package/out/zero-server/src/adapters/prisma.d.ts +17 -5
  744. package/out/zero-server/src/adapters/prisma.d.ts.map +1 -1
  745. package/out/zero-server/src/adapters/prisma.js +20 -6
  746. package/out/zero-server/src/adapters/prisma.js.map +1 -1
  747. package/out/zero-server/src/closable-db-transaction.d.ts +16 -0
  748. package/out/zero-server/src/closable-db-transaction.d.ts.map +1 -0
  749. package/out/zero-server/src/closable-db-transaction.js +31 -0
  750. package/out/zero-server/src/closable-db-transaction.js.map +1 -0
  751. package/out/zero-server/src/custom.d.ts +10 -4
  752. package/out/zero-server/src/custom.d.ts.map +1 -1
  753. package/out/zero-server/src/custom.js +15 -6
  754. package/out/zero-server/src/custom.js.map +1 -1
  755. package/out/zero-server/src/logging.d.ts +2 -2
  756. package/out/zero-server/src/logging.d.ts.map +1 -1
  757. package/out/zero-server/src/logging.js +2 -2
  758. package/out/zero-server/src/logging.js.map +1 -1
  759. package/out/zero-server/src/mod.d.ts +2 -1
  760. package/out/zero-server/src/mod.d.ts.map +1 -1
  761. package/out/zero-server/src/pg-query-executor.d.ts +2 -2
  762. package/out/zero-server/src/pg-query-executor.d.ts.map +1 -1
  763. package/out/zero-server/src/pg-query-executor.js +2 -2
  764. package/out/zero-server/src/pg-query-executor.js.map +1 -1
  765. package/out/zero-server/src/process-mutations.d.ts +25 -4
  766. package/out/zero-server/src/process-mutations.d.ts.map +1 -1
  767. package/out/zero-server/src/process-mutations.js +103 -52
  768. package/out/zero-server/src/process-mutations.js.map +1 -1
  769. package/out/zero-server/src/push-processor.d.ts +8 -2
  770. package/out/zero-server/src/push-processor.d.ts.map +1 -1
  771. package/out/zero-server/src/push-processor.js +12 -4
  772. package/out/zero-server/src/push-processor.js.map +1 -1
  773. package/out/zero-server/src/queries/process-queries.d.ts.map +1 -1
  774. package/out/zero-server/src/queries/process-queries.js +1 -1
  775. package/out/zero-server/src/queries/process-queries.js.map +1 -1
  776. package/out/zero-server/src/schema.d.ts +2 -2
  777. package/out/zero-server/src/schema.d.ts.map +1 -1
  778. package/out/zero-server/src/schema.js +3 -2
  779. package/out/zero-server/src/schema.js.map +1 -1
  780. package/out/zero-server/src/transaction-options.d.ts +24 -0
  781. package/out/zero-server/src/transaction-options.d.ts.map +1 -0
  782. package/out/zero-server/src/transaction-options.js +11 -0
  783. package/out/zero-server/src/transaction-options.js.map +1 -0
  784. package/out/zero-server/src/zql-database.d.ts +21 -1
  785. package/out/zero-server/src/zql-database.d.ts.map +1 -1
  786. package/out/zero-server/src/zql-database.js +61 -24
  787. package/out/zero-server/src/zql-database.js.map +1 -1
  788. package/out/zero-solid/src/solid-view.d.ts +17 -0
  789. package/out/zero-solid/src/solid-view.d.ts.map +1 -1
  790. package/out/zero-solid/src/solid-view.js +39 -1
  791. package/out/zero-solid/src/solid-view.js.map +1 -1
  792. package/out/zero-solid/src/use-query.js +1 -2
  793. package/out/zero-solid/src/use-query.js.map +1 -1
  794. package/out/zero-solid/src/zero.js +1 -0
  795. package/out/zql/src/builder/builder.d.ts +25 -0
  796. package/out/zql/src/builder/builder.d.ts.map +1 -1
  797. package/out/zql/src/builder/builder.js +69 -19
  798. package/out/zql/src/builder/builder.js.map +1 -1
  799. package/out/zql/src/builder/correlated-predicate-pushdown.d.ts +43 -0
  800. package/out/zql/src/builder/correlated-predicate-pushdown.d.ts.map +1 -0
  801. package/out/zql/src/builder/correlated-predicate-pushdown.js +161 -0
  802. package/out/zql/src/builder/correlated-predicate-pushdown.js.map +1 -0
  803. package/out/zql/src/builder/debug-delegate.d.ts +6 -1
  804. package/out/zql/src/builder/debug-delegate.d.ts.map +1 -1
  805. package/out/zql/src/builder/debug-delegate.js +14 -2
  806. package/out/zql/src/builder/debug-delegate.js.map +1 -1
  807. package/out/zql/src/ivm/array-view.d.ts +29 -0
  808. package/out/zql/src/ivm/array-view.d.ts.map +1 -1
  809. package/out/zql/src/ivm/array-view.js +74 -16
  810. package/out/zql/src/ivm/array-view.js.map +1 -1
  811. package/out/zql/src/ivm/cap.d.ts +2 -1
  812. package/out/zql/src/ivm/cap.d.ts.map +1 -1
  813. package/out/zql/src/ivm/cap.js +14 -4
  814. package/out/zql/src/ivm/cap.js.map +1 -1
  815. package/out/zql/src/ivm/data.d.ts.map +1 -1
  816. package/out/zql/src/ivm/data.js +8 -3
  817. package/out/zql/src/ivm/data.js.map +1 -1
  818. package/out/zql/src/ivm/deferred-input.d.ts.map +1 -1
  819. package/out/zql/src/ivm/deferred-input.js +3 -2
  820. package/out/zql/src/ivm/deferred-input.js.map +1 -1
  821. package/out/zql/src/ivm/exists.d.ts +3 -1
  822. package/out/zql/src/ivm/exists.d.ts.map +1 -1
  823. package/out/zql/src/ivm/exists.js +4 -1
  824. package/out/zql/src/ivm/exists.js.map +1 -1
  825. package/out/zql/src/ivm/fan-in.d.ts +6 -2
  826. package/out/zql/src/ivm/fan-in.d.ts.map +1 -1
  827. package/out/zql/src/ivm/fan-in.js +13 -5
  828. package/out/zql/src/ivm/fan-in.js.map +1 -1
  829. package/out/zql/src/ivm/fan-out.d.ts +5 -2
  830. package/out/zql/src/ivm/fan-out.d.ts.map +1 -1
  831. package/out/zql/src/ivm/fan-out.js +4 -0
  832. package/out/zql/src/ivm/fan-out.js.map +1 -1
  833. package/out/zql/src/ivm/filter-operators.d.ts +8 -6
  834. package/out/zql/src/ivm/filter-operators.d.ts.map +1 -1
  835. package/out/zql/src/ivm/filter-operators.js +19 -8
  836. package/out/zql/src/ivm/filter-operators.js.map +1 -1
  837. package/out/zql/src/ivm/filter.d.ts +5 -2
  838. package/out/zql/src/ivm/filter.d.ts.map +1 -1
  839. package/out/zql/src/ivm/filter.js +10 -4
  840. package/out/zql/src/ivm/filter.js.map +1 -1
  841. package/out/zql/src/ivm/flipped-join.d.ts +9 -4
  842. package/out/zql/src/ivm/flipped-join.d.ts.map +1 -1
  843. package/out/zql/src/ivm/flipped-join.js +97 -46
  844. package/out/zql/src/ivm/flipped-join.js.map +1 -1
  845. package/out/zql/src/ivm/join-index-tap.d.ts +33 -0
  846. package/out/zql/src/ivm/join-index-tap.d.ts.map +1 -0
  847. package/out/zql/src/ivm/join-index-tap.js +70 -0
  848. package/out/zql/src/ivm/join-index-tap.js.map +1 -0
  849. package/out/zql/src/ivm/join-index.d.ts +35 -0
  850. package/out/zql/src/ivm/join-index.d.ts.map +1 -0
  851. package/out/zql/src/ivm/join-index.js +141 -0
  852. package/out/zql/src/ivm/join-index.js.map +1 -0
  853. package/out/zql/src/ivm/join-utils.d.ts +6 -0
  854. package/out/zql/src/ivm/join-utils.d.ts.map +1 -1
  855. package/out/zql/src/ivm/join-utils.js +22 -1
  856. package/out/zql/src/ivm/join-utils.js.map +1 -1
  857. package/out/zql/src/ivm/join.d.ts +19 -1
  858. package/out/zql/src/ivm/join.d.ts.map +1 -1
  859. package/out/zql/src/ivm/join.js +107 -15
  860. package/out/zql/src/ivm/join.js.map +1 -1
  861. package/out/zql/src/ivm/maybe-split-and-push-edit-change.d.ts +1 -1
  862. package/out/zql/src/ivm/maybe-split-and-push-edit-change.d.ts.map +1 -1
  863. package/out/zql/src/ivm/maybe-split-and-push-edit-change.js +6 -4
  864. package/out/zql/src/ivm/maybe-split-and-push-edit-change.js.map +1 -1
  865. package/out/zql/src/ivm/memory-source.d.ts +29 -4
  866. package/out/zql/src/ivm/memory-source.d.ts.map +1 -1
  867. package/out/zql/src/ivm/memory-source.js +70 -34
  868. package/out/zql/src/ivm/memory-source.js.map +1 -1
  869. package/out/zql/src/ivm/memory-storage.d.ts +1 -0
  870. package/out/zql/src/ivm/memory-storage.d.ts.map +1 -1
  871. package/out/zql/src/ivm/memory-storage.js +1 -0
  872. package/out/zql/src/ivm/memory-storage.js.map +1 -1
  873. package/out/zql/src/ivm/operator.d.ts +45 -10
  874. package/out/zql/src/ivm/operator.d.ts.map +1 -1
  875. package/out/zql/src/ivm/operator.js +9 -4
  876. package/out/zql/src/ivm/operator.js.map +1 -1
  877. package/out/zql/src/ivm/push-accumulated.d.ts +6 -1
  878. package/out/zql/src/ivm/push-accumulated.d.ts.map +1 -1
  879. package/out/zql/src/ivm/push-accumulated.js +47 -2
  880. package/out/zql/src/ivm/push-accumulated.js.map +1 -1
  881. package/out/zql/src/ivm/skip.d.ts +2 -1
  882. package/out/zql/src/ivm/skip.d.ts.map +1 -1
  883. package/out/zql/src/ivm/skip.js +3 -0
  884. package/out/zql/src/ivm/skip.js.map +1 -1
  885. package/out/zql/src/ivm/take-gate.d.ts +57 -0
  886. package/out/zql/src/ivm/take-gate.d.ts.map +1 -0
  887. package/out/zql/src/ivm/take-gate.js +106 -0
  888. package/out/zql/src/ivm/take-gate.js.map +1 -0
  889. package/out/zql/src/ivm/take.d.ts +8 -2
  890. package/out/zql/src/ivm/take.d.ts.map +1 -1
  891. package/out/zql/src/ivm/take.js +139 -103
  892. package/out/zql/src/ivm/take.js.map +1 -1
  893. package/out/zql/src/ivm/union-fan-in.d.ts +3 -0
  894. package/out/zql/src/ivm/union-fan-in.d.ts.map +1 -1
  895. package/out/zql/src/ivm/union-fan-in.js +63 -10
  896. package/out/zql/src/ivm/union-fan-in.js.map +1 -1
  897. package/out/zql/src/ivm/union-fan-out.d.ts +2 -1
  898. package/out/zql/src/ivm/union-fan-out.d.ts.map +1 -1
  899. package/out/zql/src/ivm/union-fan-out.js +5 -0
  900. package/out/zql/src/ivm/union-fan-out.js.map +1 -1
  901. package/out/zql/src/ivm/view-apply-change.d.ts.map +1 -1
  902. package/out/zql/src/ivm/view-apply-change.js +9 -4
  903. package/out/zql/src/ivm/view-apply-change.js.map +1 -1
  904. package/out/zql/src/ivm/view.d.ts +15 -0
  905. package/out/zql/src/ivm/view.d.ts.map +1 -1
  906. package/out/zql/src/mutate/custom.d.ts +53 -1
  907. package/out/zql/src/mutate/custom.d.ts.map +1 -1
  908. package/out/zql/src/mutate/custom.js.map +1 -1
  909. package/out/zql/src/mutate/mutator-registry.d.ts.map +1 -1
  910. package/out/zql/src/mutate/mutator-registry.js +3 -3
  911. package/out/zql/src/mutate/mutator-registry.js.map +1 -1
  912. package/out/zql/src/mutate/mutator.d.ts +2 -2
  913. package/out/zql/src/mutate/mutator.d.ts.map +1 -1
  914. package/out/zql/src/mutate/mutator.js.map +1 -1
  915. package/out/zql/src/planner/planner-builder.d.ts +23 -3
  916. package/out/zql/src/planner/planner-builder.d.ts.map +1 -1
  917. package/out/zql/src/planner/planner-builder.js +34 -17
  918. package/out/zql/src/planner/planner-builder.js.map +1 -1
  919. package/out/zql/src/planner/planner-connection.d.ts +58 -2
  920. package/out/zql/src/planner/planner-connection.d.ts.map +1 -1
  921. package/out/zql/src/planner/planner-connection.js +103 -11
  922. package/out/zql/src/planner/planner-connection.js.map +1 -1
  923. package/out/zql/src/planner/planner-debug.d.ts.map +1 -1
  924. package/out/zql/src/planner/planner-debug.js +3 -8
  925. package/out/zql/src/planner/planner-debug.js.map +1 -1
  926. package/out/zql/src/planner/planner-graph.d.ts +10 -0
  927. package/out/zql/src/planner/planner-graph.d.ts.map +1 -1
  928. package/out/zql/src/planner/planner-graph.js +14 -0
  929. package/out/zql/src/planner/planner-graph.js.map +1 -1
  930. package/out/zql/src/planner/planner-source.d.ts +2 -2
  931. package/out/zql/src/planner/planner-source.d.ts.map +1 -1
  932. package/out/zql/src/planner/planner-source.js +2 -2
  933. package/out/zql/src/planner/planner-source.js.map +1 -1
  934. package/out/zql/src/planner/planner-warnings.d.ts +83 -0
  935. package/out/zql/src/planner/planner-warnings.d.ts.map +1 -0
  936. package/out/zql/src/planner/planner-warnings.js +78 -0
  937. package/out/zql/src/planner/planner-warnings.js.map +1 -0
  938. package/out/zql/src/query/expression.d.ts +2 -2
  939. package/out/zql/src/query/expression.d.ts.map +1 -1
  940. package/out/zql/src/query/expression.js.map +1 -1
  941. package/out/zql/src/query/measure-push-operator.d.ts +9 -2
  942. package/out/zql/src/query/measure-push-operator.d.ts.map +1 -1
  943. package/out/zql/src/query/measure-push-operator.js +52 -5
  944. package/out/zql/src/query/measure-push-operator.js.map +1 -1
  945. package/out/zql/src/query/query-delegate-base.d.ts +4 -2
  946. package/out/zql/src/query/query-delegate-base.d.ts.map +1 -1
  947. package/out/zql/src/query/query-delegate-base.js +66 -33
  948. package/out/zql/src/query/query-delegate-base.js.map +1 -1
  949. package/out/zql/src/query/query-delegate.d.ts +33 -6
  950. package/out/zql/src/query/query-delegate.d.ts.map +1 -1
  951. package/out/zql/src/query/query-impl.d.ts +1 -0
  952. package/out/zql/src/query/query-impl.d.ts.map +1 -1
  953. package/out/zql/src/query/query-impl.js +6 -23
  954. package/out/zql/src/query/query-impl.js.map +1 -1
  955. package/out/zql/src/query/query-registry.js +1 -1
  956. package/out/zql/src/query/query-transitions.d.ts.map +1 -1
  957. package/out/zql/src/query/query-transitions.js +2 -5
  958. package/out/zql/src/query/query-transitions.js.map +1 -1
  959. package/out/zql/src/query/query.d.ts +26 -10
  960. package/out/zql/src/query/query.d.ts.map +1 -1
  961. package/out/zql/src/query/runnable-query-impl.d.ts +1 -0
  962. package/out/zql/src/query/runnable-query-impl.d.ts.map +1 -1
  963. package/out/zql/src/query/runnable-query-impl.js +2 -10
  964. package/out/zql/src/query/runnable-query-impl.js.map +1 -1
  965. package/out/zql/src/query/typed-view.d.ts +1 -1
  966. package/out/zql/src/query/typed-view.d.ts.map +1 -1
  967. package/out/zqlite/src/database-storage.d.ts.map +1 -1
  968. package/out/zqlite/src/database-storage.js +9 -1
  969. package/out/zqlite/src/database-storage.js.map +1 -1
  970. package/out/zqlite/src/db.d.ts +17 -1
  971. package/out/zqlite/src/db.d.ts.map +1 -1
  972. package/out/zqlite/src/db.js +73 -30
  973. package/out/zqlite/src/db.js.map +1 -1
  974. package/out/zqlite/src/index-usage.d.ts +19 -0
  975. package/out/zqlite/src/index-usage.d.ts.map +1 -0
  976. package/out/zqlite/src/index-usage.js +49 -0
  977. package/out/zqlite/src/index-usage.js.map +1 -0
  978. package/out/zqlite/src/pending-delta.d.ts +110 -0
  979. package/out/zqlite/src/pending-delta.d.ts.map +1 -0
  980. package/out/zqlite/src/pending-delta.js +278 -0
  981. package/out/zqlite/src/pending-delta.js.map +1 -0
  982. package/out/zqlite/src/query-builder.d.ts +17 -1
  983. package/out/zqlite/src/query-builder.d.ts.map +1 -1
  984. package/out/zqlite/src/query-builder.js +111 -20
  985. package/out/zqlite/src/query-builder.js.map +1 -1
  986. package/out/zqlite/src/query-delegate.d.ts.map +1 -1
  987. package/out/zqlite/src/query-delegate.js +10 -7
  988. package/out/zqlite/src/query-delegate.js.map +1 -1
  989. package/out/zqlite/src/resolve-scalar-subqueries.d.ts +3 -1
  990. package/out/zqlite/src/resolve-scalar-subqueries.d.ts.map +1 -1
  991. package/out/zqlite/src/resolve-scalar-subqueries.js +1 -0
  992. package/out/zqlite/src/resolve-scalar-subqueries.js.map +1 -1
  993. package/out/zqlite/src/sqlite-cost-model.d.ts.map +1 -1
  994. package/out/zqlite/src/sqlite-cost-model.js +53 -1
  995. package/out/zqlite/src/sqlite-cost-model.js.map +1 -1
  996. package/out/zqlite/src/sqlite-stat-fanout.d.ts.map +1 -1
  997. package/out/zqlite/src/sqlite-stat-fanout.js +5 -31
  998. package/out/zqlite/src/sqlite-stat-fanout.js.map +1 -1
  999. package/out/zqlite/src/sqlite-stat4-sample.d.ts +37 -0
  1000. package/out/zqlite/src/sqlite-stat4-sample.d.ts.map +1 -0
  1001. package/out/zqlite/src/sqlite-stat4-sample.js +61 -0
  1002. package/out/zqlite/src/sqlite-stat4-sample.js.map +1 -0
  1003. package/out/zqlite/src/table-source.d.ts +87 -2
  1004. package/out/zqlite/src/table-source.d.ts.map +1 -1
  1005. package/out/zqlite/src/table-source.js +276 -42
  1006. package/out/zqlite/src/table-source.js.map +1 -1
  1007. package/package.json +5 -6
  1008. package/out/replicache/src/kv/idb-store-with-mem-fallback.d.ts +0 -25
  1009. package/out/replicache/src/kv/idb-store-with-mem-fallback.d.ts.map +0 -1
  1010. package/out/replicache/src/kv/idb-store-with-mem-fallback.js +0 -83
  1011. package/out/replicache/src/kv/idb-store-with-mem-fallback.js.map +0 -1
  1012. package/out/zero-cache/src/services/change-streamer/vfs-watermark-poller.d.ts +0 -29
  1013. package/out/zero-cache/src/services/change-streamer/vfs-watermark-poller.d.ts.map +0 -1
  1014. package/out/zero-cache/src/services/change-streamer/vfs-watermark-poller.js +0 -154
  1015. package/out/zero-cache/src/services/change-streamer/vfs-watermark-poller.js.map +0 -1
@@ -1,18 +1,52 @@
1
1
  import type { Enum } from '../../../../shared/src/enum.ts';
2
2
  import type { Subscription } from '../../types/subscription.ts';
3
3
  import type { ReplicatorMode } from '../replicator/replicator.ts';
4
+ import type { BackfillState } from './backfill-state.ts';
5
+ import type { PreSerializedBatch } from './broadcast.ts';
4
6
  import type { ChangeTag, Status, WatermarkedChange } from './change-streamer.ts';
5
7
  import type * as ErrorType from './error-type-enum.ts';
6
8
  type ErrorType = Enum<typeof ErrorType>;
7
9
  export type SubscriberOptions = {
8
10
  backlogHighWaterBytes?: number | undefined;
9
11
  backlogLowWaterRatio?: number | undefined;
12
+ wsBatched?: boolean | undefined;
10
13
  /**
11
14
  * Called whenever the subscriber's acked watermark advances, i.e. when it
12
15
  * has confirmed that a commit was durably applied to its replica. The ACK
13
16
  * therefore lags the subscriber's replica rather than leading it.
14
17
  */
15
18
  onAck?: ((watermark: string) => void) | undefined;
19
+ /**
20
+ * The subscriber's pending backfills (protocol v8+), which are tracked
21
+ * over the changes sent to the subscriber.
22
+ */
23
+ backfills?: BackfillState | undefined;
24
+ /**
25
+ * Called once the subscriber has been sent all changes up to the head of
26
+ * the stream, i.e. its catchup and backlog have been flushed. From this
27
+ * point on, the subscriber's tracked {@link backfills} reflect the same
28
+ * position in the stream as that of the change-streamer.
29
+ */
30
+ onAligned?: ((subscriber: Subscriber) => void) | undefined;
31
+ /**
32
+ * Called when a `backfill` or `backfill-completed` message is ignored for
33
+ * some of the subscriber's pending backfill columns, after the subscriber
34
+ * is aligned.
35
+ */
36
+ onBackfillIgnored?: ((columns: string[]) => void) | undefined;
37
+ /**
38
+ * Resolves to whether lag reporting is disabled upstream. If so, a
39
+ * {@link LAG_REPORTING_DISABLED} status is sent once the subscriber is
40
+ * aligned, as a stand-in for the lag reports that a subscriber would
41
+ * otherwise use to determine that it is caught up (e.g. to advertise
42
+ * readiness to serve traffic).
43
+ */
44
+ lagReportingDisabled?: Promise<boolean> | undefined;
45
+ /**
46
+ * Whether the subscriber switches over to another replication-manager
47
+ * when this one drains (see `DrainTracker`).
48
+ */
49
+ drainable?: boolean | undefined;
16
50
  };
17
51
  export type BacklogFullWait = {
18
52
  readonly promise: Promise<void>;
@@ -37,7 +71,24 @@ export declare class Subscriber {
37
71
  #private;
38
72
  readonly id: string;
39
73
  readonly mode: ReplicatorMode;
40
- constructor(protocolVersion: number, id: string, mode: ReplicatorMode, watermark: string, downstream: Subscription<string>, latestStatus: () => Status, options?: SubscriberOptions);
74
+ readonly drainable: boolean;
75
+ constructor(protocolVersion: number, id: string, mode: ReplicatorMode, watermark: string, downstream: Subscription<string | PreSerializedBatch>, options?: SubscriberOptions);
76
+ /**
77
+ * The subscriber's tracked pending backfills, or `undefined` if the
78
+ * subscriber does not report them (i.e. protocol < v8).
79
+ */
80
+ get backfills(): BackfillState | undefined;
81
+ /**
82
+ * Whether the subscriber has been sent all changes up to the head of the
83
+ * stream (see {@link SubscriberOptions.onAligned}).
84
+ */
85
+ get aligned(): boolean;
86
+ /**
87
+ * Resolves once the subscriber has caught up, i.e. once it has acked
88
+ * (durably applied) all changes up to the head of the stream at the time
89
+ * it was {@link aligned}. Never resolves if the subscriber is closed first.
90
+ */
91
+ get caughtUp(): Promise<void>;
41
92
  get watermark(): string;
42
93
  get acked(): string;
43
94
  /**
@@ -60,7 +111,25 @@ export declare class Subscriber {
60
111
  */
61
112
  whenBacklogFull(): BacklogFullWait;
62
113
  send(change: WatermarkedChange): Promise<void>;
114
+ sendBatch(changes: readonly WatermarkedChange[], preSerialized?: PreSerializedBatch | undefined): Promise<void>;
115
+ /**
116
+ * Sends a status message (e.g. a lag report) downstream. While the
117
+ * subscriber is catching up, the status is queued in the backlog behind
118
+ * the changes that preceded it in the replication stream, so that the
119
+ * subscriber processes it in stream order. This is necessary for lag
120
+ * reports to measure the lag of the subscriber, including its catchup.
121
+ *
122
+ * Status messages received before the subscriber is initialized are
123
+ * dropped.
124
+ */
63
125
  sendStatus(status: Status): void;
126
+ /**
127
+ * Sends a control status (e.g. `draining` or `restore`) downstream
128
+ * immediately, regardless of whether the subscriber is initialized or
129
+ * catching up. Unlike {@link sendStatus}, such statuses are not tied to a
130
+ * position in the replication stream.
131
+ */
132
+ sendControlStatus(status: Status): void;
64
133
  /** catchup() is called on ChangeEntries loaded from the store. */
65
134
  catchup(change: WatermarkedChange): Promise<void>;
66
135
  /**
@@ -110,7 +179,16 @@ export declare class Subscriber {
110
179
  * Callers are responsible for logging `err`; it is not carried downstream.
111
180
  */
112
181
  fail(_err?: unknown): void;
113
- close(error?: ErrorType, message?: string): void;
182
+ close(error?: ErrorType, message?: string, details?: {
183
+ replicaVersion?: string | undefined;
184
+ }): void;
114
185
  }
186
+ /**
187
+ * Sent to an aligned subscriber when lag reporting is disabled upstream,
188
+ * signaling that the subscriber is caught up. This is a lag report with a
189
+ * `nextSendTimeMs` of 0 and no `lastTimings`, so that no lag is measured
190
+ * (see `isLagReportingDisabledSignal()` in the replicator's recorder).
191
+ */
192
+ export declare const LAG_REPORTING_DISABLED: Status;
115
193
  export {};
116
194
  //# sourceMappingURL=subscriber.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"subscriber.d.ts","sourceRoot":"","sources":["../../../../../../zero-cache/src/services/change-streamer/subscriber.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAC,IAAI,EAAC,MAAM,gCAAgC,CAAC;AAKzD,OAAO,KAAK,EAAC,YAAY,EAAC,MAAM,6BAA6B,CAAC;AAC9D,OAAO,KAAK,EAAC,cAAc,EAAC,MAAM,6BAA6B,CAAC;AAChE,OAAO,KAAK,EACV,SAAS,EAET,MAAM,EACN,iBAAiB,EAClB,MAAM,sBAAsB,CAAC;AAC9B,OAAO,KAAK,KAAK,SAAS,MAAM,sBAAsB,CAAC;AAEvD,KAAK,SAAS,GAAG,IAAI,CAAC,OAAO,SAAS,CAAC,CAAC;AAKxC,MAAM,MAAM,iBAAiB,GAAG;IAC9B,qBAAqB,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IAC3C,oBAAoB,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IAE1C;;;;OAIG;IACH,KAAK,CAAC,EAAE,CAAC,CAAC,SAAS,EAAE,MAAM,KAAK,IAAI,CAAC,GAAG,SAAS,CAAC;CACnD,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG;IAC5B,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAC,IAAI,CAAC,CAAC;IAChC,MAAM,IAAI,IAAI,CAAC;CAChB,CAAC;AAEF,MAAM,MAAM,eAAe,GAAG;IAC5B,WAAW,EAAE,MAAM,CAAC;IACpB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,YAAY,EAAE,MAAM,CAAC;IACrB,kBAAkB,EAAE,MAAM,CAAC;IAC3B,iBAAiB,EAAE,OAAO,CAAC;CAC5B,CAAC;AAEF;;;;;;GAMG;AACH,qBAAa,UAAU;;IAErB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,IAAI,EAAE,cAAc,CAAC;IAgB9B,YACE,eAAe,EAAE,MAAM,EACvB,EAAE,EAAE,MAAM,EACV,IAAI,EAAE,cAAc,EACpB,SAAS,EAAE,MAAM,EACjB,UAAU,EAAE,YAAY,CAAC,MAAM,CAAC,EAChC,YAAY,EAAE,MAAM,MAAM,EAC1B,OAAO,GAAE,iBAAsB,EAehC;IAED,IAAI,SAAS,WAEZ;IAED,IAAI,KAAK,WAER;IAED;;;;;OAKG;IACH,IAAI,WAAW,YAId;IAED;;;OAGG;IACH,YAAY,YAEX;IAED;;;;;OAKG;IACH,eAAe,IAAI,eAAe,CAYjC;IAED,IAAI,CAAC,MAAM,EAAE,iBAAiB,GAAG,OAAO,CAAC,IAAI,CAAC,CAa7C;IAeD,UAAU,CAAC,MAAM,EAAE,MAAM,QAIxB;IAED,kEAAkE;IAC5D,OAAO,CAAC,MAAM,EAAE,iBAAiB,iBAGtC;IAED;;;OAGG;IACH,WAAW,IAAI,OAAO,CAAC,IAAI,CAAC,CAc3B;IA2DD;;OAEG;IACH,IAAI,UAAU,WAEb;IAED;;;OAGG;IACH,IAAI,YAAY,WAEf;IAED;;;OAGG;IACH,iBAAiB,CAAC,GAAG,EAAE,MAAM,EAAE,UAAU,SAAK,GAAG,IAAI,CAMpD;IAED,QAAQ,IAAI,eAAe,CAyB1B;IAKD,mBAAmB,CAAC,MAAM,EAAE,SAAS,GAAG,WAAW,QAKlD;IAED;;;;;;;;;;OAUG;IACH,gBAAgB,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,GAAG,aAAa,UAW9D;IAED,eAAe,CAAC,GAAG,EAAE,SAAS,WAO7B;IAED;;;;;;;;;;;OAWG;IACH,IAAI,CAAC,IAAI,CAAC,EAAE,OAAO,QAElB;IAED,KAAK,CAAC,KAAK,CAAC,EAAE,SAAS,EAAE,OAAO,CAAC,EAAE,MAAM,QAkBxC;CA0FF"}
1
+ {"version":3,"file":"subscriber.d.ts","sourceRoot":"","sources":["../../../../../../zero-cache/src/services/change-streamer/subscriber.ts"],"names":[],"mappings":"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"}
@@ -8,6 +8,12 @@ import { resolver } from "@rocicorp/resolver";
8
8
  //#region ../zero-cache/src/services/change-streamer/subscriber.ts
9
9
  var DEFAULT_BACKLOG_HIGH_WATER_BYTES = 16 * 1024 * 1024;
10
10
  var DEFAULT_BACKLOG_LOW_WATER_RATIO = .8;
11
+ function isQueuedStatus(entry) {
12
+ return !Array.isArray(entry);
13
+ }
14
+ function entryBytes(entry) {
15
+ return isQueuedStatus(entry) ? entry.status.length : entry[2].length;
16
+ }
11
17
  /**
12
18
  * Encapsulates a subscriber to changes. All subscribers start in a
13
19
  * "catchup" phase in which changes are buffered in a backlog while the
@@ -19,8 +25,9 @@ var Subscriber = class {
19
25
  #protocolVersion;
20
26
  id;
21
27
  mode;
28
+ drainable;
22
29
  #downstream;
23
- #latestStatus;
30
+ #wsBatched;
24
31
  #watermark;
25
32
  #acked;
26
33
  #backlog;
@@ -30,17 +37,57 @@ var Subscriber = class {
30
37
  #backlogBackpressure;
31
38
  #backlogFullWaiters = /* @__PURE__ */ new Set();
32
39
  #onAck;
33
- constructor(protocolVersion, id, mode, watermark, downstream, latestStatus, options = {}) {
40
+ #backfills;
41
+ #onAligned;
42
+ #onBackfillIgnored;
43
+ #lagReportingDisabled;
44
+ #aligned = false;
45
+ #caughtUpWatermark;
46
+ #caughtUp = resolver();
47
+ constructor(protocolVersion, id, mode, watermark, downstream, options = {}) {
34
48
  this.#protocolVersion = protocolVersion;
35
49
  this.id = id;
36
50
  this.mode = mode;
51
+ this.drainable = options.drainable ?? false;
37
52
  this.#downstream = downstream;
38
- this.#latestStatus = latestStatus;
53
+ this.#wsBatched = options.wsBatched ?? false;
39
54
  this.#watermark = watermark;
40
55
  this.#acked = watermark;
41
56
  this.#backlog = new RingBuffer();
42
57
  this.#backlogBackpressure = new ByteBackpressureGate(options.backlogHighWaterBytes ?? DEFAULT_BACKLOG_HIGH_WATER_BYTES, options.backlogLowWaterRatio ?? DEFAULT_BACKLOG_LOW_WATER_RATIO);
43
58
  this.#onAck = options.onAck;
59
+ this.#backfills = options.backfills;
60
+ this.#onAligned = options.onAligned;
61
+ this.#onBackfillIgnored = options.onBackfillIgnored;
62
+ this.#lagReportingDisabled = options.lagReportingDisabled;
63
+ }
64
+ /**
65
+ * The subscriber's tracked pending backfills, or `undefined` if the
66
+ * subscriber does not report them (i.e. protocol < v8).
67
+ */
68
+ get backfills() {
69
+ return this.#backfills;
70
+ }
71
+ /**
72
+ * Whether the subscriber has been sent all changes up to the head of the
73
+ * stream (see {@link SubscriberOptions.onAligned}).
74
+ */
75
+ get aligned() {
76
+ return this.#aligned;
77
+ }
78
+ /**
79
+ * Resolves once the subscriber has caught up, i.e. once it has acked
80
+ * (durably applied) all changes up to the head of the stream at the time
81
+ * it was {@link aligned}. Never resolves if the subscriber is closed first.
82
+ */
83
+ get caughtUp() {
84
+ return this.#caughtUp.promise;
85
+ }
86
+ #trackBackfills(change) {
87
+ if (this.#backfills) {
88
+ const ignored = this.#backfills.applySerialized(change);
89
+ if (ignored.length && this.#aligned) this.#onBackfillIgnored?.(ignored);
90
+ }
44
91
  }
45
92
  get watermark() {
46
93
  return this.#watermark;
@@ -95,6 +142,27 @@ var Subscriber = class {
95
142
  }
96
143
  return promiseVoid;
97
144
  }
145
+ sendBatch(changes, preSerialized) {
146
+ if (changes.length === 0) return promiseVoid;
147
+ if (this.#wsBatched && preSerialized && !this.#backlog && this.#initialized && changes[0][0] > this.#watermark && (this.#protocolVersion >= 5 || changes.every((c) => this.supportsMessage(c[1])))) {
148
+ let commitWatermark;
149
+ for (let i = changes.length - 1; i >= 0; i--) if (changes[i][1] === "commit") {
150
+ commitWatermark = changes[i][0];
151
+ break;
152
+ }
153
+ if (commitWatermark) this.#watermark = commitWatermark;
154
+ for (const change of changes) this.#trackBackfills(change);
155
+ return this.#sendPreSerializedDownstream(preSerialized, commitWatermark);
156
+ }
157
+ const promises = [];
158
+ for (const change of changes) {
159
+ const p = this.send(change);
160
+ if (p !== promiseVoid) promises.push(p);
161
+ }
162
+ if (promises.length === 0) return promiseVoid;
163
+ if (promises.length === 1) return promises[0];
164
+ return Promise.all(promises).then(() => {});
165
+ }
98
166
  #initialized = false;
99
167
  /**
100
168
  * Called once the subscriber's watermark has been validated in the initial
@@ -103,11 +171,36 @@ var Subscriber = class {
103
171
  #initialize() {
104
172
  if (!this.#initialized) {
105
173
  this.#initialized = true;
106
- this.sendStatus(this.#latestStatus());
174
+ this.#sendDownstream(["status", { tag: "status" }]);
107
175
  }
108
176
  }
177
+ /**
178
+ * Sends a status message (e.g. a lag report) downstream. While the
179
+ * subscriber is catching up, the status is queued in the backlog behind
180
+ * the changes that preceded it in the replication stream, so that the
181
+ * subscriber processes it in stream order. This is necessary for lag
182
+ * reports to measure the lag of the subscriber, including its catchup.
183
+ *
184
+ * Status messages received before the subscriber is initialized are
185
+ * dropped.
186
+ */
109
187
  sendStatus(status) {
110
- if (this.#initialized) this.#sendDownstream(["status", status]);
188
+ if (!this.#initialized) return;
189
+ const downstream = ["status", status];
190
+ if (this.#backlog) {
191
+ this.#pushBacklog({ status: BigIntJSON.stringify(downstream) });
192
+ return;
193
+ }
194
+ this.#sendDownstream(downstream);
195
+ }
196
+ /**
197
+ * Sends a control status (e.g. `draining` or `restore`) downstream
198
+ * immediately, regardless of whether the subscriber is initialized or
199
+ * catching up. Unlike {@link sendStatus}, such statuses are not tied to a
200
+ * position in the replication stream.
201
+ */
202
+ sendControlStatus(status) {
203
+ this.#sendDownstream(["status", status]);
111
204
  }
112
205
  /** catchup() is called on ChangeEntries loaded from the store. */
113
206
  async catchup(change) {
@@ -132,13 +225,22 @@ var Subscriber = class {
132
225
  if (watermark <= this.watermark) return;
133
226
  if (!this.supportsMessage(tag)) return;
134
227
  if (tag === "commit") this.#watermark = watermark;
228
+ this.#trackBackfills(change);
135
229
  const result = await this.#sendStringifiedDownstream(json);
136
- if (tag === "commit" && result === "consumed") {
137
- const acked = max(this.#acked, watermark);
138
- if (acked !== this.#acked) {
139
- this.#acked = acked;
140
- this.#onAck?.(acked);
141
- }
230
+ if (tag === "commit" && result === "consumed") this.#advanceAck(watermark);
231
+ }
232
+ #advanceAck(watermark) {
233
+ const acked = max(this.#acked, watermark);
234
+ if (acked !== this.#acked) {
235
+ this.#acked = acked;
236
+ this.#onAck?.(acked);
237
+ this.#checkCaughtUp();
238
+ }
239
+ }
240
+ #checkCaughtUp() {
241
+ if (this.#caughtUpWatermark !== void 0 && this.#acked >= this.#caughtUpWatermark) {
242
+ this.#caughtUpWatermark = void 0;
243
+ this.#caughtUp.resolve();
142
244
  }
143
245
  }
144
246
  #sendDownstream(downstream) {
@@ -157,6 +259,20 @@ var Subscriber = class {
157
259
  this.#processed++;
158
260
  }
159
261
  }
262
+ async #sendPreSerializedDownstream(batch, commitWatermark) {
263
+ const size = batch.byteLength;
264
+ this.#pending += batch.changes.length;
265
+ this.#pendingBytes += size;
266
+ const { result } = this.#downstream.push(batch);
267
+ try {
268
+ const outcome = await result;
269
+ if (commitWatermark && outcome === "consumed") this.#advanceAck(commitWatermark);
270
+ } finally {
271
+ this.#pending -= batch.changes.length;
272
+ this.#pendingBytes -= size;
273
+ this.#processed += batch.changes.length;
274
+ }
275
+ }
160
276
  #pending = 0;
161
277
  #pendingBytes = 0;
162
278
  #processed = 0;
@@ -259,14 +375,15 @@ var Subscriber = class {
259
375
  fail(_err) {
260
376
  this.close();
261
377
  }
262
- close(error, message) {
378
+ close(error, message, details) {
263
379
  this.#backlog = null;
264
380
  this.#backlogBytes = 0;
265
381
  this.#backlogBackpressure.releaseAll();
266
382
  this.#resolveBacklogFullWaiters();
267
383
  if (error !== void 0) this.#sendDownstream(["error", {
268
384
  type: error,
269
- message
385
+ message,
386
+ ...details
270
387
  }]).finally(() => this.#downstream.cancel());
271
388
  else this.#downstream.cancel();
272
389
  }
@@ -279,10 +396,10 @@ var Subscriber = class {
279
396
  get #totalBufferedBytes() {
280
397
  return this.#bufferedBacklogBytes + this.#pendingBytes;
281
398
  }
282
- #pushBacklog(change) {
399
+ #pushBacklog(entry) {
283
400
  assert(this.#backlog, "cannot push to backlog after catchup completed");
284
- this.#backlog.push(change);
285
- this.#backlogBytes += change[2].length;
401
+ this.#backlog.push(entry);
402
+ this.#backlogBytes += entryBytes(entry);
286
403
  if (this.backlogFull) this.#resolveBacklogFullWaiters();
287
404
  }
288
405
  #resolveBacklogFullWaiters() {
@@ -298,18 +415,28 @@ var Subscriber = class {
298
415
  let inFlightBytes = 0;
299
416
  try {
300
417
  for (;;) {
301
- const change = this.#backlog?.shift();
302
- if (!change) {
418
+ const entry = this.#backlog?.shift();
419
+ if (!entry) {
420
+ const closed = this.#backlog === null;
303
421
  this.#backlog = null;
304
422
  this.#backlogBytes = 0;
305
423
  this.#backlogBackpressure.releaseIfUnderLowWater(this.#bufferedBacklogBytes);
424
+ if (!closed && !this.#aligned) {
425
+ this.#aligned = true;
426
+ this.#onAligned?.(this);
427
+ this.#caughtUpWatermark = this.#watermark;
428
+ this.#checkCaughtUp();
429
+ this.#lagReportingDisabled?.then((disabled) => {
430
+ if (disabled) this.sendStatus(LAG_REPORTING_DISABLED);
431
+ });
432
+ }
306
433
  break;
307
434
  }
308
- const bytes = change[2].length;
435
+ const bytes = entryBytes(entry);
309
436
  this.#backlogBytes -= bytes;
310
437
  this.#backlogInFlightBytes += bytes;
311
438
  this.#backlogBackpressure.releaseIfUnderLowWater(this.#bufferedBacklogBytes);
312
- const promise = this.#sendChange(change).finally(() => {
439
+ const promise = (isQueuedStatus(entry) ? this.#sendStringifiedDownstream(entry.status).then(() => {}) : this.#sendChange(entry)).finally(() => {
313
440
  this.#backlogInFlightBytes -= bytes;
314
441
  this.#backlogBackpressure.releaseIfUnderLowWater(this.#bufferedBacklogBytes);
315
442
  });
@@ -354,6 +481,16 @@ var ByteBackpressureGate = class {
354
481
  for (const waiter of waiters) waiter.resolve();
355
482
  }
356
483
  };
484
+ /**
485
+ * Sent to an aligned subscriber when lag reporting is disabled upstream,
486
+ * signaling that the subscriber is caught up. This is a lag report with a
487
+ * `nextSendTimeMs` of 0 and no `lastTimings`, so that no lag is measured
488
+ * (see `isLagReportingDisabledSignal()` in the replicator's recorder).
489
+ */
490
+ var LAG_REPORTING_DISABLED = {
491
+ tag: "status",
492
+ lagReport: { nextSendTimeMs: 0 }
493
+ };
357
494
  //#endregion
358
495
  export { Subscriber };
359
496
 
@@ -1 +1 @@
1
- {"version":3,"file":"subscriber.js","names":["#protocolVersion","#downstream","#latestStatus","#backlogBackpressure","#backlogFullWaiters","#onAck","#watermark","#acked","#backlog","#bufferedBacklogBytes","#pushBacklog","#maybeWaitForBacklogSpace","#sendChange","#initialized","#sendDownstream","#initialize","#backlogDrain","#drainBacklog","#sendStringifiedDownstream","#pending","#pendingBytes","#processed","#backlogCount","#samples","#totalBufferedBytes","#missedLastTimeout","#laggingSinceMs","#backlogBytes","#resolveBacklogFullWaiters","#backlogInFlightBytes","#lowWaterBytes","#waiters"],"sources":["../../../../../../zero-cache/src/services/change-streamer/subscriber.ts"],"sourcesContent":["import {resolver, type Resolver} from '@rocicorp/resolver';\nimport {assert} from '../../../../shared/src/asserts.ts';\nimport {BigIntJSON} from '../../../../shared/src/bigint-json.ts';\nimport type {Enum} from '../../../../shared/src/enum.ts';\nimport {must} from '../../../../shared/src/must.ts';\nimport {promiseVoid} from '../../../../shared/src/resolved-promises.ts';\nimport {RingBuffer} from '../../../../shared/src/ring-buffer.ts';\nimport {max} from '../../types/lexi-version.ts';\nimport type {Subscription} from '../../types/subscription.ts';\nimport type {ReplicatorMode} from '../replicator/replicator.ts';\nimport type {\n ChangeTag,\n Downstream,\n Status,\n WatermarkedChange,\n} from './change-streamer.ts';\nimport type * as ErrorType from './error-type-enum.ts';\n\ntype ErrorType = Enum<typeof ErrorType>;\n\nconst DEFAULT_BACKLOG_HIGH_WATER_BYTES = 16 * 1024 * 1024;\nconst DEFAULT_BACKLOG_LOW_WATER_RATIO = 0.8;\n\nexport type SubscriberOptions = {\n backlogHighWaterBytes?: number | undefined;\n backlogLowWaterRatio?: number | undefined;\n\n /**\n * Called whenever the subscriber's acked watermark advances, i.e. when it\n * has confirmed that a commit was durably applied to its replica. The ACK\n * therefore lags the subscriber's replica rather than leading it.\n */\n onAck?: ((watermark: string) => void) | undefined;\n};\n\nexport type BacklogFullWait = {\n readonly promise: Promise<void>;\n cancel(): void;\n};\n\nexport type SubscriberStats = {\n processRate: number;\n pending: number;\n backlog: number;\n backlogBytes: number;\n totalBufferedBytes: number;\n missedLastTimeout: boolean;\n};\n\n/**\n * Encapsulates a subscriber to changes. All subscribers start in a\n * \"catchup\" phase in which changes are buffered in a backlog while the\n * storer is queried to send any changes that were committed since the\n * subscriber's watermark. Once the catchup is complete, calls to\n * {@link send()} result in immediately sending the change.\n */\nexport class Subscriber {\n readonly #protocolVersion: number;\n readonly id: string;\n readonly mode: ReplicatorMode;\n readonly #downstream: Subscription<string>;\n readonly #latestStatus: () => Status;\n #watermark: string;\n #acked: string;\n #backlog: RingBuffer<WatermarkedChange> | null;\n // While catchup is running, live changes are buffered here instead of being\n // pushed downstream. RingBuffer lets drainBacklog consume that backlog without\n // shifting an array, which matters when a subscriber is far behind.\n #backlogBytes = 0;\n #backlogInFlightBytes = 0;\n #backlogDrain: Promise<void> | null = null;\n readonly #backlogBackpressure: ByteBackpressureGate;\n readonly #backlogFullWaiters = new Set<Resolver<void>>();\n readonly #onAck: ((watermark: string) => void) | undefined;\n\n constructor(\n protocolVersion: number,\n id: string,\n mode: ReplicatorMode,\n watermark: string,\n downstream: Subscription<string>,\n latestStatus: () => Status,\n options: SubscriberOptions = {},\n ) {\n this.#protocolVersion = protocolVersion;\n this.id = id;\n this.mode = mode;\n this.#downstream = downstream;\n this.#latestStatus = latestStatus;\n this.#watermark = watermark;\n this.#acked = watermark;\n this.#backlog = new RingBuffer();\n this.#backlogBackpressure = new ByteBackpressureGate(\n options.backlogHighWaterBytes ?? DEFAULT_BACKLOG_HIGH_WATER_BYTES,\n options.backlogLowWaterRatio ?? DEFAULT_BACKLOG_LOW_WATER_RATIO,\n );\n this.#onAck = options.onAck;\n }\n\n get watermark() {\n return this.#watermark;\n }\n\n get acked() {\n return this.#acked;\n }\n\n /**\n * Whether the backlog of live changes buffered during catchup has reached the\n * point at which {@link send()} stops resolving. Past it the subscriber is no\n * longer free: it holds up every subsequent flush, and with no other\n * subscriber to form a majority it stalls replication outright.\n */\n get backlogFull() {\n return (\n this.#bufferedBacklogBytes >= this.#backlogBackpressure.highWaterBytes\n );\n }\n\n /**\n * @returns whether the subscriber is currently sending backlogged messages,\n * vs caught up and sending the \"head\" of the replication stream.\n */\n isBacklogged() {\n return this.#backlog !== null || this.#bufferedBacklogBytes > 0;\n }\n\n /**\n * Resolves the first time {@link backlogFull} becomes true, so that a caller\n * holding the subscriber in catchup can give up at the moment the subscriber\n * starts costing replication rather than on a timer. Call cancel() when the\n * wait is no longer needed so the subscriber does not retain it.\n */\n whenBacklogFull(): BacklogFullWait {\n if (this.backlogFull) {\n return {promise: promiseVoid, cancel() {}};\n }\n const r = resolver<void>();\n this.#backlogFullWaiters.add(r);\n return {\n promise: r.promise,\n cancel: () => {\n this.#backlogFullWaiters.delete(r);\n },\n };\n }\n\n send(change: WatermarkedChange): Promise<void> {\n const [watermark] = change;\n if (watermark > this.#watermark) {\n if (this.#backlog) {\n // During catchup, buffer live changes behind the durable catchup stream.\n // The returned promise applies backpressure if the buffered bytes cross\n // the high water mark.\n this.#pushBacklog(change);\n return this.#maybeWaitForBacklogSpace();\n }\n return this.#sendChange(change);\n }\n return promiseVoid;\n }\n\n #initialized = false;\n\n /**\n * Called once the subscriber's watermark has been validated in the initial\n * catchup process.\n */\n #initialize() {\n if (!this.#initialized) {\n this.#initialized = true;\n this.sendStatus(this.#latestStatus());\n }\n }\n\n sendStatus(status: Status) {\n if (this.#initialized) {\n void this.#sendDownstream(['status', status]);\n }\n }\n\n /** catchup() is called on ChangeEntries loaded from the store. */\n async catchup(change: WatermarkedChange) {\n this.#initialize();\n await this.#sendChange(change);\n }\n\n /**\n * Marks the Subscribe as \"caught up\" and flushes any backlog of\n * entries that were received during the catchup.\n */\n setCaughtUp(): Promise<void> {\n this.#initialize();\n if (!this.#backlog) {\n return this.#backlogDrain ?? promiseVoid;\n }\n if (!this.#backlogDrain) {\n // Keep #backlog non-null while queued entries are being handed to\n // downstream. That preserves ordering for sends that race with\n // setCaughtUp(): they append to the same backlog instead of bypassing\n // older buffered changes.\n this.#backlogDrain = this.#drainBacklog();\n void this.#backlogDrain.catch(e => this.fail(e));\n }\n return this.#backlogDrain;\n }\n\n async #sendChange(change: WatermarkedChange) {\n const [watermark, tag, json] = change;\n if (watermark <= this.watermark) {\n return;\n }\n if (!this.supportsMessage(tag)) {\n return;\n }\n if (tag === 'commit') {\n this.#watermark = watermark;\n }\n const result = await this.#sendStringifiedDownstream(json);\n if (tag === 'commit' && result === 'consumed') {\n // Sends can complete out of order (e.g. the bounded window in\n // #drainBacklog), so the ack only advances monotonically, and listeners\n // are only notified when it does.\n const acked = max(this.#acked, watermark);\n if (acked !== this.#acked) {\n this.#acked = acked;\n this.#onAck?.(acked);\n }\n }\n }\n\n #sendDownstream(downstream: Downstream) {\n return this.#sendStringifiedDownstream(BigIntJSON.stringify(downstream));\n }\n\n async #sendStringifiedDownstream(json: string) {\n const size = json.length;\n this.#pending++;\n this.#pendingBytes += size;\n const {result} = this.#downstream.push(json);\n try {\n return await result;\n } finally {\n this.#pending--;\n this.#pendingBytes -= size;\n this.#processed++;\n }\n }\n\n // `pending` and `processed` stats are tracked by periodically sampling\n // the running totals (by the progress tracker in the Forwarder).\n // This information was originally collected for use in flow control\n // decisions. The final flow control algorithm ended up being simpler\n // than expected and does not actually use this information. However, the\n // stats are still tracked and logged during flow control decisions for\n // debugging, forensics, and potential improvements to the algorithm.\n\n #pending = 0;\n #pendingBytes = 0;\n #processed = 0;\n #samples: {processed: number; timestamp: number}[] = [\n {processed: 0, timestamp: performance.now()},\n ];\n\n /**\n * The number of downstream messages that have yet to be acked.\n */\n get numPending() {\n return this.#pending + this.#backlogCount;\n }\n\n /**\n * The total number of downstream messages that the subscriber has\n * processed (i.e. acked).\n */\n get numProcessed() {\n return this.#processed;\n }\n\n /**\n * Records a new history entry for the number of messages processed,\n * keeping the number of samples bounded to `maxSamples`.\n */\n sampleProcessRate(now: number, maxSamples = 10): this {\n while (this.#samples.length >= maxSamples) {\n this.#samples.shift();\n }\n this.#samples.push({processed: this.#processed, timestamp: now});\n return this;\n }\n\n getStats(): SubscriberStats {\n const pending = this.numPending;\n if (this.#samples.length < 2) {\n return {\n processRate: 0,\n pending,\n backlog: this.#backlogCount,\n backlogBytes: this.#bufferedBacklogBytes,\n totalBufferedBytes: this.#totalBufferedBytes,\n missedLastTimeout: this.#missedLastTimeout,\n };\n }\n const from = this.#samples[0];\n const to = must(this.#samples.at(-1));\n const processed = to.processed - from.processed;\n const seconds = (to.timestamp - from.timestamp) / 1000;\n const processRate = seconds === 0 ? 0 : processed / seconds;\n return {\n processRate,\n pending,\n backlog: this.#backlogCount,\n backlogBytes: this.#bufferedBacklogBytes,\n totalBufferedBytes: this.#totalBufferedBytes,\n missedLastTimeout: this.#missedLastTimeout,\n };\n }\n\n #missedLastTimeout = false;\n #laggingSinceMs: number | undefined;\n\n trackResponseResult(result: 'on-time' | 'timed-out') {\n this.#missedLastTimeout = result === 'timed-out';\n if (result === 'on-time') {\n this.#laggingSinceMs = undefined;\n }\n }\n\n /**\n * Reports the change rate of a slow subscriber (i.e. that missed the last\n * timeout) compared to the change rate of the (slowest) subscriber that\n * responded on time.\n *\n * * `lagging` indicates that this subscriber is slower\n * * `catching-up` indicates that it is faster\n *\n * Returns the total duration in which subscriber has been continuously\n * reported as `lagging`.\n */\n reportChangeRate(now: number, status: 'lagging' | 'catching-up') {\n assert(\n this.#missedLastTimeout,\n `reportChangeRate should only be called for slow subscribers`,\n );\n if (status === 'catching-up') {\n this.#laggingSinceMs = undefined;\n return 0;\n }\n this.#laggingSinceMs ??= now;\n return now - this.#laggingSinceMs;\n }\n\n supportsMessage(tag: ChangeTag) {\n switch (tag) {\n case 'update-table-metadata':\n // update-table-row-key is only understood by subscribers >= protocol v5\n return this.#protocolVersion >= 5;\n }\n return true;\n }\n\n /**\n * Ends the subscription without sending a downstream `['error', ...]`.\n *\n * This is deliberate, and not the same as reporting the failure to the\n * subscriber: `IncrementalSyncer` treats any `['error', ...]` as terminal and\n * shuts down to restore a fresh replica from litestream, whereas a clean end\n * backs off and re-subscribes. The failures routed here -- storer catchup\n * errors, backlog drain errors, backup-monitor errors -- are transient, so a\n * reconnect is the proportionate response and a fleet-wide restore is not.\n *\n * Callers are responsible for logging `err`; it is not carried downstream.\n */\n fail(_err?: unknown) {\n this.close();\n }\n\n close(error?: ErrorType, message?: string) {\n // Closing the subscriber must also release producers that are blocked on\n // backlog capacity; there is no future drain that could wake them.\n this.#backlog = null;\n this.#backlogBytes = 0;\n this.#backlogBackpressure.releaseAll();\n // The backlog can no longer grow, so nothing would ever resolve these.\n // Waiters re-check backlogFull, which is now false, and see the close.\n this.#resolveBacklogFullWaiters();\n\n if (error !== undefined) {\n // Wait for the ACK of the error message before closing the connection.\n void this.#sendDownstream(['error', {type: error, message}]).finally(() =>\n this.#downstream.cancel(),\n );\n } else {\n this.#downstream.cancel();\n }\n }\n\n get #backlogCount() {\n return this.#backlog?.size ?? 0;\n }\n\n get #bufferedBacklogBytes() {\n // Include entries already handed to downstream but not yet consumed. Without\n // this, setCaughtUp() could move bytes out of #backlog faster than the\n // downstream Subscription can process them and release producers too early.\n return this.#backlogBytes + this.#backlogInFlightBytes;\n }\n\n get #totalBufferedBytes() {\n return this.#bufferedBacklogBytes + this.#pendingBytes;\n }\n\n #pushBacklog(change: WatermarkedChange) {\n assert(this.#backlog, 'cannot push to backlog after catchup completed');\n this.#backlog.push(change);\n this.#backlogBytes += change[2].length;\n if (this.backlogFull) {\n this.#resolveBacklogFullWaiters();\n }\n }\n\n #resolveBacklogFullWaiters() {\n const waiters = [...this.#backlogFullWaiters];\n this.#backlogFullWaiters.clear();\n for (const waiter of waiters) {\n waiter.resolve();\n }\n }\n\n #maybeWaitForBacklogSpace(): Promise<void> {\n return this.#backlogBackpressure.waitForSpace(this.#bufferedBacklogBytes);\n }\n\n async #drainBacklog() {\n const inFlight: {promise: Promise<void>; bytes: number}[] = [];\n let inFlightBytes = 0;\n\n try {\n for (;;) {\n const change = this.#backlog?.shift();\n if (!change) {\n this.#backlog = null;\n this.#backlogBytes = 0;\n this.#backlogBackpressure.releaseIfUnderLowWater(\n this.#bufferedBacklogBytes,\n );\n break;\n }\n\n const bytes = change[2].length;\n this.#backlogBytes -= bytes;\n this.#backlogInFlightBytes += bytes;\n this.#backlogBackpressure.releaseIfUnderLowWater(\n this.#bufferedBacklogBytes,\n );\n\n // Send backlog entries in order, but keep only a bounded byte window in\n // flight. This avoids replacing one unbounded buffer with another inside\n // the downstream Subscription during catchup completion.\n const promise = this.#sendChange(change).finally(() => {\n this.#backlogInFlightBytes -= bytes;\n this.#backlogBackpressure.releaseIfUnderLowWater(\n this.#bufferedBacklogBytes,\n );\n });\n inFlight.push({promise, bytes});\n inFlightBytes += bytes;\n\n while (inFlightBytes >= this.#backlogBackpressure.highWaterBytes) {\n const next = must(inFlight.shift());\n await next.promise;\n inFlightBytes -= next.bytes;\n }\n }\n\n for (const {promise} of inFlight) {\n await promise;\n }\n } finally {\n this.#backlogDrain = null;\n this.#backlogBackpressure.releaseIfUnderLowWater(\n this.#bufferedBacklogBytes,\n );\n }\n }\n}\n\nclass ByteBackpressureGate {\n readonly highWaterBytes: number;\n readonly #lowWaterBytes: number;\n readonly #waiters: Resolver<void>[] = [];\n\n constructor(highWaterBytes: number, lowWaterRatio: number) {\n this.highWaterBytes = Math.max(1, highWaterBytes);\n this.#lowWaterBytes =\n this.highWaterBytes * Math.min(1, Math.max(0, lowWaterRatio));\n }\n\n waitForSpace(bufferedBytes: number): Promise<void> {\n if (bufferedBytes < this.highWaterBytes) {\n return promiseVoid;\n }\n\n // One waiter represents one send() call that has already appended its\n // change. The producer is released when the backlog falls back below the low\n // water mark or the subscriber closes.\n const r = resolver<void>();\n this.#waiters.push(r);\n return r.promise;\n }\n\n releaseIfUnderLowWater(bufferedBytes: number) {\n if (this.#waiters.length === 0 || bufferedBytes > this.#lowWaterBytes) {\n return;\n }\n\n // Use a low water mark so waiting producers are released in batches instead\n // of waking one at a time around the high water boundary.\n this.releaseAll();\n }\n\n releaseAll() {\n const waiters = this.#waiters.splice(0);\n for (const waiter of waiters) {\n waiter.resolve();\n }\n }\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"subscriber.js","names":["#protocolVersion","#downstream","#wsBatched","#backlogBackpressure","#backlogFullWaiters","#onAck","#backfills","#onAligned","#onBackfillIgnored","#lagReportingDisabled","#caughtUp","#watermark","#acked","#backlog","#aligned","#bufferedBacklogBytes","#pushBacklog","#maybeWaitForBacklogSpace","#sendChange","#initialized","#trackBackfills","#sendPreSerializedDownstream","#sendDownstream","#initialize","#backlogDrain","#drainBacklog","#sendStringifiedDownstream","#advanceAck","#checkCaughtUp","#caughtUpWatermark","#pending","#pendingBytes","#processed","#backlogCount","#samples","#totalBufferedBytes","#missedLastTimeout","#laggingSinceMs","#backlogBytes","#resolveBacklogFullWaiters","#backlogInFlightBytes","#lowWaterBytes","#waiters"],"sources":["../../../../../../zero-cache/src/services/change-streamer/subscriber.ts"],"sourcesContent":["import {resolver, type Resolver} from '@rocicorp/resolver';\nimport {assert} from '../../../../shared/src/asserts.ts';\nimport {BigIntJSON} from '../../../../shared/src/bigint-json.ts';\nimport type {Enum} from '../../../../shared/src/enum.ts';\nimport {must} from '../../../../shared/src/must.ts';\nimport {promiseVoid} from '../../../../shared/src/resolved-promises.ts';\nimport {RingBuffer} from '../../../../shared/src/ring-buffer.ts';\nimport {max} from '../../types/lexi-version.ts';\nimport type {Subscription} from '../../types/subscription.ts';\nimport type {ReplicatorMode} from '../replicator/replicator.ts';\nimport type {BackfillState} from './backfill-state.ts';\nimport type {PreSerializedBatch} from './broadcast.ts';\nimport type {\n ChangeTag,\n Downstream,\n Status,\n WatermarkedChange,\n} from './change-streamer.ts';\nimport type * as ErrorType from './error-type-enum.ts';\n\ntype ErrorType = Enum<typeof ErrorType>;\n\nconst DEFAULT_BACKLOG_HIGH_WATER_BYTES = 16 * 1024 * 1024;\nconst DEFAULT_BACKLOG_LOW_WATER_RATIO = 0.8;\n\nexport type SubscriberOptions = {\n backlogHighWaterBytes?: number | undefined;\n backlogLowWaterRatio?: number | undefined;\n wsBatched?: boolean | undefined;\n\n /**\n * Called whenever the subscriber's acked watermark advances, i.e. when it\n * has confirmed that a commit was durably applied to its replica. The ACK\n * therefore lags the subscriber's replica rather than leading it.\n */\n onAck?: ((watermark: string) => void) | undefined;\n\n /**\n * The subscriber's pending backfills (protocol v8+), which are tracked\n * over the changes sent to the subscriber.\n */\n backfills?: BackfillState | undefined;\n\n /**\n * Called once the subscriber has been sent all changes up to the head of\n * the stream, i.e. its catchup and backlog have been flushed. From this\n * point on, the subscriber's tracked {@link backfills} reflect the same\n * position in the stream as that of the change-streamer.\n */\n onAligned?: ((subscriber: Subscriber) => void) | undefined;\n\n /**\n * Called when a `backfill` or `backfill-completed` message is ignored for\n * some of the subscriber's pending backfill columns, after the subscriber\n * is aligned.\n */\n onBackfillIgnored?: ((columns: string[]) => void) | undefined;\n\n /**\n * Resolves to whether lag reporting is disabled upstream. If so, a\n * {@link LAG_REPORTING_DISABLED} status is sent once the subscriber is\n * aligned, as a stand-in for the lag reports that a subscriber would\n * otherwise use to determine that it is caught up (e.g. to advertise\n * readiness to serve traffic).\n */\n lagReportingDisabled?: Promise<boolean> | undefined;\n\n /**\n * Whether the subscriber switches over to another replication-manager\n * when this one drains (see `DrainTracker`).\n */\n drainable?: boolean | undefined;\n};\n\n/**\n * A status message queued in the backlog, so that it is sent downstream in\n * the order in which it was received relative to (backlogged) changes.\n */\ntype QueuedStatus = {readonly status: string};\n\ntype BacklogEntry = WatermarkedChange | QueuedStatus;\n\nfunction isQueuedStatus(entry: BacklogEntry): entry is QueuedStatus {\n return !Array.isArray(entry);\n}\n\nfunction entryBytes(entry: BacklogEntry): number {\n return isQueuedStatus(entry) ? entry.status.length : entry[2].length;\n}\n\nexport type BacklogFullWait = {\n readonly promise: Promise<void>;\n cancel(): void;\n};\n\nexport type SubscriberStats = {\n processRate: number;\n pending: number;\n backlog: number;\n backlogBytes: number;\n totalBufferedBytes: number;\n missedLastTimeout: boolean;\n};\n\n/**\n * Encapsulates a subscriber to changes. All subscribers start in a\n * \"catchup\" phase in which changes are buffered in a backlog while the\n * storer is queried to send any changes that were committed since the\n * subscriber's watermark. Once the catchup is complete, calls to\n * {@link send()} result in immediately sending the change.\n */\nexport class Subscriber {\n readonly #protocolVersion: number;\n readonly id: string;\n readonly mode: ReplicatorMode;\n readonly drainable: boolean;\n readonly #downstream: Subscription<string | PreSerializedBatch>;\n readonly #wsBatched: boolean;\n #watermark: string;\n #acked: string;\n #backlog: RingBuffer<BacklogEntry> | null;\n // While catchup is running, live changes are buffered here instead of being\n // pushed downstream. RingBuffer lets drainBacklog consume that backlog without\n // shifting an array, which matters when a subscriber is far behind.\n #backlogBytes = 0;\n #backlogInFlightBytes = 0;\n #backlogDrain: Promise<void> | null = null;\n readonly #backlogBackpressure: ByteBackpressureGate;\n readonly #backlogFullWaiters = new Set<Resolver<void>>();\n readonly #onAck: ((watermark: string) => void) | undefined;\n readonly #backfills: BackfillState | undefined;\n readonly #onAligned: ((subscriber: Subscriber) => void) | undefined;\n readonly #onBackfillIgnored: ((columns: string[]) => void) | undefined;\n readonly #lagReportingDisabled: Promise<boolean> | undefined;\n #aligned = false;\n // The watermark to be acked for the subscriber to be caught up, set when\n // it is aligned.\n #caughtUpWatermark: string | undefined;\n readonly #caughtUp = resolver<void>();\n\n constructor(\n protocolVersion: number,\n id: string,\n mode: ReplicatorMode,\n watermark: string,\n downstream: Subscription<string | PreSerializedBatch>,\n options: SubscriberOptions = {},\n ) {\n this.#protocolVersion = protocolVersion;\n this.id = id;\n this.mode = mode;\n this.drainable = options.drainable ?? false;\n this.#downstream = downstream;\n this.#wsBatched = options.wsBatched ?? false;\n this.#watermark = watermark;\n this.#acked = watermark;\n this.#backlog = new RingBuffer();\n this.#backlogBackpressure = new ByteBackpressureGate(\n options.backlogHighWaterBytes ?? DEFAULT_BACKLOG_HIGH_WATER_BYTES,\n options.backlogLowWaterRatio ?? DEFAULT_BACKLOG_LOW_WATER_RATIO,\n );\n this.#onAck = options.onAck;\n this.#backfills = options.backfills;\n this.#onAligned = options.onAligned;\n this.#onBackfillIgnored = options.onBackfillIgnored;\n this.#lagReportingDisabled = options.lagReportingDisabled;\n }\n\n /**\n * The subscriber's tracked pending backfills, or `undefined` if the\n * subscriber does not report them (i.e. protocol < v8).\n */\n get backfills(): BackfillState | undefined {\n return this.#backfills;\n }\n\n /**\n * Whether the subscriber has been sent all changes up to the head of the\n * stream (see {@link SubscriberOptions.onAligned}).\n */\n get aligned(): boolean {\n return this.#aligned;\n }\n\n /**\n * Resolves once the subscriber has caught up, i.e. once it has acked\n * (durably applied) all changes up to the head of the stream at the time\n * it was {@link aligned}. Never resolves if the subscriber is closed first.\n */\n get caughtUp(): Promise<void> {\n return this.#caughtUp.promise;\n }\n\n #trackBackfills(change: WatermarkedChange) {\n if (this.#backfills) {\n const ignored = this.#backfills.applySerialized(change);\n if (ignored.length && this.#aligned) {\n this.#onBackfillIgnored?.(ignored);\n }\n }\n }\n\n get watermark() {\n return this.#watermark;\n }\n\n get acked() {\n return this.#acked;\n }\n\n /**\n * Whether the backlog of live changes buffered during catchup has reached the\n * point at which {@link send()} stops resolving. Past it the subscriber is no\n * longer free: it holds up every subsequent flush, and with no other\n * subscriber to form a majority it stalls replication outright.\n */\n get backlogFull() {\n return (\n this.#bufferedBacklogBytes >= this.#backlogBackpressure.highWaterBytes\n );\n }\n\n /**\n * @returns whether the subscriber is currently sending backlogged messages,\n * vs caught up and sending the \"head\" of the replication stream.\n */\n isBacklogged() {\n return this.#backlog !== null || this.#bufferedBacklogBytes > 0;\n }\n\n /**\n * Resolves the first time {@link backlogFull} becomes true, so that a caller\n * holding the subscriber in catchup can give up at the moment the subscriber\n * starts costing replication rather than on a timer. Call cancel() when the\n * wait is no longer needed so the subscriber does not retain it.\n */\n whenBacklogFull(): BacklogFullWait {\n if (this.backlogFull) {\n return {promise: promiseVoid, cancel() {}};\n }\n const r = resolver<void>();\n this.#backlogFullWaiters.add(r);\n return {\n promise: r.promise,\n cancel: () => {\n this.#backlogFullWaiters.delete(r);\n },\n };\n }\n\n send(change: WatermarkedChange): Promise<void> {\n const [watermark] = change;\n if (watermark > this.#watermark) {\n if (this.#backlog) {\n // During catchup, buffer live changes behind the durable catchup stream.\n // The returned promise applies backpressure if the buffered bytes cross\n // the high water mark.\n this.#pushBacklog(change);\n return this.#maybeWaitForBacklogSpace();\n }\n return this.#sendChange(change);\n }\n return promiseVoid;\n }\n\n sendBatch(\n changes: readonly WatermarkedChange[],\n preSerialized?: PreSerializedBatch | undefined,\n ): Promise<void> {\n if (changes.length === 0) {\n return promiseVoid;\n }\n\n if (\n this.#wsBatched &&\n preSerialized &&\n !this.#backlog &&\n this.#initialized &&\n changes[0][0] > this.#watermark &&\n (this.#protocolVersion >= 5 ||\n changes.every(c => this.supportsMessage(c[1])))\n ) {\n let commitWatermark: string | undefined;\n for (let i = changes.length - 1; i >= 0; i--) {\n if (changes[i][1] === 'commit') {\n commitWatermark = changes[i][0];\n break;\n }\n }\n if (commitWatermark) {\n this.#watermark = commitWatermark;\n }\n for (const change of changes) {\n this.#trackBackfills(change);\n }\n return this.#sendPreSerializedDownstream(preSerialized, commitWatermark);\n }\n\n const promises: Promise<void>[] = [];\n for (const change of changes) {\n const p = this.send(change);\n if (p !== promiseVoid) {\n promises.push(p);\n }\n }\n if (promises.length === 0) {\n return promiseVoid;\n }\n if (promises.length === 1) {\n return promises[0];\n }\n return Promise.all(promises).then(() => {});\n }\n\n #initialized = false;\n\n /**\n * Called once the subscriber's watermark has been validated in the initial\n * catchup process.\n */\n #initialize() {\n if (!this.#initialized) {\n this.#initialized = true;\n // The initial status precedes the catchup, so it bypasses the backlog.\n void this.#sendDownstream(['status', {tag: 'status'}]);\n }\n }\n\n /**\n * Sends a status message (e.g. a lag report) downstream. While the\n * subscriber is catching up, the status is queued in the backlog behind\n * the changes that preceded it in the replication stream, so that the\n * subscriber processes it in stream order. This is necessary for lag\n * reports to measure the lag of the subscriber, including its catchup.\n *\n * Status messages received before the subscriber is initialized are\n * dropped.\n */\n sendStatus(status: Status) {\n if (!this.#initialized) {\n return;\n }\n const downstream: Downstream = ['status', status];\n if (this.#backlog) {\n this.#pushBacklog({status: BigIntJSON.stringify(downstream)});\n return;\n }\n void this.#sendDownstream(downstream);\n }\n\n /**\n * Sends a control status (e.g. `draining` or `restore`) downstream\n * immediately, regardless of whether the subscriber is initialized or\n * catching up. Unlike {@link sendStatus}, such statuses are not tied to a\n * position in the replication stream.\n */\n sendControlStatus(status: Status) {\n void this.#sendDownstream(['status', status]);\n }\n\n /** catchup() is called on ChangeEntries loaded from the store. */\n async catchup(change: WatermarkedChange) {\n this.#initialize();\n await this.#sendChange(change);\n }\n\n /**\n * Marks the Subscribe as \"caught up\" and flushes any backlog of\n * entries that were received during the catchup.\n */\n setCaughtUp(): Promise<void> {\n this.#initialize();\n if (!this.#backlog) {\n return this.#backlogDrain ?? promiseVoid;\n }\n if (!this.#backlogDrain) {\n // Keep #backlog non-null while queued entries are being handed to\n // downstream. That preserves ordering for sends that race with\n // setCaughtUp(): they append to the same backlog instead of bypassing\n // older buffered changes.\n this.#backlogDrain = this.#drainBacklog();\n void this.#backlogDrain.catch(e => this.fail(e));\n }\n return this.#backlogDrain;\n }\n\n async #sendChange(change: WatermarkedChange) {\n const [watermark, tag, json] = change;\n if (watermark <= this.watermark) {\n return;\n }\n if (!this.supportsMessage(tag)) {\n return;\n }\n if (tag === 'commit') {\n this.#watermark = watermark;\n }\n this.#trackBackfills(change);\n const result = await this.#sendStringifiedDownstream(json);\n if (tag === 'commit' && result === 'consumed') {\n this.#advanceAck(watermark);\n }\n }\n\n #advanceAck(watermark: string) {\n // Sends can complete out of order (e.g. the bounded window in\n // #drainBacklog), so the ack only advances monotonically, and listeners\n // are only notified when it does.\n const acked = max(this.#acked, watermark);\n if (acked !== this.#acked) {\n this.#acked = acked;\n this.#onAck?.(acked);\n this.#checkCaughtUp();\n }\n }\n\n #checkCaughtUp() {\n if (\n this.#caughtUpWatermark !== undefined &&\n this.#acked >= this.#caughtUpWatermark\n ) {\n this.#caughtUpWatermark = undefined;\n this.#caughtUp.resolve();\n }\n }\n\n #sendDownstream(downstream: Downstream) {\n return this.#sendStringifiedDownstream(BigIntJSON.stringify(downstream));\n }\n\n async #sendStringifiedDownstream(json: string) {\n const size = json.length;\n this.#pending++;\n this.#pendingBytes += size;\n const {result} = this.#downstream.push(json);\n try {\n return await result;\n } finally {\n this.#pending--;\n this.#pendingBytes -= size;\n this.#processed++;\n }\n }\n\n async #sendPreSerializedDownstream(\n batch: PreSerializedBatch,\n commitWatermark?: string | undefined,\n ): Promise<void> {\n const size = batch.byteLength;\n this.#pending += batch.changes.length;\n this.#pendingBytes += size;\n const {result} = this.#downstream.push(batch);\n try {\n const outcome = await result;\n if (commitWatermark && outcome === 'consumed') {\n this.#advanceAck(commitWatermark);\n }\n } finally {\n this.#pending -= batch.changes.length;\n this.#pendingBytes -= size;\n this.#processed += batch.changes.length;\n }\n }\n\n // `pending` and `processed` stats are tracked by periodically sampling\n // the running totals (by the progress tracker in the Forwarder).\n // This information was originally collected for use in flow control\n // decisions. The final flow control algorithm ended up being simpler\n // than expected and does not actually use this information. However, the\n // stats are still tracked and logged during flow control decisions for\n // debugging, forensics, and potential improvements to the algorithm.\n\n #pending = 0;\n #pendingBytes = 0;\n #processed = 0;\n #samples: {processed: number; timestamp: number}[] = [\n {processed: 0, timestamp: performance.now()},\n ];\n\n /**\n * The number of downstream messages that have yet to be acked.\n */\n get numPending() {\n return this.#pending + this.#backlogCount;\n }\n\n /**\n * The total number of downstream messages that the subscriber has\n * processed (i.e. acked).\n */\n get numProcessed() {\n return this.#processed;\n }\n\n /**\n * Records a new history entry for the number of messages processed,\n * keeping the number of samples bounded to `maxSamples`.\n */\n sampleProcessRate(now: number, maxSamples = 10): this {\n while (this.#samples.length >= maxSamples) {\n this.#samples.shift();\n }\n this.#samples.push({processed: this.#processed, timestamp: now});\n return this;\n }\n\n getStats(): SubscriberStats {\n const pending = this.numPending;\n if (this.#samples.length < 2) {\n return {\n processRate: 0,\n pending,\n backlog: this.#backlogCount,\n backlogBytes: this.#bufferedBacklogBytes,\n totalBufferedBytes: this.#totalBufferedBytes,\n missedLastTimeout: this.#missedLastTimeout,\n };\n }\n const from = this.#samples[0];\n const to = must(this.#samples.at(-1));\n const processed = to.processed - from.processed;\n const seconds = (to.timestamp - from.timestamp) / 1000;\n const processRate = seconds === 0 ? 0 : processed / seconds;\n return {\n processRate,\n pending,\n backlog: this.#backlogCount,\n backlogBytes: this.#bufferedBacklogBytes,\n totalBufferedBytes: this.#totalBufferedBytes,\n missedLastTimeout: this.#missedLastTimeout,\n };\n }\n\n #missedLastTimeout = false;\n #laggingSinceMs: number | undefined;\n\n trackResponseResult(result: 'on-time' | 'timed-out') {\n this.#missedLastTimeout = result === 'timed-out';\n if (result === 'on-time') {\n this.#laggingSinceMs = undefined;\n }\n }\n\n /**\n * Reports the change rate of a slow subscriber (i.e. that missed the last\n * timeout) compared to the change rate of the (slowest) subscriber that\n * responded on time.\n *\n * * `lagging` indicates that this subscriber is slower\n * * `catching-up` indicates that it is faster\n *\n * Returns the total duration in which subscriber has been continuously\n * reported as `lagging`.\n */\n reportChangeRate(now: number, status: 'lagging' | 'catching-up') {\n assert(\n this.#missedLastTimeout,\n `reportChangeRate should only be called for slow subscribers`,\n );\n if (status === 'catching-up') {\n this.#laggingSinceMs = undefined;\n return 0;\n }\n this.#laggingSinceMs ??= now;\n return now - this.#laggingSinceMs;\n }\n\n supportsMessage(tag: ChangeTag) {\n switch (tag) {\n case 'update-table-metadata':\n // update-table-row-key is only understood by subscribers >= protocol v5\n return this.#protocolVersion >= 5;\n }\n return true;\n }\n\n /**\n * Ends the subscription without sending a downstream `['error', ...]`.\n *\n * This is deliberate, and not the same as reporting the failure to the\n * subscriber: `IncrementalSyncer` treats any `['error', ...]` as terminal and\n * shuts down to restore a fresh replica from litestream, whereas a clean end\n * backs off and re-subscribes. The failures routed here -- storer catchup\n * errors, backlog drain errors, backup-monitor errors -- are transient, so a\n * reconnect is the proportionate response and a fleet-wide restore is not.\n *\n * Callers are responsible for logging `err`; it is not carried downstream.\n */\n fail(_err?: unknown) {\n this.close();\n }\n\n close(\n error?: ErrorType,\n message?: string,\n details?: {replicaVersion?: string | undefined},\n ) {\n // Closing the subscriber must also release producers that are blocked on\n // backlog capacity; there is no future drain that could wake them.\n this.#backlog = null;\n this.#backlogBytes = 0;\n this.#backlogBackpressure.releaseAll();\n // The backlog can no longer grow, so nothing would ever resolve these.\n // Waiters re-check backlogFull, which is now false, and see the close.\n this.#resolveBacklogFullWaiters();\n\n if (error !== undefined) {\n // Wait for the ACK of the error message before closing the connection.\n void this.#sendDownstream([\n 'error',\n {type: error, message, ...details},\n ]).finally(() => this.#downstream.cancel());\n } else {\n this.#downstream.cancel();\n }\n }\n\n get #backlogCount() {\n return this.#backlog?.size ?? 0;\n }\n\n get #bufferedBacklogBytes() {\n // Include entries already handed to downstream but not yet consumed. Without\n // this, setCaughtUp() could move bytes out of #backlog faster than the\n // downstream Subscription can process them and release producers too early.\n return this.#backlogBytes + this.#backlogInFlightBytes;\n }\n\n get #totalBufferedBytes() {\n return this.#bufferedBacklogBytes + this.#pendingBytes;\n }\n\n #pushBacklog(entry: BacklogEntry) {\n assert(this.#backlog, 'cannot push to backlog after catchup completed');\n this.#backlog.push(entry);\n this.#backlogBytes += entryBytes(entry);\n if (this.backlogFull) {\n this.#resolveBacklogFullWaiters();\n }\n }\n\n #resolveBacklogFullWaiters() {\n const waiters = [...this.#backlogFullWaiters];\n this.#backlogFullWaiters.clear();\n for (const waiter of waiters) {\n waiter.resolve();\n }\n }\n\n #maybeWaitForBacklogSpace(): Promise<void> {\n return this.#backlogBackpressure.waitForSpace(this.#bufferedBacklogBytes);\n }\n\n async #drainBacklog() {\n const inFlight: {promise: Promise<void>; bytes: number}[] = [];\n let inFlightBytes = 0;\n\n try {\n for (;;) {\n const entry = this.#backlog?.shift();\n if (!entry) {\n const closed = this.#backlog === null;\n this.#backlog = null;\n this.#backlogBytes = 0;\n this.#backlogBackpressure.releaseIfUnderLowWater(\n this.#bufferedBacklogBytes,\n );\n if (!closed && !this.#aligned) {\n // All changes up to the head have been handed to #sendChange()\n // (and thus tracked), and subsequent changes are sent directly.\n this.#aligned = true;\n this.#onAligned?.(this);\n this.#caughtUpWatermark = this.#watermark;\n this.#checkCaughtUp();\n void this.#lagReportingDisabled?.then(disabled => {\n if (disabled) {\n this.sendStatus(LAG_REPORTING_DISABLED);\n }\n });\n }\n break;\n }\n\n const bytes = entryBytes(entry);\n this.#backlogBytes -= bytes;\n this.#backlogInFlightBytes += bytes;\n this.#backlogBackpressure.releaseIfUnderLowWater(\n this.#bufferedBacklogBytes,\n );\n\n // Send backlog entries in order, but keep only a bounded byte window in\n // flight. This avoids replacing one unbounded buffer with another inside\n // the downstream Subscription during catchup completion.\n const send = isQueuedStatus(entry)\n ? this.#sendStringifiedDownstream(entry.status).then(() => {})\n : this.#sendChange(entry);\n const promise = send.finally(() => {\n this.#backlogInFlightBytes -= bytes;\n this.#backlogBackpressure.releaseIfUnderLowWater(\n this.#bufferedBacklogBytes,\n );\n });\n inFlight.push({promise, bytes});\n inFlightBytes += bytes;\n\n while (inFlightBytes >= this.#backlogBackpressure.highWaterBytes) {\n const next = must(inFlight.shift());\n await next.promise;\n inFlightBytes -= next.bytes;\n }\n }\n\n for (const {promise} of inFlight) {\n await promise;\n }\n } finally {\n this.#backlogDrain = null;\n this.#backlogBackpressure.releaseIfUnderLowWater(\n this.#bufferedBacklogBytes,\n );\n }\n }\n}\n\nclass ByteBackpressureGate {\n readonly highWaterBytes: number;\n readonly #lowWaterBytes: number;\n readonly #waiters: Resolver<void>[] = [];\n\n constructor(highWaterBytes: number, lowWaterRatio: number) {\n this.highWaterBytes = Math.max(1, highWaterBytes);\n this.#lowWaterBytes =\n this.highWaterBytes * Math.min(1, Math.max(0, lowWaterRatio));\n }\n\n waitForSpace(bufferedBytes: number): Promise<void> {\n if (bufferedBytes < this.highWaterBytes) {\n return promiseVoid;\n }\n\n // One waiter represents one send() call that has already appended its\n // change. The producer is released when the backlog falls back below the low\n // water mark or the subscriber closes.\n const r = resolver<void>();\n this.#waiters.push(r);\n return r.promise;\n }\n\n releaseIfUnderLowWater(bufferedBytes: number) {\n if (this.#waiters.length === 0 || bufferedBytes > this.#lowWaterBytes) {\n return;\n }\n\n // Use a low water mark so waiting producers are released in batches instead\n // of waking one at a time around the high water boundary.\n this.releaseAll();\n }\n\n releaseAll() {\n const waiters = this.#waiters.splice(0);\n for (const waiter of waiters) {\n waiter.resolve();\n }\n }\n}\n\n/**\n * Sent to an aligned subscriber when lag reporting is disabled upstream,\n * signaling that the subscriber is caught up. This is a lag report with a\n * `nextSendTimeMs` of 0 and no `lastTimings`, so that no lag is measured\n * (see `isLagReportingDisabledSignal()` in the replicator's recorder).\n */\nexport const LAG_REPORTING_DISABLED: Status = {\n tag: 'status',\n lagReport: {nextSendTimeMs: 0},\n};\n"],"mappings":"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"}
@@ -25,7 +25,25 @@ type Opts = {
25
25
  export declare class UpstreamAcker {
26
26
  #private;
27
27
  constructor({ trackPgChangeLog, trackBackup }: Opts);
28
- reset(upstream: Sink<ChangeSourceUpstream>): void;
28
+ /**
29
+ * Starts tracking a new upstream connection, which resumes the change stream
30
+ * after `resumeWatermark`.
31
+ *
32
+ * Everything at or before `resumeWatermark` was committed on an earlier
33
+ * connection, so it counts as committed on this one: a status watermark past
34
+ * it waits for the tracked stores to reach it, as it would for a commit on
35
+ * this connection. Otherwise the first keepalive of a stream that resumes
36
+ * ahead of the stores -- a change log ahead of its backup, which is the
37
+ * normal state -- would move the replication slot past transactions that the
38
+ * backup has not persisted, and a task restored from the backup would then
39
+ * resume below the slot, which the upstream moves forward without a word.
40
+ *
41
+ * When the PG change log is tracked, the stream resumes from its head, so
42
+ * `resumeWatermark` has been persisted in it (by this or another
43
+ * change-streamer). Without this, status messages would not be acked on an
44
+ * idle upstream until a commit is stored.
45
+ */
46
+ reset(upstream: Sink<ChangeSourceUpstream>, resumeWatermark: string): void;
29
47
  trackDownstream(downstream: ChangeStreamMessage): void;
30
48
  trackPgChangeLog(committedWatermark: string): void;
31
49
  trackBackup(backedUpWatermark: string): void;
@@ -1 +1 @@
1
- {"version":3,"file":"upstream-acker.d.ts","sourceRoot":"","sources":["../../../../../../zero-cache/src/services/change-streamer/upstream-acker.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAC,IAAI,EAAC,MAAM,wBAAwB,CAAC;AACjD,OAAO,KAAK,EACV,oBAAoB,EACpB,mBAAmB,EACpB,MAAM,sCAAsC,CAAC;AAE9C,KAAK,IAAI,GAAG;IACV,gBAAgB,EAAE,OAAO,CAAC;IAC1B,WAAW,EAAE,OAAO,CAAC;CACtB,CAAC;AAEF;;;;;;;;;;;;;;;;;GAiBG;AACH,qBAAa,aAAa;;IAYxB,YAAY,EAAC,gBAAgB,EAAE,WAAW,EAAC,EAAE,IAAI,EAOhD;IAED,KAAK,CAAC,QAAQ,EAAE,IAAI,CAAC,oBAAoB,CAAC,QAKzC;IAED,eAAe,CAAC,UAAU,EAAE,mBAAmB,QAc9C;IAED,gBAAgB,CAAC,kBAAkB,EAAE,MAAM,QAO1C;IAED,WAAW,CAAC,iBAAiB,EAAE,MAAM,QAIpC;CA2BF"}
1
+ {"version":3,"file":"upstream-acker.d.ts","sourceRoot":"","sources":["../../../../../../zero-cache/src/services/change-streamer/upstream-acker.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAC,IAAI,EAAC,MAAM,wBAAwB,CAAC;AACjD,OAAO,KAAK,EACV,oBAAoB,EACpB,mBAAmB,EACpB,MAAM,sCAAsC,CAAC;AAE9C,KAAK,IAAI,GAAG;IACV,gBAAgB,EAAE,OAAO,CAAC;IAC1B,WAAW,EAAE,OAAO,CAAC;CACtB,CAAC;AAEF;;;;;;;;;;;;;;;;;GAiBG;AACH,qBAAa,aAAa;;IAYxB,YAAY,EAAC,gBAAgB,EAAE,WAAW,EAAC,EAAE,IAAI,EAOhD;IAED;;;;;;;;;;;;;;;;;OAiBG;IACH,KAAK,CAAC,QAAQ,EAAE,IAAI,CAAC,oBAAoB,CAAC,EAAE,eAAe,EAAE,MAAM,QAalE;IAED,eAAe,CAAC,UAAU,EAAE,mBAAmB,QAe9C;IAED,gBAAgB,CAAC,kBAAkB,EAAE,MAAM,QAO1C;IAED,WAAW,CAAC,iBAAiB,EAAE,MAAM,QAIpC;CA2BF"}
@@ -33,11 +33,31 @@ var UpstreamAcker = class {
33
33
  this.#trackPgChangeLog = trackPgChangeLog;
34
34
  this.#trackBackup = trackBackup;
35
35
  }
36
- reset(upstream) {
36
+ /**
37
+ * Starts tracking a new upstream connection, which resumes the change stream
38
+ * after `resumeWatermark`.
39
+ *
40
+ * Everything at or before `resumeWatermark` was committed on an earlier
41
+ * connection, so it counts as committed on this one: a status watermark past
42
+ * it waits for the tracked stores to reach it, as it would for a commit on
43
+ * this connection. Otherwise the first keepalive of a stream that resumes
44
+ * ahead of the stores -- a change log ahead of its backup, which is the
45
+ * normal state -- would move the replication slot past transactions that the
46
+ * backup has not persisted, and a task restored from the backup would then
47
+ * resume below the slot, which the upstream moves forward without a word.
48
+ *
49
+ * When the PG change log is tracked, the stream resumes from its head, so
50
+ * `resumeWatermark` has been persisted in it (by this or another
51
+ * change-streamer). Without this, status messages would not be acked on an
52
+ * idle upstream until a commit is stored.
53
+ */
54
+ reset(upstream, resumeWatermark) {
37
55
  this.#upstream = upstream;
38
- this.#lastTx = "";
56
+ this.#lastTx = resumeWatermark;
39
57
  this.#lastStatus = "";
40
58
  this.#lastAck = "";
59
+ if (this.#trackPgChangeLog) this.#pgChangeLogWatermark = max(resumeWatermark, this.#pgChangeLogWatermark);
60
+ this.#maybeAck();
41
61
  }
42
62
  trackDownstream(downstream) {
43
63
  const [tag, msg] = downstream;
@@ -47,7 +67,7 @@ var UpstreamAcker = class {
47
67
  this.#maybeAck();
48
68
  break;
49
69
  case "commit":
50
- this.#lastTx = downstream[2].watermark;
70
+ this.#lastTx = max(this.#lastTx, downstream[2].watermark);
51
71
  this.#maybeAck();
52
72
  break;
53
73
  }