@tearleads/client-sdk 0.1.81 → 0.1.84

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 (160) hide show
  1. package/client/organizations/organizationReadModels.js +4 -2
  2. package/client/organizations/organizationReadModels.js.map +1 -1
  3. package/data/documents/documentSync.js.map +1 -1
  4. package/data/documents/shared/crypto.js.map +1 -1
  5. package/data/documents/shared/types.d.ts +1 -1
  6. package/data/documents/shared/types.js.map +1 -1
  7. package/data/persistence/container-contents/containerContentsPersistence.js +2 -2
  8. package/data/persistence/container-contents/containerContentsPersistence.js.map +1 -1
  9. package/data/persistence/container-contents/containerContentsPersistenceTypes.d.ts +1 -1
  10. package/data/persistence/container-contents/containerContentsPersistenceTypes.js.map +1 -1
  11. package/data/persistence/container-contents/containerDeletionPersistence.js +1 -1
  12. package/data/persistence/container-contents/containerDeletionPersistence.js.map +1 -1
  13. package/data/persistence/container-contents/containerMetadataMutationPersistence.js +3 -3
  14. package/data/persistence/container-contents/containerMetadataMutationPersistence.js.map +1 -1
  15. package/data/persistence/container-contents/containerMetadataPullContinuationPersistence.js +1 -1
  16. package/data/persistence/container-contents/containerMetadataPullContinuationPersistence.js.map +1 -1
  17. package/data/persistence/container-contents/containerMetadataRows.js +1 -1
  18. package/data/persistence/container-contents/containerMetadataRows.js.map +1 -1
  19. package/data/persistence/container-contents/containerPendingUpdatePersistence.js +2 -2
  20. package/data/persistence/container-contents/containerPendingUpdatePersistence.js.map +1 -1
  21. package/data/persistence/container-contents/containerReconcilePersistence.js +1 -1
  22. package/data/persistence/container-contents/containerReconcilePersistence.js.map +1 -1
  23. package/data/persistence/container-contents/containerRemovalWork.js +1 -1
  24. package/data/persistence/container-contents/containerRemovalWork.js.map +1 -1
  25. package/data/persistence/documents/documentDiscoveryReset.d.ts +6 -0
  26. package/data/persistence/documents/documentsPersistence.js +2 -2
  27. package/data/persistence/documents/documentsPersistence.js.map +1 -1
  28. package/data/persistence/documents/internal/createDocumentWithHistoryCheckpoint.js +1 -1
  29. package/data/persistence/documents/internal/createDocumentWithHistoryCheckpoint.js.map +1 -1
  30. package/data/persistence/documents/internal/discardDocument.js +2 -2
  31. package/data/persistence/documents/internal/discardDocument.js.map +1 -1
  32. package/data/persistence/documents/internal/documentDeletionPersistence.js +2 -2
  33. package/data/persistence/documents/internal/documentDeletionPersistence.js.map +1 -1
  34. package/data/persistence/documents/internal/documentMutationPersistence.js +3 -3
  35. package/data/persistence/documents/internal/documentMutationPersistence.js.map +1 -1
  36. package/data/persistence/documents/internal/documentPullContinuationPersistence.js +1 -1
  37. package/data/persistence/documents/internal/documentPullContinuationPersistence.js.map +1 -1
  38. package/data/persistence/documents/internal/documentRecordIdentity.js.map +1 -1
  39. package/data/persistence/documents/internal/documentRows.js.map +1 -1
  40. package/data/persistence/documents/internal/ensureDocumentsSchema.js +1 -1
  41. package/data/persistence/documents/internal/ensureDocumentsSchema.js.map +1 -1
  42. package/data/persistence/documents/internal/orphanSideRows.js +1 -1
  43. package/data/persistence/documents/internal/orphanSideRows.js.map +1 -1
  44. package/data/persistence/documents/internal/rowQueryPersistence.js +1 -1
  45. package/data/persistence/documents/internal/rowQueryPersistence.js.map +1 -1
  46. package/data/persistence/documents/internal/syncQueuePersistence.js +2 -2
  47. package/data/persistence/documents/internal/syncQueuePersistence.js.map +1 -1
  48. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentHistoryPersistence.d.ts +1 -1
  49. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentHistoryPersistence.js +5 -5
  50. package/data/persistence/documents/records/documentHistoryPersistence.js.map +1 -0
  51. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentPendingUpdatePersistence.d.ts +2 -2
  52. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentPendingUpdatePersistence.js +2 -2
  53. package/data/persistence/documents/records/documentPendingUpdatePersistence.js.map +1 -0
  54. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentPersistenceTypes.d.ts +2 -2
  55. package/data/persistence/documents/records/documentPersistenceTypes.js.map +1 -0
  56. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentRecordPersistence.d.ts +1 -1
  57. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentRecordPersistence.js +4 -4
  58. package/data/persistence/documents/records/documentRecordPersistence.js.map +1 -0
  59. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentSyncFailurePersistence.d.ts +2 -2
  60. package/data/{sqlite/documentPersistence → persistence/documents/records}/documentSyncFailurePersistence.js +3 -3
  61. package/data/persistence/documents/records/documentSyncFailurePersistence.js.map +1 -0
  62. package/data/{sqlite/documentPersistence → persistence/documents/records}/index.d.ts +2 -2
  63. package/data/{sqlite/documentPersistence → persistence/documents/records}/index.js +4 -4
  64. package/data/persistence/documents/records/index.js.map +1 -0
  65. package/data/persistence/documents/types.d.ts +2 -2
  66. package/data/persistence/documents/types.js.map +1 -1
  67. package/{workflows/sync/remoteResetPrincipalScope.d.ts → data/persistence/principalPolicy/principalPolicyRemoteReset.d.ts} +1 -1
  68. package/{workflows/sync/remoteResetPrincipalScope.js → data/persistence/principalPolicy/principalPolicyRemoteReset.js} +7 -7
  69. package/data/persistence/principalPolicy/principalPolicyRemoteReset.js.map +1 -0
  70. package/data/persistence/verifiedManifestBundlePersistence.d.ts +2 -0
  71. package/data/persistence/verifiedManifestBundlePersistence.js +7 -0
  72. package/data/persistence/verifiedManifestBundlePersistence.js.map +1 -1
  73. package/data/sqlite/{documentPersistence/documentOrphanBlobReclaims.js → schema/documentOrphanBlobReclaimSchema.js} +1 -1
  74. package/data/sqlite/schema/documentOrphanBlobReclaimSchema.js.map +1 -0
  75. package/data/sqlite/schema/index.js +1 -1
  76. package/data/sqlite/schema/index.js.map +1 -1
  77. package/data/sqlite/sqliteBindBudget.js +12 -0
  78. package/data/sqlite/sqliteBindBudget.js.map +1 -1
  79. package/package.json +1 -1
  80. package/workflows/container-contents/container-state/create/createIntentSeed.js.map +1 -1
  81. package/workflows/container-contents/container-state/create/createWithMetadataPlan.js.map +1 -1
  82. package/workflows/container-contents/container-state/types.js.map +1 -1
  83. package/workflows/container-contents/metadata/index.js.map +1 -1
  84. package/workflows/container-contents/metadata/metadataEvents.d.ts +1 -1
  85. package/workflows/container-contents/metadata/metadataEvents.js.map +1 -1
  86. package/workflows/container-contents/metadata/metadataIncomingUpdateIsolation.js +1 -1
  87. package/workflows/container-contents/metadata/metadataIncomingUpdateIsolation.js.map +1 -1
  88. package/workflows/container-contents/metadata/metadataRemoteSync.d.ts +1 -1
  89. package/workflows/container-contents/metadata/metadataRemoteSync.js.map +1 -1
  90. package/workflows/container-contents/pendingWrites/index.js +1 -1
  91. package/workflows/container-contents/pendingWrites/index.js.map +1 -1
  92. package/{client/organizations/organizationAccessRestoration.js → workflows/container-contents/recovery/accessRestoration.js} +16 -12
  93. package/workflows/container-contents/recovery/accessRestoration.js.map +1 -0
  94. package/workflows/container-contents/remoteReset/containerRemoteReset.d.ts +185 -0
  95. package/workflows/container-contents/remoteReset/containerRemoteReset.js +174 -0
  96. package/workflows/container-contents/remoteReset/containerRemoteReset.js.map +1 -0
  97. package/workflows/container-contents/remoteReset/remoteResetCursorScope.d.ts +14 -0
  98. package/workflows/{sync → container-contents/remoteReset}/remoteResetCursorScope.js +2 -2
  99. package/workflows/container-contents/remoteReset/remoteResetCursorScope.js.map +1 -0
  100. package/workflows/documents/create/documentCreationPersistence.js.map +1 -1
  101. package/workflows/documents/create/index.d.ts +1 -1
  102. package/workflows/documents/create/index.js.map +1 -1
  103. package/workflows/documents/documentMutationCommit.d.ts +1 -1
  104. package/workflows/documents/documentMutationCommit.js.map +1 -1
  105. package/workflows/documents/index.d.ts +2 -2
  106. package/workflows/documents/index.js +2 -2
  107. package/workflows/documents/index.js.map +1 -1
  108. package/workflows/documents/remoteReset/documentRemoteReset.d.ts +56 -0
  109. package/workflows/documents/remoteReset/documentRemoteReset.js +135 -0
  110. package/workflows/documents/remoteReset/documentRemoteReset.js.map +1 -0
  111. package/workflows/{sync → documents/remoteReset}/remoteResetAttachments.js +3 -3
  112. package/workflows/documents/remoteReset/remoteResetAttachments.js.map +1 -0
  113. package/workflows/{sync → documents/remoteReset}/remoteResetPlans.d.ts +1 -1
  114. package/workflows/{sync → documents/remoteReset}/remoteResetPlans.js +7 -7
  115. package/workflows/documents/remoteReset/remoteResetPlans.js.map +1 -0
  116. package/workflows/documents/sync/index.js.map +1 -1
  117. package/workflows/documents/sync/initialSync.d.ts +1 -1
  118. package/workflows/documents/sync/initialSync.js.map +1 -1
  119. package/workflows/documents/sync/readOnlySync.d.ts +1 -1
  120. package/workflows/documents/sync/readOnlySync.js.map +1 -1
  121. package/workflows/documents/sync/syncAttemptPlanning.js.map +1 -1
  122. package/workflows/documents/sync/syncAttemptState.d.ts +1 -1
  123. package/workflows/documents/sync/syncAttemptState.js.map +1 -1
  124. package/workflows/documents/sync/syncResponseResult.js.map +1 -1
  125. package/workflows/documents/sync/syncSubmittedResult.js.map +1 -1
  126. package/workflows/documents/syncFailures/index.js.map +1 -1
  127. package/workflows/documents/syncPlan/syncContentKeys.d.ts +1 -1
  128. package/workflows/documents/syncPlan/syncContentKeys.js.map +1 -1
  129. package/workflows/documents/syncPlan/syncPlanMaterial.js.map +1 -1
  130. package/workflows/documents/syncPlan/syncPlanRequestBounds.js.map +1 -1
  131. package/workflows/documents/syncRekeys/syncContainerRekeys.js.map +1 -1
  132. package/workflows/documents/syncRekeys/syncRecoveryRekey.d.ts +1 -1
  133. package/workflows/documents/syncRekeys/syncRecoveryRekey.js +1 -1
  134. package/workflows/documents/syncRekeys/syncRecoveryRekey.js.map +1 -1
  135. package/workflows/organizations/readModel/listLocalOrganizations.js +1 -1
  136. package/workflows/organizations/readModel/listLocalOrganizations.js.map +1 -1
  137. package/workflows/organizations/readModel/organizationRemoteReset.js +25 -0
  138. package/workflows/organizations/readModel/organizationRemoteReset.js.map +1 -0
  139. package/workflows/registration/persistRegistrationBootstrap.d.ts +1 -1
  140. package/workflows/registration/persistRegistrationBootstrap.js.map +1 -1
  141. package/workflows/sync/remoteReset.js +60 -229
  142. package/workflows/sync/remoteReset.js.map +1 -1
  143. package/workflows/sync/remoteResetScope.d.ts +7 -10
  144. package/workflows/sync/remoteResetScope.js +26 -108
  145. package/workflows/sync/remoteResetScope.js.map +1 -1
  146. package/client/organizations/organizationAccessRestoration.js.map +0 -1
  147. package/data/sqlite/documentPersistence/documentHistoryPersistence.js.map +0 -1
  148. package/data/sqlite/documentPersistence/documentOrphanBlobReclaims.js.map +0 -1
  149. package/data/sqlite/documentPersistence/documentPendingUpdatePersistence.js.map +0 -1
  150. package/data/sqlite/documentPersistence/documentPersistenceTypes.js.map +0 -1
  151. package/data/sqlite/documentPersistence/documentRecordPersistence.js.map +0 -1
  152. package/data/sqlite/documentPersistence/documentSyncFailurePersistence.js.map +0 -1
  153. package/data/sqlite/documentPersistence/index.js.map +0 -1
  154. package/workflows/sync/remoteResetAttachments.js.map +0 -1
  155. package/workflows/sync/remoteResetBatches.js +0 -13
  156. package/workflows/sync/remoteResetBatches.js.map +0 -1
  157. package/workflows/sync/remoteResetCursorScope.js.map +0 -1
  158. package/workflows/sync/remoteResetPlans.js.map +0 -1
  159. package/workflows/sync/remoteResetPrincipalScope.js.map +0 -1
  160. /package/data/{sqlite/documentPersistence → persistence/documents/records}/documentPersistenceTypes.js +0 -0
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,MAAM,mBAAmB,CAAC;AAE5D,OAAO,EAAE,4BAA4B,EAAE,MAAM,sCAAsC,CAAC;AACpF,OAAO,EAAE,kCAAkC,EAAE,MAAM,iEAAiE,CAAC;AACrH,OAAO,EAEL,wCAAwC,GACzC,MAAM,oDAAoD,CAAC;AAK5D,OAAO,EACL,sCAAsC,EAEtC,gCAAgC,GACjC,MAAM,4CAA4C,CAAC;AAEpD,OAAO,EAAE,2CAA2C,EAAE,MAAM,UAAU,CAAC;AACvE,OAAO,EACL,6BAA6B,EAC7B,kCAAkC,EAClC,kCAAkC,GACnC,MAAM,iBAAiB,CAAC;AACzB,OAAO,EACL,8BAA8B,EAC9B,kBAAkB,GACnB,MAAM,6BAA6B,CAAC;AACrC,OAAO,EAAE,yBAAyB,EAAE,MAAM,mCAAmC,CAAC;AAC9E,OAAO,EAAE,gCAAgC,EAAE,MAAM,6CAA6C,CAAC;AAC/F,OAAO,EAEL,gCAAgC,GACjC,MAAM,gBAAgB,CAAC;AACxB,OAAO,EACL,uBAAuB,EACvB,wBAAwB,GACzB,MAAM,uBAAuB,CAAC;AAK/B,OAAO,EAAE,kCAAkC,EAAE,MAAM,uBAAuB,CAAC;AAE3E,MAAM,UAAU,sBAAsB,CACpC,MAA8B,EAC9B,UAAqC;IAErC,IAAI,CAAC,UAAU;QAAE,OAAO,KAAK,CAAC;IAC9B,OAAO,MAAM,CAAC,IAAI,CAChB,CAAC,KAAK,EAAE,EAAE,CACR,4BAA4B,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,UAAU,KAAK,UAAU,CACzE,CAAC;AACJ,CAAC;AACD;;;GAGG;AACH,SAAS,4BAA4B,CAAC,KAA8B;IAClE,KAAK,CAAC,SAAS,CAAC,6BAA6B,EAAE,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC;AACpE,CAAC;AAED;;;;;;GAMG;AACH,SAAS,8BAA8B,CAAC,KAKvC;IACC,OAAO,CACL,CAAC,KAAK,CAAC,2BAA2B;QAClC,CAAC,KAAK,CAAC,gBAAgB,CAAC,2BAA2B;QACnD,KAAK,CAAC,IAAI,CAAC,qBAAqB,KAAK,SAAS;QAC9C,KAAK,CAAC,cAAc,CAAC,IAAI,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC,mBAAmB,IAAI,IAAI,CAAC,CAC1E,CAAC;AACJ,CAAC;AAED,KAAK,UAAU,wBAAwB,CAAC,IASvC;IACC,IAAI,CAAC;QACH,OAAO,MAAM,kCAAkC,CAAC;YAC9C,SAAS,EAAE,IAAI,CAAC,IAAI,CAAC,SAAS;YAC9B,OAAO,EAAE,IAAI,CAAC,OAAO;YACrB,8BAA8B,EAAE,8BAA8B,CAAC;gBAC7D,gBAAgB,EAAE,IAAI,CAAC,gBAAgB;gBACvC,cAAc,EAAE,IAAI,CAAC,cAAc;gBACnC,2BAA2B,EAAE,IAAI,CAAC,2BAA2B;gBAC7D,IAAI,EAAE,IAAI,CAAC,IAAI;aAChB,CAAC;YACF,UAAU,EAAE,IAAI,CAAC,IAAI,CAAC,UAAU;YAChC,qBAAqB,EAAE,IAAI,CAAC,gBAAgB,EAAE,aAAa;YAC3D,mBAAmB,EAAE,IAAI,CAAC,IAAI,CAAC,mBAAmB;YAClD,WAAW,EAAE,IAAI,CAAC,WAAW;YAC7B,qBAAqB,EAAE,GAAG,EAAE,CAAC,gCAAgC,CAAC,IAAI,CAAC,IAAI,CAAC;YACxE,uBAAuB,EAAE,IAAI,CAAC,IAAI,CAAC,uBAAuB;YAC1D,6BAA6B,EAAE,IAAI,CAAC,IAAI,CAAC,6BAA6B;YACtE,WAAW,EAAE,IAAI,CAAC,IAAI,CAAC,WAAW;YAClC,uBAAuB,EAAE,IAAI,CAAC,IAAI,CAAC,uBAAuB;YAC1D,cAAc,EAAE,IAAI,CAAC,cAAc;YACnC,IAAI,EAAE,IAAI,CAAC,gBAAgB,CAAC,IAAI;YAChC,yBAAyB,EAAE,IAAI,CAAC,yBAAyB;YACzD,YAAY,EAAE,IAAI,CAAC,IAAI,CAAC,YAAY;YACpC,+BAA+B,EAC7B,IAAI,CAAC,IAAI,CAAC,+BAA+B;SAC5C,CAAC,CAAC;IACL,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IACE,KAAK,YAAY,wCAAwC;YACzD,IAAI,CAAC,gBAAgB,KAAK,SAAS;YACnC,IAAI,CAAC,IAAI,CAAC,WAAW,KAAK,KAAK,EAC/B,CAAC;YACD,OAAO,OAAgB,CAAC;QAC1B,CAAC;QACD,MAAM,KAAK,CAAC;IACd,CAAC;AACH,CAAC;AAED,SAAS,wBAAwB,CAC/B,KAA8B,EAC9B,yBAAkC,EAClC,wBAAiE;IAEjE,OAAO,kCAAkC,CAAC;QACxC,SAAS,EAAE,KAAK,CAAC,SAAS;QAC1B,UAAU,EAAE,KAAK,CAAC,UAAU;QAC5B,uBAAuB,EAAE,KAAK,CAAC,uBAAuB;QACtD,eAAe,EAAE,KAAK,CAAC,eAAe;QACtC,WAAW,EAAE,KAAK,CAAC,WAAW;QAC9B,iBAAiB,EAAE,wBAAwB,CACzC,KAAK,EACL,yBAAyB,CAC1B;QACD,wBAAwB;QACxB,YAAY,EAAE,KAAK,CAAC,YAAY;KACjC,CAAC,CAAC;AACL,CAAC;AACD,SAAS,kCAAkC,CAAC,KAA8B;IACxE,OAAO,gCAAgC,CACrC,KAAK,CAAC,wBAAwB,EAC9B,sBAAsB,CACvB,CAAC;AACJ,CAAC;AAED,KAAK,UAAU,oBAAoB,CACjC,KAA8B,EAC9B,gBAA0D;IAE1D,IAAI,gBAAgB,KAAK,SAAS,EAAE,CAAC;QACnC,MAAM,KAAK,CAAC,6BAA6B,EAAE,CAAC,gBAAgB,CAAC,CAAC;IAChE,CAAC;IACD,OAAO,SAAS,CAAC;AACnB,CAAC;AAED,KAAK,UAAU,4BAA4B,CACzC,KAA8B,EAC9B,wBAAmD;IAQnD,IAAI,gBAAgB,GAAG,KAAK,CAAC,gBAAgB,CAAC;IAC9C,IAAI,CAAC;QACH,MAAM,SAAS,GAAG,MAAM,gCAAgC,CACtD,KAAK,EACL,wBAAwB,CACzB,CAAC;QACF,IAAI,SAAS,EAAE,IAAI,KAAK,WAAW;YAAE,OAAO,SAAS,CAAC;QACtD,IAAI,SAAS,EAAE,IAAI,KAAK,eAAe,IAAI,KAAK,CAAC,WAAW,KAAK,KAAK,EAAE,CAAC;YACvE,gBAAgB,GAAG,MAAM,oBAAoB,CAAC,KAAK,EAAE,gBAAgB,CAAC,CAAC;QACzE,CAAC;IACH,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IACE,CAAC,CAAC,KAAK,YAAY,wCAAwC,CAAC;YAC5D,gBAAgB,KAAK,SAAS;YAC9B,KAAK,CAAC,WAAW,KAAK,KAAK,EAC3B,CAAC;YACD,MAAM,KAAK,CAAC;QACd,CAAC;QACD,gBAAgB,GAAG,MAAM,oBAAoB,CAAC,KAAK,EAAE,gBAAgB,CAAC,CAAC;IACzE,CAAC;IACD,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,gBAAgB,EAAE,CAAC;AAChD,CAAC;AAED,SAAS,yBAAyB,CAAC,KAGlC;IACC,OAAO,CACL,KAAK,CAAC,cAAc,CAAC,MAAM,GAAG,CAAC,IAAI,KAAK,CAAC,0BAA0B,GAAG,CAAC,CACxE,CAAC;AACJ,CAAC;AAED,KAAK,UAAU,sBAAsB,CACnC,IAA6B,EAC7B,YAAsD;IAEtD,4BAA4B,CAAC,IAAI,CAAC,CAAC;IACnC,OAAO;QACL,IAAI,EAAE,OAAO;QACb,gBAAgB,EAAE,MAAM,oBAAoB,CAAC,IAAI,EAAE,YAAY,CAAC;KACjE,CAAC;AACJ,CAAC;AAED,KAAK,UAAU,4BAA4B,CAAC,KAO3C;IACC,IAAI,KAAK,CAAC,IAAI,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK,EAAE,CAAC;QAC1C,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC;IAC5C,CAAC;IACD,MAAM,kBAAkB,GAAG,yBAAyB,CAAC;QACnD,cAAc,EAAE,KAAK,CAAC,KAAK,CAAC,cAAc;QAC1C,0BAA0B,EAAE,KAAK,CAAC,KAAK,CAAC,0BAA0B,CAAC,IAAI;KACxE,CAAC,CAAC;IACH,MAAM,gBAAgB,GAAG,MAAM,wBAAwB,CACrD,KAAK,CAAC,IAAI,EACV,kBAAkB,EAClB,KAAK,CAAC,KAAK,CAAC,wBAAwB,CACrC,CAAC;IACF,IAAI,KAAK,CAAC,IAAI,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK,IAAI,CAAC,gBAAgB,EAAE,CAAC;QAC/D,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC;IAC5C,CAAC;IACD,MAAM,OAAO,GAAG,MAAM,uBAAuB,CAAC;QAC5C,cAAc,EAAE,KAAK,CAAC,KAAK,CAAC,cAAc;QAC1C,gBAAgB,EAAE,KAAK,CAAC,KAAK,CAAC,gBAAgB;QAC9C,2BAA2B,EAAE,KAAK,CAAC,KAAK,CAAC,2BAA2B;QACpE,IAAI,EAAE,KAAK,CAAC,IAAI;QAChB,yBAAyB,EAAE,kBAAkB;QAC7C,gBAAgB;KACjB,CAAC,CAAC;IACH,IAAI,OAAO,KAAK,OAAO,EAAE,CAAC;QACxB,OAAO,sBAAsB,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,KAAK,CAAC,gBAAgB,CAAC,CAAC;IAC1E,CAAC;IACD,IAAI,CAAC,OAAO,IAAI,KAAK,CAAC,IAAI,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK,EAAE,CAAC;QACtD,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC;IAC5C,CAAC;IACD,MAAM,CAAC,gBAAgB,CAAC,GAAG,OAAO,CAAC;IACnC,MAAM,SAAS,GAAG,MAAM,wBAAwB,CAAC;QAC/C,OAAO,EAAE,KAAK,CAAC,OAAO;QACtB,gBAAgB;QAChB,WAAW,EAAE,KAAK,CAAC,WAAW;QAC9B,cAAc,EAAE,yBAAyB,CACvC,KAAK,CAAC,KAAK,CAAC,cAAc,EAC1B,gBAAgB,CACjB;QACD,gBAAgB,EAAE,KAAK,CAAC,KAAK,CAAC,gBAAgB;QAC9C,2BAA2B,EAAE,KAAK,CAAC,KAAK,CAAC,2BAA2B;QACpE,IAAI,EAAE,KAAK,CAAC,IAAI;QAChB,yBAAyB,EAAE,kBAAkB;KAC9C,CAAC,CAAC;IACH,IAAI,KAAK,CAAC,IAAI,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK,IAAI,SAAS,KAAK,WAAW,EAAE,CAAC;QACvE,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC;IAC5C,CAAC;IACD,IAAI,SAAS,KAAK,OAAO,EAAE,CAAC;QAC1B,6BAA6B,CAC3B,KAAK,CAAC,IAAI,CAAC,WAAW,EACtB,KAAK,CAAC,KAAK,CAAC,gBAAgB,CAC7B,CAAC;QACF,OAAO,sBAAsB,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,KAAK,CAAC,gBAAgB,CAAC,CAAC;IAC1E,CAAC;IACD,IAAI,SAAS,KAAK,SAAS,EAAE,CAAC;QAC5B,kBAAkB,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;QAC/B,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC;IAC5C,CAAC;IACD,IAAI,SAAS,KAAK,MAAM,EAAE,CAAC;QACzB,KAAK,CAAC,IAAI,CAAC,eAAe,EAAE,CAAC,mCAAmC,CAAC,CAAC;QAClE,OAAO,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC;IAC5C,CAAC;IACD,IAAI,SAAS,CAAC,IAAI,KAAK,+BAA+B,EAAE,CAAC;QACvD,OAAO,EAAE,IAAI,EAAE,YAAY,EAAE,CAAC;IAChC,CAAC;IACD,IAAI,SAAS,CAAC,IAAI,KAAK,4BAA4B,EAAE,CAAC;QACpD,2EAA2E;QAC3E,4EAA4E;QAC5E,0EAA0E;QAC1E,4BAA4B,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;QACzC,OAAO,EAAE,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,SAAS,CAAC,0BAA0B,EAAE,CAAC;IAC5E,CAAC;IACD,MAAM,MAAM,GAAG,MAAM,kCAAkC,CAAC;QACtD,gBAAgB;QAChB,gBAAgB,EAAE,KAAK,CAAC,gBAAgB;QACxC,YAAY,EAAE,SAAS,CAAC,YAAY;QACpC,0BAA0B,EAAE,KAAK,CAAC,KAAK,CAAC,0BAA0B;QAClE,wBAAwB,EAAE,KAAK,CAAC,wBAAwB;QACxD,QAAQ,EAAE,SAAS,CAAC,QAAQ;QAC5B,IAAI,EAAE,KAAK,CAAC,IAAI;QAChB,gBAAgB,EAAE,gBAAgB,CAAC,gBAAgB;KACpD,CAAC,CAAC;IACH,OAAO;QACL,IAAI,EAAE,UAAU;QAChB,MAAM,EAAE,KAAK,CAAC,IAAI,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,MAAM;KAC9D,CAAC;AACJ,CAAC;AAED,KAAK,UAAU,0BAA0B,CACvC,KAA8B;IAE9B,IAAI,KAAK,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK;QAAE,OAAO,IAAI,CAAC;IAClD,MAAM,wBAAwB,GAAG,kCAAkC,CAAC,KAAK,CAAC,CAAC;IAC3E,MAAM,WAAW,GAAG,CAAC,CAAC;IACtB,IAAI,cAAc,GAAG,KAAK,CAAC,cAAc,IAAI,EAAE,CAAC;IAChD,MAAM,gBAAgB,GAAG,cAAc,CAAC,GAAG,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC;IACnE,IAAI,0BAA0B,GAAG,IAAI,GAAG,EAA+B,CAAC;IACxE,IAAI,2BAA2B,GAAG,KAAK,CAAC;IACxC,IAAI,wBAAwB,GAAG,KAAK,CAAC,gBAAgB,IAAI,IAAI,CAAC;IAC9D,MAAM,aAAa,GAAG,MAAM,4BAA4B,CACtD,KAAK,EACL,wBAAwB,CACzB,CAAC;IACF,IAAI,KAAK,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK;QAAE,OAAO,IAAI,CAAC;IAClD,IAAI,aAAa,CAAC,IAAI,KAAK,WAAW;QAAE,OAAO,aAAa,CAAC,MAAM,CAAC;IACpE,IAAI,gBAAgB,GAAG,aAAa,CAAC,gBAAgB,CAAC;IACtD,KAAK,IAAI,OAAO,GAAG,CAAC,EAAE,OAAO,IAAI,WAAW,EAAE,OAAO,IAAI,CAAC,EAAE,CAAC;QAC3D,MAAM,OAAO,GAAG,MAAM,4BAA4B,CAAC;YACjD,OAAO;YACP,WAAW;YACX,gBAAgB;YAChB,wBAAwB;YACxB,KAAK,EAAE;gBACL,cAAc;gBACd,gBAAgB;gBAChB,0BAA0B;gBAC1B,2BAA2B;gBAC3B,wBAAwB;aACzB;YACD,IAAI,EAAE,KAAK;SACZ,CAAC,CAAC;QACH,wBAAwB,GAAG,IAAI,CAAC;QAChC,IAAI,OAAO,CAAC,IAAI,KAAK,UAAU;YAAE,OAAO,OAAO,CAAC,MAAM,CAAC;QACvD,IAAI,OAAO,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;YAC7B,gBAAgB,GAAG,OAAO,CAAC,gBAAgB,CAAC;YAC5C,IAAI,KAAK,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK;gBAAE,OAAO,IAAI,CAAC;YAClD,SAAS;QACX,CAAC;QACD,IAAI,OAAO,CAAC,IAAI,KAAK,YAAY,EAAE,CAAC;YAClC,2BAA2B,GAAG,IAAI,CAAC;YACnC,SAAS;QACX,CAAC;QACD,0BAA0B,GAAG,OAAO,CAAC,OAAO,CAAC;QAC7C,cAAc,GAAG,EAAE,CAAC;IACtB,CAAC;IACD,OAAO,8BAA8B,CAAC,KAAK,CAAC,CAAC;AAC/C,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,kBAAkB,CACtC,KAA8B;IAE9B,IAAI,CAAC;QACH,OAAO,MAAM,0BAA0B,CAAC;YACtC,GAAG,KAAK;YACR,uBAAuB,EAAE,2CAA2C,CAAC;gBACnE,SAAS,EAAE,KAAK,CAAC,SAAS;gBAC1B,OAAO,EAAE,KAAK,CAAC,OAAO;gBACtB,sBAAsB,EAAE,KAAK,CAAC,MAAM,CAAC,cAAc;gBACnD,kBAAkB,EAAE,CAAC,EAAE,gBAAgB,EAAE,UAAU,EAAE,EAAE,EAAE;oBACvD,IAAI,KAAK,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK;wBAAE,OAAO;oBAC7C,IAAI,CAAC,KAAK,CAAC,uBAAuB,EAAE,CAAC;wBACnC,MAAM,IAAI,uBAAuB,CAC/B,oBAAoB,EACpB,yDAAyD,CAC1D,CAAC;oBACJ,CAAC;oBACD,OAAO,KAAK,CAAC,uBAAuB,CAAC;wBACnC,gBAAgB;wBAChB,UAAU;qBACX,CAAC,CAAC;gBACL,CAAC;gBACD,wBAAwB,EAAE,KAAK,CAAC,wBAAwB;gBACxD,YAAY,EAAE,KAAK,CAAC,YAAY;gBAChC,+BAA+B,EAAE,KAAK,CAAC,+BAA+B;aACvE,CAAC;SACH,CAAC,CAAC;IACL,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IAAI,sCAAsC,CAAC,KAAK,CAAC;YAAE,OAAO,IAAI,CAAC;QAC/D,IACE,KAAK,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK;YAChC,kCAAkC,CAAC,KAAK,CAAC,EACzC,CAAC;YACD,MAAM,KAAK,CAAC,gCAAgC,EAAE,CAAC,KAAK,CAAC,CAAC;QACxD,CAAC;QACD,MAAM,KAAK,CAAC;IACd,CAAC;AACH,CAAC","sourcesContent":["import { KeyingVerificationError } from \"@tearleads/crypto\";\nimport type { DocumentWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport { isDocumentUpdateCreatedEvent } from \"../../../data/documents/documentSync\";\nimport { isDocumentSyncUpdateIsolationError } from \"../../../data/documents/shared/sync/documentSyncUpdateIsolation\";\nimport {\n type DocumentSyncPullContinuation,\n InvalidDocumentSyncPullContinuationError,\n} from \"../../../data/documents/shared/sync/syncPagination\";\nimport type {\n MaterializedDocumentSyncPlan,\n SyncRemoteDocumentResult,\n} from \"../../../data/documents/shared/types\";\nimport {\n isProjectionVerificationCancelledError,\n type ProjectionUserKeyResolver,\n requireProjectionUserKeyResolver,\n} from \"../../../data/keyingProjectionVerification\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport { createVerifiedRemoteDocumentDeletionHandler } from \"../purge\";\nimport {\n assertRawContinuationCanRetry,\n resolveSyncAttemptWriterProjection,\n submitDocumentSyncAttemptIfAllowed,\n} from \"../syncFailures\";\nimport {\n abandonAfterRetryableConflicts,\n abandonBlockedSync,\n} from \"../syncFailures/syncAbandon\";\nimport { recoverablePendingUpdates } from \"../syncPlan/syncPlanRequestBounds\";\nimport { requireStandaloneAncestorRepairs } from \"../syncRekeys/syncContainerRekeyPreparation\";\nimport {\n type SyncRemoteDocumentInput,\n tryPersistedReadOnlyDocumentSync,\n} from \"./readOnlySync\";\nimport {\n planDocumentSyncAttempt,\n projectionFailureHandler,\n} from \"./syncAttemptPlanning\";\nimport type {\n RemoteDocumentSyncAttemptOutcome,\n RemoteDocumentSyncAttemptState,\n} from \"./syncAttemptState\";\nimport { resolveSubmittedDocumentSyncResult } from \"./syncSubmittedResult\";\n\nexport function hasDocumentUpdateEvent(\n events: ReadonlyArray<unknown>,\n documentId: string | null | undefined,\n): boolean {\n if (!documentId) return false;\n return events.some(\n (event) =>\n isDocumentUpdateCreatedEvent(event) && event.documentId === documentId,\n );\n}\n/**\n * A retryable stale-projection conflict means this writer projection is behind\n * the server. Evict only this document so the next attempt re-derives targets.\n */\nfunction evictStaleProjectionForRetry(input: SyncRemoteDocumentInput): void {\n input.apiClient.evictDocumentWriterProjection?.(input.documentId);\n}\n\n/**\n * A pass may repair a covering-baseline rejection by regenerating queued\n * rotation checkpoints — but only when there is something to regenerate FROM\n * (a snapshot provider and queued checkpoint rows), the failed pass was not\n * already a heal or a regeneration (whose fresh baseline proves this device\n * is simply behind), and an attempt remains.\n */\nfunction canRegenerateQueuedCheckpoints(input: {\n materializedPlan: MaterializedDocumentSyncPlan;\n pendingUpdates: readonly PendingUpdateRecord[];\n regenerateQueuedCheckpoints: boolean;\n sync: SyncRemoteDocumentInput;\n}): boolean {\n return (\n !input.regenerateQueuedCheckpoints &&\n !input.materializedPlan.healedStaleContentKeyBundle &&\n input.sync.buildRotationSnapshot !== undefined &&\n input.pendingUpdates.some((update) => update.sourceVersionVector != null)\n );\n}\n\nasync function submitPlannedSyncAttempt(args: {\n attempt: number;\n materializedPlan: MaterializedDocumentSyncPlan;\n maxAttempts: number;\n pendingUpdates: readonly PendingUpdateRecord[];\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n regenerateQueuedCheckpoints: boolean;\n sync: SyncRemoteDocumentInput;\n failureBlocksQueuedWrites: boolean;\n}) {\n try {\n return await submitDocumentSyncAttemptIfAllowed({\n apiClient: args.sync.apiClient,\n attempt: args.attempt,\n canRegenerateQueuedCheckpoints: canRegenerateQueuedCheckpoints({\n materializedPlan: args.materializedPlan,\n pendingUpdates: args.pendingUpdates,\n regenerateQueuedCheckpoints: args.regenerateQueuedCheckpoints,\n sync: args.sync,\n }),\n documentId: args.sync.documentId,\n expectedCommitLsnMode: args.pullContinuation?.commitLsnMode,\n isRemoteSyncBlocked: args.sync.isRemoteSyncBlocked,\n maxAttempts: args.maxAttempts,\n onInlineRepairRefused: () => requireStandaloneAncestorRepairs(args.sync),\n onRemoteDocumentDeleted: args.sync.onRemoteDocumentDeleted,\n onOutgoingUpdatesMaterialized: args.sync.onOutgoingUpdatesMaterialized,\n onSyncTrace: args.sync.onSyncTrace,\n onTerminalSubmitFailure: args.sync.onTerminalSubmitFailure,\n pendingUpdates: args.pendingUpdates,\n plan: args.materializedPlan.plan,\n failureBlocksQueuedWrites: args.failureBlocksQueuedWrites,\n stillCurrent: args.sync.stillCurrent,\n warmReferencedPrincipalPolicies:\n args.sync.warmReferencedPrincipalPolicies,\n });\n } catch (error) {\n if (\n error instanceof InvalidDocumentSyncPullContinuationError &&\n args.pullContinuation !== undefined &&\n args.sync.historyMode !== \"raw\"\n ) {\n return \"retry\" as const;\n }\n throw error;\n }\n}\n\nfunction resolveAttemptProjection(\n input: SyncRemoteDocumentInput,\n failureBlocksQueuedWrites: boolean,\n reusableWriterProjection: DocumentWriterProjectionResponse | null,\n) {\n return resolveSyncAttemptWriterProjection({\n apiClient: input.apiClient,\n documentId: input.documentId,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n onSyncAbandoned: input.onSyncAbandoned,\n onSyncTrace: input.onSyncTrace,\n onTerminalFailure: projectionFailureHandler(\n input,\n failureBlocksQueuedWrites,\n ),\n reusableWriterProjection,\n stillCurrent: input.stillCurrent,\n });\n}\nfunction resolveRemoteSyncProjectionUserKey(input: SyncRemoteDocumentInput) {\n return requireProjectionUserKeyResolver(\n input.resolveProjectionUserKey,\n \"Remote document sync\",\n );\n}\n\nasync function invalidatePullCursor(\n input: SyncRemoteDocumentInput,\n pullContinuation: DocumentSyncPullContinuation | undefined,\n): Promise<undefined> {\n if (pullContinuation !== undefined) {\n await input.onPullContinuationInvalidated?.(pullContinuation);\n }\n return undefined;\n}\n\nasync function preparePersistedDocumentSync(\n input: SyncRemoteDocumentInput,\n resolveProjectionUserKey: ProjectionUserKeyResolver,\n): Promise<\n | { readonly kind: \"completed\"; result: SyncRemoteDocumentResult | null }\n | {\n readonly kind: \"continue\";\n pullContinuation: DocumentSyncPullContinuation | undefined;\n }\n> {\n let pullContinuation = input.pullContinuation;\n try {\n const persisted = await tryPersistedReadOnlyDocumentSync(\n input,\n resolveProjectionUserKey,\n );\n if (persisted?.kind === \"completed\") return persisted;\n if (persisted?.kind === \"not_completed\" && input.historyMode !== \"raw\") {\n pullContinuation = await invalidatePullCursor(input, pullContinuation);\n }\n } catch (error) {\n if (\n !(error instanceof InvalidDocumentSyncPullContinuationError) ||\n pullContinuation === undefined ||\n input.historyMode === \"raw\"\n ) {\n throw error;\n }\n pullContinuation = await invalidatePullCursor(input, pullContinuation);\n }\n return { kind: \"continue\", pullContinuation };\n}\n\nfunction failureBlocksQueuedWrites(input: {\n readonly pendingUpdates: readonly PendingUpdateRecord[];\n readonly recoveryPendingUpdateCount: number;\n}): boolean {\n return (\n input.pendingUpdates.length > 0 || input.recoveryPendingUpdateCount > 0\n );\n}\n\nasync function retryRemoteSyncAttempt(\n sync: SyncRemoteDocumentInput,\n continuation: DocumentSyncPullContinuation | undefined,\n): Promise<RemoteDocumentSyncAttemptOutcome> {\n evictStaleProjectionForRetry(sync);\n return {\n kind: \"retry\",\n pullContinuation: await invalidatePullCursor(sync, continuation),\n };\n}\n\nasync function runRemoteDocumentSyncAttempt(input: {\n attempt: number;\n maxAttempts: number;\n pendingUpdateIds: readonly string[];\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n state: RemoteDocumentSyncAttemptState;\n sync: SyncRemoteDocumentInput;\n}): Promise<RemoteDocumentSyncAttemptOutcome> {\n if (input.sync.stillCurrent?.() === false) {\n return { kind: \"complete\", result: null };\n }\n const blocksQueuedWrites = failureBlocksQueuedWrites({\n pendingUpdates: input.state.pendingUpdates,\n recoveryPendingUpdateCount: input.state.recoveryPendingUpdatesById.size,\n });\n const writerProjection = await resolveAttemptProjection(\n input.sync,\n blocksQueuedWrites,\n input.state.reusableWriterProjection,\n );\n if (input.sync.stillCurrent?.() === false || !writerProjection) {\n return { kind: \"complete\", result: null };\n }\n const planned = await planDocumentSyncAttempt({\n pendingUpdates: input.state.pendingUpdates,\n pullContinuation: input.state.pullContinuation,\n regenerateQueuedCheckpoints: input.state.regenerateQueuedCheckpoints,\n sync: input.sync,\n failureBlocksQueuedWrites: blocksQueuedWrites,\n writerProjection,\n });\n if (planned === \"retry\") {\n return retryRemoteSyncAttempt(input.sync, input.state.pullContinuation);\n }\n if (!planned || input.sync.stillCurrent?.() === false) {\n return { kind: \"complete\", result: null };\n }\n const [materializedPlan] = planned;\n const submitted = await submitPlannedSyncAttempt({\n attempt: input.attempt,\n materializedPlan,\n maxAttempts: input.maxAttempts,\n pendingUpdates: recoverablePendingUpdates(\n input.state.pendingUpdates,\n materializedPlan,\n ),\n pullContinuation: input.state.pullContinuation,\n regenerateQueuedCheckpoints: input.state.regenerateQueuedCheckpoints,\n sync: input.sync,\n failureBlocksQueuedWrites: blocksQueuedWrites,\n });\n if (input.sync.stillCurrent?.() === false || submitted === \"cancelled\") {\n return { kind: \"complete\", result: null };\n }\n if (submitted === \"retry\") {\n assertRawContinuationCanRetry(\n input.sync.historyMode,\n input.state.pullContinuation,\n );\n return retryRemoteSyncAttempt(input.sync, input.state.pullContinuation);\n }\n if (submitted === \"blocked\") {\n abandonBlockedSync(input.sync);\n return { kind: \"complete\", result: null };\n }\n if (submitted === \"stop\") {\n input.sync.onSyncAbandoned?.(\"the sync submit failed terminally\");\n return { kind: \"complete\", result: null };\n }\n if (submitted.kind === \"regenerate_queued_checkpoints\") {\n return { kind: \"regenerate\" };\n }\n if (submitted.kind === \"recover_update_id_conflict\") {\n // A lost response may mean the server committed both this update id and an\n // inline container rekey. Force the read-only recovery pass to observe that\n // committed successor projection instead of reusing a cached predecessor.\n evictStaleProjectionForRetry(input.sync);\n return { kind: \"recover\", updates: submitted.recoveryPendingUpdatesById };\n }\n const result = await resolveSubmittedDocumentSyncResult({\n materializedPlan,\n pendingUpdateIds: input.pendingUpdateIds,\n pullComplete: submitted.pullComplete,\n recoveryPendingUpdatesById: input.state.recoveryPendingUpdatesById,\n resolveProjectionUserKey: input.resolveProjectionUserKey,\n response: submitted.response,\n sync: input.sync,\n writerProjection: materializedPlan.writerProjection,\n });\n return {\n kind: \"complete\",\n result: input.sync.stillCurrent?.() === false ? null : result,\n };\n}\n\nasync function syncRemoteDocumentInternal(\n input: SyncRemoteDocumentInput,\n): Promise<SyncRemoteDocumentResult | null> {\n if (input.stillCurrent?.() === false) return null;\n const resolveProjectionUserKey = resolveRemoteSyncProjectionUserKey(input);\n const maxAttempts = 3;\n let pendingUpdates = input.pendingUpdates ?? [];\n const pendingUpdateIds = pendingUpdates.map((update) => update.id);\n let recoveryPendingUpdatesById = new Map<string, PendingUpdateRecord>();\n let regenerateQueuedCheckpoints = false;\n let reusableWriterProjection = input.writerProjection ?? null;\n const persistedSync = await preparePersistedDocumentSync(\n input,\n resolveProjectionUserKey,\n );\n if (input.stillCurrent?.() === false) return null;\n if (persistedSync.kind === \"completed\") return persistedSync.result;\n let pullContinuation = persistedSync.pullContinuation;\n for (let attempt = 1; attempt <= maxAttempts; attempt += 1) {\n const outcome = await runRemoteDocumentSyncAttempt({\n attempt,\n maxAttempts,\n pendingUpdateIds,\n resolveProjectionUserKey,\n state: {\n pendingUpdates,\n pullContinuation,\n recoveryPendingUpdatesById,\n regenerateQueuedCheckpoints,\n reusableWriterProjection,\n },\n sync: input,\n });\n reusableWriterProjection = null;\n if (outcome.kind === \"complete\") return outcome.result;\n if (outcome.kind === \"retry\") {\n pullContinuation = outcome.pullContinuation;\n if (input.stillCurrent?.() === false) return null;\n continue;\n }\n if (outcome.kind === \"regenerate\") {\n regenerateQueuedCheckpoints = true;\n continue;\n }\n recoveryPendingUpdatesById = outcome.updates;\n pendingUpdates = [];\n }\n return abandonAfterRetryableConflicts(input);\n}\n\nexport async function syncRemoteDocument(\n input: SyncRemoteDocumentInput,\n): Promise<SyncRemoteDocumentResult | null> {\n try {\n return await syncRemoteDocumentInternal({\n ...input,\n onRemoteDocumentDeleted: createVerifiedRemoteDocumentDeletionHandler({\n apiClient: input.apiClient,\n execSql: input.execSql,\n expectedOrganizationId: input.author.organizationId,\n onVerifiedDeletion: ({ commitPurgeProof, documentId }) => {\n if (input.stillCurrent?.() === false) return;\n if (!input.onRemoteDocumentDeleted) {\n throw new KeyingVerificationError(\n \"missing_dependency\",\n \"Remote document deletion requires atomic local teardown\",\n );\n }\n return input.onRemoteDocumentDeleted({\n commitPurgeProof,\n documentId,\n });\n },\n resolveProjectionUserKey: input.resolveProjectionUserKey,\n stillCurrent: input.stillCurrent,\n warmReferencedPrincipalPolicies: input.warmReferencedPrincipalPolicies,\n }),\n });\n } catch (error) {\n if (isProjectionVerificationCancelledError(error)) return null;\n if (\n input.stillCurrent?.() !== false &&\n isDocumentSyncUpdateIsolationError(error)\n ) {\n await input.onIncomingUpdateIsolationFailure?.(error);\n }\n throw error;\n }\n}\n"]}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["index.ts"],"names":[],"mappings":"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","sourcesContent":["import { KeyingVerificationError } from \"@tearleads/crypto\";\nimport type { DocumentWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport { isDocumentUpdateCreatedEvent } from \"../../../data/documents/documentSync\";\nimport { isDocumentSyncUpdateIsolationError } from \"../../../data/documents/shared/sync/documentSyncUpdateIsolation\";\nimport {\n type DocumentSyncPullContinuation,\n InvalidDocumentSyncPullContinuationError,\n} from \"../../../data/documents/shared/sync/syncPagination\";\nimport type {\n MaterializedDocumentSyncPlan,\n SyncRemoteDocumentResult,\n} from \"../../../data/documents/shared/types\";\nimport {\n isProjectionVerificationCancelledError,\n type ProjectionUserKeyResolver,\n requireProjectionUserKeyResolver,\n} from \"../../../data/keyingProjectionVerification\";\nimport type { PendingUpdateRecord } from \"../../../data/persistence/documents/records\";\nimport { createVerifiedRemoteDocumentDeletionHandler } from \"../purge\";\nimport {\n assertRawContinuationCanRetry,\n resolveSyncAttemptWriterProjection,\n submitDocumentSyncAttemptIfAllowed,\n} from \"../syncFailures\";\nimport {\n abandonAfterRetryableConflicts,\n abandonBlockedSync,\n} from \"../syncFailures/syncAbandon\";\nimport { recoverablePendingUpdates } from \"../syncPlan/syncPlanRequestBounds\";\nimport { requireStandaloneAncestorRepairs } from \"../syncRekeys/syncContainerRekeyPreparation\";\nimport {\n type SyncRemoteDocumentInput,\n tryPersistedReadOnlyDocumentSync,\n} from \"./readOnlySync\";\nimport {\n planDocumentSyncAttempt,\n projectionFailureHandler,\n} from \"./syncAttemptPlanning\";\nimport type {\n RemoteDocumentSyncAttemptOutcome,\n RemoteDocumentSyncAttemptState,\n} from \"./syncAttemptState\";\nimport { resolveSubmittedDocumentSyncResult } from \"./syncSubmittedResult\";\n\nexport function hasDocumentUpdateEvent(\n events: ReadonlyArray<unknown>,\n documentId: string | null | undefined,\n): boolean {\n if (!documentId) return false;\n return events.some(\n (event) =>\n isDocumentUpdateCreatedEvent(event) && event.documentId === documentId,\n );\n}\n/**\n * A retryable stale-projection conflict means this writer projection is behind\n * the server. Evict only this document so the next attempt re-derives targets.\n */\nfunction evictStaleProjectionForRetry(input: SyncRemoteDocumentInput): void {\n input.apiClient.evictDocumentWriterProjection?.(input.documentId);\n}\n\n/**\n * A pass may repair a covering-baseline rejection by regenerating queued\n * rotation checkpoints — but only when there is something to regenerate FROM\n * (a snapshot provider and queued checkpoint rows), the failed pass was not\n * already a heal or a regeneration (whose fresh baseline proves this device\n * is simply behind), and an attempt remains.\n */\nfunction canRegenerateQueuedCheckpoints(input: {\n materializedPlan: MaterializedDocumentSyncPlan;\n pendingUpdates: readonly PendingUpdateRecord[];\n regenerateQueuedCheckpoints: boolean;\n sync: SyncRemoteDocumentInput;\n}): boolean {\n return (\n !input.regenerateQueuedCheckpoints &&\n !input.materializedPlan.healedStaleContentKeyBundle &&\n input.sync.buildRotationSnapshot !== undefined &&\n input.pendingUpdates.some((update) => update.sourceVersionVector != null)\n );\n}\n\nasync function submitPlannedSyncAttempt(args: {\n attempt: number;\n materializedPlan: MaterializedDocumentSyncPlan;\n maxAttempts: number;\n pendingUpdates: readonly PendingUpdateRecord[];\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n regenerateQueuedCheckpoints: boolean;\n sync: SyncRemoteDocumentInput;\n failureBlocksQueuedWrites: boolean;\n}) {\n try {\n return await submitDocumentSyncAttemptIfAllowed({\n apiClient: args.sync.apiClient,\n attempt: args.attempt,\n canRegenerateQueuedCheckpoints: canRegenerateQueuedCheckpoints({\n materializedPlan: args.materializedPlan,\n pendingUpdates: args.pendingUpdates,\n regenerateQueuedCheckpoints: args.regenerateQueuedCheckpoints,\n sync: args.sync,\n }),\n documentId: args.sync.documentId,\n expectedCommitLsnMode: args.pullContinuation?.commitLsnMode,\n isRemoteSyncBlocked: args.sync.isRemoteSyncBlocked,\n maxAttempts: args.maxAttempts,\n onInlineRepairRefused: () => requireStandaloneAncestorRepairs(args.sync),\n onRemoteDocumentDeleted: args.sync.onRemoteDocumentDeleted,\n onOutgoingUpdatesMaterialized: args.sync.onOutgoingUpdatesMaterialized,\n onSyncTrace: args.sync.onSyncTrace,\n onTerminalSubmitFailure: args.sync.onTerminalSubmitFailure,\n pendingUpdates: args.pendingUpdates,\n plan: args.materializedPlan.plan,\n failureBlocksQueuedWrites: args.failureBlocksQueuedWrites,\n stillCurrent: args.sync.stillCurrent,\n warmReferencedPrincipalPolicies:\n args.sync.warmReferencedPrincipalPolicies,\n });\n } catch (error) {\n if (\n error instanceof InvalidDocumentSyncPullContinuationError &&\n args.pullContinuation !== undefined &&\n args.sync.historyMode !== \"raw\"\n ) {\n return \"retry\" as const;\n }\n throw error;\n }\n}\n\nfunction resolveAttemptProjection(\n input: SyncRemoteDocumentInput,\n failureBlocksQueuedWrites: boolean,\n reusableWriterProjection: DocumentWriterProjectionResponse | null,\n) {\n return resolveSyncAttemptWriterProjection({\n apiClient: input.apiClient,\n documentId: input.documentId,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n onSyncAbandoned: input.onSyncAbandoned,\n onSyncTrace: input.onSyncTrace,\n onTerminalFailure: projectionFailureHandler(\n input,\n failureBlocksQueuedWrites,\n ),\n reusableWriterProjection,\n stillCurrent: input.stillCurrent,\n });\n}\nfunction resolveRemoteSyncProjectionUserKey(input: SyncRemoteDocumentInput) {\n return requireProjectionUserKeyResolver(\n input.resolveProjectionUserKey,\n \"Remote document sync\",\n );\n}\n\nasync function invalidatePullCursor(\n input: SyncRemoteDocumentInput,\n pullContinuation: DocumentSyncPullContinuation | undefined,\n): Promise<undefined> {\n if (pullContinuation !== undefined) {\n await input.onPullContinuationInvalidated?.(pullContinuation);\n }\n return undefined;\n}\n\nasync function preparePersistedDocumentSync(\n input: SyncRemoteDocumentInput,\n resolveProjectionUserKey: ProjectionUserKeyResolver,\n): Promise<\n | { readonly kind: \"completed\"; result: SyncRemoteDocumentResult | null }\n | {\n readonly kind: \"continue\";\n pullContinuation: DocumentSyncPullContinuation | undefined;\n }\n> {\n let pullContinuation = input.pullContinuation;\n try {\n const persisted = await tryPersistedReadOnlyDocumentSync(\n input,\n resolveProjectionUserKey,\n );\n if (persisted?.kind === \"completed\") return persisted;\n if (persisted?.kind === \"not_completed\" && input.historyMode !== \"raw\") {\n pullContinuation = await invalidatePullCursor(input, pullContinuation);\n }\n } catch (error) {\n if (\n !(error instanceof InvalidDocumentSyncPullContinuationError) ||\n pullContinuation === undefined ||\n input.historyMode === \"raw\"\n ) {\n throw error;\n }\n pullContinuation = await invalidatePullCursor(input, pullContinuation);\n }\n return { kind: \"continue\", pullContinuation };\n}\n\nfunction failureBlocksQueuedWrites(input: {\n readonly pendingUpdates: readonly PendingUpdateRecord[];\n readonly recoveryPendingUpdateCount: number;\n}): boolean {\n return (\n input.pendingUpdates.length > 0 || input.recoveryPendingUpdateCount > 0\n );\n}\n\nasync function retryRemoteSyncAttempt(\n sync: SyncRemoteDocumentInput,\n continuation: DocumentSyncPullContinuation | undefined,\n): Promise<RemoteDocumentSyncAttemptOutcome> {\n evictStaleProjectionForRetry(sync);\n return {\n kind: \"retry\",\n pullContinuation: await invalidatePullCursor(sync, continuation),\n };\n}\n\nasync function runRemoteDocumentSyncAttempt(input: {\n attempt: number;\n maxAttempts: number;\n pendingUpdateIds: readonly string[];\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n state: RemoteDocumentSyncAttemptState;\n sync: SyncRemoteDocumentInput;\n}): Promise<RemoteDocumentSyncAttemptOutcome> {\n if (input.sync.stillCurrent?.() === false) {\n return { kind: \"complete\", result: null };\n }\n const blocksQueuedWrites = failureBlocksQueuedWrites({\n pendingUpdates: input.state.pendingUpdates,\n recoveryPendingUpdateCount: input.state.recoveryPendingUpdatesById.size,\n });\n const writerProjection = await resolveAttemptProjection(\n input.sync,\n blocksQueuedWrites,\n input.state.reusableWriterProjection,\n );\n if (input.sync.stillCurrent?.() === false || !writerProjection) {\n return { kind: \"complete\", result: null };\n }\n const planned = await planDocumentSyncAttempt({\n pendingUpdates: input.state.pendingUpdates,\n pullContinuation: input.state.pullContinuation,\n regenerateQueuedCheckpoints: input.state.regenerateQueuedCheckpoints,\n sync: input.sync,\n failureBlocksQueuedWrites: blocksQueuedWrites,\n writerProjection,\n });\n if (planned === \"retry\") {\n return retryRemoteSyncAttempt(input.sync, input.state.pullContinuation);\n }\n if (!planned || input.sync.stillCurrent?.() === false) {\n return { kind: \"complete\", result: null };\n }\n const [materializedPlan] = planned;\n const submitted = await submitPlannedSyncAttempt({\n attempt: input.attempt,\n materializedPlan,\n maxAttempts: input.maxAttempts,\n pendingUpdates: recoverablePendingUpdates(\n input.state.pendingUpdates,\n materializedPlan,\n ),\n pullContinuation: input.state.pullContinuation,\n regenerateQueuedCheckpoints: input.state.regenerateQueuedCheckpoints,\n sync: input.sync,\n failureBlocksQueuedWrites: blocksQueuedWrites,\n });\n if (input.sync.stillCurrent?.() === false || submitted === \"cancelled\") {\n return { kind: \"complete\", result: null };\n }\n if (submitted === \"retry\") {\n assertRawContinuationCanRetry(\n input.sync.historyMode,\n input.state.pullContinuation,\n );\n return retryRemoteSyncAttempt(input.sync, input.state.pullContinuation);\n }\n if (submitted === \"blocked\") {\n abandonBlockedSync(input.sync);\n return { kind: \"complete\", result: null };\n }\n if (submitted === \"stop\") {\n input.sync.onSyncAbandoned?.(\"the sync submit failed terminally\");\n return { kind: \"complete\", result: null };\n }\n if (submitted.kind === \"regenerate_queued_checkpoints\") {\n return { kind: \"regenerate\" };\n }\n if (submitted.kind === \"recover_update_id_conflict\") {\n // A lost response may mean the server committed both this update id and an\n // inline container rekey. Force the read-only recovery pass to observe that\n // committed successor projection instead of reusing a cached predecessor.\n evictStaleProjectionForRetry(input.sync);\n return { kind: \"recover\", updates: submitted.recoveryPendingUpdatesById };\n }\n const result = await resolveSubmittedDocumentSyncResult({\n materializedPlan,\n pendingUpdateIds: input.pendingUpdateIds,\n pullComplete: submitted.pullComplete,\n recoveryPendingUpdatesById: input.state.recoveryPendingUpdatesById,\n resolveProjectionUserKey: input.resolveProjectionUserKey,\n response: submitted.response,\n sync: input.sync,\n writerProjection: materializedPlan.writerProjection,\n });\n return {\n kind: \"complete\",\n result: input.sync.stillCurrent?.() === false ? null : result,\n };\n}\n\nasync function syncRemoteDocumentInternal(\n input: SyncRemoteDocumentInput,\n): Promise<SyncRemoteDocumentResult | null> {\n if (input.stillCurrent?.() === false) return null;\n const resolveProjectionUserKey = resolveRemoteSyncProjectionUserKey(input);\n const maxAttempts = 3;\n let pendingUpdates = input.pendingUpdates ?? [];\n const pendingUpdateIds = pendingUpdates.map((update) => update.id);\n let recoveryPendingUpdatesById = new Map<string, PendingUpdateRecord>();\n let regenerateQueuedCheckpoints = false;\n let reusableWriterProjection = input.writerProjection ?? null;\n const persistedSync = await preparePersistedDocumentSync(\n input,\n resolveProjectionUserKey,\n );\n if (input.stillCurrent?.() === false) return null;\n if (persistedSync.kind === \"completed\") return persistedSync.result;\n let pullContinuation = persistedSync.pullContinuation;\n for (let attempt = 1; attempt <= maxAttempts; attempt += 1) {\n const outcome = await runRemoteDocumentSyncAttempt({\n attempt,\n maxAttempts,\n pendingUpdateIds,\n resolveProjectionUserKey,\n state: {\n pendingUpdates,\n pullContinuation,\n recoveryPendingUpdatesById,\n regenerateQueuedCheckpoints,\n reusableWriterProjection,\n },\n sync: input,\n });\n reusableWriterProjection = null;\n if (outcome.kind === \"complete\") return outcome.result;\n if (outcome.kind === \"retry\") {\n pullContinuation = outcome.pullContinuation;\n if (input.stillCurrent?.() === false) return null;\n continue;\n }\n if (outcome.kind === \"regenerate\") {\n regenerateQueuedCheckpoints = true;\n continue;\n }\n recoveryPendingUpdatesById = outcome.updates;\n pendingUpdates = [];\n }\n return abandonAfterRetryableConflicts(input);\n}\n\nexport async function syncRemoteDocument(\n input: SyncRemoteDocumentInput,\n): Promise<SyncRemoteDocumentResult | null> {\n try {\n return await syncRemoteDocumentInternal({\n ...input,\n onRemoteDocumentDeleted: createVerifiedRemoteDocumentDeletionHandler({\n apiClient: input.apiClient,\n execSql: input.execSql,\n expectedOrganizationId: input.author.organizationId,\n onVerifiedDeletion: ({ commitPurgeProof, documentId }) => {\n if (input.stillCurrent?.() === false) return;\n if (!input.onRemoteDocumentDeleted) {\n throw new KeyingVerificationError(\n \"missing_dependency\",\n \"Remote document deletion requires atomic local teardown\",\n );\n }\n return input.onRemoteDocumentDeleted({\n commitPurgeProof,\n documentId,\n });\n },\n resolveProjectionUserKey: input.resolveProjectionUserKey,\n stillCurrent: input.stillCurrent,\n warmReferencedPrincipalPolicies: input.warmReferencedPrincipalPolicies,\n }),\n });\n } catch (error) {\n if (isProjectionVerificationCancelledError(error)) return null;\n if (\n input.stillCurrent?.() !== false &&\n isDocumentSyncUpdateIsolationError(error)\n ) {\n await input.onIncomingUpdateIsolationFailure?.(error);\n }\n throw error;\n }\n}\n"]}
@@ -1,7 +1,7 @@
1
1
  import type { DocumentSyncRequest } from "../../../internal/validators/request/index.js";
2
2
  import type { ContainerWriterProjectionResponse } from "../../../internal/validators/response/index.js";
3
3
  import type { DocumentCreateAuthor, MaterializedDocumentCreatePlan } from "../../../data/documents/shared/types.js";
4
- import type { PendingUpdateRecord } from "../../../data/sqlite/documentPersistence/index.js";
4
+ import type { PendingUpdateRecord } from "../../../data/persistence/documents/records/index.js";
5
5
  /**
6
6
  * Builds the single encrypted initial write for a provisioned document. The
7
7
  * server commits it with the organization and document manifest transaction.
@@ -1 +1 @@
1
- {"version":3,"file":"initialSync.js","sourceRoot":"","sources":["initialSync.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n emptyVersionVector,\n satisfiesVersionVector,\n versionVectorsEqual,\n} from \"@tearleads/loro\";\nimport type { DocumentSyncRequest } from \"@tearleads/validators/request\";\nimport type { ContainerWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport { MAX_DOCUMENT_SYNC_REQUEST_BYTES } from \"@tearleads/validators/util\";\nimport { createPendingUpdateFields } from \"../../../data/documents/documentSync\";\nimport { importContentKeyMaterial } from \"../../../data/documents/shared/contentRecordKeys\";\nimport { encryptDocumentPendingUpdate } from \"../../../data/documents/shared/crypto\";\nimport { containerPathRefs } from \"../../../data/documents/shared/projection\";\nimport type {\n DocumentCreateAuthor,\n MaterializedDocumentCreatePlan,\n} from \"../../../data/documents/shared/types\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport { signDocumentOutgoingUpdate } from \"../syncPlan/syncPlanIdentity\";\n\n/**\n * Builds the single encrypted initial write for a provisioned document. The\n * server commits it with the organization and document manifest transaction.\n */\nexport async function buildInitialDocumentSyncRequest(input: {\n readonly author: DocumentCreateAuthor;\n readonly containerProjection: ContainerWriterProjectionResponse;\n readonly initialUpdate: Uint8Array;\n readonly materializedDocument: MaterializedDocumentCreatePlan;\n}): Promise<DocumentSyncRequest> {\n const pendingFields = createPendingUpdateFields(input.initialUpdate);\n if (!pendingFields) {\n throw new Error(\"Initial document sync update is empty\");\n }\n return buildDocumentCreateSeedRequest({\n ...input,\n pendingUpdate: { id: crypto.randomUUID(), ...pendingFields },\n });\n}\n\n/**\n * Builds a create's seed: the one queued update that holds a new document's\n * whole content, signed against the create plan, so the create commits it and\n * no follow-up sync is needed. The update keeps its queue row id.\n */\nexport async function buildDocumentCreateSeedRequest(input: {\n readonly author: DocumentCreateAuthor;\n readonly containerProjection: ContainerWriterProjectionResponse;\n readonly materializedDocument: MaterializedDocumentCreatePlan;\n readonly pendingUpdate: PendingUpdateRecord;\n}): Promise<DocumentSyncRequest> {\n const { pendingUpdate } = input;\n const documentId = input.materializedDocument.plan.documentId;\n const contentKeyBundle =\n input.materializedDocument.plan.request.contentKeyBundle;\n const encrypted = await encryptDocumentPendingUpdate({\n contentKeyMaterial: await importContentKeyMaterial(\n input.materializedDocument.contentKey,\n ),\n contentKeyEpoch: contentKeyBundle.contentKeyEpoch,\n documentId,\n organizationId: input.containerProjection.organizationId,\n update: pendingUpdate,\n });\n const outgoingUpdate = await signDocumentOutgoingUpdate({\n authorizingContainerPathRefs: [\n containerPathRefs(input.containerProjection.path),\n ],\n author: input.author,\n contentKeyEpoch: contentKeyBundle.contentKeyEpoch,\n documentId,\n expectedLinkSetManifestHash: contentKeyBundle.linkSetManifestHash,\n expectedTargetHash: contentKeyBundle.targetHash,\n organizationId: input.containerProjection.organizationId,\n signedAt: new Date().toISOString(),\n update: {\n contentRecordId: encrypted.contentRecordId,\n encryptedData: encrypted.encryptedData,\n id: pendingUpdate.id,\n partialEndVersionVector: pendingUpdate.partialEndVersionVector,\n partialStartVersionVector: pendingUpdate.partialStartVersionVector,\n metadataHash: encrypted.metadataHash,\n ciphertextHash: encrypted.ciphertextHash,\n plaintextHash: encrypted.plaintextHash,\n },\n });\n\n return {\n authorizingContainerPathRefs: [\n containerPathRefs(input.containerProjection.path),\n ],\n contentKeyBundle,\n contentKeyEpoch: contentKeyBundle.contentKeyEpoch,\n expectedLinkSetManifestHash: contentKeyBundle.linkSetManifestHash,\n expectedTargetHash: contentKeyBundle.targetHash,\n // The creating device already holds this exact content, so it does not\n // need the transaction response to echo the update back.\n localVersionVector: pendingUpdate.partialEndVersionVector,\n outgoingUpdates: [outgoingUpdate],\n supportsPullPagination: true,\n };\n}\n\n/**\n * The queued row that may seed a create: the only row, a plain update (not a\n * rotation baseline) that holds the document's whole content. Anything else\n * syncs after the create as before.\n */\nexport function documentCreateSeedCandidate(input: {\n readonly documentVersion: string;\n readonly pendingUpdates: readonly PendingUpdateRecord[];\n}): PendingUpdateRecord | null {\n const [row, ...rest] = input.pendingUpdates;\n if (!row || rest.length > 0 || row.sourceVersionVector != null) return null;\n // The start may name peers at counter zero; the server checks it the same way.\n return satisfiesVersionVector(\n emptyVersionVector(),\n row.partialStartVersionVector,\n ) && versionVectorsEqual(row.partialEndVersionVector, input.documentVersion)\n ? row\n : null;\n}\n\nconst TEXT_ENCODER = new TextEncoder();\n\n/**\n * A seed is held to the sync request limit (the API refuses a larger one), so\n * a seed that does not fit is left out and the row syncs in ordinary batches.\n */\nexport function documentCreateSeedFits(seed: DocumentSyncRequest): boolean {\n return (\n TEXT_ENCODER.encode(JSON.stringify(seed)).byteLength <=\n MAX_DOCUMENT_SYNC_REQUEST_BYTES\n );\n}\n"]}
1
+ {"version":3,"file":"initialSync.js","sourceRoot":"","sources":["initialSync.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n emptyVersionVector,\n satisfiesVersionVector,\n versionVectorsEqual,\n} from \"@tearleads/loro\";\nimport type { DocumentSyncRequest } from \"@tearleads/validators/request\";\nimport type { ContainerWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport { MAX_DOCUMENT_SYNC_REQUEST_BYTES } from \"@tearleads/validators/util\";\nimport { createPendingUpdateFields } from \"../../../data/documents/documentSync\";\nimport { importContentKeyMaterial } from \"../../../data/documents/shared/contentRecordKeys\";\nimport { encryptDocumentPendingUpdate } from \"../../../data/documents/shared/crypto\";\nimport { containerPathRefs } from \"../../../data/documents/shared/projection\";\nimport type {\n DocumentCreateAuthor,\n MaterializedDocumentCreatePlan,\n} from \"../../../data/documents/shared/types\";\nimport type { PendingUpdateRecord } from \"../../../data/persistence/documents/records\";\nimport { signDocumentOutgoingUpdate } from \"../syncPlan/syncPlanIdentity\";\n\n/**\n * Builds the single encrypted initial write for a provisioned document. The\n * server commits it with the organization and document manifest transaction.\n */\nexport async function buildInitialDocumentSyncRequest(input: {\n readonly author: DocumentCreateAuthor;\n readonly containerProjection: ContainerWriterProjectionResponse;\n readonly initialUpdate: Uint8Array;\n readonly materializedDocument: MaterializedDocumentCreatePlan;\n}): Promise<DocumentSyncRequest> {\n const pendingFields = createPendingUpdateFields(input.initialUpdate);\n if (!pendingFields) {\n throw new Error(\"Initial document sync update is empty\");\n }\n return buildDocumentCreateSeedRequest({\n ...input,\n pendingUpdate: { id: crypto.randomUUID(), ...pendingFields },\n });\n}\n\n/**\n * Builds a create's seed: the one queued update that holds a new document's\n * whole content, signed against the create plan, so the create commits it and\n * no follow-up sync is needed. The update keeps its queue row id.\n */\nexport async function buildDocumentCreateSeedRequest(input: {\n readonly author: DocumentCreateAuthor;\n readonly containerProjection: ContainerWriterProjectionResponse;\n readonly materializedDocument: MaterializedDocumentCreatePlan;\n readonly pendingUpdate: PendingUpdateRecord;\n}): Promise<DocumentSyncRequest> {\n const { pendingUpdate } = input;\n const documentId = input.materializedDocument.plan.documentId;\n const contentKeyBundle =\n input.materializedDocument.plan.request.contentKeyBundle;\n const encrypted = await encryptDocumentPendingUpdate({\n contentKeyMaterial: await importContentKeyMaterial(\n input.materializedDocument.contentKey,\n ),\n contentKeyEpoch: contentKeyBundle.contentKeyEpoch,\n documentId,\n organizationId: input.containerProjection.organizationId,\n update: pendingUpdate,\n });\n const outgoingUpdate = await signDocumentOutgoingUpdate({\n authorizingContainerPathRefs: [\n containerPathRefs(input.containerProjection.path),\n ],\n author: input.author,\n contentKeyEpoch: contentKeyBundle.contentKeyEpoch,\n documentId,\n expectedLinkSetManifestHash: contentKeyBundle.linkSetManifestHash,\n expectedTargetHash: contentKeyBundle.targetHash,\n organizationId: input.containerProjection.organizationId,\n signedAt: new Date().toISOString(),\n update: {\n contentRecordId: encrypted.contentRecordId,\n encryptedData: encrypted.encryptedData,\n id: pendingUpdate.id,\n partialEndVersionVector: pendingUpdate.partialEndVersionVector,\n partialStartVersionVector: pendingUpdate.partialStartVersionVector,\n metadataHash: encrypted.metadataHash,\n ciphertextHash: encrypted.ciphertextHash,\n plaintextHash: encrypted.plaintextHash,\n },\n });\n\n return {\n authorizingContainerPathRefs: [\n containerPathRefs(input.containerProjection.path),\n ],\n contentKeyBundle,\n contentKeyEpoch: contentKeyBundle.contentKeyEpoch,\n expectedLinkSetManifestHash: contentKeyBundle.linkSetManifestHash,\n expectedTargetHash: contentKeyBundle.targetHash,\n // The creating device already holds this exact content, so it does not\n // need the transaction response to echo the update back.\n localVersionVector: pendingUpdate.partialEndVersionVector,\n outgoingUpdates: [outgoingUpdate],\n supportsPullPagination: true,\n };\n}\n\n/**\n * The queued row that may seed a create: the only row, a plain update (not a\n * rotation baseline) that holds the document's whole content. Anything else\n * syncs after the create as before.\n */\nexport function documentCreateSeedCandidate(input: {\n readonly documentVersion: string;\n readonly pendingUpdates: readonly PendingUpdateRecord[];\n}): PendingUpdateRecord | null {\n const [row, ...rest] = input.pendingUpdates;\n if (!row || rest.length > 0 || row.sourceVersionVector != null) return null;\n // The start may name peers at counter zero; the server checks it the same way.\n return satisfiesVersionVector(\n emptyVersionVector(),\n row.partialStartVersionVector,\n ) && versionVectorsEqual(row.partialEndVersionVector, input.documentVersion)\n ? row\n : null;\n}\n\nconst TEXT_ENCODER = new TextEncoder();\n\n/**\n * A seed is held to the sync request limit (the API refuses a larger one), so\n * a seed that does not fit is left out and the row syncs in ordinary batches.\n */\nexport function documentCreateSeedFits(seed: DocumentSyncRequest): boolean {\n return (\n TEXT_ENCODER.encode(JSON.stringify(seed)).byteLength <=\n MAX_DOCUMENT_SYNC_REQUEST_BYTES\n );\n}\n"]}
@@ -3,7 +3,7 @@ import type { DocumentSyncUpdateIsolationError, IncomingDocumentSyncUpdateValida
3
3
  import { type DocumentSyncPullContinuation } from "../../../data/documents/shared/sync/syncPagination.js";
4
4
  import type { DocumentCreateAuthor, DocumentSyncApi, DocumentWriterPublicKeyResolver, PersistedDocumentSyncState, SyncRemoteDocumentResult } from "../../../data/documents/shared/types.js";
5
5
  import type { ProjectionUserKeyResolver, ReferencedPrincipalPolicyWarmer } from "../../../data/keyingProjectionVerification/index.js";
6
- import type { PendingUpdateRecord } from "../../../data/sqlite/documentPersistence/index.js";
6
+ import type { PendingUpdateRecord } from "../../../data/persistence/documents/records/index.js";
7
7
  import type { ExecSql } from "../../../data/sqlite/sqlSchema.js";
8
8
  import { type RemoteDocumentDeletionHandler, type TerminalSubmitFailureHandler } from "../syncFailures/syncFailureClassification.js";
9
9
  import type { RekeyPendingUpdate } from "../syncRekeys/syncRecoveryRekey.js";
@@ -1 +1 @@
1
- {"version":3,"file":"readOnlySync.js","sourceRoot":"","sources":["readOnlySync.ts"],"names":[],"mappings":"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","sourcesContent":["import type {\n DocumentCreateResponse,\n DocumentSyncResponse,\n DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport {\n isAccessManifestBundleWireResponse,\n isDocumentContentKeyBundleResponse,\n isDocumentKekTargetsResponse,\n} from \"@tearleads/validators/response\";\nimport {\n isRetryableDocumentSyncConflict,\n persistedDocumentSyncStateFromResponse,\n submitDocumentSync,\n} from \"../../../data/documents/shared/responses\";\nimport { limitDocumentSyncRequestBytes } from \"../../../data/documents/shared/sync/documentSyncOutgoingBatch\";\nimport type {\n DocumentSyncUpdateIsolationError,\n IncomingDocumentSyncUpdateValidator,\n} from \"../../../data/documents/shared/sync/documentSyncUpdateIsolation\";\nimport {\n type DocumentSyncPullContinuation,\n resolvePullContinuationMinLsn,\n} from \"../../../data/documents/shared/sync/syncPagination\";\nimport type {\n DocumentCreateAuthor,\n DocumentSyncApi,\n DocumentSyncPlan,\n DocumentWriterPublicKeyResolver,\n PersistedDocumentSyncState,\n SyncRemoteDocumentResult,\n} from \"../../../data/documents/shared/types\";\nimport { projectionVerificationOptions } from \"../../../data/documents/shared/types\";\nimport { readCanonicalRecord } from \"../../../data/keying/canonicalJson\";\nimport type {\n ProjectionUserKeyResolver,\n ReferencedPrincipalPolicyWarmer,\n} from \"../../../data/keyingProjectionVerification\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport type { ExecSql } from \"../../../data/sqlite/sqlSchema\";\nimport {\n assertRawContinuationCanRetry,\n refreshSyncAttemptWriterProjection,\n resolveSyncAttemptWriterProjection,\n} from \"../syncFailures\";\nimport {\n handleUpstreamDeletedDocumentSyncFailure,\n projectionIntegrityErrorCode,\n type RemoteDocumentDeletionHandler,\n type TerminalSubmitFailureHandler,\n} from \"../syncFailures/syncFailureClassification\";\nimport { DocumentRawHistoryUnavailableError } from \"../syncPlan/syncContentKeys\";\nimport { buildDocumentSyncPlan } from \"../syncPlan/syncPlanIdentity\";\nimport { buildMaterializedDocumentSyncPlan } from \"../syncPlan/syncPlanMaterial\";\nimport type { RekeyPendingUpdate } from \"../syncRekeys/syncRecoveryRekey\";\nimport {\n handleReadOnlyProjectionCompletionError,\n REFRESH_CACHED_PROJECTION,\n} from \"./readOnlyProjectionFailure\";\nimport type { DocumentSyncContainerRekeyBuilder } from \"./syncAttemptState\";\nimport { syncRemoteDocumentResultFromResponse } from \"./syncResponseResult\";\nimport { type DocumentSyncTraceEmitter, traceSubmitFailed } from \"./syncTrace\";\n\nasync function completeReadOnlyRemoteDocumentSyncWithProjection(\n input: Omit<ReadOnlyDocumentSyncCompletionInput, \"writerProjection\"> & {\n writerProjection: DocumentWriterProjectionResponse;\n },\n): Promise<SyncRemoteDocumentResult> {\n const materializedPlan = await buildMaterializedDocumentSyncPlan({\n author: input.author,\n execSql: input.execSql,\n historyMode: input.historyMode,\n localVersionVector: input.localVersionVector,\n minLsn: resolvePullContinuationMinLsn(input.pullContinuation, input.minLsn),\n pullCursor: input.pullContinuation?.cursor,\n onSyncTrace: input.onSyncTrace,\n pendingUpdates: [],\n signedAt: input.signedAt,\n targetSecretKey: input.targetSecretKey,\n writerProjection: input.writerProjection,\n ...projectionVerificationOptions(input),\n });\n\n const result = await syncRemoteDocumentResultFromResponse({\n ...projectionVerificationOptions(input),\n execSql: input.execSql,\n materializedPlan,\n recoveryPendingUpdatesById: new Map(),\n resolveWriterPublicKey: input.resolveWriterPublicKey,\n response: input.response,\n targetSecretKey: input.targetSecretKey,\n validateIncomingUpdates: input.validateIncomingUpdates,\n writerProjection: input.writerProjection,\n resolveProjectionUserKey: input.resolveProjectionUserKey,\n });\n return {\n ...result,\n hasIncompletePull: !input.pullComplete,\n };\n}\n\nfunction parsePersistedDocumentSyncRecord<T>(\n value: string | null | undefined,\n label: string,\n isRecord: (value: unknown) => value is T,\n): T | null {\n if (!value) {\n return null;\n }\n\n try {\n const record = readCanonicalRecord(JSON.parse(value), label);\n return isRecord(record) ? record : null;\n } catch {\n return null;\n }\n}\n\nfunction parsePersistedDocumentSyncState(\n persistedState: PersistedDocumentSyncState | null | undefined,\n documentId: string,\n): {\n contentKeyBundle: DocumentCreateResponse[\"contentKeyBundle\"];\n documentKekTargets: DocumentSyncResponse[\"documentKekTargets\"];\n documentManifest: DocumentCreateResponse[\"accessManifest\"];\n} | null {\n if (persistedState?.documentId !== documentId) {\n return null;\n }\n\n const contentKeyBundle = parsePersistedDocumentSyncRecord(\n persistedState.contentKeyBundle,\n \"Persisted document sync content-key bundle\",\n isDocumentContentKeyBundleResponse,\n );\n const documentKekTargets = parsePersistedDocumentSyncRecord(\n persistedState.documentKekTargets,\n \"Persisted document sync KEK targets\",\n isDocumentKekTargetsResponse,\n );\n const documentManifest = parsePersistedDocumentSyncRecord(\n persistedState.documentManifestBundle,\n \"Persisted document sync manifest\",\n isAccessManifestBundleWireResponse,\n );\n\n if (!contentKeyBundle || !documentKekTargets || !documentManifest) {\n return null;\n }\n\n return {\n contentKeyBundle,\n documentKekTargets,\n documentManifest,\n };\n}\n\nasync function buildReadOnlyDocumentSyncPlanFromPersistedState(input: {\n author: DocumentCreateAuthor;\n documentId: string;\n historyMode?: \"raw\" | undefined;\n localVersionVector: string | null;\n minLsn?: string | undefined;\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n persistedState?: PersistedDocumentSyncState | null | undefined;\n signedAt?: string | undefined;\n}): Promise<DocumentSyncPlan | null> {\n const persisted = parsePersistedDocumentSyncState(\n input.persistedState,\n input.documentId,\n );\n if (!persisted) {\n return null;\n }\n\n const plan = await buildDocumentSyncPlan({\n author: input.author,\n contentKeyBundle: persisted.contentKeyBundle,\n documentId: input.documentId,\n documentKekTargets: persisted.documentKekTargets,\n documentManifest: persisted.documentManifest,\n historyMode: input.historyMode,\n localVersionVector: input.localVersionVector,\n minLsn: resolvePullContinuationMinLsn(input.pullContinuation, input.minLsn),\n outgoingUpdates: [],\n pullCursor: input.pullContinuation?.cursor,\n signedAt: input.signedAt,\n });\n const request = limitDocumentSyncRequestBytes(plan.request);\n return request === plan.request ? plan : { ...plan, request };\n}\n\ntype PersistedReadOnlyDocumentSyncResult =\n | {\n kind: \"completed\";\n result: SyncRemoteDocumentResult | null;\n }\n | {\n kind: \"not_completed\";\n };\n\ninterface ReadOnlyDocumentSyncCompletionInput {\n apiClient: DocumentSyncApi;\n author: DocumentCreateAuthor;\n documentId: string;\n execSql: ExecSql;\n historyMode?: \"raw\" | undefined;\n localVersionVector: string | null;\n minLsn?: string | undefined;\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n onReadOnlyProjectionFailure?: TerminalSubmitFailureHandler | undefined;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n pullComplete: boolean;\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n resolveWriterPublicKey: DocumentWriterPublicKeyResolver;\n response: DocumentSyncResponse;\n signedAt?: string | undefined;\n stillCurrent?: (() => boolean) | undefined;\n targetSecretKey: Uint8Array;\n validateIncomingUpdates: IncomingDocumentSyncUpdateValidator;\n warmReferencedPrincipalPolicies?: ReferencedPrincipalPolicyWarmer | undefined;\n writerProjection?: DocumentWriterProjectionResponse | undefined;\n}\n\nasync function tryCompleteReadOnlyRemoteDocumentSyncWithProjection(input: {\n allowCachedProjectionRefresh: boolean;\n completion: ReadOnlyDocumentSyncCompletionInput;\n writerProjection: DocumentWriterProjectionResponse;\n}): Promise<\n | DocumentRawHistoryUnavailableError\n | SyncRemoteDocumentResult\n | null\n | typeof REFRESH_CACHED_PROJECTION\n> {\n try {\n return await completeReadOnlyRemoteDocumentSyncWithProjection({\n ...input.completion,\n writerProjection: input.writerProjection,\n });\n } catch (error) {\n return handleReadOnlyProjectionCompletionError(error, {\n allowCachedProjectionRefresh: input.allowCachedProjectionRefresh,\n historyMode: input.completion.historyMode,\n });\n }\n}\nasync function completeReadOnlyRemoteDocumentSyncWithUpdates(\n input: ReadOnlyDocumentSyncCompletionInput,\n): Promise<PersistedReadOnlyDocumentSyncResult> {\n const reusableWriterProjection =\n input.writerProjection?.documentId === input.documentId\n ? input.writerProjection\n : null;\n const writerProjection =\n reusableWriterProjection ??\n (await resolveSyncAttemptWriterProjection({\n apiClient: input.apiClient,\n documentId: input.documentId,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n onSyncTrace: input.onSyncTrace,\n onTerminalFailure: input.onReadOnlyProjectionFailure,\n reusableWriterProjection: null,\n stillCurrent: input.stillCurrent,\n }));\n if (!writerProjection) {\n return { kind: \"completed\", result: null };\n }\n const canRefreshProjection =\n input.historyMode === \"raw\" || Boolean(reusableWriterProjection);\n let result:\n | DocumentRawHistoryUnavailableError\n | SyncRemoteDocumentResult\n | null\n | typeof REFRESH_CACHED_PROJECTION = null;\n let retryAfterRollback = false;\n try {\n result = await tryCompleteReadOnlyRemoteDocumentSyncWithProjection({\n allowCachedProjectionRefresh: canRefreshProjection,\n completion: input,\n writerProjection,\n });\n } catch (error) {\n if (projectionIntegrityErrorCode(error) !== \"rollback\") {\n throw error;\n }\n retryAfterRollback = true;\n }\n if (\n !retryAfterRollback &&\n result !== REFRESH_CACHED_PROJECTION &&\n !(result instanceof DocumentRawHistoryUnavailableError) &&\n (result || !reusableWriterProjection)\n ) {\n return { kind: \"completed\", result };\n }\n const freshWriterProjection = await refreshSyncAttemptWriterProjection({\n apiClient: input.apiClient,\n documentId: input.documentId,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n onSyncTrace: input.onSyncTrace,\n onTerminalFailure: input.onReadOnlyProjectionFailure,\n stillCurrent: input.stillCurrent,\n unavailableError:\n result instanceof DocumentRawHistoryUnavailableError ? result : undefined,\n });\n if (!freshWriterProjection) {\n return { kind: \"completed\", result: null };\n }\n const freshResult = await tryCompleteReadOnlyRemoteDocumentSyncWithProjection(\n {\n allowCachedProjectionRefresh: false,\n completion: input,\n writerProjection: freshWriterProjection,\n },\n );\n if (\n freshResult === REFRESH_CACHED_PROJECTION ||\n freshResult instanceof DocumentRawHistoryUnavailableError\n ) {\n throw new Error(\"Fresh document projection unexpectedly requested refresh\");\n }\n return freshResult\n ? { kind: \"completed\", result: freshResult }\n : { kind: \"not_completed\" };\n}\nasync function syncReadOnlyRemoteDocumentFromPersistedState(\n input: Omit<\n ReadOnlyDocumentSyncCompletionInput,\n \"pullComplete\" | \"response\"\n > & {\n persistedState?: PersistedDocumentSyncState | null | undefined;\n },\n): Promise<PersistedReadOnlyDocumentSyncResult> {\n let plan: DocumentSyncPlan | null;\n try {\n plan = await buildReadOnlyDocumentSyncPlanFromPersistedState(input);\n } catch {\n plan = null;\n }\n if (!plan) {\n return { kind: \"not_completed\" };\n }\n if (input.stillCurrent?.() === false) {\n return { kind: \"completed\", result: null };\n }\n const submitted = await submitDocumentSync({\n apiClient: input.apiClient,\n expectedCommitLsnMode: input.pullContinuation?.commitLsnMode,\n plan,\n });\n if (input.stillCurrent?.() === false) {\n return { kind: \"completed\", result: null };\n }\n if (!submitted) {\n return { kind: \"completed\", result: null };\n }\n if (!submitted.ok) {\n if (\n await handleUpstreamDeletedDocumentSyncFailure({\n documentId: input.documentId,\n failure: submitted,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n })\n ) {\n return { kind: \"completed\", result: null };\n }\n\n if (isRetryableDocumentSyncConflict(submitted)) {\n traceSubmitFailed(input.onSyncTrace, {\n action: \"retry\",\n code: submitted.code,\n documentId: input.documentId,\n status: submitted.status,\n });\n assertRawContinuationCanRetry(input.historyMode, input.pullContinuation);\n return { kind: \"not_completed\" };\n }\n\n traceSubmitFailed(input.onSyncTrace, {\n action: \"stop\",\n code: submitted.code,\n documentId: input.documentId,\n status: submitted.status,\n });\n submitted.report();\n return { kind: \"completed\", result: null };\n }\n\n if (submitted.response.updates.length > 0) {\n return completeReadOnlyRemoteDocumentSyncWithUpdates({\n ...input,\n pullComplete: submitted.pullComplete,\n response: submitted.response,\n });\n }\n\n try {\n const persistedState = await persistedDocumentSyncStateFromResponse(\n plan,\n submitted.response,\n { resolveWriterPublicKey: input.resolveWriterPublicKey },\n );\n\n return {\n kind: \"completed\",\n result: {\n contentKey: new Uint8Array(),\n decryptedUpdates: [],\n exhaustedPendingUpdateCount: 0,\n hasDeferredPendingUpdates: false,\n hasIncompletePull: !submitted.pullComplete,\n persistedState,\n plan,\n rekeyedPendingUpdateIds: [],\n response: submitted.response,\n settledPendingUpdateIds: [],\n acceptedRecoveryBaseline: false,\n },\n };\n } catch (error) {\n if (input.historyMode === \"raw\") {\n throw error;\n }\n return { kind: \"not_completed\" };\n }\n}\n\nexport interface SyncRemoteDocumentInput {\n apiClient: DocumentSyncApi;\n author: DocumentCreateAuthor;\n /**\n * Supplies a full-history Loro snapshot of the local document so a\n * write-bearing pass can heal a stale content-key bundle by rotating to a\n * fresh content key anchored by a rotation baseline.\n */\n buildRotationSnapshot?: (() => Promise<Uint8Array | null>) | undefined;\n /** Overrides automatic ancestor repair for each submission's current projection. */\n buildContainerRekeys?: DocumentSyncContainerRekeyBuilder;\n documentId: string;\n execSql: ExecSql;\n /** Explicit read-only recovery that bypasses rotation-baseline redirect. */\n historyMode?: \"raw\" | undefined;\n isRemoteSyncBlocked?: ((organizationId: string) => boolean) | undefined;\n localVersionVector: string | null;\n minLsn?: string | undefined;\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n /** Atomically commits the verified purge proof with matching local teardown. */\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncAbandoned?: ((reason: string) => void) | undefined;\n /** Clipboard-safe trace sink (see syncTrace.ts); never receives content. */\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n /**\n * Fires when a pass WITHOUT queued writes cannot resolve its writer\n * projection (e.g. a coded 409 from the projection route). Read-only\n * revalidation otherwise fails silently — one burned request and a trace\n * line — leaving the document permanently stale with nothing durable to\n * explain why (edge-case row 13).\n */\n onReadOnlyProjectionFailure?: TerminalSubmitFailureHandler | undefined;\n /** Records a verified response update that could not be decrypted/imported. */\n onIncomingUpdateIsolationFailure?:\n | ((failure: DocumentSyncUpdateIsolationError) => void | Promise<void>)\n | undefined;\n /** Fires immediately before a materialized outgoing batch is submitted. */\n onOutgoingUpdatesMaterialized?:\n | ((updateIds: readonly string[]) => void)\n | undefined;\n /** Invalidates continuation state after the server rejects its snapshot. */\n onPullContinuationInvalidated?:\n | ((continuation: DocumentSyncPullContinuation) => void | Promise<void>)\n | undefined;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n pendingUpdates?: readonly PendingUpdateRecord[] | undefined;\n persistedState?: PersistedDocumentSyncState | null | undefined;\n rekeyPendingUpdate?: RekeyPendingUpdate | undefined;\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n resolveWriterPublicKey: DocumentWriterPublicKeyResolver;\n signedAt?: string | undefined;\n stillCurrent?: (() => boolean) | undefined;\n targetSecretKey: Uint8Array;\n /** Validates decrypted updates against scratch state before callers persist. */\n validateIncomingUpdates: IncomingDocumentSyncUpdateValidator;\n warmReferencedPrincipalPolicies?: ReferencedPrincipalPolicyWarmer | undefined;\n writerProjection?: DocumentWriterProjectionResponse | undefined;\n}\n\nexport async function tryPersistedReadOnlyDocumentSync(\n input: SyncRemoteDocumentInput,\n resolveProjectionUserKey: ProjectionUserKeyResolver,\n): Promise<PersistedReadOnlyDocumentSyncResult | null> {\n if (input.stillCurrent?.() === false) return null;\n if ((input.pendingUpdates ?? []).length > 0) return null;\n\n return syncReadOnlyRemoteDocumentFromPersistedState({\n ...input,\n resolveProjectionUserKey,\n });\n}\n"]}
1
+ {"version":3,"file":"readOnlySync.js","sourceRoot":"","sources":["readOnlySync.ts"],"names":[],"mappings":"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","sourcesContent":["import type {\n DocumentCreateResponse,\n DocumentSyncResponse,\n DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport {\n isAccessManifestBundleWireResponse,\n isDocumentContentKeyBundleResponse,\n isDocumentKekTargetsResponse,\n} from \"@tearleads/validators/response\";\nimport {\n isRetryableDocumentSyncConflict,\n persistedDocumentSyncStateFromResponse,\n submitDocumentSync,\n} from \"../../../data/documents/shared/responses\";\nimport { limitDocumentSyncRequestBytes } from \"../../../data/documents/shared/sync/documentSyncOutgoingBatch\";\nimport type {\n DocumentSyncUpdateIsolationError,\n IncomingDocumentSyncUpdateValidator,\n} from \"../../../data/documents/shared/sync/documentSyncUpdateIsolation\";\nimport {\n type DocumentSyncPullContinuation,\n resolvePullContinuationMinLsn,\n} from \"../../../data/documents/shared/sync/syncPagination\";\nimport type {\n DocumentCreateAuthor,\n DocumentSyncApi,\n DocumentSyncPlan,\n DocumentWriterPublicKeyResolver,\n PersistedDocumentSyncState,\n SyncRemoteDocumentResult,\n} from \"../../../data/documents/shared/types\";\nimport { projectionVerificationOptions } from \"../../../data/documents/shared/types\";\nimport { readCanonicalRecord } from \"../../../data/keying/canonicalJson\";\nimport type {\n ProjectionUserKeyResolver,\n ReferencedPrincipalPolicyWarmer,\n} from \"../../../data/keyingProjectionVerification\";\nimport type { PendingUpdateRecord } from \"../../../data/persistence/documents/records\";\nimport type { ExecSql } from \"../../../data/sqlite/sqlSchema\";\nimport {\n assertRawContinuationCanRetry,\n refreshSyncAttemptWriterProjection,\n resolveSyncAttemptWriterProjection,\n} from \"../syncFailures\";\nimport {\n handleUpstreamDeletedDocumentSyncFailure,\n projectionIntegrityErrorCode,\n type RemoteDocumentDeletionHandler,\n type TerminalSubmitFailureHandler,\n} from \"../syncFailures/syncFailureClassification\";\nimport { DocumentRawHistoryUnavailableError } from \"../syncPlan/syncContentKeys\";\nimport { buildDocumentSyncPlan } from \"../syncPlan/syncPlanIdentity\";\nimport { buildMaterializedDocumentSyncPlan } from \"../syncPlan/syncPlanMaterial\";\nimport type { RekeyPendingUpdate } from \"../syncRekeys/syncRecoveryRekey\";\nimport {\n handleReadOnlyProjectionCompletionError,\n REFRESH_CACHED_PROJECTION,\n} from \"./readOnlyProjectionFailure\";\nimport type { DocumentSyncContainerRekeyBuilder } from \"./syncAttemptState\";\nimport { syncRemoteDocumentResultFromResponse } from \"./syncResponseResult\";\nimport { type DocumentSyncTraceEmitter, traceSubmitFailed } from \"./syncTrace\";\n\nasync function completeReadOnlyRemoteDocumentSyncWithProjection(\n input: Omit<ReadOnlyDocumentSyncCompletionInput, \"writerProjection\"> & {\n writerProjection: DocumentWriterProjectionResponse;\n },\n): Promise<SyncRemoteDocumentResult> {\n const materializedPlan = await buildMaterializedDocumentSyncPlan({\n author: input.author,\n execSql: input.execSql,\n historyMode: input.historyMode,\n localVersionVector: input.localVersionVector,\n minLsn: resolvePullContinuationMinLsn(input.pullContinuation, input.minLsn),\n pullCursor: input.pullContinuation?.cursor,\n onSyncTrace: input.onSyncTrace,\n pendingUpdates: [],\n signedAt: input.signedAt,\n targetSecretKey: input.targetSecretKey,\n writerProjection: input.writerProjection,\n ...projectionVerificationOptions(input),\n });\n\n const result = await syncRemoteDocumentResultFromResponse({\n ...projectionVerificationOptions(input),\n execSql: input.execSql,\n materializedPlan,\n recoveryPendingUpdatesById: new Map(),\n resolveWriterPublicKey: input.resolveWriterPublicKey,\n response: input.response,\n targetSecretKey: input.targetSecretKey,\n validateIncomingUpdates: input.validateIncomingUpdates,\n writerProjection: input.writerProjection,\n resolveProjectionUserKey: input.resolveProjectionUserKey,\n });\n return {\n ...result,\n hasIncompletePull: !input.pullComplete,\n };\n}\n\nfunction parsePersistedDocumentSyncRecord<T>(\n value: string | null | undefined,\n label: string,\n isRecord: (value: unknown) => value is T,\n): T | null {\n if (!value) {\n return null;\n }\n\n try {\n const record = readCanonicalRecord(JSON.parse(value), label);\n return isRecord(record) ? record : null;\n } catch {\n return null;\n }\n}\n\nfunction parsePersistedDocumentSyncState(\n persistedState: PersistedDocumentSyncState | null | undefined,\n documentId: string,\n): {\n contentKeyBundle: DocumentCreateResponse[\"contentKeyBundle\"];\n documentKekTargets: DocumentSyncResponse[\"documentKekTargets\"];\n documentManifest: DocumentCreateResponse[\"accessManifest\"];\n} | null {\n if (persistedState?.documentId !== documentId) {\n return null;\n }\n\n const contentKeyBundle = parsePersistedDocumentSyncRecord(\n persistedState.contentKeyBundle,\n \"Persisted document sync content-key bundle\",\n isDocumentContentKeyBundleResponse,\n );\n const documentKekTargets = parsePersistedDocumentSyncRecord(\n persistedState.documentKekTargets,\n \"Persisted document sync KEK targets\",\n isDocumentKekTargetsResponse,\n );\n const documentManifest = parsePersistedDocumentSyncRecord(\n persistedState.documentManifestBundle,\n \"Persisted document sync manifest\",\n isAccessManifestBundleWireResponse,\n );\n\n if (!contentKeyBundle || !documentKekTargets || !documentManifest) {\n return null;\n }\n\n return {\n contentKeyBundle,\n documentKekTargets,\n documentManifest,\n };\n}\n\nasync function buildReadOnlyDocumentSyncPlanFromPersistedState(input: {\n author: DocumentCreateAuthor;\n documentId: string;\n historyMode?: \"raw\" | undefined;\n localVersionVector: string | null;\n minLsn?: string | undefined;\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n persistedState?: PersistedDocumentSyncState | null | undefined;\n signedAt?: string | undefined;\n}): Promise<DocumentSyncPlan | null> {\n const persisted = parsePersistedDocumentSyncState(\n input.persistedState,\n input.documentId,\n );\n if (!persisted) {\n return null;\n }\n\n const plan = await buildDocumentSyncPlan({\n author: input.author,\n contentKeyBundle: persisted.contentKeyBundle,\n documentId: input.documentId,\n documentKekTargets: persisted.documentKekTargets,\n documentManifest: persisted.documentManifest,\n historyMode: input.historyMode,\n localVersionVector: input.localVersionVector,\n minLsn: resolvePullContinuationMinLsn(input.pullContinuation, input.minLsn),\n outgoingUpdates: [],\n pullCursor: input.pullContinuation?.cursor,\n signedAt: input.signedAt,\n });\n const request = limitDocumentSyncRequestBytes(plan.request);\n return request === plan.request ? plan : { ...plan, request };\n}\n\ntype PersistedReadOnlyDocumentSyncResult =\n | {\n kind: \"completed\";\n result: SyncRemoteDocumentResult | null;\n }\n | {\n kind: \"not_completed\";\n };\n\ninterface ReadOnlyDocumentSyncCompletionInput {\n apiClient: DocumentSyncApi;\n author: DocumentCreateAuthor;\n documentId: string;\n execSql: ExecSql;\n historyMode?: \"raw\" | undefined;\n localVersionVector: string | null;\n minLsn?: string | undefined;\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n onReadOnlyProjectionFailure?: TerminalSubmitFailureHandler | undefined;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n pullComplete: boolean;\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n resolveWriterPublicKey: DocumentWriterPublicKeyResolver;\n response: DocumentSyncResponse;\n signedAt?: string | undefined;\n stillCurrent?: (() => boolean) | undefined;\n targetSecretKey: Uint8Array;\n validateIncomingUpdates: IncomingDocumentSyncUpdateValidator;\n warmReferencedPrincipalPolicies?: ReferencedPrincipalPolicyWarmer | undefined;\n writerProjection?: DocumentWriterProjectionResponse | undefined;\n}\n\nasync function tryCompleteReadOnlyRemoteDocumentSyncWithProjection(input: {\n allowCachedProjectionRefresh: boolean;\n completion: ReadOnlyDocumentSyncCompletionInput;\n writerProjection: DocumentWriterProjectionResponse;\n}): Promise<\n | DocumentRawHistoryUnavailableError\n | SyncRemoteDocumentResult\n | null\n | typeof REFRESH_CACHED_PROJECTION\n> {\n try {\n return await completeReadOnlyRemoteDocumentSyncWithProjection({\n ...input.completion,\n writerProjection: input.writerProjection,\n });\n } catch (error) {\n return handleReadOnlyProjectionCompletionError(error, {\n allowCachedProjectionRefresh: input.allowCachedProjectionRefresh,\n historyMode: input.completion.historyMode,\n });\n }\n}\nasync function completeReadOnlyRemoteDocumentSyncWithUpdates(\n input: ReadOnlyDocumentSyncCompletionInput,\n): Promise<PersistedReadOnlyDocumentSyncResult> {\n const reusableWriterProjection =\n input.writerProjection?.documentId === input.documentId\n ? input.writerProjection\n : null;\n const writerProjection =\n reusableWriterProjection ??\n (await resolveSyncAttemptWriterProjection({\n apiClient: input.apiClient,\n documentId: input.documentId,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n onSyncTrace: input.onSyncTrace,\n onTerminalFailure: input.onReadOnlyProjectionFailure,\n reusableWriterProjection: null,\n stillCurrent: input.stillCurrent,\n }));\n if (!writerProjection) {\n return { kind: \"completed\", result: null };\n }\n const canRefreshProjection =\n input.historyMode === \"raw\" || Boolean(reusableWriterProjection);\n let result:\n | DocumentRawHistoryUnavailableError\n | SyncRemoteDocumentResult\n | null\n | typeof REFRESH_CACHED_PROJECTION = null;\n let retryAfterRollback = false;\n try {\n result = await tryCompleteReadOnlyRemoteDocumentSyncWithProjection({\n allowCachedProjectionRefresh: canRefreshProjection,\n completion: input,\n writerProjection,\n });\n } catch (error) {\n if (projectionIntegrityErrorCode(error) !== \"rollback\") {\n throw error;\n }\n retryAfterRollback = true;\n }\n if (\n !retryAfterRollback &&\n result !== REFRESH_CACHED_PROJECTION &&\n !(result instanceof DocumentRawHistoryUnavailableError) &&\n (result || !reusableWriterProjection)\n ) {\n return { kind: \"completed\", result };\n }\n const freshWriterProjection = await refreshSyncAttemptWriterProjection({\n apiClient: input.apiClient,\n documentId: input.documentId,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n onSyncTrace: input.onSyncTrace,\n onTerminalFailure: input.onReadOnlyProjectionFailure,\n stillCurrent: input.stillCurrent,\n unavailableError:\n result instanceof DocumentRawHistoryUnavailableError ? result : undefined,\n });\n if (!freshWriterProjection) {\n return { kind: \"completed\", result: null };\n }\n const freshResult = await tryCompleteReadOnlyRemoteDocumentSyncWithProjection(\n {\n allowCachedProjectionRefresh: false,\n completion: input,\n writerProjection: freshWriterProjection,\n },\n );\n if (\n freshResult === REFRESH_CACHED_PROJECTION ||\n freshResult instanceof DocumentRawHistoryUnavailableError\n ) {\n throw new Error(\"Fresh document projection unexpectedly requested refresh\");\n }\n return freshResult\n ? { kind: \"completed\", result: freshResult }\n : { kind: \"not_completed\" };\n}\nasync function syncReadOnlyRemoteDocumentFromPersistedState(\n input: Omit<\n ReadOnlyDocumentSyncCompletionInput,\n \"pullComplete\" | \"response\"\n > & {\n persistedState?: PersistedDocumentSyncState | null | undefined;\n },\n): Promise<PersistedReadOnlyDocumentSyncResult> {\n let plan: DocumentSyncPlan | null;\n try {\n plan = await buildReadOnlyDocumentSyncPlanFromPersistedState(input);\n } catch {\n plan = null;\n }\n if (!plan) {\n return { kind: \"not_completed\" };\n }\n if (input.stillCurrent?.() === false) {\n return { kind: \"completed\", result: null };\n }\n const submitted = await submitDocumentSync({\n apiClient: input.apiClient,\n expectedCommitLsnMode: input.pullContinuation?.commitLsnMode,\n plan,\n });\n if (input.stillCurrent?.() === false) {\n return { kind: \"completed\", result: null };\n }\n if (!submitted) {\n return { kind: \"completed\", result: null };\n }\n if (!submitted.ok) {\n if (\n await handleUpstreamDeletedDocumentSyncFailure({\n documentId: input.documentId,\n failure: submitted,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n })\n ) {\n return { kind: \"completed\", result: null };\n }\n\n if (isRetryableDocumentSyncConflict(submitted)) {\n traceSubmitFailed(input.onSyncTrace, {\n action: \"retry\",\n code: submitted.code,\n documentId: input.documentId,\n status: submitted.status,\n });\n assertRawContinuationCanRetry(input.historyMode, input.pullContinuation);\n return { kind: \"not_completed\" };\n }\n\n traceSubmitFailed(input.onSyncTrace, {\n action: \"stop\",\n code: submitted.code,\n documentId: input.documentId,\n status: submitted.status,\n });\n submitted.report();\n return { kind: \"completed\", result: null };\n }\n\n if (submitted.response.updates.length > 0) {\n return completeReadOnlyRemoteDocumentSyncWithUpdates({\n ...input,\n pullComplete: submitted.pullComplete,\n response: submitted.response,\n });\n }\n\n try {\n const persistedState = await persistedDocumentSyncStateFromResponse(\n plan,\n submitted.response,\n { resolveWriterPublicKey: input.resolveWriterPublicKey },\n );\n\n return {\n kind: \"completed\",\n result: {\n contentKey: new Uint8Array(),\n decryptedUpdates: [],\n exhaustedPendingUpdateCount: 0,\n hasDeferredPendingUpdates: false,\n hasIncompletePull: !submitted.pullComplete,\n persistedState,\n plan,\n rekeyedPendingUpdateIds: [],\n response: submitted.response,\n settledPendingUpdateIds: [],\n acceptedRecoveryBaseline: false,\n },\n };\n } catch (error) {\n if (input.historyMode === \"raw\") {\n throw error;\n }\n return { kind: \"not_completed\" };\n }\n}\n\nexport interface SyncRemoteDocumentInput {\n apiClient: DocumentSyncApi;\n author: DocumentCreateAuthor;\n /**\n * Supplies a full-history Loro snapshot of the local document so a\n * write-bearing pass can heal a stale content-key bundle by rotating to a\n * fresh content key anchored by a rotation baseline.\n */\n buildRotationSnapshot?: (() => Promise<Uint8Array | null>) | undefined;\n /** Overrides automatic ancestor repair for each submission's current projection. */\n buildContainerRekeys?: DocumentSyncContainerRekeyBuilder;\n documentId: string;\n execSql: ExecSql;\n /** Explicit read-only recovery that bypasses rotation-baseline redirect. */\n historyMode?: \"raw\" | undefined;\n isRemoteSyncBlocked?: ((organizationId: string) => boolean) | undefined;\n localVersionVector: string | null;\n minLsn?: string | undefined;\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n /** Atomically commits the verified purge proof with matching local teardown. */\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncAbandoned?: ((reason: string) => void) | undefined;\n /** Clipboard-safe trace sink (see syncTrace.ts); never receives content. */\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n /**\n * Fires when a pass WITHOUT queued writes cannot resolve its writer\n * projection (e.g. a coded 409 from the projection route). Read-only\n * revalidation otherwise fails silently — one burned request and a trace\n * line — leaving the document permanently stale with nothing durable to\n * explain why (edge-case row 13).\n */\n onReadOnlyProjectionFailure?: TerminalSubmitFailureHandler | undefined;\n /** Records a verified response update that could not be decrypted/imported. */\n onIncomingUpdateIsolationFailure?:\n | ((failure: DocumentSyncUpdateIsolationError) => void | Promise<void>)\n | undefined;\n /** Fires immediately before a materialized outgoing batch is submitted. */\n onOutgoingUpdatesMaterialized?:\n | ((updateIds: readonly string[]) => void)\n | undefined;\n /** Invalidates continuation state after the server rejects its snapshot. */\n onPullContinuationInvalidated?:\n | ((continuation: DocumentSyncPullContinuation) => void | Promise<void>)\n | undefined;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n pendingUpdates?: readonly PendingUpdateRecord[] | undefined;\n persistedState?: PersistedDocumentSyncState | null | undefined;\n rekeyPendingUpdate?: RekeyPendingUpdate | undefined;\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n resolveWriterPublicKey: DocumentWriterPublicKeyResolver;\n signedAt?: string | undefined;\n stillCurrent?: (() => boolean) | undefined;\n targetSecretKey: Uint8Array;\n /** Validates decrypted updates against scratch state before callers persist. */\n validateIncomingUpdates: IncomingDocumentSyncUpdateValidator;\n warmReferencedPrincipalPolicies?: ReferencedPrincipalPolicyWarmer | undefined;\n writerProjection?: DocumentWriterProjectionResponse | undefined;\n}\n\nexport async function tryPersistedReadOnlyDocumentSync(\n input: SyncRemoteDocumentInput,\n resolveProjectionUserKey: ProjectionUserKeyResolver,\n): Promise<PersistedReadOnlyDocumentSyncResult | null> {\n if (input.stillCurrent?.() === false) return null;\n if ((input.pendingUpdates ?? []).length > 0) return null;\n\n return syncReadOnlyRemoteDocumentFromPersistedState({\n ...input,\n resolveProjectionUserKey,\n });\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"syncAttemptPlanning.js","sourceRoot":"","sources":["syncAttemptPlanning.ts"],"names":[],"mappings":"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","sourcesContent":["import type { DocumentWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport { ContainerKekRepairInaccessibleError } from \"../../../data/documents/shared/containerKek/containerKekCurrency\";\nimport { assertDocumentManifestBundleConsistent } from \"../../../data/documents/shared/readers\";\nimport { isDocumentSyncRequestLimitError } from \"../../../data/documents/shared/sync/documentSyncOutgoingBatch\";\nimport {\n type DocumentSyncPullContinuation,\n resolvePullContinuationMinLsn,\n} from \"../../../data/documents/shared/sync/syncPagination\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport { retrySyncPlanOrAbandon } from \"../syncFailures\";\nimport {\n abandonAncestorRepair,\n abandonBlockedSync,\n abandonInaccessibleAncestorRepair,\n abandonOversizedSyncPlan,\n} from \"../syncFailures/syncAbandon\";\nimport type { TerminalSubmitFailureHandler } from \"../syncFailures/syncFailureClassification\";\nimport {\n DocumentAncestorRepairAbandonedError,\n DocumentSyncPreparationRequiredError,\n} from \"../syncFailures/syncRepairAbandon\";\nimport { prepareSyncAttemptContainerRekeys } from \"../syncRekeys/syncContainerRekeyPreparation\";\nimport { buildRemoteDocumentSyncPlan } from \"../syncRekeys/syncContainerRekeys\";\nimport type { SyncRemoteDocumentInput } from \"./readOnlySync\";\n\n/**\n * A write-bearing pass records through the submit handler (its queued writes\n * are what the failure blocks). A read-only pass records through the\n * revalidation handler so the refusal still leaves a durable trail instead\n * of silently never revalidating (edge-case row 13). A cursor continuation is\n * wire-level read-only, but its failure still blocks the queued writes it\n * deliberately deferred. Update-id recovery likewise empties the in-flight\n * batch while durable rows remain. Both keep the submit classification and\n * its 403 handling.\n */\nexport function projectionFailureHandler(\n input: SyncRemoteDocumentInput,\n failureBlocksQueuedWrites: boolean,\n): TerminalSubmitFailureHandler | undefined {\n return failureBlocksQueuedWrites\n ? input.onTerminalSubmitFailure\n : input.onReadOnlyProjectionFailure;\n}\nexport async function planDocumentSyncAttempt(input: {\n pendingUpdates: readonly PendingUpdateRecord[];\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n regenerateQueuedCheckpoints: boolean;\n sync: SyncRemoteDocumentInput;\n failureBlocksQueuedWrites: boolean;\n writerProjection: DocumentWriterProjectionResponse;\n}) {\n try {\n const pendingUpdates =\n input.pullContinuation === undefined ? input.pendingUpdates : [];\n if (\n pendingUpdates.length &&\n input.sync.isRemoteSyncBlocked?.(\n (\n await assertDocumentManifestBundleConsistent({\n bundle: input.writerProjection.documentManifest,\n label: \"Document sync manifest\",\n })\n ).organizationId,\n )\n ) {\n return abandonBlockedSync(input.sync);\n }\n // Durable repair happens once at this explicit attempt boundary. The\n // retryable builder below may only sign inline plans against its projection.\n const prepared =\n pendingUpdates.length &&\n !input.sync.buildContainerRekeys &&\n input.sync.buildRotationSnapshot\n ? await prepareSyncAttemptContainerRekeys(\n input.sync,\n input.writerProjection,\n )\n : { projection: input.writerProjection, plans: undefined };\n if (!prepared) return null;\n return await retrySyncPlanOrAbandon({\n apiClient: input.sync.apiClient,\n buildWithProjection: (projection) =>\n buildRemoteDocumentSyncPlan({\n pendingUpdates,\n preparedRekeys:\n projection === prepared.projection ? prepared.plans : undefined,\n minLsn: resolvePullContinuationMinLsn(\n input.pullContinuation,\n input.sync.minLsn,\n ),\n pullCursor: input.pullContinuation?.cursor,\n projection,\n regenerateQueuedCheckpoints: input.regenerateQueuedCheckpoints,\n sync: input.sync,\n }),\n documentId: input.sync.documentId,\n onRemoteDocumentDeleted: input.sync.onRemoteDocumentDeleted,\n onSyncAbandoned: input.sync.onSyncAbandoned,\n onSyncTrace: input.sync.onSyncTrace,\n onTerminalFailure: projectionFailureHandler(\n input.sync,\n input.failureBlocksQueuedWrites,\n ),\n stillCurrent: input.sync.stillCurrent,\n writerProjection: prepared.projection,\n });\n } catch (error) {\n if (error instanceof DocumentSyncPreparationRequiredError)\n return \"retry\" as const;\n if (error instanceof DocumentAncestorRepairAbandonedError) {\n return abandonAncestorRepair(input.sync, error);\n }\n if (error instanceof ContainerKekRepairInaccessibleError) {\n return abandonInaccessibleAncestorRepair(input.sync, error);\n }\n if (!isDocumentSyncRequestLimitError(error)) {\n throw error;\n }\n return abandonOversizedSyncPlan(input.sync, error);\n }\n}\n"]}
1
+ {"version":3,"file":"syncAttemptPlanning.js","sourceRoot":"","sources":["syncAttemptPlanning.ts"],"names":[],"mappings":"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","sourcesContent":["import type { DocumentWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport { ContainerKekRepairInaccessibleError } from \"../../../data/documents/shared/containerKek/containerKekCurrency\";\nimport { assertDocumentManifestBundleConsistent } from \"../../../data/documents/shared/readers\";\nimport { isDocumentSyncRequestLimitError } from \"../../../data/documents/shared/sync/documentSyncOutgoingBatch\";\nimport {\n type DocumentSyncPullContinuation,\n resolvePullContinuationMinLsn,\n} from \"../../../data/documents/shared/sync/syncPagination\";\nimport type { PendingUpdateRecord } from \"../../../data/persistence/documents/records\";\nimport { retrySyncPlanOrAbandon } from \"../syncFailures\";\nimport {\n abandonAncestorRepair,\n abandonBlockedSync,\n abandonInaccessibleAncestorRepair,\n abandonOversizedSyncPlan,\n} from \"../syncFailures/syncAbandon\";\nimport type { TerminalSubmitFailureHandler } from \"../syncFailures/syncFailureClassification\";\nimport {\n DocumentAncestorRepairAbandonedError,\n DocumentSyncPreparationRequiredError,\n} from \"../syncFailures/syncRepairAbandon\";\nimport { prepareSyncAttemptContainerRekeys } from \"../syncRekeys/syncContainerRekeyPreparation\";\nimport { buildRemoteDocumentSyncPlan } from \"../syncRekeys/syncContainerRekeys\";\nimport type { SyncRemoteDocumentInput } from \"./readOnlySync\";\n\n/**\n * A write-bearing pass records through the submit handler (its queued writes\n * are what the failure blocks). A read-only pass records through the\n * revalidation handler so the refusal still leaves a durable trail instead\n * of silently never revalidating (edge-case row 13). A cursor continuation is\n * wire-level read-only, but its failure still blocks the queued writes it\n * deliberately deferred. Update-id recovery likewise empties the in-flight\n * batch while durable rows remain. Both keep the submit classification and\n * its 403 handling.\n */\nexport function projectionFailureHandler(\n input: SyncRemoteDocumentInput,\n failureBlocksQueuedWrites: boolean,\n): TerminalSubmitFailureHandler | undefined {\n return failureBlocksQueuedWrites\n ? input.onTerminalSubmitFailure\n : input.onReadOnlyProjectionFailure;\n}\nexport async function planDocumentSyncAttempt(input: {\n pendingUpdates: readonly PendingUpdateRecord[];\n pullContinuation?: DocumentSyncPullContinuation | undefined;\n regenerateQueuedCheckpoints: boolean;\n sync: SyncRemoteDocumentInput;\n failureBlocksQueuedWrites: boolean;\n writerProjection: DocumentWriterProjectionResponse;\n}) {\n try {\n const pendingUpdates =\n input.pullContinuation === undefined ? input.pendingUpdates : [];\n if (\n pendingUpdates.length &&\n input.sync.isRemoteSyncBlocked?.(\n (\n await assertDocumentManifestBundleConsistent({\n bundle: input.writerProjection.documentManifest,\n label: \"Document sync manifest\",\n })\n ).organizationId,\n )\n ) {\n return abandonBlockedSync(input.sync);\n }\n // Durable repair happens once at this explicit attempt boundary. The\n // retryable builder below may only sign inline plans against its projection.\n const prepared =\n pendingUpdates.length &&\n !input.sync.buildContainerRekeys &&\n input.sync.buildRotationSnapshot\n ? await prepareSyncAttemptContainerRekeys(\n input.sync,\n input.writerProjection,\n )\n : { projection: input.writerProjection, plans: undefined };\n if (!prepared) return null;\n return await retrySyncPlanOrAbandon({\n apiClient: input.sync.apiClient,\n buildWithProjection: (projection) =>\n buildRemoteDocumentSyncPlan({\n pendingUpdates,\n preparedRekeys:\n projection === prepared.projection ? prepared.plans : undefined,\n minLsn: resolvePullContinuationMinLsn(\n input.pullContinuation,\n input.sync.minLsn,\n ),\n pullCursor: input.pullContinuation?.cursor,\n projection,\n regenerateQueuedCheckpoints: input.regenerateQueuedCheckpoints,\n sync: input.sync,\n }),\n documentId: input.sync.documentId,\n onRemoteDocumentDeleted: input.sync.onRemoteDocumentDeleted,\n onSyncAbandoned: input.sync.onSyncAbandoned,\n onSyncTrace: input.sync.onSyncTrace,\n onTerminalFailure: projectionFailureHandler(\n input.sync,\n input.failureBlocksQueuedWrites,\n ),\n stillCurrent: input.sync.stillCurrent,\n writerProjection: prepared.projection,\n });\n } catch (error) {\n if (error instanceof DocumentSyncPreparationRequiredError)\n return \"retry\" as const;\n if (error instanceof DocumentAncestorRepairAbandonedError) {\n return abandonAncestorRepair(input.sync, error);\n }\n if (error instanceof ContainerKekRepairInaccessibleError) {\n return abandonInaccessibleAncestorRepair(input.sync, error);\n }\n if (!isDocumentSyncRequestLimitError(error)) {\n throw error;\n }\n return abandonOversizedSyncPlan(input.sync, error);\n }\n}\n"]}
@@ -2,7 +2,7 @@ import type { DocumentWriterProjectionResponse } from "../../../internal/validat
2
2
  import type { MaterializedContainerRekeyPlan } from "../../../data/containers/shared/types.js";
3
3
  import type { DocumentSyncPullContinuation } from "../../../data/documents/shared/sync/syncPagination.js";
4
4
  import type { SyncRemoteDocumentResult } from "../../../data/documents/shared/types.js";
5
- import type { PendingUpdateRecord } from "../../../data/sqlite/documentPersistence/index.js";
5
+ import type { PendingUpdateRecord } from "../../../data/persistence/documents/records/index.js";
6
6
  export type DocumentSyncContainerRekeyBuilder = (writerProjection: DocumentWriterProjectionResponse, verification: {
7
7
  readonly persistVerificationCheckpoints: false;
8
8
  }) => Promise<readonly MaterializedContainerRekeyPlan[]>;
@@ -1 +1 @@
1
- {"version":3,"file":"syncAttemptState.js","sourceRoot":"","sources":["syncAttemptState.ts"],"names":[],"mappings":"","sourcesContent":["import type { DocumentWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport type { MaterializedContainerRekeyPlan } from \"../../../data/containers/shared/types\";\nimport type { DocumentSyncPullContinuation } from \"../../../data/documents/shared/sync/syncPagination\";\nimport type { SyncRemoteDocumentResult } from \"../../../data/documents/shared/types\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\n\nexport type DocumentSyncContainerRekeyBuilder = (\n writerProjection: DocumentWriterProjectionResponse,\n verification: { readonly persistVerificationCheckpoints: false },\n) => Promise<readonly MaterializedContainerRekeyPlan[]>;\n\nexport interface RemoteDocumentSyncAttemptState {\n pendingUpdates: readonly PendingUpdateRecord[];\n pullContinuation: DocumentSyncPullContinuation | undefined;\n recoveryPendingUpdatesById: Map<string, PendingUpdateRecord>;\n regenerateQueuedCheckpoints: boolean;\n reusableWriterProjection: DocumentWriterProjectionResponse | null;\n}\n\nexport type RemoteDocumentSyncAttemptOutcome =\n | { kind: \"complete\"; result: SyncRemoteDocumentResult | null }\n | { kind: \"recover\"; updates: Map<string, PendingUpdateRecord> }\n | { kind: \"regenerate\" }\n | {\n kind: \"retry\";\n pullContinuation: DocumentSyncPullContinuation | undefined;\n };\n"]}
1
+ {"version":3,"file":"syncAttemptState.js","sourceRoot":"","sources":["syncAttemptState.ts"],"names":[],"mappings":"","sourcesContent":["import type { DocumentWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport type { MaterializedContainerRekeyPlan } from \"../../../data/containers/shared/types\";\nimport type { DocumentSyncPullContinuation } from \"../../../data/documents/shared/sync/syncPagination\";\nimport type { SyncRemoteDocumentResult } from \"../../../data/documents/shared/types\";\nimport type { PendingUpdateRecord } from \"../../../data/persistence/documents/records\";\n\nexport type DocumentSyncContainerRekeyBuilder = (\n writerProjection: DocumentWriterProjectionResponse,\n verification: { readonly persistVerificationCheckpoints: false },\n) => Promise<readonly MaterializedContainerRekeyPlan[]>;\n\nexport interface RemoteDocumentSyncAttemptState {\n pendingUpdates: readonly PendingUpdateRecord[];\n pullContinuation: DocumentSyncPullContinuation | undefined;\n recoveryPendingUpdatesById: Map<string, PendingUpdateRecord>;\n regenerateQueuedCheckpoints: boolean;\n reusableWriterProjection: DocumentWriterProjectionResponse | null;\n}\n\nexport type RemoteDocumentSyncAttemptOutcome =\n | { kind: \"complete\"; result: SyncRemoteDocumentResult | null }\n | { kind: \"recover\"; updates: Map<string, PendingUpdateRecord> }\n | { kind: \"regenerate\" }\n | {\n kind: \"retry\";\n pullContinuation: DocumentSyncPullContinuation | undefined;\n };\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"syncResponseResult.js","sourceRoot":"","sources":["syncResponseResult.ts"],"names":[],"mappings":"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","sourcesContent":["import { KeyingVerificationError } from \"@tearleads/crypto\";\nimport type {\n DocumentSyncResponse,\n DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport { decryptDocumentSyncUpdatesByEpoch } from \"../../../data/documents/shared/crypto\";\nimport { assertDocumentWriterProjectionConsistent } from \"../../../data/documents/shared/projection\";\nimport {\n DocumentSyncResponseUpdateContentKeyError,\n persistedDocumentSyncStateFromResponse,\n} from \"../../../data/documents/shared/responses\";\nimport {\n type IncomingDocumentSyncUpdateValidator,\n isolateDocumentSyncBatchError,\n} from \"../../../data/documents/shared/sync/documentSyncUpdateIsolation\";\nimport type {\n DocumentWriterPublicKeyResolver,\n MaterializedDocumentSyncPlan,\n SyncRemoteDocumentResult,\n} from \"../../../data/documents/shared/types\";\nimport { projectionVerificationOptions } from \"../../../data/documents/shared/types\";\nimport type {\n ProjectionUserKeyResolver,\n ReferencedPrincipalPolicyWarmer,\n} from \"../../../data/keyingProjectionVerification\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport type { ExecSql } from \"../../../data/sqlite/sqlSchema\";\nimport type { TerminalSubmitFailureHandler } from \"../syncFailures/syncFailureClassification\";\nimport { unwrapDocumentSyncResponseContentKeys } from \"../syncPlan/syncContentKeys\";\nimport {\n acceptedHeldBackPendingUpdateIds,\n responseAcceptedRecoveryBaseline,\n} from \"../syncPlan/syncPlanRequestBounds\";\nimport {\n type RekeyPendingUpdate,\n rekeyAndReportUnsettledRecoveryPendingUpdates,\n settledPendingUpdateIdsFromSync,\n} from \"../syncRekeys/syncRecoveryRekey\";\n\nfunction isolateContentKeyResponseFailure(\n error: unknown,\n response: DocumentSyncResponse,\n): never {\n if (\n !(error instanceof DocumentSyncResponseUpdateContentKeyError) ||\n response.updates.length === 0\n ) {\n throw error;\n }\n throw isolateDocumentSyncBatchError({\n cause: new KeyingVerificationError(\"invalid_shape\", error.message),\n stage: \"content_key\",\n updateIds: response.updates.map((update) => update.id),\n });\n}\n\ntype SyncRemoteDocumentResultInput = {\n execSql: ExecSql;\n materializedPlan: MaterializedDocumentSyncPlan;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n recoveryPendingUpdatesById: ReadonlyMap<string, PendingUpdateRecord>;\n rekeyPendingUpdate?: RekeyPendingUpdate | undefined;\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n warmReferencedPrincipalPolicies?: ReferencedPrincipalPolicyWarmer | undefined;\n resolveWriterPublicKey: DocumentWriterPublicKeyResolver;\n response: DocumentSyncResponse;\n stillCurrent?: (() => boolean) | undefined;\n targetSecretKey: Uint8Array;\n validateIncomingUpdates: IncomingDocumentSyncUpdateValidator;\n writerProjection: DocumentWriterProjectionResponse;\n};\n\n/** @internal Exercises poison precedence for the decryptable subset of a raw page. */\nexport async function validateDecryptableRawHistorySiblings(input: {\n contentKeysByEpoch: ReadonlyMap<number, Uint8Array>;\n documentId: string;\n organizationId: string;\n response: DocumentSyncResponse;\n updates: readonly DocumentSyncResponse[\"updates\"][number][];\n validateIncomingUpdates: IncomingDocumentSyncUpdateValidator;\n}): Promise<void> {\n if (input.updates.length === 0) return;\n const decryptedUpdates = await decryptDocumentSyncUpdatesByEpoch({\n contentKeysByEpoch: input.contentKeysByEpoch,\n documentId: input.documentId,\n organizationId: input.organizationId,\n updates: input.updates,\n });\n // The current wire contract authenticates each update's operation range but\n // not its exact dependency set. An unresolved import therefore cannot prove\n // that the missing parent belongs to an unavailable sibling; preserve the\n // isolation failure instead of downgrading unrelated poison to availability.\n await input.validateIncomingUpdates({\n decryptedUpdates,\n response: { ...input.response, updates: [...input.updates] },\n });\n}\n\nasync function resolveVerifiedResponseState(\n input: SyncRemoteDocumentResultInput,\n) {\n const { plan } = input.materializedPlan;\n let persistedState: Awaited<\n ReturnType<typeof persistedDocumentSyncStateFromResponse>\n >;\n try {\n persistedState = await persistedDocumentSyncStateFromResponse(\n plan,\n input.response,\n {\n resolveWriterPublicKey: input.resolveWriterPublicKey,\n },\n );\n } catch (error) {\n // Missing or future bundles are response-integrity failures. They must be\n // poison-isolated before key availability is considered, because the\n // referenced update has not yet authenticated against a bundle.\n isolateContentKeyResponseFailure(error, input.response);\n }\n if ((plan.request.containerRekeys?.length ?? 0) > 0) {\n await assertDocumentWriterProjectionConsistent(input.writerProjection, {\n allowStaleContentKeyBundle: true,\n execSql: input.execSql,\n stillCurrent: input.stillCurrent,\n ...projectionVerificationOptions(input),\n });\n }\n const contentKeysByEpoch = await unwrapDocumentSyncResponseContentKeys({\n currentContentKey: input.materializedPlan.contentKey,\n currentContentKeyEpoch: plan.contentKeyEpoch,\n execSql: input.execSql,\n historyMode: plan.request.historyMode,\n onRawHistoryUnavailable: async ({ contentKeysByEpoch, updates }) =>\n validateDecryptableRawHistorySiblings({\n contentKeysByEpoch,\n documentId: plan.documentId,\n organizationId: plan.organizationId,\n response: input.response,\n updates,\n validateIncomingUpdates: input.validateIncomingUpdates,\n }),\n response: input.response,\n targetSecretKey: input.targetSecretKey,\n writerProjection: input.writerProjection,\n ...projectionVerificationOptions(input),\n });\n return { contentKeysByEpoch, persistedState };\n}\n\nexport async function syncRemoteDocumentResultFromResponse(\n input: SyncRemoteDocumentResultInput,\n): Promise<SyncRemoteDocumentResult> {\n const { plan } = input.materializedPlan;\n const { contentKeysByEpoch, persistedState } =\n await resolveVerifiedResponseState(input);\n const decryptedUpdates = await decryptDocumentSyncUpdatesByEpoch({\n contentKeysByEpoch,\n documentId: plan.documentId,\n organizationId: plan.organizationId,\n updates: input.response.updates,\n });\n await input.validateIncomingUpdates({\n decryptedUpdates,\n response: input.response,\n });\n const recoveryBaselineId =\n input.materializedPlan.staleRecoveryBaselineUpdateId;\n const acceptedRecoveryBaseline = responseAcceptedRecoveryBaseline(\n input.materializedPlan,\n input.response,\n );\n // Two heal-specific corrections: the synthetic heal baseline matches no\n // pending-queue row, so its ack must not count as a settled pending update;\n // and checkpoints the heal held back ARE settled by it — the committed\n // covering baseline subsumes their full-history content, and resubmitting\n // them post-heal could become the LATEST baseline at the healed epoch and\n // shrink the redirect's coverage below the pre-heal frontier.\n const settledPendingUpdateIds = [\n ...settledPendingUpdateIdsFromSync({\n decryptedUpdates,\n recoveryPendingUpdatesById: input.recoveryPendingUpdatesById,\n response: input.response,\n }).filter((updateId) => updateId !== recoveryBaselineId),\n ...acceptedHeldBackPendingUpdateIds(input.materializedPlan, input.response),\n ];\n const { exhaustedPendingUpdateCount, rekeyedPendingUpdateIds } =\n await rekeyAndReportUnsettledRecoveryPendingUpdates({\n execSql: input.execSql,\n onTerminalSubmitFailure: input.onTerminalSubmitFailure,\n recoveryPendingUpdatesById: input.recoveryPendingUpdatesById,\n rekeyPendingUpdate: input.rekeyPendingUpdate,\n settledPendingUpdateIds,\n stillCurrent: input.stillCurrent,\n });\n\n return {\n exhaustedPendingUpdateCount,\n contentKey: input.materializedPlan.contentKey,\n decryptedUpdates,\n hasDeferredPendingUpdates: false,\n hasIncompletePull: false,\n persistedState,\n plan,\n rekeyedPendingUpdateIds,\n response: input.response,\n settledPendingUpdateIds,\n acceptedRecoveryBaseline,\n writerProjection: input.writerProjection,\n };\n}\n"]}
1
+ {"version":3,"file":"syncResponseResult.js","sourceRoot":"","sources":["syncResponseResult.ts"],"names":[],"mappings":"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","sourcesContent":["import { KeyingVerificationError } from \"@tearleads/crypto\";\nimport type {\n DocumentSyncResponse,\n DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport { decryptDocumentSyncUpdatesByEpoch } from \"../../../data/documents/shared/crypto\";\nimport { assertDocumentWriterProjectionConsistent } from \"../../../data/documents/shared/projection\";\nimport {\n DocumentSyncResponseUpdateContentKeyError,\n persistedDocumentSyncStateFromResponse,\n} from \"../../../data/documents/shared/responses\";\nimport {\n type IncomingDocumentSyncUpdateValidator,\n isolateDocumentSyncBatchError,\n} from \"../../../data/documents/shared/sync/documentSyncUpdateIsolation\";\nimport type {\n DocumentWriterPublicKeyResolver,\n MaterializedDocumentSyncPlan,\n SyncRemoteDocumentResult,\n} from \"../../../data/documents/shared/types\";\nimport { projectionVerificationOptions } from \"../../../data/documents/shared/types\";\nimport type {\n ProjectionUserKeyResolver,\n ReferencedPrincipalPolicyWarmer,\n} from \"../../../data/keyingProjectionVerification\";\nimport type { PendingUpdateRecord } from \"../../../data/persistence/documents/records\";\nimport type { ExecSql } from \"../../../data/sqlite/sqlSchema\";\nimport type { TerminalSubmitFailureHandler } from \"../syncFailures/syncFailureClassification\";\nimport { unwrapDocumentSyncResponseContentKeys } from \"../syncPlan/syncContentKeys\";\nimport {\n acceptedHeldBackPendingUpdateIds,\n responseAcceptedRecoveryBaseline,\n} from \"../syncPlan/syncPlanRequestBounds\";\nimport {\n type RekeyPendingUpdate,\n rekeyAndReportUnsettledRecoveryPendingUpdates,\n settledPendingUpdateIdsFromSync,\n} from \"../syncRekeys/syncRecoveryRekey\";\n\nfunction isolateContentKeyResponseFailure(\n error: unknown,\n response: DocumentSyncResponse,\n): never {\n if (\n !(error instanceof DocumentSyncResponseUpdateContentKeyError) ||\n response.updates.length === 0\n ) {\n throw error;\n }\n throw isolateDocumentSyncBatchError({\n cause: new KeyingVerificationError(\"invalid_shape\", error.message),\n stage: \"content_key\",\n updateIds: response.updates.map((update) => update.id),\n });\n}\n\ntype SyncRemoteDocumentResultInput = {\n execSql: ExecSql;\n materializedPlan: MaterializedDocumentSyncPlan;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n recoveryPendingUpdatesById: ReadonlyMap<string, PendingUpdateRecord>;\n rekeyPendingUpdate?: RekeyPendingUpdate | undefined;\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n warmReferencedPrincipalPolicies?: ReferencedPrincipalPolicyWarmer | undefined;\n resolveWriterPublicKey: DocumentWriterPublicKeyResolver;\n response: DocumentSyncResponse;\n stillCurrent?: (() => boolean) | undefined;\n targetSecretKey: Uint8Array;\n validateIncomingUpdates: IncomingDocumentSyncUpdateValidator;\n writerProjection: DocumentWriterProjectionResponse;\n};\n\n/** @internal Exercises poison precedence for the decryptable subset of a raw page. */\nexport async function validateDecryptableRawHistorySiblings(input: {\n contentKeysByEpoch: ReadonlyMap<number, Uint8Array>;\n documentId: string;\n organizationId: string;\n response: DocumentSyncResponse;\n updates: readonly DocumentSyncResponse[\"updates\"][number][];\n validateIncomingUpdates: IncomingDocumentSyncUpdateValidator;\n}): Promise<void> {\n if (input.updates.length === 0) return;\n const decryptedUpdates = await decryptDocumentSyncUpdatesByEpoch({\n contentKeysByEpoch: input.contentKeysByEpoch,\n documentId: input.documentId,\n organizationId: input.organizationId,\n updates: input.updates,\n });\n // The current wire contract authenticates each update's operation range but\n // not its exact dependency set. An unresolved import therefore cannot prove\n // that the missing parent belongs to an unavailable sibling; preserve the\n // isolation failure instead of downgrading unrelated poison to availability.\n await input.validateIncomingUpdates({\n decryptedUpdates,\n response: { ...input.response, updates: [...input.updates] },\n });\n}\n\nasync function resolveVerifiedResponseState(\n input: SyncRemoteDocumentResultInput,\n) {\n const { plan } = input.materializedPlan;\n let persistedState: Awaited<\n ReturnType<typeof persistedDocumentSyncStateFromResponse>\n >;\n try {\n persistedState = await persistedDocumentSyncStateFromResponse(\n plan,\n input.response,\n {\n resolveWriterPublicKey: input.resolveWriterPublicKey,\n },\n );\n } catch (error) {\n // Missing or future bundles are response-integrity failures. They must be\n // poison-isolated before key availability is considered, because the\n // referenced update has not yet authenticated against a bundle.\n isolateContentKeyResponseFailure(error, input.response);\n }\n if ((plan.request.containerRekeys?.length ?? 0) > 0) {\n await assertDocumentWriterProjectionConsistent(input.writerProjection, {\n allowStaleContentKeyBundle: true,\n execSql: input.execSql,\n stillCurrent: input.stillCurrent,\n ...projectionVerificationOptions(input),\n });\n }\n const contentKeysByEpoch = await unwrapDocumentSyncResponseContentKeys({\n currentContentKey: input.materializedPlan.contentKey,\n currentContentKeyEpoch: plan.contentKeyEpoch,\n execSql: input.execSql,\n historyMode: plan.request.historyMode,\n onRawHistoryUnavailable: async ({ contentKeysByEpoch, updates }) =>\n validateDecryptableRawHistorySiblings({\n contentKeysByEpoch,\n documentId: plan.documentId,\n organizationId: plan.organizationId,\n response: input.response,\n updates,\n validateIncomingUpdates: input.validateIncomingUpdates,\n }),\n response: input.response,\n targetSecretKey: input.targetSecretKey,\n writerProjection: input.writerProjection,\n ...projectionVerificationOptions(input),\n });\n return { contentKeysByEpoch, persistedState };\n}\n\nexport async function syncRemoteDocumentResultFromResponse(\n input: SyncRemoteDocumentResultInput,\n): Promise<SyncRemoteDocumentResult> {\n const { plan } = input.materializedPlan;\n const { contentKeysByEpoch, persistedState } =\n await resolveVerifiedResponseState(input);\n const decryptedUpdates = await decryptDocumentSyncUpdatesByEpoch({\n contentKeysByEpoch,\n documentId: plan.documentId,\n organizationId: plan.organizationId,\n updates: input.response.updates,\n });\n await input.validateIncomingUpdates({\n decryptedUpdates,\n response: input.response,\n });\n const recoveryBaselineId =\n input.materializedPlan.staleRecoveryBaselineUpdateId;\n const acceptedRecoveryBaseline = responseAcceptedRecoveryBaseline(\n input.materializedPlan,\n input.response,\n );\n // Two heal-specific corrections: the synthetic heal baseline matches no\n // pending-queue row, so its ack must not count as a settled pending update;\n // and checkpoints the heal held back ARE settled by it — the committed\n // covering baseline subsumes their full-history content, and resubmitting\n // them post-heal could become the LATEST baseline at the healed epoch and\n // shrink the redirect's coverage below the pre-heal frontier.\n const settledPendingUpdateIds = [\n ...settledPendingUpdateIdsFromSync({\n decryptedUpdates,\n recoveryPendingUpdatesById: input.recoveryPendingUpdatesById,\n response: input.response,\n }).filter((updateId) => updateId !== recoveryBaselineId),\n ...acceptedHeldBackPendingUpdateIds(input.materializedPlan, input.response),\n ];\n const { exhaustedPendingUpdateCount, rekeyedPendingUpdateIds } =\n await rekeyAndReportUnsettledRecoveryPendingUpdates({\n execSql: input.execSql,\n onTerminalSubmitFailure: input.onTerminalSubmitFailure,\n recoveryPendingUpdatesById: input.recoveryPendingUpdatesById,\n rekeyPendingUpdate: input.rekeyPendingUpdate,\n settledPendingUpdateIds,\n stillCurrent: input.stillCurrent,\n });\n\n return {\n exhaustedPendingUpdateCount,\n contentKey: input.materializedPlan.contentKey,\n decryptedUpdates,\n hasDeferredPendingUpdates: false,\n hasIncompletePull: false,\n persistedState,\n plan,\n rekeyedPendingUpdateIds,\n response: input.response,\n settledPendingUpdateIds,\n acceptedRecoveryBaseline,\n writerProjection: input.writerProjection,\n };\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"syncSubmittedResult.js","sourceRoot":"","sources":["syncSubmittedResult.ts"],"names":[],"mappings":"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","sourcesContent":["import type {\n DocumentSyncResponse,\n DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport type {\n MaterializedDocumentSyncPlan,\n SyncRemoteDocumentResult,\n} from \"../../../data/documents/shared/types\";\nimport { projectionVerificationOptions } from \"../../../data/documents/shared/types\";\nimport {\n type ProjectionUserKeyResolver,\n verifyDocumentWriterProjectionAuthorization,\n} from \"../../../data/keyingProjectionVerification\";\nimport { isKeyingVerificationError } from \"../../../data/keyingProjectionVerification/error\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport { refreshSyncAttemptWriterProjection } from \"../syncFailures\";\nimport { DocumentRawHistoryUnavailableError } from \"../syncPlan/syncContentKeys\";\nimport {\n hasDeferredPendingUpdatesAfterSubmit,\n responseAcceptedRecoveryBaseline,\n} from \"../syncPlan/syncPlanRequestBounds\";\nimport type { SyncRemoteDocumentInput } from \"./readOnlySync\";\nimport { syncRemoteDocumentResultFromResponse } from \"./syncResponseResult\";\nimport { traceHealed } from \"./syncTrace\";\n\ntype SubmittedDocumentSyncResultInput = {\n materializedPlan: MaterializedDocumentSyncPlan;\n pendingUpdateIds: readonly string[];\n pullComplete: boolean;\n recoveryPendingUpdatesById: ReadonlyMap<string, PendingUpdateRecord>;\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n response: DocumentSyncResponse;\n sync: SyncRemoteDocumentInput;\n writerProjection: DocumentWriterProjectionResponse;\n};\n\n/** @internal Applies post-verification heal effects under the sync generation. */\nexport function applyAcceptedHealSideEffects(input: {\n documentId: string;\n evictWriterProjection?: ((documentId: string) => void) | undefined;\n materializedPlan: MaterializedDocumentSyncPlan;\n onSyncTrace: SyncRemoteDocumentInput[\"onSyncTrace\"];\n response: DocumentSyncResponse;\n stillCurrent: SyncRemoteDocumentInput[\"stillCurrent\"];\n}): void {\n if (\n !input.materializedPlan.healedStaleContentKeyBundle ||\n !responseAcceptedRecoveryBaseline(input.materializedPlan, input.response) ||\n input.stillCurrent?.() === false\n ) {\n return;\n }\n input.evictWriterProjection?.(input.documentId);\n if (input.stillCurrent?.() === false) {\n return;\n }\n traceHealed(input.onSyncTrace, {\n accepted: input.response.acceptedOutgoingUpdateIds.length,\n documentId: input.materializedPlan.plan.documentId,\n epoch: input.materializedPlan.plan.contentKeyEpoch,\n });\n}\n\nasync function submittedDocumentSyncResult(\n input: SubmittedDocumentSyncResultInput,\n): Promise<SyncRemoteDocumentResult> {\n const result = await syncRemoteDocumentResultFromResponse({\n ...projectionVerificationOptions(input.sync),\n execSql: input.sync.execSql,\n materializedPlan: input.materializedPlan,\n onTerminalSubmitFailure: input.sync.onTerminalSubmitFailure,\n recoveryPendingUpdatesById: input.recoveryPendingUpdatesById,\n rekeyPendingUpdate: input.sync.rekeyPendingUpdate,\n resolveWriterPublicKey: input.sync.resolveWriterPublicKey,\n response: input.response,\n stillCurrent: input.sync.stillCurrent,\n targetSecretKey: input.sync.targetSecretKey,\n validateIncomingUpdates: input.sync.validateIncomingUpdates,\n writerProjection: input.writerProjection,\n resolveProjectionUserKey: input.resolveProjectionUserKey,\n });\n if (\n (input.materializedPlan.plan.request.containerRekeys?.length ?? 0) > 0 &&\n input.sync.stillCurrent?.() !== false\n ) {\n input.sync.apiClient.clearWriterProjectionCaches?.();\n }\n applyAcceptedHealSideEffects({\n documentId: input.sync.documentId,\n evictWriterProjection:\n input.sync.apiClient.evictDocumentWriterProjection?.bind(\n input.sync.apiClient,\n ),\n materializedPlan: input.materializedPlan,\n onSyncTrace: input.sync.onSyncTrace,\n response: input.response,\n stillCurrent: input.sync.stillCurrent,\n });\n return {\n ...result,\n hasDeferredPendingUpdates:\n (input.materializedPlan.plan.request.pullCursor !== undefined &&\n input.pendingUpdateIds.length > 0 &&\n result.exhaustedPendingUpdateCount === 0) ||\n hasDeferredPendingUpdatesAfterSubmit({\n acceptedRecoveryBaseline: result.acceptedRecoveryBaseline,\n exhaustedPendingUpdateCount: result.exhaustedPendingUpdateCount,\n pendingUpdateIds: input.pendingUpdateIds,\n rekeyedPendingUpdateIds: result.rekeyedPendingUpdateIds,\n settledPendingUpdateIds: result.settledPendingUpdateIds,\n }),\n hasIncompletePull: !input.pullComplete,\n };\n}\n\nasync function retrySubmittedResponseWithFreshProjection(\n input: SubmittedDocumentSyncResultInput,\n unavailableError: unknown,\n refreshAuthorization: boolean,\n): Promise<SyncRemoteDocumentResult | null> {\n const writerProjection = await refreshSyncAttemptWriterProjection({\n apiClient: input.sync.apiClient,\n documentId: input.sync.documentId,\n onRemoteDocumentDeleted: input.sync.onRemoteDocumentDeleted,\n onSyncAbandoned: input.sync.onSyncAbandoned,\n onSyncTrace: input.sync.onSyncTrace,\n onTerminalFailure: input.sync.onReadOnlyProjectionFailure,\n stillCurrent: input.sync.stillCurrent,\n unavailableError,\n });\n if (!writerProjection) return null;\n const materializedPlan = refreshAuthorization\n ? {\n ...input.materializedPlan,\n plan: {\n ...input.materializedPlan.plan,\n documentWriterAuthorization:\n await verifyDocumentWriterProjectionAuthorization({\n execSql: input.sync.execSql,\n projection: writerProjection,\n resolveUserKey: input.resolveProjectionUserKey,\n stillCurrent: input.sync.stillCurrent,\n warmReferencedPrincipalPolicies:\n input.sync.warmReferencedPrincipalPolicies,\n }),\n },\n }\n : input.materializedPlan;\n // Keep the submitted request, keys, and response frozen. Only refreshed,\n // verified evidence may be added; this retry never resubmits outgoing edits.\n return submittedDocumentSyncResult({\n ...input,\n materializedPlan,\n writerProjection,\n });\n}\n\nexport async function resolveSubmittedDocumentSyncResult(\n input: SubmittedDocumentSyncResultInput,\n): Promise<SyncRemoteDocumentResult | null> {\n try {\n return await submittedDocumentSyncResult(input);\n } catch (error) {\n const missingDependency =\n isKeyingVerificationError(error) && error.code === \"missing_dependency\";\n if (\n !missingDependency &&\n (input.sync.historyMode !== \"raw\" ||\n !(error instanceof DocumentRawHistoryUnavailableError))\n ) {\n throw error;\n }\n return retrySubmittedResponseWithFreshProjection(\n input,\n error,\n missingDependency,\n );\n }\n}\n"]}
1
+ {"version":3,"file":"syncSubmittedResult.js","sourceRoot":"","sources":["syncSubmittedResult.ts"],"names":[],"mappings":"AAQA,OAAO,EAAE,6BAA6B,EAAE,MAAM,sCAAsC,CAAC;AACrF,OAAO,EAEL,2CAA2C,GAC5C,MAAM,4CAA4C,CAAC;AACpD,OAAO,EAAE,yBAAyB,EAAE,MAAM,kDAAkD,CAAC;AAE7F,OAAO,EAAE,kCAAkC,EAAE,MAAM,iBAAiB,CAAC;AACrE,OAAO,EAAE,kCAAkC,EAAE,MAAM,6BAA6B,CAAC;AACjF,OAAO,EACL,oCAAoC,EACpC,gCAAgC,GACjC,MAAM,mCAAmC,CAAC;AAE3C,OAAO,EAAE,oCAAoC,EAAE,MAAM,sBAAsB,CAAC;AAC5E,OAAO,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAa1C,kFAAkF;AAClF,MAAM,UAAU,4BAA4B,CAAC,KAO5C;IACC,IACE,CAAC,KAAK,CAAC,gBAAgB,CAAC,2BAA2B;QACnD,CAAC,gCAAgC,CAAC,KAAK,CAAC,gBAAgB,EAAE,KAAK,CAAC,QAAQ,CAAC;QACzE,KAAK,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK,EAChC,CAAC;QACD,OAAO;IACT,CAAC;IACD,KAAK,CAAC,qBAAqB,EAAE,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC;IAChD,IAAI,KAAK,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK,EAAE,CAAC;QACrC,OAAO;IACT,CAAC;IACD,WAAW,CAAC,KAAK,CAAC,WAAW,EAAE;QAC7B,QAAQ,EAAE,KAAK,CAAC,QAAQ,CAAC,yBAAyB,CAAC,MAAM;QACzD,UAAU,EAAE,KAAK,CAAC,gBAAgB,CAAC,IAAI,CAAC,UAAU;QAClD,KAAK,EAAE,KAAK,CAAC,gBAAgB,CAAC,IAAI,CAAC,eAAe;KACnD,CAAC,CAAC;AACL,CAAC;AAED,KAAK,UAAU,2BAA2B,CACxC,KAAuC;IAEvC,MAAM,MAAM,GAAG,MAAM,oCAAoC,CAAC;QACxD,GAAG,6BAA6B,CAAC,KAAK,CAAC,IAAI,CAAC;QAC5C,OAAO,EAAE,KAAK,CAAC,IAAI,CAAC,OAAO;QAC3B,gBAAgB,EAAE,KAAK,CAAC,gBAAgB;QACxC,uBAAuB,EAAE,KAAK,CAAC,IAAI,CAAC,uBAAuB;QAC3D,0BAA0B,EAAE,KAAK,CAAC,0BAA0B;QAC5D,kBAAkB,EAAE,KAAK,CAAC,IAAI,CAAC,kBAAkB;QACjD,sBAAsB,EAAE,KAAK,CAAC,IAAI,CAAC,sBAAsB;QACzD,QAAQ,EAAE,KAAK,CAAC,QAAQ;QACxB,YAAY,EAAE,KAAK,CAAC,IAAI,CAAC,YAAY;QACrC,eAAe,EAAE,KAAK,CAAC,IAAI,CAAC,eAAe;QAC3C,uBAAuB,EAAE,KAAK,CAAC,IAAI,CAAC,uBAAuB;QAC3D,gBAAgB,EAAE,KAAK,CAAC,gBAAgB;QACxC,wBAAwB,EAAE,KAAK,CAAC,wBAAwB;KACzD,CAAC,CAAC;IACH,IACE,CAAC,KAAK,CAAC,gBAAgB,CAAC,IAAI,CAAC,OAAO,CAAC,eAAe,EAAE,MAAM,IAAI,CAAC,CAAC,GAAG,CAAC;QACtE,KAAK,CAAC,IAAI,CAAC,YAAY,EAAE,EAAE,KAAK,KAAK,EACrC,CAAC;QACD,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC,2BAA2B,EAAE,EAAE,CAAC;IACvD,CAAC;IACD,4BAA4B,CAAC;QAC3B,UAAU,EAAE,KAAK,CAAC,IAAI,CAAC,UAAU;QACjC,qBAAqB,EACnB,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC,6BAA6B,EAAE,IAAI,CACtD,KAAK,CAAC,IAAI,CAAC,SAAS,CACrB;QACH,gBAAgB,EAAE,KAAK,CAAC,gBAAgB;QACxC,WAAW,EAAE,KAAK,CAAC,IAAI,CAAC,WAAW;QACnC,QAAQ,EAAE,KAAK,CAAC,QAAQ;QACxB,YAAY,EAAE,KAAK,CAAC,IAAI,CAAC,YAAY;KACtC,CAAC,CAAC;IACH,OAAO;QACL,GAAG,MAAM;QACT,yBAAyB,EACvB,CAAC,KAAK,CAAC,gBAAgB,CAAC,IAAI,CAAC,OAAO,CAAC,UAAU,KAAK,SAAS;YAC3D,KAAK,CAAC,gBAAgB,CAAC,MAAM,GAAG,CAAC;YACjC,MAAM,CAAC,2BAA2B,KAAK,CAAC,CAAC;YAC3C,oCAAoC,CAAC;gBACnC,wBAAwB,EAAE,MAAM,CAAC,wBAAwB;gBACzD,2BAA2B,EAAE,MAAM,CAAC,2BAA2B;gBAC/D,gBAAgB,EAAE,KAAK,CAAC,gBAAgB;gBACxC,uBAAuB,EAAE,MAAM,CAAC,uBAAuB;gBACvD,uBAAuB,EAAE,MAAM,CAAC,uBAAuB;aACxD,CAAC;QACJ,iBAAiB,EAAE,CAAC,KAAK,CAAC,YAAY;KACvC,CAAC;AACJ,CAAC;AAED,KAAK,UAAU,yCAAyC,CACtD,KAAuC,EACvC,gBAAyB,EACzB,oBAA6B;IAE7B,MAAM,gBAAgB,GAAG,MAAM,kCAAkC,CAAC;QAChE,SAAS,EAAE,KAAK,CAAC,IAAI,CAAC,SAAS;QAC/B,UAAU,EAAE,KAAK,CAAC,IAAI,CAAC,UAAU;QACjC,uBAAuB,EAAE,KAAK,CAAC,IAAI,CAAC,uBAAuB;QAC3D,eAAe,EAAE,KAAK,CAAC,IAAI,CAAC,eAAe;QAC3C,WAAW,EAAE,KAAK,CAAC,IAAI,CAAC,WAAW;QACnC,iBAAiB,EAAE,KAAK,CAAC,IAAI,CAAC,2BAA2B;QACzD,YAAY,EAAE,KAAK,CAAC,IAAI,CAAC,YAAY;QACrC,gBAAgB;KACjB,CAAC,CAAC;IACH,IAAI,CAAC,gBAAgB;QAAE,OAAO,IAAI,CAAC;IACnC,MAAM,gBAAgB,GAAG,oBAAoB;QAC3C,CAAC,CAAC;YACE,GAAG,KAAK,CAAC,gBAAgB;YACzB,IAAI,EAAE;gBACJ,GAAG,KAAK,CAAC,gBAAgB,CAAC,IAAI;gBAC9B,2BAA2B,EACzB,MAAM,2CAA2C,CAAC;oBAChD,OAAO,EAAE,KAAK,CAAC,IAAI,CAAC,OAAO;oBAC3B,UAAU,EAAE,gBAAgB;oBAC5B,cAAc,EAAE,KAAK,CAAC,wBAAwB;oBAC9C,YAAY,EAAE,KAAK,CAAC,IAAI,CAAC,YAAY;oBACrC,+BAA+B,EAC7B,KAAK,CAAC,IAAI,CAAC,+BAA+B;iBAC7C,CAAC;aACL;SACF;QACH,CAAC,CAAC,KAAK,CAAC,gBAAgB,CAAC;IAC3B,yEAAyE;IACzE,6EAA6E;IAC7E,OAAO,2BAA2B,CAAC;QACjC,GAAG,KAAK;QACR,gBAAgB;QAChB,gBAAgB;KACjB,CAAC,CAAC;AACL,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,kCAAkC,CACtD,KAAuC;IAEvC,IAAI,CAAC;QACH,OAAO,MAAM,2BAA2B,CAAC,KAAK,CAAC,CAAC;IAClD,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,MAAM,iBAAiB,GACrB,yBAAyB,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,IAAI,KAAK,oBAAoB,CAAC;QAC1E,IACE,CAAC,iBAAiB;YAClB,CAAC,KAAK,CAAC,IAAI,CAAC,WAAW,KAAK,KAAK;gBAC/B,CAAC,CAAC,KAAK,YAAY,kCAAkC,CAAC,CAAC,EACzD,CAAC;YACD,MAAM,KAAK,CAAC;QACd,CAAC;QACD,OAAO,yCAAyC,CAC9C,KAAK,EACL,KAAK,EACL,iBAAiB,CAClB,CAAC;IACJ,CAAC;AACH,CAAC","sourcesContent":["import type {\n DocumentSyncResponse,\n DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport type {\n MaterializedDocumentSyncPlan,\n SyncRemoteDocumentResult,\n} from \"../../../data/documents/shared/types\";\nimport { projectionVerificationOptions } from \"../../../data/documents/shared/types\";\nimport {\n type ProjectionUserKeyResolver,\n verifyDocumentWriterProjectionAuthorization,\n} from \"../../../data/keyingProjectionVerification\";\nimport { isKeyingVerificationError } from \"../../../data/keyingProjectionVerification/error\";\nimport type { PendingUpdateRecord } from \"../../../data/persistence/documents/records\";\nimport { refreshSyncAttemptWriterProjection } from \"../syncFailures\";\nimport { DocumentRawHistoryUnavailableError } from \"../syncPlan/syncContentKeys\";\nimport {\n hasDeferredPendingUpdatesAfterSubmit,\n responseAcceptedRecoveryBaseline,\n} from \"../syncPlan/syncPlanRequestBounds\";\nimport type { SyncRemoteDocumentInput } from \"./readOnlySync\";\nimport { syncRemoteDocumentResultFromResponse } from \"./syncResponseResult\";\nimport { traceHealed } from \"./syncTrace\";\n\ntype SubmittedDocumentSyncResultInput = {\n materializedPlan: MaterializedDocumentSyncPlan;\n pendingUpdateIds: readonly string[];\n pullComplete: boolean;\n recoveryPendingUpdatesById: ReadonlyMap<string, PendingUpdateRecord>;\n resolveProjectionUserKey: ProjectionUserKeyResolver;\n response: DocumentSyncResponse;\n sync: SyncRemoteDocumentInput;\n writerProjection: DocumentWriterProjectionResponse;\n};\n\n/** @internal Applies post-verification heal effects under the sync generation. */\nexport function applyAcceptedHealSideEffects(input: {\n documentId: string;\n evictWriterProjection?: ((documentId: string) => void) | undefined;\n materializedPlan: MaterializedDocumentSyncPlan;\n onSyncTrace: SyncRemoteDocumentInput[\"onSyncTrace\"];\n response: DocumentSyncResponse;\n stillCurrent: SyncRemoteDocumentInput[\"stillCurrent\"];\n}): void {\n if (\n !input.materializedPlan.healedStaleContentKeyBundle ||\n !responseAcceptedRecoveryBaseline(input.materializedPlan, input.response) ||\n input.stillCurrent?.() === false\n ) {\n return;\n }\n input.evictWriterProjection?.(input.documentId);\n if (input.stillCurrent?.() === false) {\n return;\n }\n traceHealed(input.onSyncTrace, {\n accepted: input.response.acceptedOutgoingUpdateIds.length,\n documentId: input.materializedPlan.plan.documentId,\n epoch: input.materializedPlan.plan.contentKeyEpoch,\n });\n}\n\nasync function submittedDocumentSyncResult(\n input: SubmittedDocumentSyncResultInput,\n): Promise<SyncRemoteDocumentResult> {\n const result = await syncRemoteDocumentResultFromResponse({\n ...projectionVerificationOptions(input.sync),\n execSql: input.sync.execSql,\n materializedPlan: input.materializedPlan,\n onTerminalSubmitFailure: input.sync.onTerminalSubmitFailure,\n recoveryPendingUpdatesById: input.recoveryPendingUpdatesById,\n rekeyPendingUpdate: input.sync.rekeyPendingUpdate,\n resolveWriterPublicKey: input.sync.resolveWriterPublicKey,\n response: input.response,\n stillCurrent: input.sync.stillCurrent,\n targetSecretKey: input.sync.targetSecretKey,\n validateIncomingUpdates: input.sync.validateIncomingUpdates,\n writerProjection: input.writerProjection,\n resolveProjectionUserKey: input.resolveProjectionUserKey,\n });\n if (\n (input.materializedPlan.plan.request.containerRekeys?.length ?? 0) > 0 &&\n input.sync.stillCurrent?.() !== false\n ) {\n input.sync.apiClient.clearWriterProjectionCaches?.();\n }\n applyAcceptedHealSideEffects({\n documentId: input.sync.documentId,\n evictWriterProjection:\n input.sync.apiClient.evictDocumentWriterProjection?.bind(\n input.sync.apiClient,\n ),\n materializedPlan: input.materializedPlan,\n onSyncTrace: input.sync.onSyncTrace,\n response: input.response,\n stillCurrent: input.sync.stillCurrent,\n });\n return {\n ...result,\n hasDeferredPendingUpdates:\n (input.materializedPlan.plan.request.pullCursor !== undefined &&\n input.pendingUpdateIds.length > 0 &&\n result.exhaustedPendingUpdateCount === 0) ||\n hasDeferredPendingUpdatesAfterSubmit({\n acceptedRecoveryBaseline: result.acceptedRecoveryBaseline,\n exhaustedPendingUpdateCount: result.exhaustedPendingUpdateCount,\n pendingUpdateIds: input.pendingUpdateIds,\n rekeyedPendingUpdateIds: result.rekeyedPendingUpdateIds,\n settledPendingUpdateIds: result.settledPendingUpdateIds,\n }),\n hasIncompletePull: !input.pullComplete,\n };\n}\n\nasync function retrySubmittedResponseWithFreshProjection(\n input: SubmittedDocumentSyncResultInput,\n unavailableError: unknown,\n refreshAuthorization: boolean,\n): Promise<SyncRemoteDocumentResult | null> {\n const writerProjection = await refreshSyncAttemptWriterProjection({\n apiClient: input.sync.apiClient,\n documentId: input.sync.documentId,\n onRemoteDocumentDeleted: input.sync.onRemoteDocumentDeleted,\n onSyncAbandoned: input.sync.onSyncAbandoned,\n onSyncTrace: input.sync.onSyncTrace,\n onTerminalFailure: input.sync.onReadOnlyProjectionFailure,\n stillCurrent: input.sync.stillCurrent,\n unavailableError,\n });\n if (!writerProjection) return null;\n const materializedPlan = refreshAuthorization\n ? {\n ...input.materializedPlan,\n plan: {\n ...input.materializedPlan.plan,\n documentWriterAuthorization:\n await verifyDocumentWriterProjectionAuthorization({\n execSql: input.sync.execSql,\n projection: writerProjection,\n resolveUserKey: input.resolveProjectionUserKey,\n stillCurrent: input.sync.stillCurrent,\n warmReferencedPrincipalPolicies:\n input.sync.warmReferencedPrincipalPolicies,\n }),\n },\n }\n : input.materializedPlan;\n // Keep the submitted request, keys, and response frozen. Only refreshed,\n // verified evidence may be added; this retry never resubmits outgoing edits.\n return submittedDocumentSyncResult({\n ...input,\n materializedPlan,\n writerProjection,\n });\n}\n\nexport async function resolveSubmittedDocumentSyncResult(\n input: SubmittedDocumentSyncResultInput,\n): Promise<SyncRemoteDocumentResult | null> {\n try {\n return await submittedDocumentSyncResult(input);\n } catch (error) {\n const missingDependency =\n isKeyingVerificationError(error) && error.code === \"missing_dependency\";\n if (\n !missingDependency &&\n (input.sync.historyMode !== \"raw\" ||\n !(error instanceof DocumentRawHistoryUnavailableError))\n ) {\n throw error;\n }\n return retrySubmittedResponseWithFreshProjection(\n input,\n error,\n missingDependency,\n );\n }\n}\n"]}