@tearleads/client-sdk 0.1.64 → 0.1.65
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/client/organizations/organizationAccessRestoration.js +1 -1
- package/data/containers/shared/mutationAcknowledgement.js +1 -1
- package/data/containers/shared/mutationAcknowledgement.js.map +1 -1
- package/data/documents/blob/shared/projection.js +3 -3
- package/data/documents/blob/shared/projection.js.map +1 -1
- package/data/documents/shared/{containerKekCurrency.d.ts → containerKek/containerKekCurrency.d.ts} +1 -1
- package/data/documents/shared/{containerKekEntryVerification.js → containerKek/containerKekEntryVerification.js} +1 -1
- package/data/documents/shared/{containerKekLogFetch.d.ts → containerKek/containerKekLogFetch.d.ts} +1 -1
- package/data/documents/shared/{containerKekLogFetch.js → containerKek/containerKekLogFetch.js} +1 -1
- package/data/documents/shared/{containerKekPath.js → containerKek/containerKekPath.js} +3 -3
- package/data/documents/shared/containerKek/containerKekPath.js.map +1 -0
- package/data/documents/shared/{containerKekPathHistory.d.ts → containerKek/containerKekPathHistory.d.ts} +3 -3
- package/data/documents/shared/{containerKekPathHistory.js → containerKek/containerKekPathHistory.js} +4 -4
- package/data/documents/shared/containerKek/containerKekPathHistory.js.map +1 -0
- package/data/documents/shared/{containerKekPathVerification.d.ts → containerKek/containerKekPathVerification.d.ts} +5 -5
- package/data/documents/shared/{containerKekPathVerification.js → containerKek/containerKekPathVerification.js} +2 -2
- package/data/documents/shared/containerKek/containerKekPathVerification.js.map +1 -0
- package/data/documents/shared/{containerKekWrapping.js → containerKek/containerKekWrapping.js} +3 -3
- package/data/documents/shared/containerKek/containerKekWrapping.js.map +1 -0
- package/data/documents/shared/{keyringLogWalk.d.ts → containerKek/keyringLogWalk.d.ts} +2 -2
- package/data/documents/shared/{keyringLogWalk.js → containerKek/keyringLogWalk.js} +1 -1
- package/data/documents/shared/{keyringRebuild.d.ts → containerKek/keyringRebuild.d.ts} +3 -3
- package/data/documents/shared/{keyringRebuild.js → containerKek/keyringRebuild.js} +3 -3
- package/data/documents/shared/containerKek/keyringRebuild.js.map +1 -0
- package/data/documents/shared/crypto.js +2 -2
- package/data/documents/shared/crypto.js.map +1 -1
- package/data/documents/shared/events.js +1 -1
- package/data/documents/shared/{projection.d.ts → projection/index.d.ts} +7 -7
- package/data/documents/shared/{projection.js → projection/index.js} +9 -9
- package/data/documents/shared/projection/index.js.map +1 -0
- package/data/documents/shared/{projectionContentKeys.d.ts → projection/projectionContentKeys.d.ts} +6 -6
- package/data/documents/shared/{projectionContentKeys.js → projection/projectionContentKeys.js} +9 -9
- package/data/documents/shared/projection/projectionContentKeys.js.map +1 -0
- package/data/documents/shared/{projectionTargets.d.ts → projection/projectionTargets.d.ts} +4 -4
- package/data/documents/shared/{projectionTargets.js → projection/projectionTargets.js} +3 -3
- package/data/documents/shared/projection/projectionTargets.js.map +1 -0
- package/data/documents/shared/responses.d.ts +1 -1
- package/data/documents/shared/responses.js +1 -1
- package/data/documents/shared/responses.js.map +1 -1
- package/data/documents/shared/{documentSyncUpdateDecryption.js → sync/documentSyncUpdateDecryption.js} +10 -10
- package/data/documents/shared/sync/documentSyncUpdateDecryption.js.map +1 -0
- package/data/documents/shared/{documentSyncUpdateIsolation.d.ts → sync/documentSyncUpdateIsolation.d.ts} +3 -3
- package/data/documents/shared/{documentSyncUpdateIsolation.js → sync/documentSyncUpdateIsolation.js} +1 -1
- package/data/documents/shared/sync/documentSyncUpdateIsolation.js.map +1 -0
- package/data/documents/shared/{mutationAcknowledgement.js → sync/mutationAcknowledgement.js} +1 -1
- package/data/documents/shared/sync/mutationAcknowledgement.js.map +1 -0
- package/data/documents/shared/{pullContinuation.js → sync/pullContinuation.js} +1 -1
- package/data/documents/shared/{syncPagination.d.ts → sync/syncPagination.d.ts} +2 -2
- package/data/documents/shared/{syncPagination.js → sync/syncPagination.js} +1 -1
- package/data/documents/shared/sync/syncPagination.js.map +1 -0
- package/data/documents/shared/{syncResponseAuthorization.js → sync/syncResponseAuthorization.js} +3 -3
- package/data/documents/shared/sync/syncResponseAuthorization.js.map +1 -0
- package/data/documents/shared/{syncResponses.d.ts → sync/syncResponses.d.ts} +2 -2
- package/data/documents/shared/{syncResponses.js → sync/syncResponses.js} +6 -6
- package/data/documents/shared/sync/syncResponses.js.map +1 -0
- package/data/documents/shared/{syncSubmitFailure.d.ts → sync/syncSubmitFailure.d.ts} +1 -1
- package/data/documents/shared/types.d.ts +3 -3
- package/data/documents/shared/types.js.map +1 -1
- package/data/keyingProjectionVerification/checkpoints/accessManifestCheckpointEnforcement.js +1 -1
- package/data/keyingProjectionVerification/checkpoints/accessManifestCheckpointEnforcement.js.map +1 -1
- package/data/keyingProjectionVerification/checkpoints/checkpointContext.d.ts +1 -1
- package/data/keyingProjectionVerification/checkpoints/checkpointContext.js +1 -1
- package/data/keyingProjectionVerification/checkpoints/checkpointContext.js.map +1 -1
- package/data/keyingProjectionVerification/checkpoints/manifestCheckpointVerification.js +1 -1
- package/data/keyingProjectionVerification/checkpoints/manifestCheckpointVerification.js.map +1 -1
- package/data/keyingProjectionVerification/documentPurge/documentPurgeCheckpointCurrency.js +4 -4
- package/data/keyingProjectionVerification/documentPurge/documentPurgeCheckpointCurrency.js.map +1 -1
- package/data/keyingProjectionVerification/documentPurge/documentPurgeCheckpointEnforcement.js +1 -1
- package/data/keyingProjectionVerification/documentPurge/documentPurgeCheckpointEnforcement.js.map +1 -1
- package/data/keyingProjectionVerification/documentPurge/documentPurgePolicyCheckpoints.js +1 -1
- package/data/keyingProjectionVerification/documentPurge/documentPurgePolicyCheckpoints.js.map +1 -1
- package/data/keyingProjectionVerification/documentPurge/documentPurgePolicyCurrency.js +1 -1
- package/data/keyingProjectionVerification/documentPurge/documentPurgePolicyCurrency.js.map +1 -1
- package/data/keyingProjectionVerification/principalPolicy/principalPolicyCache.js +3 -3
- package/data/keyingProjectionVerification/principalPolicy/principalPolicyCache.js.map +1 -1
- package/data/keyingProjectionVerification/principalPolicy/principalPolicyVerification.js +4 -4
- package/data/keyingProjectionVerification/principalPolicy/principalPolicyVerification.js.map +1 -1
- package/data/keyingProjectionVerification/principalPolicy/resolvedPrincipalPolicy.js +2 -2
- package/data/keyingProjectionVerification/principalPolicy/resolvedPrincipalPolicy.js.map +1 -1
- package/data/persistence/container-contents/containerContentsPersistence.js +3 -3
- package/data/persistence/container-contents/containerContentsPersistence.js.map +1 -1
- package/data/persistence/container-contents/containerContentsPersistenceTypes.d.ts +2 -2
- package/data/persistence/container-contents/containerContentsPersistenceTypes.js.map +1 -1
- package/data/persistence/container-contents/containerCreateIntentSettlement.js +1 -1
- package/data/persistence/container-contents/containerDeletionPersistence.js +2 -2
- package/data/persistence/container-contents/containerDocumentReassignment.js +2 -2
- package/data/persistence/container-contents/containerDocumentReassignment.js.map +1 -1
- package/data/persistence/container-contents/containerHydrationPersistence.js +3 -3
- package/data/persistence/container-contents/containerHydrationPersistence.js.map +1 -1
- package/data/persistence/container-contents/containerIntentPersistence.js +1 -1
- package/data/persistence/container-contents/containerMetadataMutationPersistence.js +5 -5
- package/data/persistence/container-contents/containerMetadataMutationPersistence.js.map +1 -1
- package/data/persistence/container-contents/containerMetadataPullContinuationPersistence.js +1 -1
- package/data/persistence/container-contents/containerMetadataRows.js +3 -3
- package/data/persistence/container-contents/containerMetadataRows.js.map +1 -1
- package/data/persistence/container-contents/containerMoveAbandonPersistence.js +1 -1
- package/data/persistence/container-contents/containerMoveIntentRows.js +1 -1
- package/data/persistence/container-contents/containerPendingUpdatePersistence.js +3 -3
- package/data/persistence/container-contents/containerPendingUpdatePersistence.js.map +1 -1
- package/data/persistence/container-contents/containerRebindPersistence.js +1 -1
- package/data/persistence/container-contents/containerReconcilePersistence.js +2 -2
- package/data/persistence/container-contents/containerRecoveryPersistence.js +1 -1
- package/data/persistence/container-contents/containerRemovalWork.js +3 -3
- package/data/persistence/container-contents/containerRemovalWork.js.map +1 -1
- package/data/persistence/container-contents/containerStructuralRepair.js +1 -1
- package/data/persistence/container-contents/documentLinkRemovalRepair.js +2 -2
- package/data/persistence/container-contents/documentLinkRemovalRepair.js.map +1 -1
- package/data/persistence/container-contents/documentMoveIntentPersistence.js +2 -2
- package/data/persistence/container-contents/documentMoveIntentPersistence.js.map +1 -1
- package/data/persistence/container-contents/documentPlacementIntentEnqueue.js +2 -2
- package/data/persistence/container-contents/documentPlacementIntentEnqueue.js.map +1 -1
- package/data/persistence/container-contents/documentPurgePlacement.js +1 -1
- package/data/persistence/container-contents/dormantContainerMetadata.js +1 -1
- package/data/persistence/container-contents/dormantMetadataSweep.js +1 -1
- package/data/persistence/container-contents/pendingContainerCreate.js +1 -1
- package/data/persistence/container-contents/supersededContainerBindings.js +1 -1
- package/data/persistence/containers/containerPersistence.js +1 -1
- package/data/persistence/containers/containerSyncWatermarkPersistence.js +1 -1
- package/data/persistence/containers/documentContainerProjectionPersistence.js +1 -1
- package/data/persistence/containers/documentPlacement.js +1 -1
- package/data/persistence/documents/containerDocumentTombstoneHoldsPersistence.js +1 -1
- package/data/persistence/documents/documentDiscoveryEvidencePersistence.js +3 -3
- package/data/persistence/documents/documentDiscoveryEvidencePersistence.js.map +1 -1
- package/data/persistence/documents/documentDiscoveryReset.js +1 -1
- package/data/persistence/documents/documentDiscoveryReset.js.map +1 -1
- package/data/persistence/documents/documentsPersistence.js +3 -3
- package/data/persistence/documents/documentsPersistence.js.map +1 -1
- package/data/persistence/documents/internal/attachmentStagingPersistence.js +1 -1
- package/data/persistence/documents/internal/containerDocumentTombstoneHolds.js +1 -1
- package/data/persistence/documents/internal/containerDocumentTombstones.js +1 -1
- package/data/persistence/documents/internal/createDocumentWithHistoryCheckpoint.js +2 -2
- package/data/persistence/documents/internal/createDocumentWithHistoryCheckpoint.js.map +1 -1
- package/data/persistence/documents/internal/discardDocument.js +3 -3
- package/data/persistence/documents/internal/discardDocument.js.map +1 -1
- package/data/persistence/documents/internal/documentDeletionPersistence.js +4 -4
- package/data/persistence/documents/internal/documentDeletionPersistence.js.map +1 -1
- package/data/persistence/documents/internal/documentMutationPersistence.js +5 -5
- package/data/persistence/documents/internal/documentMutationPersistence.js.map +1 -1
- package/data/persistence/documents/internal/documentProjectionRows.js +1 -1
- package/data/persistence/documents/internal/documentPullContinuationPersistence.js +1 -1
- package/data/persistence/documents/internal/documentRows.js +2 -2
- package/data/persistence/documents/internal/documentRows.js.map +1 -1
- package/data/persistence/documents/internal/documentSummaryQueries.js +1 -1
- package/data/persistence/documents/internal/ensureDocumentsSchema.js +2 -2
- package/data/persistence/documents/internal/hydratedAttachmentPersistence.js +1 -1
- package/data/persistence/documents/internal/orphanSideRows.js +2 -2
- package/data/persistence/documents/internal/orphanSideRows.js.map +1 -1
- package/data/persistence/documents/internal/pendingCreateAdoption.js +1 -1
- package/data/persistence/documents/internal/rowQueryPersistence.js +2 -2
- package/data/persistence/documents/internal/syncQueuePersistence.js +3 -3
- package/data/persistence/documents/internal/syncQueuePersistence.js.map +1 -1
- package/data/persistence/documents/types.d.ts +3 -3
- package/data/persistence/documents/types.js.map +1 -1
- package/data/persistence/{documentPurgeCheckpointPersistence.d.ts → keyingCheckpoints/documentPurgeCheckpointPersistence.d.ts} +2 -2
- package/data/persistence/{documentPurgeCheckpointPersistence.js → keyingCheckpoints/documentPurgeCheckpointPersistence.js} +4 -4
- package/data/persistence/keyingCheckpoints/documentPurgeCheckpointPersistence.js.map +1 -0
- package/data/persistence/{keyingCheckpointAdvancePersistence.js → keyingCheckpoints/keyingCheckpointAdvancePersistence.js} +9 -9
- package/data/persistence/keyingCheckpoints/keyingCheckpointAdvancePersistence.js.map +1 -0
- package/data/persistence/{keyingCheckpointEvidence.js → keyingCheckpoints/keyingCheckpointEvidence.js} +1 -1
- package/data/persistence/{keyingCheckpointPersistence.js → keyingCheckpoints/keyingCheckpointPersistence.js} +5 -5
- package/data/persistence/keyingCheckpoints/keyingCheckpointPersistence.js.map +1 -0
- package/data/persistence/{locallyAcknowledgedCheckpointPersistence.d.ts → keyingCheckpoints/locallyAcknowledgedCheckpointPersistence.d.ts} +4 -4
- package/data/persistence/{locallyAcknowledgedCheckpointPersistence.js → keyingCheckpoints/locallyAcknowledgedCheckpointPersistence.js} +7 -7
- package/data/persistence/keyingCheckpoints/locallyAcknowledgedCheckpointPersistence.js.map +1 -0
- package/data/persistence/{organizationReplacementCheckpointPersistence.js → keyingCheckpoints/organizationReplacementCheckpointPersistence.js} +6 -6
- package/data/persistence/keyingCheckpoints/organizationReplacementCheckpointPersistence.js.map +1 -0
- package/data/persistence/{principalAuthorizationCheckpoints.js → keyingCheckpoints/principalAuthorizationCheckpoints.js} +1 -1
- package/data/persistence/keyingCheckpoints/principalAuthorizationCheckpoints.js.map +1 -0
- package/data/persistence/organizationFounderPersistence.js +2 -2
- package/data/persistence/organizationFounderPersistence.js.map +1 -1
- package/data/persistence/organizations/organizationAccessRevocationPersistence.js +3 -3
- package/data/persistence/organizations/organizationAccessRevocationPersistence.js.map +1 -1
- package/data/persistence/organizations/organizationDataUsagePersistence.js +2 -2
- package/data/persistence/organizations/organizationDataUsagePersistence.js.map +1 -1
- package/data/persistence/organizations/organizationGroupNamePersistence.js +2 -2
- package/data/persistence/organizations/organizationGroupNamePersistence.js.map +1 -1
- package/data/persistence/organizations/organizationPresentationDenialPersistence.js +2 -2
- package/data/persistence/organizations/organizationPresentationDenialPersistence.js.map +1 -1
- package/data/persistence/organizations/organizationProfileDocumentPointers.js +2 -2
- package/data/persistence/organizations/organizationProfileDocumentPointers.js.map +1 -1
- package/data/persistence/organizations/organizationProvisioningAttemptPersistence.js +1 -1
- package/data/persistence/organizations/organizationProvisioningAttemptPersistence.js.map +1 -1
- package/data/persistence/organizations/organizationReadModelGrantPersistence.js +1 -1
- package/data/persistence/organizations/organizationReadModelGrantPersistence.js.map +1 -1
- package/data/persistence/organizations/organizationReadModelMemberLoad.js +1 -1
- package/data/persistence/organizations/organizationReadModelMemberLoad.js.map +1 -1
- package/data/persistence/organizations/organizationReadModelMembershipPersistence.js +1 -1
- package/data/persistence/organizations/organizationReadModelMembershipPersistence.js.map +1 -1
- package/data/persistence/organizations/organizationReadModelPersistence.js +3 -3
- package/data/persistence/organizations/organizationReadModelPersistence.js.map +1 -1
- package/data/persistence/organizations/organizationReadModelProjection.js +1 -1
- package/data/persistence/organizations/organizationReadModelProjection.js.map +1 -1
- package/data/persistence/organizations/organizationReadModelPurge.js +3 -3
- package/data/persistence/organizations/organizationReadModelPurge.js.map +1 -1
- package/data/persistence/principalCurrentAcknowledgementPersistence.d.ts +3 -3
- package/data/persistence/principalCurrentAcknowledgementPersistence.js +10 -10
- package/data/persistence/principalCurrentAcknowledgementPersistence.js.map +1 -1
- package/data/persistence/{principalHistoryEvidencePersistence.d.ts → principalHistory/principalHistoryEvidencePersistence.d.ts} +4 -4
- package/data/persistence/{principalHistoryEvidencePersistence.js → principalHistory/principalHistoryEvidencePersistence.js} +7 -7
- package/data/persistence/principalHistory/principalHistoryEvidencePersistence.js.map +1 -0
- package/data/persistence/{principalHistoryIncompleteRetention.js → principalHistory/principalHistoryIncompleteRetention.js} +1 -1
- package/data/persistence/principalHistory/principalHistoryIncompleteRetention.js.map +1 -0
- package/data/persistence/{principalHistoryNodeRetention.js → principalHistory/principalHistoryNodeRetention.js} +4 -4
- package/data/persistence/principalHistory/principalHistoryNodeRetention.js.map +1 -0
- package/data/persistence/{principalHistoryPrefixPersistence.d.ts → principalHistory/principalHistoryPrefixPersistence.d.ts} +2 -2
- package/data/persistence/{principalHistoryPrefixPersistence.js → principalHistory/principalHistoryPrefixPersistence.js} +6 -6
- package/data/persistence/principalHistory/principalHistoryPrefixPersistence.js.map +1 -0
- package/data/persistence/{principalHistoryRootOwnership.js → principalHistory/principalHistoryRootOwnership.js} +1 -1
- package/data/persistence/principalHistory/principalHistoryRootOwnership.js.map +1 -0
- package/data/persistence/{principalHistoryStagePersistence.d.ts → principalHistory/principalHistoryStagePersistence.d.ts} +2 -2
- package/data/persistence/{principalHistoryStagePersistence.js → principalHistory/principalHistoryStagePersistence.js} +6 -6
- package/data/persistence/principalHistory/principalHistoryStagePersistence.js.map +1 -0
- package/data/persistence/{principalHistoryStageRetention.js → principalHistory/principalHistoryStageRetention.js} +2 -2
- package/data/persistence/principalHistory/principalHistoryStageRetention.js.map +1 -0
- package/data/persistence/{principalHistoryUnpublishedRetention.js → principalHistory/principalHistoryUnpublishedRetention.js} +3 -3
- package/data/persistence/principalHistory/principalHistoryUnpublishedRetention.js.map +1 -0
- package/data/persistence/{principalGrantRetirementPersistence.d.ts → principalKeys/principalGrantRetirementPersistence.d.ts} +2 -2
- package/data/persistence/{principalGrantRetirementPersistence.js → principalKeys/principalGrantRetirementPersistence.js} +2 -2
- package/data/persistence/principalKeys/principalGrantRetirementPersistence.js.map +1 -0
- package/data/persistence/{principalKeyEnvelopeArchivePersistence.js → principalKeys/principalKeyEnvelopeArchivePersistence.js} +3 -3
- package/data/persistence/principalKeys/principalKeyEnvelopeArchivePersistence.js.map +1 -0
- package/data/persistence/{principalKeyEnvelopeCandidates.js → principalKeys/principalKeyEnvelopeCandidates.js} +9 -9
- package/data/persistence/principalKeys/principalKeyEnvelopeCandidates.js.map +1 -0
- package/data/persistence/principalMutationJournalPersistence.d.ts +1 -1
- package/data/persistence/principalMutationJournalPersistence.js +1 -1
- package/data/persistence/principalMutationJournalPersistence.js.map +1 -1
- package/data/persistence/{principalPolicyBundleIntegrity.js → principalPolicy/principalPolicyBundleIntegrity.js} +3 -3
- package/data/persistence/principalPolicy/principalPolicyBundleIntegrity.js.map +1 -0
- package/data/persistence/{principalPolicyCheckpointSelection.js → principalPolicy/principalPolicyCheckpointSelection.js} +2 -2
- package/data/persistence/principalPolicy/principalPolicyCheckpointSelection.js.map +1 -0
- package/data/persistence/{principalPolicyOrganizationPersistence.js → principalPolicy/principalPolicyOrganizationPersistence.js} +2 -2
- package/data/persistence/principalPolicy/principalPolicyOrganizationPersistence.js.map +1 -0
- package/data/persistence/{principalPolicyPersistence.js → principalPolicy/principalPolicyPersistence.js} +5 -5
- package/data/persistence/principalPolicy/principalPolicyPersistence.js.map +1 -0
- package/data/persistence/{principalPolicyReferenceCheckpoint.js → principalPolicy/principalPolicyReferenceCheckpoint.js} +3 -3
- package/data/persistence/principalPolicy/principalPolicyReferenceCheckpoint.js.map +1 -0
- package/data/persistence/{principalPolicyReferenceIndexPersistence.js → principalPolicy/principalPolicyReferenceIndexPersistence.js} +4 -4
- package/data/persistence/principalPolicy/principalPolicyReferenceIndexPersistence.js.map +1 -0
- package/data/persistence/{principalPolicyReferencePersistence.js → principalPolicy/principalPolicyReferencePersistence.js} +5 -5
- package/data/persistence/principalPolicy/principalPolicyReferencePersistence.js.map +1 -0
- package/data/persistence/{verifiedPrincipalPolicyBundle.js → principalPolicy/verifiedPrincipalPolicyBundle.js} +2 -2
- package/data/persistence/principalPolicy/verifiedPrincipalPolicyBundle.js.map +1 -0
- package/data/persistence/{verifiedPrincipalPolicyCurrent.js → principalPolicy/verifiedPrincipalPolicyCurrent.js} +2 -2
- package/data/persistence/principalPolicy/verifiedPrincipalPolicyCurrent.js.map +1 -0
- package/data/persistence/{verifiedPrincipalPolicyRetentionPersistence.js → principalPolicy/verifiedPrincipalPolicyRetentionPersistence.js} +1 -1
- package/data/persistence/principalPolicy/verifiedPrincipalPolicyRetentionPersistence.js.map +1 -0
- package/data/persistence/securityIncidentPersistence.js +1 -1
- package/data/persistence/securityIncidentPersistence.js.map +1 -1
- package/data/persistence/trustedUserIdentityPinPersistence.js +1 -1
- package/data/persistence/verifiedManifestBundlePersistence.d.ts +1 -1
- package/data/persistence/verifiedManifestBundlePersistence.js +4 -4
- package/data/persistence/verifiedManifestBundlePersistence.js.map +1 -1
- package/data/principals/organizationGroupRoles.js +2 -2
- package/data/principals/organizationGroupRoles.js.map +1 -1
- package/data/principals/principalHistoryPrefixProtection.js.map +1 -1
- package/data/principals/principalHistoryStageProtection.js.map +1 -1
- package/data/principals/principalPolicyCrypto.js +1 -1
- package/data/principals/principalPolicyCrypto.js.map +1 -1
- package/data/sqlite/{documentHistoryPersistence.d.ts → documentPersistence/documentHistoryPersistence.d.ts} +1 -1
- package/data/sqlite/{documentHistoryPersistence.js → documentPersistence/documentHistoryPersistence.js} +5 -5
- package/data/sqlite/documentPersistence/documentHistoryPersistence.js.map +1 -0
- package/data/sqlite/{documentOrphanBlobReclaims.js → documentPersistence/documentOrphanBlobReclaims.js} +1 -1
- package/data/sqlite/documentPersistence/documentOrphanBlobReclaims.js.map +1 -0
- package/data/sqlite/{documentPendingUpdatePersistence.d.ts → documentPersistence/documentPendingUpdatePersistence.d.ts} +2 -2
- package/data/sqlite/{documentPendingUpdatePersistence.js → documentPersistence/documentPendingUpdatePersistence.js} +2 -2
- package/data/sqlite/documentPersistence/documentPendingUpdatePersistence.js.map +1 -0
- package/data/sqlite/{documentPersistenceTypes.d.ts → documentPersistence/documentPersistenceTypes.d.ts} +2 -2
- package/data/sqlite/documentPersistence/documentPersistenceTypes.js.map +1 -0
- package/data/sqlite/{documentRecordPersistence.d.ts → documentPersistence/documentRecordPersistence.d.ts} +1 -1
- package/data/sqlite/{documentRecordPersistence.js → documentPersistence/documentRecordPersistence.js} +4 -4
- package/data/sqlite/documentPersistence/documentRecordPersistence.js.map +1 -0
- package/data/sqlite/{documentSyncFailurePersistence.d.ts → documentPersistence/documentSyncFailurePersistence.d.ts} +2 -2
- package/data/sqlite/{documentSyncFailurePersistence.js → documentPersistence/documentSyncFailurePersistence.js} +3 -3
- package/data/sqlite/documentPersistence/documentSyncFailurePersistence.js.map +1 -0
- package/data/sqlite/{documentPersistence.d.ts → documentPersistence/index.d.ts} +2 -2
- package/data/sqlite/{documentPersistence.js → documentPersistence/index.js} +5 -5
- package/data/sqlite/documentPersistence/index.js.map +1 -0
- package/data/sqlite/{containerSchema.d.ts → schema/containerSchema.d.ts} +1 -1
- package/data/sqlite/{containerSchema.js → schema/containerSchema.js} +1 -1
- package/data/sqlite/schema/containerSchema.js.map +1 -0
- package/data/sqlite/{schema.d.ts → schema/index.d.ts} +1 -1
- package/data/sqlite/{schema.js → schema/index.js} +3 -3
- package/data/sqlite/schema/index.js.map +1 -0
- package/data/sqlite/{organizationDataUsageSchema.js → schema/organizationDataUsageSchema.js} +1 -1
- package/data/sqlite/schema/organizationDataUsageSchema.js.map +1 -0
- package/data/sqlite/{organizationProvisioningAttemptSchema.js → schema/organizationProvisioningAttemptSchema.js} +1 -1
- package/data/sqlite/schema/organizationProvisioningAttemptSchema.js.map +1 -0
- package/data/sqlite/{organizationReadModelTableRegistry.d.ts → schema/organizationReadModelTableRegistry.d.ts} +1 -1
- package/data/sqlite/{organizationReadModelTableRegistry.js → schema/organizationReadModelTableRegistry.js} +1 -1
- package/data/sqlite/schema/organizationReadModelTableRegistry.js.map +1 -0
- package/data/sqlite/{principalHistoryEvidenceSchema.d.ts → schema/principalHistoryEvidenceSchema.d.ts} +1 -1
- package/data/sqlite/{principalHistoryEvidenceSchema.js → schema/principalHistoryEvidenceSchema.js} +2 -2
- package/data/sqlite/schema/principalHistoryEvidenceSchema.js.map +1 -0
- package/data/sqlite/{principalHistoryNodeRetentionSchema.js → schema/principalHistoryNodeRetentionSchema.js} +1 -1
- package/data/sqlite/schema/principalHistoryNodeRetentionSchema.js.map +1 -0
- package/data/sqlite/{principalHistoryRetentionSchema.js → schema/principalHistoryRetentionSchema.js} +1 -1
- package/data/sqlite/{principalHistoryRetentionSchema.js.map → schema/principalHistoryRetentionSchema.js.map} +1 -1
- package/data/sqlite/{principalHistoryStageSchema.d.ts → schema/principalHistoryStageSchema.d.ts} +1 -1
- package/data/sqlite/{principalHistoryStageSchema.js → schema/principalHistoryStageSchema.js} +2 -2
- package/data/sqlite/schema/principalHistoryStageSchema.js.map +1 -0
- package/data/sqlite/{principalMutationJournalSchema.d.ts → schema/principalMutationJournalSchema.d.ts} +1 -1
- package/data/sqlite/{principalMutationJournalSchema.js → schema/principalMutationJournalSchema.js} +1 -1
- package/data/sqlite/{principalMutationJournalSchema.js.map → schema/principalMutationJournalSchema.js.map} +1 -1
- package/data/sqlite/{principalPolicySchema.js → schema/principalPolicySchema.js} +1 -1
- package/data/sqlite/schema/principalPolicySchema.js.map +1 -0
- package/data/sqlite/{securityIncidentSchema.d.ts → schema/securityIncidentSchema.d.ts} +1 -1
- package/data/sqlite/{securityIncidentSchema.js → schema/securityIncidentSchema.js} +1 -1
- package/data/sqlite/schema/securityIncidentSchema.js.map +1 -0
- package/data/sqlite/{verifiedManifestBundleSchema.d.ts → schema/verifiedManifestBundleSchema.d.ts} +1 -1
- package/data/sqlite/{verifiedManifestBundleSchema.js → schema/verifiedManifestBundleSchema.js} +1 -1
- package/data/sqlite/schema/verifiedManifestBundleSchema.js.map +1 -0
- package/data/sqlite/sqlitePersistenceRuntime.d.ts +1 -1
- package/data/sqlite/sqlitePersistenceRuntime.js +1 -1
- package/package.json +1 -1
- package/sqlite/index.d.ts +1 -1
- package/sqlite/index.js +1 -1
- package/stores/documents/documentStore/history/historyRebuild.js +1 -1
- package/stores/documents/documentStore/history/historyRebuild.js.map +1 -1
- package/stores/documents/documentStore/state.js.map +1 -1
- package/stores/documents/documentStore/sync/syncFinalize.js +1 -1
- package/stores/documents/documentStore/sync/syncFinalize.js.map +1 -1
- package/stores/documents/documentStore/sync/syncUpdateImport.js +1 -1
- package/stores/documents/documentStore/sync/syncUpdateImport.js.map +1 -1
- package/workflows/blobs/detach.js +1 -1
- package/workflows/blobs/hydration/decrypt.js +1 -1
- package/workflows/blobs/upload/index.js +1 -1
- package/workflows/blobs/verification/retainedAttachmentVerification.js +1 -1
- package/workflows/blobs/verification/writerProjection.js +1 -1
- package/workflows/container-contents/container-state/create/createWithMetadata.js +2 -2
- package/workflows/container-contents/container-state/create/createWithMetadata.js.map +1 -1
- package/workflows/container-contents/container-state/share/index.js +1 -1
- package/workflows/container-contents/documentLinks/index.js +1 -1
- package/workflows/container-contents/documentMove/documentMoveVanishedRefresh.js +1 -1
- package/workflows/container-contents/documentPriming/documentHydrationProbe.js +1 -1
- package/workflows/container-contents/documentPriming/index.js +1 -1
- package/workflows/container-contents/documentQueries/index.js +1 -1
- package/workflows/container-contents/documentQueries/sql.js +1 -1
- package/workflows/container-contents/info/blobInfo.js +1 -1
- package/workflows/container-contents/info/containerInfo.js +1 -1
- package/workflows/container-contents/info/documentInfo.js +1 -1
- package/workflows/container-contents/metadata/index.js +1 -1
- package/workflows/container-contents/metadata/index.js.map +1 -1
- package/workflows/container-contents/metadata/metadataEvents.d.ts +1 -1
- package/workflows/container-contents/metadata/metadataIncomingUpdateIsolation.js +2 -2
- package/workflows/container-contents/metadata/metadataIncomingUpdateIsolation.js.map +1 -1
- package/workflows/container-contents/metadata/metadataMutationPreparation.js +1 -1
- package/workflows/container-contents/metadata/metadataMutationPreparation.js.map +1 -1
- package/workflows/container-contents/metadata/metadataPullContinuationInvalidation.js +1 -1
- package/workflows/container-contents/metadata/metadataPullContinuationInvalidation.js.map +1 -1
- package/workflows/container-contents/metadata/metadataRemoteSync.d.ts +1 -1
- package/workflows/container-contents/metadata/metadataSyncErrors.js +1 -1
- package/workflows/container-contents/metadata/metadataSyncErrors.js.map +1 -1
- package/workflows/container-contents/metadata/metadataSyncSettlement.d.ts +1 -1
- package/workflows/container-contents/metadata/metadataSyncSettlement.js.map +1 -1
- package/workflows/container-contents/metadata/metadataTypes.d.ts +1 -1
- package/workflows/container-contents/metadata/metadataTypes.js.map +1 -1
- package/workflows/container-contents/pendingWrites/index.js +2 -2
- package/workflows/container-contents/pendingWrites/sources.js +1 -1
- package/workflows/container-contents/remoteHydration/destination/replacementBinding.js +1 -1
- package/workflows/container-contents/remoteHydration/destination/replacementBinding.js.map +1 -1
- package/workflows/container-contents/remoteHydration/reattachMetadata.js.map +1 -1
- package/workflows/container-contents/tombstones/documentTombstoneEvidence.js +2 -2
- package/workflows/container-contents/tombstones/documentTombstoneEvidence.js.map +1 -1
- package/workflows/containers/child/create/index.js +2 -2
- package/workflows/containers/child/create/index.js.map +1 -1
- package/workflows/containers/child/move/index.js +1 -1
- package/workflows/containers/child/move/moveRotation.js +1 -1
- package/workflows/containers/child/move/moveRotation.js.map +1 -1
- package/workflows/containers/child/move/moveWraps.js +1 -1
- package/workflows/containers/child/move/moveWraps.js.map +1 -1
- package/workflows/containers/child/recite.js +2 -2
- package/workflows/containers/child/recite.js.map +1 -1
- package/workflows/containers/child/rotation/rotationContext.js +3 -3
- package/workflows/containers/child/rotation/rotationContext.js.map +1 -1
- package/workflows/containers/child/share/currentSharePrincipalPolicy.js +1 -1
- package/workflows/containers/child/share/currentSharePrincipalPolicy.js.map +1 -1
- package/workflows/containers/child/share/index.js +1 -1
- package/workflows/containers/child/share/index.js.map +1 -1
- package/workflows/containers/child/share/shareAncestorRepair.js +2 -2
- package/workflows/containers/child/share/shareAncestorRepair.js.map +1 -1
- package/workflows/containers/child/share/shareMaterialization.js +1 -1
- package/workflows/containers/child/share/sharePrincipalPolicy.js +5 -5
- package/workflows/containers/child/share/sharePrincipalPolicy.js.map +1 -1
- package/workflows/containers/index.d.ts +3 -3
- package/workflows/containers/index.js +2 -2
- package/workflows/containers/index.js.map +1 -1
- package/workflows/containers/writeRefusal.js +1 -1
- package/workflows/containers/writeRefusal.js.map +1 -1
- package/workflows/documents/create/createAdoption.js +1 -1
- package/workflows/documents/create/createResponse.js +2 -2
- package/workflows/documents/create/createResponse.js.map +1 -1
- package/workflows/documents/create/index.js +1 -1
- package/workflows/documents/documentMutationCommit.d.ts +1 -1
- package/workflows/documents/documentMutationPreparation.d.ts +1 -1
- package/workflows/documents/documentMutationPreparation.js +1 -1
- package/workflows/documents/documentMutationPreparation.js.map +1 -1
- package/workflows/documents/index.d.ts +5 -5
- package/workflows/documents/index.js +5 -5
- package/workflows/documents/index.js.map +1 -1
- package/workflows/documents/linkSet/index.js +2 -2
- package/workflows/documents/linkSet/index.js.map +1 -1
- package/workflows/documents/linkSet/linkSetAuthority.js +1 -1
- package/workflows/documents/linkSet/linkSetBlobRewraps.js +1 -1
- package/workflows/documents/linkSet/linkSetProjectionSeed.js +1 -1
- package/workflows/documents/linkSet/linkSetRemote.js +1 -1
- package/workflows/documents/linkSet/linkSetRemote.js.map +1 -1
- package/workflows/documents/purge/index.js +1 -1
- package/workflows/documents/sync/index.js +2 -2
- package/workflows/documents/sync/index.js.map +1 -1
- package/workflows/documents/sync/initialSync.js +1 -1
- package/workflows/documents/sync/readOnlyProjectionFailure.js +1 -1
- package/workflows/documents/sync/readOnlyProjectionFailure.js.map +1 -1
- package/workflows/documents/sync/readOnlySync.d.ts +3 -3
- package/workflows/documents/sync/readOnlySync.js +1 -1
- package/workflows/documents/sync/readOnlySync.js.map +1 -1
- package/workflows/documents/sync/reportDocumentSyncQuarantine.js.map +1 -1
- package/workflows/documents/sync/syncAttemptPlanning.js +2 -2
- package/workflows/documents/sync/syncAttemptPlanning.js.map +1 -1
- package/workflows/documents/sync/syncAttemptState.d.ts +2 -2
- package/workflows/documents/sync/syncAttemptState.js.map +1 -1
- package/workflows/documents/sync/syncResponseResult.js +2 -2
- package/workflows/documents/sync/syncResponseResult.js.map +1 -1
- package/workflows/documents/syncFailures/index.js +1 -1
- package/workflows/documents/syncFailures/index.js.map +1 -1
- package/workflows/documents/syncFailures/syncAbandon.js.map +1 -1
- package/workflows/documents/syncFailures/syncFailureClassification.js +1 -1
- package/workflows/documents/syncFailures/syncFailureClassification.js.map +1 -1
- package/workflows/documents/syncPlan/syncContentKeys.d.ts +1 -1
- package/workflows/documents/syncPlan/syncContentKeys.js +3 -3
- package/workflows/documents/syncPlan/syncContentKeys.js.map +1 -1
- package/workflows/documents/syncPlan/syncPlanMaterial.js +2 -2
- package/workflows/documents/syncPlan/syncPlanMaterial.js.map +1 -1
- package/workflows/documents/syncRekeys/syncAutomaticContainerRekeys.js +2 -2
- package/workflows/documents/syncRekeys/syncAutomaticContainerRekeys.js.map +1 -1
- package/workflows/documents/syncRekeys/syncContainerRekeyPreparation.js +1 -1
- package/workflows/documents/syncRekeys/syncRecoveryRekey.d.ts +1 -1
- package/workflows/documents/syncRekeys/syncRecoveryRekey.js +1 -1
- package/workflows/organizations/currentOrganizationAuthority.js +2 -2
- package/workflows/organizations/currentOrganizationAuthority.js.map +1 -1
- package/workflows/organizations/groupMetadata/groupMetadataAccess.js +1 -1
- package/workflows/organizations/groupMetadata/groupMetadataAccess.js.map +1 -1
- package/workflows/organizations/groupMetadata/groupMetadataContainerAuthority.js +1 -1
- package/workflows/organizations/groupMetadata/groupMetadataContainerAuthority.js.map +1 -1
- package/workflows/organizations/groupNames/currentOrganizationGroupNames.js +1 -1
- package/workflows/organizations/groupNames/currentOrganizationGroupNames.js.map +1 -1
- package/workflows/organizations/groupNames/groupNameUniqueness.js +3 -3
- package/workflows/organizations/groupNames/groupNameUniqueness.js.map +1 -1
- package/workflows/organizations/groupNames/organizationGroupNamePolicies.js +2 -2
- package/workflows/organizations/groupNames/organizationGroupNamePolicies.js.map +1 -1
- package/workflows/organizations/groupPolicy/currentGroupPolicyMutationContext.js +1 -1
- package/workflows/organizations/groupPolicy/currentGroupPolicyMutationContext.js.map +1 -1
- package/workflows/organizations/groupPolicy/groupPolicyMutationContext.js +2 -2
- package/workflows/organizations/groupPolicy/groupPolicyMutationContext.js.map +1 -1
- package/workflows/organizations/groupPolicy/groupPolicyMutationEvidence.js +1 -1
- package/workflows/organizations/groupPolicy/groupPolicyMutationEvidence.js.map +1 -1
- package/workflows/organizations/groupPolicy/groupPolicyVerification.js +1 -1
- package/workflows/organizations/groupPolicy/groupPolicyVerification.js.map +1 -1
- package/workflows/organizations/groups/createCurrentOrganizationGroup.js +1 -1
- package/workflows/organizations/groups/createCurrentOrganizationGroup.js.map +1 -1
- package/workflows/organizations/groups/deleteOrganizationGroup.js +1 -1
- package/workflows/organizations/groups/deleteOrganizationGroup.js.map +1 -1
- package/workflows/organizations/groups/organizationGroupDirectory.js +1 -1
- package/workflows/organizations/groups/organizationGroupDirectory.js.map +1 -1
- package/workflows/organizations/principalMutations/runtimeCurrentOrganizationMutation.js +1 -1
- package/workflows/organizations/principalMutations/runtimeCurrentOrganizationMutation.js.map +1 -1
- package/workflows/organizations/provisioning/organizationReplacementVerification.js +1 -1
- package/workflows/organizations/provisioning/organizationReplacementVerification.js.map +1 -1
- package/workflows/organizations/readModel/listLocalOrganizations.js +1 -1
- package/workflows/organizations/readModel/localReadModelDetails.js +1 -1
- package/workflows/organizations/readModel/localReadModelDetails.js.map +1 -1
- package/workflows/principals/acknowledgements/acknowledgedPrincipalCurrents.js +1 -1
- package/workflows/principals/acknowledgements/acknowledgedPrincipalCurrents.js.map +1 -1
- package/workflows/principals/acknowledgements/acknowledgedPrincipalPredecessor.d.ts +1 -1
- package/workflows/principals/acknowledgements/acknowledgedPrincipalPredecessor.js +1 -1
- package/workflows/principals/acknowledgements/acknowledgedPrincipalPredecessor.js.map +1 -1
- package/workflows/principals/acknowledgements/initialPrincipalCurrentPublication.js +1 -1
- package/workflows/principals/acknowledgements/initialPrincipalCurrentPublication.js.map +1 -1
- package/workflows/principals/acknowledgements/reconcileAcknowledgedPrincipalCurrent.js +2 -2
- package/workflows/principals/acknowledgements/reconcileAcknowledgedPrincipalCurrent.js.map +1 -1
- package/workflows/principals/externalAdminPolicy.js +2 -2
- package/workflows/principals/externalAdminPolicy.js.map +1 -1
- package/workflows/principals/historyRecovery/loadRecoveredPrincipalHistoryPage.js +2 -2
- package/workflows/principals/historyRecovery/loadRecoveredPrincipalHistoryPage.js.map +1 -1
- package/workflows/principals/historyRecovery/principalHistoryRecoveryPrefix.js +1 -1
- package/workflows/principals/historyRecovery/principalHistoryRecoveryPrefix.js.map +1 -1
- package/workflows/principals/historyRecovery/principalHistoryRecoveryReferences.js +1 -1
- package/workflows/principals/historyRecovery/principalHistoryRecoveryReferences.js.map +1 -1
- package/workflows/principals/historyRecovery/principalHistoryRecoveryStage.js +1 -1
- package/workflows/principals/historyRecovery/principalHistoryRecoveryStage.js.map +1 -1
- package/workflows/principals/historyRecovery/recoverPrincipalPolicyHistory.js +3 -3
- package/workflows/principals/historyRecovery/recoverPrincipalPolicyHistory.js.map +1 -1
- package/workflows/principals/policyCache/index.js +3 -3
- package/workflows/principals/policyCache/index.js.map +1 -1
- package/workflows/principals/policyCache/principalPolicyCacheAdvance.js +1 -1
- package/workflows/principals/policyCache/principalPolicyCacheAdvance.js.map +1 -1
- package/workflows/principals/policyCache/principalPolicyOrganizationScope.js +3 -3
- package/workflows/principals/policyCache/principalPolicyOrganizationScope.js.map +1 -1
- package/workflows/principals/publicHistory/publicPrincipalHistoryAuthority.js.map +1 -1
- package/workflows/principals/publicHistory/publicPrincipalHistoryPage.js +2 -2
- package/workflows/principals/publicHistory/publicPrincipalHistoryPage.js.map +1 -1
- package/workflows/principals/publicHistory/publicPrincipalHistoryProgress.js +3 -3
- package/workflows/principals/publicHistory/publicPrincipalHistoryProgress.js.map +1 -1
- package/workflows/principals/publicHistory/publicPrincipalHistoryTypes.d.ts +2 -2
- package/workflows/principals/publicHistory/publicPrincipalHistoryTypes.js.map +1 -1
- package/workflows/principals/publicHistory/publicProjectionPrincipal.js +1 -1
- package/workflows/principals/publicHistory/publicProjectionPrincipal.js.map +1 -1
- package/workflows/principals/publicHistory/recoverPublicPrincipalHistory.js +1 -1
- package/workflows/principals/publicHistory/recoverPublicPrincipalHistory.js.map +1 -1
- package/workflows/principals/publicHistory/selectPublicPrincipalHistory.js +1 -1
- package/workflows/principals/publicHistory/selectPublicPrincipalHistory.js.map +1 -1
- package/workflows/principals/recoveryOperation/principalRecoveryDirectory.js +1 -1
- package/workflows/principals/recoveryOperation/principalRecoveryDirectory.js.map +1 -1
- package/workflows/principals/recoveryOperation/principalRecoveryMemoValidity.js +1 -1
- package/workflows/principals/recoveryOperation/principalRecoveryMemoValidity.js.map +1 -1
- package/workflows/registration/persistRegistrationBootstrap.d.ts +2 -2
- package/workflows/registration/persistRegistrationBootstrap.js +2 -2
- package/workflows/registration/persistRegistrationBootstrap.js.map +1 -1
- package/workflows/registration/provisioningAcknowledgement.js +1 -1
- package/workflows/registration/provisioningAcknowledgement.js.map +1 -1
- package/workflows/registration/registrationPrincipalPolicyPersistence.js +1 -1
- package/workflows/registration/registrationPrincipalPolicyPersistence.js.map +1 -1
- package/workflows/sync/remoteReset.js +7 -7
- package/workflows/sync/remoteReset.js.map +1 -1
- package/workflows/sync/remoteResetAttachments.js +1 -1
- package/workflows/sync/remoteResetCursorScope.js +1 -1
- package/workflows/sync/remoteResetPlans.js +1 -1
- package/workflows/sync/remoteResetPrincipalScope.js +5 -5
- package/workflows/sync/remoteResetPrincipalScope.js.map +1 -1
- package/workflows/sync/remoteResetScope.js +1 -1
- package/data/documents/shared/containerKekPath.js.map +0 -1
- package/data/documents/shared/containerKekPathHistory.js.map +0 -1
- package/data/documents/shared/containerKekPathVerification.js.map +0 -1
- package/data/documents/shared/containerKekWrapping.js.map +0 -1
- package/data/documents/shared/documentSyncUpdateDecryption.js.map +0 -1
- package/data/documents/shared/documentSyncUpdateIsolation.js.map +0 -1
- package/data/documents/shared/keyringRebuild.js.map +0 -1
- package/data/documents/shared/mutationAcknowledgement.js.map +0 -1
- package/data/documents/shared/projection.js.map +0 -1
- package/data/documents/shared/projectionContentKeys.js.map +0 -1
- package/data/documents/shared/projectionTargets.js.map +0 -1
- package/data/documents/shared/syncPagination.js.map +0 -1
- package/data/documents/shared/syncResponseAuthorization.js.map +0 -1
- package/data/documents/shared/syncResponses.js.map +0 -1
- package/data/persistence/documentPurgeCheckpointPersistence.js.map +0 -1
- package/data/persistence/keyingCheckpointAdvancePersistence.js.map +0 -1
- package/data/persistence/keyingCheckpointPersistence.js.map +0 -1
- package/data/persistence/locallyAcknowledgedCheckpointPersistence.js.map +0 -1
- package/data/persistence/organizationReplacementCheckpointPersistence.js.map +0 -1
- package/data/persistence/principalAuthorizationCheckpoints.js.map +0 -1
- package/data/persistence/principalGrantRetirementPersistence.js.map +0 -1
- package/data/persistence/principalHistoryEvidencePersistence.js.map +0 -1
- package/data/persistence/principalHistoryIncompleteRetention.js.map +0 -1
- package/data/persistence/principalHistoryNodeRetention.js.map +0 -1
- package/data/persistence/principalHistoryPrefixPersistence.js.map +0 -1
- package/data/persistence/principalHistoryRootOwnership.js.map +0 -1
- package/data/persistence/principalHistoryStagePersistence.js.map +0 -1
- package/data/persistence/principalHistoryStageRetention.js.map +0 -1
- package/data/persistence/principalHistoryUnpublishedRetention.js.map +0 -1
- package/data/persistence/principalKeyEnvelopeArchivePersistence.js.map +0 -1
- package/data/persistence/principalKeyEnvelopeCandidates.js.map +0 -1
- package/data/persistence/principalPolicyBundleIntegrity.js.map +0 -1
- package/data/persistence/principalPolicyCheckpointSelection.js.map +0 -1
- package/data/persistence/principalPolicyOrganizationPersistence.js.map +0 -1
- package/data/persistence/principalPolicyPersistence.js.map +0 -1
- package/data/persistence/principalPolicyReferenceCheckpoint.js.map +0 -1
- package/data/persistence/principalPolicyReferenceIndexPersistence.js.map +0 -1
- package/data/persistence/principalPolicyReferencePersistence.js.map +0 -1
- package/data/persistence/verifiedPrincipalPolicyBundle.js.map +0 -1
- package/data/persistence/verifiedPrincipalPolicyCurrent.js.map +0 -1
- package/data/persistence/verifiedPrincipalPolicyRetentionPersistence.js.map +0 -1
- package/data/sqlite/containerSchema.js.map +0 -1
- package/data/sqlite/documentHistoryPersistence.js.map +0 -1
- package/data/sqlite/documentOrphanBlobReclaims.js.map +0 -1
- package/data/sqlite/documentPendingUpdatePersistence.js.map +0 -1
- package/data/sqlite/documentPersistence.js.map +0 -1
- package/data/sqlite/documentPersistenceTypes.js.map +0 -1
- package/data/sqlite/documentRecordPersistence.js.map +0 -1
- package/data/sqlite/documentSyncFailurePersistence.js.map +0 -1
- package/data/sqlite/organizationDataUsageSchema.js.map +0 -1
- package/data/sqlite/organizationProvisioningAttemptSchema.js.map +0 -1
- package/data/sqlite/organizationReadModelTableRegistry.js.map +0 -1
- package/data/sqlite/principalHistoryEvidenceSchema.js.map +0 -1
- package/data/sqlite/principalHistoryNodeRetentionSchema.js.map +0 -1
- package/data/sqlite/principalHistoryStageSchema.js.map +0 -1
- package/data/sqlite/principalPolicySchema.js.map +0 -1
- package/data/sqlite/schema.js.map +0 -1
- package/data/sqlite/securityIncidentSchema.js.map +0 -1
- package/data/sqlite/verifiedManifestBundleSchema.js.map +0 -1
- /package/data/documents/shared/{containerKekCurrency.js → containerKek/containerKekCurrency.js} +0 -0
- /package/data/documents/shared/{containerKekCurrency.js.map → containerKek/containerKekCurrency.js.map} +0 -0
- /package/data/documents/shared/{containerKekEntryVerification.js.map → containerKek/containerKekEntryVerification.js.map} +0 -0
- /package/data/documents/shared/{containerKekLogFetch.js.map → containerKek/containerKekLogFetch.js.map} +0 -0
- /package/data/documents/shared/{containerKekPath.d.ts → containerKek/containerKekPath.d.ts} +0 -0
- /package/data/documents/shared/{keyringLogWalk.js.map → containerKek/keyringLogWalk.js.map} +0 -0
- /package/data/documents/shared/{pullContinuation.d.ts → sync/pullContinuation.d.ts} +0 -0
- /package/data/documents/shared/{pullContinuation.js.map → sync/pullContinuation.js.map} +0 -0
- /package/data/documents/shared/{syncSubmitFailure.js → sync/syncSubmitFailure.js} +0 -0
- /package/data/documents/shared/{syncSubmitFailure.js.map → sync/syncSubmitFailure.js.map} +0 -0
- /package/data/persistence/{keyingCheckpointEvidence.js.map → keyingCheckpoints/keyingCheckpointEvidence.js.map} +0 -0
- /package/data/persistence/{storedPrincipalPolicyBundle.js → principalPolicy/storedPrincipalPolicyBundle.js} +0 -0
- /package/data/persistence/{storedPrincipalPolicyBundle.js.map → principalPolicy/storedPrincipalPolicyBundle.js.map} +0 -0
- /package/data/sqlite/{documentPersistenceTypes.js → documentPersistence/documentPersistenceTypes.js} +0 -0
- /package/data/sqlite/{containerDocumentTombstoneHoldSchema.d.ts → schema/containerDocumentTombstoneHoldSchema.d.ts} +0 -0
- /package/data/sqlite/{containerDocumentTombstoneHoldSchema.js → schema/containerDocumentTombstoneHoldSchema.js} +0 -0
- /package/data/sqlite/{containerDocumentTombstoneHoldSchema.js.map → schema/containerDocumentTombstoneHoldSchema.js.map} +0 -0
- /package/data/sqlite/{documentAttachmentSchema.d.ts → schema/documentAttachmentSchema.d.ts} +0 -0
- /package/data/sqlite/{documentAttachmentSchema.js → schema/documentAttachmentSchema.js} +0 -0
- /package/data/sqlite/{documentAttachmentSchema.js.map → schema/documentAttachmentSchema.js.map} +0 -0
- /package/data/sqlite/{documentDiscoveryEvidenceSchema.js → schema/documentDiscoveryEvidenceSchema.js} +0 -0
- /package/data/sqlite/{documentDiscoveryEvidenceSchema.js.map → schema/documentDiscoveryEvidenceSchema.js.map} +0 -0
- /package/data/sqlite/{documentPlacementIntentSchema.js → schema/documentPlacementIntentSchema.js} +0 -0
- /package/data/sqlite/{documentPlacementIntentSchema.js.map → schema/documentPlacementIntentSchema.js.map} +0 -0
- /package/data/sqlite/{localIntentSchema.d.ts → schema/localIntentSchema.d.ts} +0 -0
- /package/data/sqlite/{localIntentSchema.js → schema/localIntentSchema.js} +0 -0
- /package/data/sqlite/{localIntentSchema.js.map → schema/localIntentSchema.js.map} +0 -0
- /package/data/sqlite/{organizationFounderSchema.js → schema/organizationFounderSchema.js} +0 -0
- /package/data/sqlite/{organizationFounderSchema.js.map → schema/organizationFounderSchema.js.map} +0 -0
- /package/data/sqlite/{organizationReadModelSchema.js → schema/organizationReadModelSchema.js} +0 -0
- /package/data/sqlite/{organizationReadModelSchema.js.map → schema/organizationReadModelSchema.js.map} +0 -0
- /package/data/sqlite/{principalGrantRetirementSchema.js → schema/principalGrantRetirementSchema.js} +0 -0
- /package/data/sqlite/{principalGrantRetirementSchema.js.map → schema/principalGrantRetirementSchema.js.map} +0 -0
- /package/data/sqlite/{principalPolicySchema.d.ts → schema/principalPolicySchema.d.ts} +0 -0
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"reportDocumentSyncQuarantine.js","sourceRoot":"","sources":["reportDocumentSyncQuarantine.ts"],"names":[],"mappings":"AAGA,MAAM,qBAAqB,GAAG,IAAI,OAAO,EAAkB,CAAC;AAE5D,4EAA4E;AAC5E,MAAM,UAAU,4BAA4B,CAC1C,KAAa,EACb,QAA0D,EAC1D,OAAyC;IAEzC,IAAI,CAAC,QAAQ;QAAE,OAAO;IACtB,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,CAAC,CAAC,OAAO,CAAC,OAAO,EAAE,OAAO,CAAC,cAAc,CAAC,CAAC,CAAC;IAC5E,IAAI,qBAAqB,CAAC,GAAG,CAAC,KAAK,CAAC,KAAK,SAAS;QAAE,OAAO;IAC3D,4EAA4E;IAC5E,yEAAyE;IACzE,qBAAqB,CAAC,GAAG,CAAC,KAAK,EAAE,SAAS,CAAC,CAAC;IAC5C,IAAI,CAAC;QACH,KAAK,OAAO,CAAC,OAAO,CAClB,QAAQ,CAAC,qCAAqC,EAAE,OAAO,CAAC,CACzD,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;IAC3B,CAAC;IAAC,MAAM,CAAC;QACP,8DAA8D;IAChE,CAAC;AACH,CAAC","sourcesContent":["import type { DocumentSyncUpdateIsolationError } from \"../../../data/documents/shared/documentSyncUpdateIsolation\";\nimport type { WorkflowRuntimeUtilInput } from \"../../shared/runtimeInput\";\n\nconst lastQuarantineByScope = new WeakMap<object, string>();\n\n/** Keep host diagnostics failures from replacing the durable quarantine. */\nexport function reportDocumentSyncQuarantine(\n scope: object,\n logError: WorkflowRuntimeUtilInput[\"logError\"] | undefined,\n failure: DocumentSyncUpdateIsolationError,\n): void {\n if (!logError) return;\n const signature = JSON.stringify([failure.message, failure.batchUpdateIds]);\n if (lastQuarantineByScope.get(scope) === signature) return;\n // Suppress repeats before the host appends local logs and breadcrumbs. Keep\n // only the last failure, and let discarded document scopes be collected.\n lastQuarantineByScope.set(scope, signature);\n try {\n void Promise.resolve(\n logError(\"Documents: sync updates quarantined\", failure),\n ).catch(() => undefined);\n } catch {\n // Hosts may throw synchronously or return a rejected promise.\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"reportDocumentSyncQuarantine.js","sourceRoot":"","sources":["reportDocumentSyncQuarantine.ts"],"names":[],"mappings":"AAGA,MAAM,qBAAqB,GAAG,IAAI,OAAO,EAAkB,CAAC;AAE5D,4EAA4E;AAC5E,MAAM,UAAU,4BAA4B,CAC1C,KAAa,EACb,QAA0D,EAC1D,OAAyC;IAEzC,IAAI,CAAC,QAAQ;QAAE,OAAO;IACtB,MAAM,SAAS,GAAG,IAAI,CAAC,SAAS,CAAC,CAAC,OAAO,CAAC,OAAO,EAAE,OAAO,CAAC,cAAc,CAAC,CAAC,CAAC;IAC5E,IAAI,qBAAqB,CAAC,GAAG,CAAC,KAAK,CAAC,KAAK,SAAS;QAAE,OAAO;IAC3D,4EAA4E;IAC5E,yEAAyE;IACzE,qBAAqB,CAAC,GAAG,CAAC,KAAK,EAAE,SAAS,CAAC,CAAC;IAC5C,IAAI,CAAC;QACH,KAAK,OAAO,CAAC,OAAO,CAClB,QAAQ,CAAC,qCAAqC,EAAE,OAAO,CAAC,CACzD,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;IAC3B,CAAC;IAAC,MAAM,CAAC;QACP,8DAA8D;IAChE,CAAC;AACH,CAAC","sourcesContent":["import type { DocumentSyncUpdateIsolationError } from \"../../../data/documents/shared/sync/documentSyncUpdateIsolation\";\nimport type { WorkflowRuntimeUtilInput } from \"../../shared/runtimeInput\";\n\nconst lastQuarantineByScope = new WeakMap<object, string>();\n\n/** Keep host diagnostics failures from replacing the durable quarantine. */\nexport function reportDocumentSyncQuarantine(\n scope: object,\n logError: WorkflowRuntimeUtilInput[\"logError\"] | undefined,\n failure: DocumentSyncUpdateIsolationError,\n): void {\n if (!logError) return;\n const signature = JSON.stringify([failure.message, failure.batchUpdateIds]);\n if (lastQuarantineByScope.get(scope) === signature) return;\n // Suppress repeats before the host appends local logs and breadcrumbs. Keep\n // only the last failure, and let discarded document scopes be collected.\n lastQuarantineByScope.set(scope, signature);\n try {\n void Promise.resolve(\n logError(\"Documents: sync updates quarantined\", failure),\n ).catch(() => undefined);\n } catch {\n // Hosts may throw synchronously or return a rejected promise.\n }\n}\n"]}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { ContainerKekRepairInaccessibleError } from "../../../data/documents/shared/containerKekCurrency.js";
|
|
1
|
+
import { ContainerKekRepairInaccessibleError } from "../../../data/documents/shared/containerKek/containerKekCurrency.js";
|
|
2
2
|
import { assertDocumentManifestBundleConsistent } from "../../../data/documents/shared/readers.js";
|
|
3
|
-
import { resolvePullContinuationMinLsn, } from "../../../data/documents/shared/syncPagination.js";
|
|
3
|
+
import { resolvePullContinuationMinLsn, } from "../../../data/documents/shared/sync/syncPagination.js";
|
|
4
4
|
import { isDocumentSyncRequestLimitError } from "../../../data/sync/documentSyncOutgoingBatch.js";
|
|
5
5
|
import { retrySyncPlanOrAbandon } from "../syncFailures/index.js";
|
|
6
6
|
import { abandonAncestorRepair, abandonBlockedSync, abandonInaccessibleAncestorRepair, abandonOversizedSyncPlan, } from "../syncFailures/syncAbandon.js";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"syncAttemptPlanning.js","sourceRoot":"","sources":["syncAttemptPlanning.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,mCAAmC,EAAE,MAAM,
|
|
1
|
+
{"version":3,"file":"syncAttemptPlanning.js","sourceRoot":"","sources":["syncAttemptPlanning.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,mCAAmC,EAAE,MAAM,kEAAkE,CAAC;AACvH,OAAO,EAAE,sCAAsC,EAAE,MAAM,wCAAwC,CAAC;AAChG,OAAO,EAEL,6BAA6B,GAC9B,MAAM,oDAAoD,CAAC;AAE5D,OAAO,EAAE,+BAA+B,EAAE,MAAM,8CAA8C,CAAC;AAC/F,OAAO,EAAE,sBAAsB,EAAE,MAAM,iBAAiB,CAAC;AACzD,OAAO,EACL,qBAAqB,EACrB,kBAAkB,EAClB,iCAAiC,EACjC,wBAAwB,GACzB,MAAM,6BAA6B,CAAC;AAErC,OAAO,EACL,oCAAoC,EACpC,oCAAoC,GACrC,MAAM,mCAAmC,CAAC;AAC3C,OAAO,EAAE,iCAAiC,EAAE,MAAM,6CAA6C,CAAC;AAChG,OAAO,EAAE,2BAA2B,EAAE,MAAM,mCAAmC,CAAC;AAGhF;;;;;;;;;GASG;AACH,MAAM,UAAU,wBAAwB,CACtC,KAA8B,EAC9B,yBAAkC;IAElC,OAAO,yBAAyB;QAC9B,CAAC,CAAC,KAAK,CAAC,uBAAuB;QAC/B,CAAC,CAAC,KAAK,CAAC,2BAA2B,CAAC;AACxC,CAAC;AACD,MAAM,CAAC,KAAK,UAAU,uBAAuB,CAAC,KAO7C;IACC,IAAI,CAAC;QACH,MAAM,cAAc,GAClB,KAAK,CAAC,gBAAgB,KAAK,SAAS,CAAC,CAAC,CAAC,KAAK,CAAC,cAAc,CAAC,CAAC,CAAC,EAAE,CAAC;QACnE,IACE,cAAc,CAAC,MAAM;YACrB,KAAK,CAAC,IAAI,CAAC,mBAAmB,EAAE,CAC9B,CACE,MAAM,sCAAsC,CAAC;gBAC3C,MAAM,EAAE,KAAK,CAAC,gBAAgB,CAAC,gBAAgB;gBAC/C,KAAK,EAAE,wBAAwB;aAChC,CAAC,CACH,CAAC,cAAc,CACjB,EACD,CAAC;YACD,OAAO,kBAAkB,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;QACxC,CAAC;QACD,qEAAqE;QACrE,6EAA6E;QAC7E,MAAM,QAAQ,GACZ,cAAc,CAAC,MAAM;YACrB,CAAC,KAAK,CAAC,IAAI,CAAC,oBAAoB;YAChC,KAAK,CAAC,IAAI,CAAC,qBAAqB;YAC9B,CAAC,CAAC,MAAM,iCAAiC,CACrC,KAAK,CAAC,IAAI,EACV,KAAK,CAAC,gBAAgB,CACvB;YACH,CAAC,CAAC,EAAE,UAAU,EAAE,KAAK,CAAC,gBAAgB,EAAE,KAAK,EAAE,SAAS,EAAE,CAAC;QAC/D,IAAI,CAAC,QAAQ;YAAE,OAAO,IAAI,CAAC;QAC3B,OAAO,MAAM,sBAAsB,CAAC;YAClC,SAAS,EAAE,KAAK,CAAC,IAAI,CAAC,SAAS;YAC/B,mBAAmB,EAAE,CAAC,UAAU,EAAE,EAAE,CAClC,2BAA2B,CAAC;gBAC1B,cAAc;gBACd,cAAc,EACZ,UAAU,KAAK,QAAQ,CAAC,UAAU,CAAC,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS;gBACjE,MAAM,EAAE,6BAA6B,CACnC,KAAK,CAAC,gBAAgB,EACtB,KAAK,CAAC,IAAI,CAAC,MAAM,CAClB;gBACD,UAAU,EAAE,KAAK,CAAC,gBAAgB,EAAE,MAAM;gBAC1C,UAAU;gBACV,2BAA2B,EAAE,KAAK,CAAC,2BAA2B;gBAC9D,IAAI,EAAE,KAAK,CAAC,IAAI;aACjB,CAAC;YACJ,UAAU,EAAE,KAAK,CAAC,IAAI,CAAC,UAAU;YACjC,uBAAuB,EAAE,KAAK,CAAC,IAAI,CAAC,uBAAuB;YAC3D,eAAe,EAAE,KAAK,CAAC,IAAI,CAAC,eAAe;YAC3C,WAAW,EAAE,KAAK,CAAC,IAAI,CAAC,WAAW;YACnC,iBAAiB,EAAE,wBAAwB,CACzC,KAAK,CAAC,IAAI,EACV,KAAK,CAAC,yBAAyB,CAChC;YACD,YAAY,EAAE,KAAK,CAAC,IAAI,CAAC,YAAY;YACrC,gBAAgB,EAAE,QAAQ,CAAC,UAAU;SACtC,CAAC,CAAC;IACL,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IAAI,KAAK,YAAY,oCAAoC;YACvD,OAAO,OAAgB,CAAC;QAC1B,IAAI,KAAK,YAAY,oCAAoC,EAAE,CAAC;YAC1D,OAAO,qBAAqB,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QAClD,CAAC;QACD,IAAI,KAAK,YAAY,mCAAmC,EAAE,CAAC;YACzD,OAAO,iCAAiC,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QAC9D,CAAC;QACD,IAAI,CAAC,+BAA+B,CAAC,KAAK,CAAC,EAAE,CAAC;YAC5C,MAAM,KAAK,CAAC;QACd,CAAC;QACD,OAAO,wBAAwB,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;IACrD,CAAC;AACH,CAAC","sourcesContent":["import type { DocumentWriterProjectionResponse } from \"@tearleads/validators/response\";\nimport { ContainerKekRepairInaccessibleError } from \"../../../data/documents/shared/containerKek/containerKekCurrency\";\nimport { assertDocumentManifestBundleConsistent } from \"../../../data/documents/shared/readers\";\nimport {\n type DocumentSyncPullContinuation,\n resolvePullContinuationMinLsn,\n} from \"../../../data/documents/shared/sync/syncPagination\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport { isDocumentSyncRequestLimitError } from \"../../../data/sync/documentSyncOutgoingBatch\";\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,8 +1,8 @@
|
|
|
1
1
|
import type { DocumentWriterProjectionResponse } from "../../../internal/validators/response/index.js";
|
|
2
2
|
import type { MaterializedContainerRekeyPlan } from "../../../data/containers/shared/types.js";
|
|
3
|
-
import type { DocumentSyncPullContinuation } from "../../../data/documents/shared/syncPagination.js";
|
|
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.js";
|
|
5
|
+
import type { PendingUpdateRecord } from "../../../data/sqlite/documentPersistence/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/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/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,8 +1,8 @@
|
|
|
1
1
|
import { KeyingVerificationError } from "../../../internal/crypto/index.js";
|
|
2
2
|
import { decryptDocumentSyncUpdatesByEpoch } from "../../../data/documents/shared/crypto.js";
|
|
3
|
-
import {
|
|
4
|
-
import { assertDocumentWriterProjectionConsistent } from "../../../data/documents/shared/projection.js";
|
|
3
|
+
import { assertDocumentWriterProjectionConsistent } from "../../../data/documents/shared/projection/index.js";
|
|
5
4
|
import { DocumentSyncResponseUpdateContentKeyError, persistedDocumentSyncStateFromResponse, } from "../../../data/documents/shared/responses.js";
|
|
5
|
+
import { isolateDocumentSyncBatchError, } from "../../../data/documents/shared/sync/documentSyncUpdateIsolation.js";
|
|
6
6
|
import { projectionVerificationOptions } from "../../../data/documents/shared/types.js";
|
|
7
7
|
import { unwrapDocumentSyncResponseContentKeys } from "../syncPlan/syncContentKeys.js";
|
|
8
8
|
import { acceptedHeldBackPendingUpdateIds, responseAcceptedRecoveryBaseline, } from "../syncPlan/syncPlanRequestBounds.js";
|
|
@@ -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 {\n type IncomingDocumentSyncUpdateValidator,\n isolateDocumentSyncBatchError,\n} from \"../../../data/documents/shared/documentSyncUpdateIsolation\";\nimport { assertDocumentWriterProjectionConsistent } from \"../../../data/documents/shared/projection\";\nimport {\n DocumentSyncResponseUpdateContentKeyError,\n persistedDocumentSyncStateFromResponse,\n} from \"../../../data/documents/shared/responses\";\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/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,6 +1,6 @@
|
|
|
1
1
|
import { DOCUMENT_SYNC_ERROR_CODES, } from "../../../internal/validators/response/index.js";
|
|
2
2
|
import { isUpstreamDeletedDocumentSyncFailure, submitDocumentSync, } from "../../../data/documents/shared/responses.js";
|
|
3
|
-
import { InvalidDocumentSyncPullContinuationError, } from "../../../data/documents/shared/syncPagination.js";
|
|
3
|
+
import { InvalidDocumentSyncPullContinuationError, } from "../../../data/documents/shared/sync/syncPagination.js";
|
|
4
4
|
import { traceProjectionFailed, traceSubmitFailed, } from "../sync/syncTrace.js";
|
|
5
5
|
import { canRecoverDocumentUpdateIdConflict, canRetryDocumentSyncConflict, handleUpstreamDeletedDocumentSyncFailure, isCheckpointCoverageConflict, shouldRetrySyncWithFreshWriterProjection, } from "./syncFailureClassification.js";
|
|
6
6
|
import { recoverDocumentSyncPolicyRepair } from "./syncPolicyRepair.js";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["index.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n DOCUMENT_SYNC_ERROR_CODES,\n type DocumentSyncResponse,\n type DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport {\n isUpstreamDeletedDocumentSyncFailure,\n submitDocumentSync,\n} from \"../../../data/documents/shared/responses\";\nimport {\n type DocumentSyncCommitLsnMode,\n type DocumentSyncPullContinuation,\n InvalidDocumentSyncPullContinuationError,\n} from \"../../../data/documents/shared/syncPagination\";\nimport type {\n DocumentSyncApi,\n DocumentSyncPlan,\n DocumentSyncSubmitFailure,\n MaterializedDocumentSyncPlan,\n} from \"../../../data/documents/shared/types\";\nimport type { ReferencedPrincipalPolicyWarmer } from \"../../../data/keyingProjectionVerification\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport {\n type DocumentSyncTraceEmitter,\n traceProjectionFailed,\n traceSubmitFailed,\n} from \"../sync/syncTrace\";\nimport {\n canRecoverDocumentUpdateIdConflict,\n canRetryDocumentSyncConflict,\n handleUpstreamDeletedDocumentSyncFailure,\n isCheckpointCoverageConflict,\n type RemoteDocumentDeletionHandler,\n shouldRetrySyncWithFreshWriterProjection,\n type TerminalSubmitFailureHandler,\n} from \"./syncFailureClassification\";\nimport { recoverDocumentSyncPolicyRepair } from \"./syncPolicyRepair\";\n\nconst REMOTE_DOCUMENT_DELETED = Symbol(\"remoteDocumentDeleted\");\n\nexport function assertRawContinuationCanRetry(\n historyMode: \"raw\" | undefined,\n pullContinuation: DocumentSyncPullContinuation | undefined,\n): void {\n if (historyMode === \"raw\" && pullContinuation !== undefined) {\n throw new InvalidDocumentSyncPullContinuationError(\n \"Document raw-history continuation became stale\",\n );\n }\n}\n\ntype DocumentWriterProjectionResolution =\n | DocumentWriterProjectionResponse\n | typeof REMOTE_DOCUMENT_DELETED\n | null;\n\ntype FailedDocumentSyncAction =\n | \"retry\"\n | \"stop\"\n | {\n readonly kind: \"recover_update_id_conflict\";\n readonly recoveryPendingUpdatesById: Map<string, PendingUpdateRecord>;\n }\n | { readonly kind: \"regenerate_queued_checkpoints\" };\n\ntype DocumentSyncAttemptSubmission =\n | {\n readonly kind: \"completed\";\n readonly pullComplete: boolean;\n readonly response: DocumentSyncResponse;\n }\n | FailedDocumentSyncAction\n | \"cancelled\"\n | \"blocked\";\n\nasync function resolveFailedDocumentSyncAction(input: {\n attempt: number;\n canRegenerateQueuedCheckpoints?: boolean | undefined;\n documentId: string;\n failure: DocumentSyncSubmitFailure;\n maxAttempts: number;\n onInlineRepairRefused?: (() => void) | undefined;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n pendingUpdates: readonly PendingUpdateRecord[];\n}): Promise<FailedDocumentSyncAction> {\n const action = await classifyFailedDocumentSyncAction(input);\n traceSubmitFailed(input.onSyncTrace, {\n action:\n action === \"retry\" || action === \"stop\"\n ? action\n : action.kind === \"recover_update_id_conflict\"\n ? \"recover-update-ids\"\n : \"regenerate-checkpoints\",\n code: input.failure.code,\n documentId: input.documentId,\n status: input.failure.status,\n });\n return action;\n}\n\nasync function classifyFailedDocumentSyncAction(input: {\n attempt: number;\n canRegenerateQueuedCheckpoints?: boolean | undefined;\n documentId: string;\n failure: DocumentSyncSubmitFailure;\n maxAttempts: number;\n onInlineRepairRefused?: (() => void) | undefined;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n pendingUpdates: readonly PendingUpdateRecord[];\n}): Promise<FailedDocumentSyncAction> {\n if (\n await handleUpstreamDeletedDocumentSyncFailure({\n documentId: input.documentId,\n failure: input.failure,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n })\n ) {\n return \"stop\";\n }\n\n if (\n canRetryDocumentSyncConflict({\n attempt: input.attempt,\n failure: input.failure,\n maxAttempts: input.maxAttempts,\n })\n ) {\n return \"retry\";\n }\n\n // The write rolled back whole. Its inline repairs would have stranded a\n // level above a directly granted container, and a flat rekey list cannot say\n // what each must carry: the retry commits them standalone instead.\n if (\n input.attempt < input.maxAttempts &&\n input.onInlineRepairRefused &&\n input.failure.code === DOCUMENT_SYNC_ERROR_CODES.descendantRekeysRequired\n ) {\n input.onInlineRepairRefused();\n return \"retry\";\n }\n\n if (\n canRecoverDocumentUpdateIdConflict({\n attempt: input.attempt,\n failure: input.failure,\n maxAttempts: input.maxAttempts,\n pendingUpdateCount: input.pendingUpdates.length,\n })\n ) {\n return {\n kind: \"recover_update_id_conflict\",\n recoveryPendingUpdatesById: new Map(\n input.pendingUpdates.map((update) => [update.id, update]),\n ),\n };\n }\n\n if (\n input.attempt < input.maxAttempts &&\n input.canRegenerateQueuedCheckpoints === true &&\n isCheckpointCoverageConflict(input.failure)\n ) {\n return { kind: \"regenerate_queued_checkpoints\" };\n }\n\n input.failure.report();\n await input.onTerminalSubmitFailure?.(input.failure);\n return \"stop\";\n}\n\nasync function submitDocumentSyncAttempt(input: {\n apiClient: DocumentSyncApi;\n attempt: number;\n canRegenerateQueuedCheckpoints?: boolean | undefined;\n documentId: string;\n expectedCommitLsnMode?: DocumentSyncCommitLsnMode | undefined;\n maxAttempts: number;\n onInlineRepairRefused?: (() => void) | undefined;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n pendingUpdates: readonly PendingUpdateRecord[];\n plan: DocumentSyncPlan;\n stillCurrent?: (() => boolean) | undefined;\n warmReferencedPrincipalPolicies?: ReferencedPrincipalPolicyWarmer | undefined;\n}): Promise<DocumentSyncAttemptSubmission> {\n if (input.stillCurrent?.() === false) return \"cancelled\";\n const submitted = await submitDocumentSync({\n apiClient: input.apiClient,\n expectedCommitLsnMode: input.expectedCommitLsnMode,\n plan: input.plan,\n });\n if (input.stillCurrent?.() === false) return \"cancelled\";\n if (!submitted) {\n return \"stop\";\n }\n if (submitted.ok) {\n return {\n kind: \"completed\",\n pullComplete: submitted.pullComplete,\n response: submitted.response,\n };\n }\n\n await recoverDocumentSyncPolicyRepair({\n failure: submitted,\n plan: input.plan,\n stillCurrent: input.stillCurrent,\n warmReferencedPrincipalPolicies: input.warmReferencedPrincipalPolicies,\n });\n if (input.stillCurrent?.() === false) return \"cancelled\";\n\n return resolveFailedDocumentSyncAction({\n attempt: input.attempt,\n canRegenerateQueuedCheckpoints: input.canRegenerateQueuedCheckpoints,\n documentId: input.documentId,\n failure: submitted,\n maxAttempts: input.maxAttempts,\n onInlineRepairRefused: input.onInlineRepairRefused,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n onSyncTrace: input.onSyncTrace,\n onTerminalSubmitFailure: input.onTerminalSubmitFailure,\n pendingUpdates: input.pendingUpdates,\n });\n}\n\nexport async function submitDocumentSyncAttemptIfAllowed(\n input: Parameters<typeof submitDocumentSyncAttempt>[0] & {\n isRemoteSyncBlocked?: ((organizationId: string) => boolean) | undefined;\n onOutgoingUpdatesMaterialized?:\n | ((updateIds: readonly string[]) => void)\n | undefined;\n failureBlocksQueuedWrites?: boolean | undefined;\n },\n): Promise<DocumentSyncAttemptSubmission> {\n const {\n failureBlocksQueuedWrites,\n isRemoteSyncBlocked,\n onOutgoingUpdatesMaterialized,\n ...submissionInput\n } = input;\n const hasRemoteWrites =\n input.plan.request.outgoingUpdates.length > 0 ||\n (input.plan.request.containerRekeys?.length ?? 0) > 0;\n if (hasRemoteWrites && isRemoteSyncBlocked?.(input.plan.organizationId)) {\n return \"blocked\";\n }\n if (input.stillCurrent?.() === false) return \"cancelled\";\n\n onOutgoingUpdatesMaterialized?.(\n input.plan.request.outgoingUpdates.map(({ id }) => id),\n );\n\n return submitDocumentSyncAttempt({\n ...submissionInput,\n // A read-only pass carries no writes, so a terminal failure describes a\n // pull, not queued local data — recording it would flag the next local\n // edit as failed before it was ever attempted. A cursor continuation and\n // update-id recovery both submit an empty request while durable rows still\n // exist; a terminal 403 there IS what blocks the queued edits.\n onTerminalSubmitFailure:\n hasRemoteWrites || failureBlocksQueuedWrites\n ? submissionInput.onTerminalSubmitFailure\n : undefined,\n });\n}\n\nasync function resolveDocumentSyncWriterProjection(input: {\n apiClient: DocumentSyncApi;\n documentId: string;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n /**\n * Invoked when the projection fetch fails terminally. Write-bearing sync\n * passes persist this: without a writer projection their queued writes can\n * never submit, so the failure (e.g. a 403 after access revocation) is what\n * the write queue should surface.\n */\n onTerminalFailure?: TerminalSubmitFailureHandler | undefined;\n reusableWriterProjection: DocumentWriterProjectionResponse | null;\n stillCurrent?: (() => boolean) | undefined;\n}): Promise<DocumentWriterProjectionResolution> {\n if (input.stillCurrent?.() === false) return null;\n if (input.reusableWriterProjection) {\n return input.reusableWriterProjection;\n }\n\n const result = await input.apiClient.getDocumentWriterProjectionResult(\n input.documentId,\n { reportErrors: false },\n );\n if (input.stillCurrent?.() === false) return null;\n if (result.ok) {\n return result.data;\n }\n if (isUpstreamDeletedDocumentSyncFailure(result)) {\n return REMOTE_DOCUMENT_DELETED;\n }\n traceProjectionFailed(input.onSyncTrace, {\n code: result.code,\n documentId: input.documentId,\n status: result.status,\n });\n result.report();\n await input.onTerminalFailure?.(result);\n return null;\n}\n\nexport async function retrySyncPlan(input: {\n apiClient: DocumentSyncApi;\n buildWithProjection: (\n projection: DocumentWriterProjectionResponse,\n ) => Promise<MaterializedDocumentSyncPlan>;\n documentId: string;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalFailure?: TerminalSubmitFailureHandler | undefined;\n stillCurrent?: (() => boolean) | undefined;\n writerProjection: DocumentWriterProjectionResponse;\n}): Promise<\n | readonly [MaterializedDocumentSyncPlan, DocumentWriterProjectionResponse]\n | null\n> {\n try {\n return [\n await input.buildWithProjection(input.writerProjection),\n input.writerProjection,\n ];\n } catch (error) {\n if (\n !input.apiClient.evictDocumentWriterProjection ||\n !shouldRetrySyncWithFreshWriterProjection(error)\n ) {\n throw error;\n }\n }\n if (input.stillCurrent?.() === false) return null;\n\n // Only this document's projection was stale; evict just it so unrelated\n // documents keep their warm cache instead of a global wipe.\n input.apiClient.evictDocumentWriterProjection?.(input.documentId);\n const writerProjection = await resolveDocumentSyncWriterProjection({\n apiClient: input.apiClient,\n documentId: input.documentId,\n onSyncTrace: input.onSyncTrace,\n onTerminalFailure: input.onTerminalFailure,\n reusableWriterProjection: null,\n stillCurrent: input.stillCurrent,\n });\n if (input.stillCurrent?.() === false) return null;\n if (writerProjection === REMOTE_DOCUMENT_DELETED) {\n await input.onRemoteDocumentDeleted?.({ documentId: input.documentId });\n return null;\n }\n if (!writerProjection) {\n return null;\n }\n\n return [await input.buildWithProjection(writerProjection), writerProjection];\n}\n\n/**\n * Resolves the writer projection for one sync attempt, converting the two\n * unrecoverable outcomes into an abandoned (null) result with a named reason\n * so callers that turn a null sync into their own error can surface the real\n * cause.\n */\nexport async function resolveSyncAttemptWriterProjection(input: {\n apiClient: DocumentSyncApi;\n documentId: string;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncAbandoned?: ((reason: string) => void) | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalFailure?: TerminalSubmitFailureHandler | undefined;\n reusableWriterProjection: DocumentWriterProjectionResponse | null;\n stillCurrent?: (() => boolean) | undefined;\n}): Promise<DocumentWriterProjectionResponse | null> {\n const writerProjection = await resolveDocumentSyncWriterProjection(input);\n if (input.stillCurrent?.() === false) return null;\n if (writerProjection === REMOTE_DOCUMENT_DELETED) {\n await input.onRemoteDocumentDeleted?.({ documentId: input.documentId });\n if (input.stillCurrent?.() !== false) {\n input.onSyncAbandoned?.(\"the remote document was deleted\");\n }\n return null;\n }\n if (!writerProjection) {\n input.onSyncAbandoned?.(\n \"the document writer projection could not be fetched\",\n );\n return null;\n }\n return writerProjection;\n}\n\nexport async function refreshSyncAttemptWriterProjection(\n input: Omit<\n Parameters<typeof resolveSyncAttemptWriterProjection>[0],\n \"reusableWriterProjection\"\n > & { unavailableError?: unknown },\n): Promise<DocumentWriterProjectionResponse | null> {\n const { onRemoteDocumentDeleted, unavailableError, ...resolutionInput } =\n input;\n if (input.stillCurrent?.() === false) return null;\n if (input.apiClient.evictDocumentWriterProjection) {\n input.apiClient.evictDocumentWriterProjection(input.documentId);\n } else {\n input.apiClient.clearWriterProjectionCaches?.();\n }\n let remoteDocumentDeleted = false;\n const writerProjection = await resolveSyncAttemptWriterProjection({\n ...resolutionInput,\n onRemoteDocumentDeleted: async (deleted) => {\n remoteDocumentDeleted = true;\n await onRemoteDocumentDeleted?.(deleted);\n },\n reusableWriterProjection: null,\n });\n if (\n !writerProjection &&\n unavailableError !== undefined &&\n !remoteDocumentDeleted &&\n input.stillCurrent?.() !== false\n ) {\n throw unavailableError;\n }\n return writerProjection;\n}\n\nexport async function retrySyncPlanOrAbandon(input: {\n apiClient: DocumentSyncApi;\n buildWithProjection: (\n projection: DocumentWriterProjectionResponse,\n ) => Promise<MaterializedDocumentSyncPlan>;\n documentId: string;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncAbandoned?: ((reason: string) => void) | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalFailure?: TerminalSubmitFailureHandler | undefined;\n stillCurrent?: (() => boolean) | undefined;\n writerProjection: DocumentWriterProjectionResponse;\n}): Promise<\n | readonly [MaterializedDocumentSyncPlan, DocumentWriterProjectionResponse]\n | null\n> {\n const planned = await retrySyncPlan(input);\n if (!planned && input.stillCurrent?.() !== false) {\n input.onSyncAbandoned?.(\n \"a sync plan could not be built against the current projection\",\n );\n }\n return planned;\n}\n"]}
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["index.ts"],"names":[],"mappings":"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","sourcesContent":["import {\n DOCUMENT_SYNC_ERROR_CODES,\n type DocumentSyncResponse,\n type DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport {\n isUpstreamDeletedDocumentSyncFailure,\n submitDocumentSync,\n} from \"../../../data/documents/shared/responses\";\nimport {\n type DocumentSyncCommitLsnMode,\n type DocumentSyncPullContinuation,\n InvalidDocumentSyncPullContinuationError,\n} from \"../../../data/documents/shared/sync/syncPagination\";\nimport type {\n DocumentSyncApi,\n DocumentSyncPlan,\n DocumentSyncSubmitFailure,\n MaterializedDocumentSyncPlan,\n} from \"../../../data/documents/shared/types\";\nimport type { ReferencedPrincipalPolicyWarmer } from \"../../../data/keyingProjectionVerification\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport {\n type DocumentSyncTraceEmitter,\n traceProjectionFailed,\n traceSubmitFailed,\n} from \"../sync/syncTrace\";\nimport {\n canRecoverDocumentUpdateIdConflict,\n canRetryDocumentSyncConflict,\n handleUpstreamDeletedDocumentSyncFailure,\n isCheckpointCoverageConflict,\n type RemoteDocumentDeletionHandler,\n shouldRetrySyncWithFreshWriterProjection,\n type TerminalSubmitFailureHandler,\n} from \"./syncFailureClassification\";\nimport { recoverDocumentSyncPolicyRepair } from \"./syncPolicyRepair\";\n\nconst REMOTE_DOCUMENT_DELETED = Symbol(\"remoteDocumentDeleted\");\n\nexport function assertRawContinuationCanRetry(\n historyMode: \"raw\" | undefined,\n pullContinuation: DocumentSyncPullContinuation | undefined,\n): void {\n if (historyMode === \"raw\" && pullContinuation !== undefined) {\n throw new InvalidDocumentSyncPullContinuationError(\n \"Document raw-history continuation became stale\",\n );\n }\n}\n\ntype DocumentWriterProjectionResolution =\n | DocumentWriterProjectionResponse\n | typeof REMOTE_DOCUMENT_DELETED\n | null;\n\ntype FailedDocumentSyncAction =\n | \"retry\"\n | \"stop\"\n | {\n readonly kind: \"recover_update_id_conflict\";\n readonly recoveryPendingUpdatesById: Map<string, PendingUpdateRecord>;\n }\n | { readonly kind: \"regenerate_queued_checkpoints\" };\n\ntype DocumentSyncAttemptSubmission =\n | {\n readonly kind: \"completed\";\n readonly pullComplete: boolean;\n readonly response: DocumentSyncResponse;\n }\n | FailedDocumentSyncAction\n | \"cancelled\"\n | \"blocked\";\n\nasync function resolveFailedDocumentSyncAction(input: {\n attempt: number;\n canRegenerateQueuedCheckpoints?: boolean | undefined;\n documentId: string;\n failure: DocumentSyncSubmitFailure;\n maxAttempts: number;\n onInlineRepairRefused?: (() => void) | undefined;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n pendingUpdates: readonly PendingUpdateRecord[];\n}): Promise<FailedDocumentSyncAction> {\n const action = await classifyFailedDocumentSyncAction(input);\n traceSubmitFailed(input.onSyncTrace, {\n action:\n action === \"retry\" || action === \"stop\"\n ? action\n : action.kind === \"recover_update_id_conflict\"\n ? \"recover-update-ids\"\n : \"regenerate-checkpoints\",\n code: input.failure.code,\n documentId: input.documentId,\n status: input.failure.status,\n });\n return action;\n}\n\nasync function classifyFailedDocumentSyncAction(input: {\n attempt: number;\n canRegenerateQueuedCheckpoints?: boolean | undefined;\n documentId: string;\n failure: DocumentSyncSubmitFailure;\n maxAttempts: number;\n onInlineRepairRefused?: (() => void) | undefined;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n pendingUpdates: readonly PendingUpdateRecord[];\n}): Promise<FailedDocumentSyncAction> {\n if (\n await handleUpstreamDeletedDocumentSyncFailure({\n documentId: input.documentId,\n failure: input.failure,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n })\n ) {\n return \"stop\";\n }\n\n if (\n canRetryDocumentSyncConflict({\n attempt: input.attempt,\n failure: input.failure,\n maxAttempts: input.maxAttempts,\n })\n ) {\n return \"retry\";\n }\n\n // The write rolled back whole. Its inline repairs would have stranded a\n // level above a directly granted container, and a flat rekey list cannot say\n // what each must carry: the retry commits them standalone instead.\n if (\n input.attempt < input.maxAttempts &&\n input.onInlineRepairRefused &&\n input.failure.code === DOCUMENT_SYNC_ERROR_CODES.descendantRekeysRequired\n ) {\n input.onInlineRepairRefused();\n return \"retry\";\n }\n\n if (\n canRecoverDocumentUpdateIdConflict({\n attempt: input.attempt,\n failure: input.failure,\n maxAttempts: input.maxAttempts,\n pendingUpdateCount: input.pendingUpdates.length,\n })\n ) {\n return {\n kind: \"recover_update_id_conflict\",\n recoveryPendingUpdatesById: new Map(\n input.pendingUpdates.map((update) => [update.id, update]),\n ),\n };\n }\n\n if (\n input.attempt < input.maxAttempts &&\n input.canRegenerateQueuedCheckpoints === true &&\n isCheckpointCoverageConflict(input.failure)\n ) {\n return { kind: \"regenerate_queued_checkpoints\" };\n }\n\n input.failure.report();\n await input.onTerminalSubmitFailure?.(input.failure);\n return \"stop\";\n}\n\nasync function submitDocumentSyncAttempt(input: {\n apiClient: DocumentSyncApi;\n attempt: number;\n canRegenerateQueuedCheckpoints?: boolean | undefined;\n documentId: string;\n expectedCommitLsnMode?: DocumentSyncCommitLsnMode | undefined;\n maxAttempts: number;\n onInlineRepairRefused?: (() => void) | undefined;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalSubmitFailure?: TerminalSubmitFailureHandler | undefined;\n pendingUpdates: readonly PendingUpdateRecord[];\n plan: DocumentSyncPlan;\n stillCurrent?: (() => boolean) | undefined;\n warmReferencedPrincipalPolicies?: ReferencedPrincipalPolicyWarmer | undefined;\n}): Promise<DocumentSyncAttemptSubmission> {\n if (input.stillCurrent?.() === false) return \"cancelled\";\n const submitted = await submitDocumentSync({\n apiClient: input.apiClient,\n expectedCommitLsnMode: input.expectedCommitLsnMode,\n plan: input.plan,\n });\n if (input.stillCurrent?.() === false) return \"cancelled\";\n if (!submitted) {\n return \"stop\";\n }\n if (submitted.ok) {\n return {\n kind: \"completed\",\n pullComplete: submitted.pullComplete,\n response: submitted.response,\n };\n }\n\n await recoverDocumentSyncPolicyRepair({\n failure: submitted,\n plan: input.plan,\n stillCurrent: input.stillCurrent,\n warmReferencedPrincipalPolicies: input.warmReferencedPrincipalPolicies,\n });\n if (input.stillCurrent?.() === false) return \"cancelled\";\n\n return resolveFailedDocumentSyncAction({\n attempt: input.attempt,\n canRegenerateQueuedCheckpoints: input.canRegenerateQueuedCheckpoints,\n documentId: input.documentId,\n failure: submitted,\n maxAttempts: input.maxAttempts,\n onInlineRepairRefused: input.onInlineRepairRefused,\n onRemoteDocumentDeleted: input.onRemoteDocumentDeleted,\n onSyncTrace: input.onSyncTrace,\n onTerminalSubmitFailure: input.onTerminalSubmitFailure,\n pendingUpdates: input.pendingUpdates,\n });\n}\n\nexport async function submitDocumentSyncAttemptIfAllowed(\n input: Parameters<typeof submitDocumentSyncAttempt>[0] & {\n isRemoteSyncBlocked?: ((organizationId: string) => boolean) | undefined;\n onOutgoingUpdatesMaterialized?:\n | ((updateIds: readonly string[]) => void)\n | undefined;\n failureBlocksQueuedWrites?: boolean | undefined;\n },\n): Promise<DocumentSyncAttemptSubmission> {\n const {\n failureBlocksQueuedWrites,\n isRemoteSyncBlocked,\n onOutgoingUpdatesMaterialized,\n ...submissionInput\n } = input;\n const hasRemoteWrites =\n input.plan.request.outgoingUpdates.length > 0 ||\n (input.plan.request.containerRekeys?.length ?? 0) > 0;\n if (hasRemoteWrites && isRemoteSyncBlocked?.(input.plan.organizationId)) {\n return \"blocked\";\n }\n if (input.stillCurrent?.() === false) return \"cancelled\";\n\n onOutgoingUpdatesMaterialized?.(\n input.plan.request.outgoingUpdates.map(({ id }) => id),\n );\n\n return submitDocumentSyncAttempt({\n ...submissionInput,\n // A read-only pass carries no writes, so a terminal failure describes a\n // pull, not queued local data — recording it would flag the next local\n // edit as failed before it was ever attempted. A cursor continuation and\n // update-id recovery both submit an empty request while durable rows still\n // exist; a terminal 403 there IS what blocks the queued edits.\n onTerminalSubmitFailure:\n hasRemoteWrites || failureBlocksQueuedWrites\n ? submissionInput.onTerminalSubmitFailure\n : undefined,\n });\n}\n\nasync function resolveDocumentSyncWriterProjection(input: {\n apiClient: DocumentSyncApi;\n documentId: string;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n /**\n * Invoked when the projection fetch fails terminally. Write-bearing sync\n * passes persist this: without a writer projection their queued writes can\n * never submit, so the failure (e.g. a 403 after access revocation) is what\n * the write queue should surface.\n */\n onTerminalFailure?: TerminalSubmitFailureHandler | undefined;\n reusableWriterProjection: DocumentWriterProjectionResponse | null;\n stillCurrent?: (() => boolean) | undefined;\n}): Promise<DocumentWriterProjectionResolution> {\n if (input.stillCurrent?.() === false) return null;\n if (input.reusableWriterProjection) {\n return input.reusableWriterProjection;\n }\n\n const result = await input.apiClient.getDocumentWriterProjectionResult(\n input.documentId,\n { reportErrors: false },\n );\n if (input.stillCurrent?.() === false) return null;\n if (result.ok) {\n return result.data;\n }\n if (isUpstreamDeletedDocumentSyncFailure(result)) {\n return REMOTE_DOCUMENT_DELETED;\n }\n traceProjectionFailed(input.onSyncTrace, {\n code: result.code,\n documentId: input.documentId,\n status: result.status,\n });\n result.report();\n await input.onTerminalFailure?.(result);\n return null;\n}\n\nexport async function retrySyncPlan(input: {\n apiClient: DocumentSyncApi;\n buildWithProjection: (\n projection: DocumentWriterProjectionResponse,\n ) => Promise<MaterializedDocumentSyncPlan>;\n documentId: string;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalFailure?: TerminalSubmitFailureHandler | undefined;\n stillCurrent?: (() => boolean) | undefined;\n writerProjection: DocumentWriterProjectionResponse;\n}): Promise<\n | readonly [MaterializedDocumentSyncPlan, DocumentWriterProjectionResponse]\n | null\n> {\n try {\n return [\n await input.buildWithProjection(input.writerProjection),\n input.writerProjection,\n ];\n } catch (error) {\n if (\n !input.apiClient.evictDocumentWriterProjection ||\n !shouldRetrySyncWithFreshWriterProjection(error)\n ) {\n throw error;\n }\n }\n if (input.stillCurrent?.() === false) return null;\n\n // Only this document's projection was stale; evict just it so unrelated\n // documents keep their warm cache instead of a global wipe.\n input.apiClient.evictDocumentWriterProjection?.(input.documentId);\n const writerProjection = await resolveDocumentSyncWriterProjection({\n apiClient: input.apiClient,\n documentId: input.documentId,\n onSyncTrace: input.onSyncTrace,\n onTerminalFailure: input.onTerminalFailure,\n reusableWriterProjection: null,\n stillCurrent: input.stillCurrent,\n });\n if (input.stillCurrent?.() === false) return null;\n if (writerProjection === REMOTE_DOCUMENT_DELETED) {\n await input.onRemoteDocumentDeleted?.({ documentId: input.documentId });\n return null;\n }\n if (!writerProjection) {\n return null;\n }\n\n return [await input.buildWithProjection(writerProjection), writerProjection];\n}\n\n/**\n * Resolves the writer projection for one sync attempt, converting the two\n * unrecoverable outcomes into an abandoned (null) result with a named reason\n * so callers that turn a null sync into their own error can surface the real\n * cause.\n */\nexport async function resolveSyncAttemptWriterProjection(input: {\n apiClient: DocumentSyncApi;\n documentId: string;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncAbandoned?: ((reason: string) => void) | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalFailure?: TerminalSubmitFailureHandler | undefined;\n reusableWriterProjection: DocumentWriterProjectionResponse | null;\n stillCurrent?: (() => boolean) | undefined;\n}): Promise<DocumentWriterProjectionResponse | null> {\n const writerProjection = await resolveDocumentSyncWriterProjection(input);\n if (input.stillCurrent?.() === false) return null;\n if (writerProjection === REMOTE_DOCUMENT_DELETED) {\n await input.onRemoteDocumentDeleted?.({ documentId: input.documentId });\n if (input.stillCurrent?.() !== false) {\n input.onSyncAbandoned?.(\"the remote document was deleted\");\n }\n return null;\n }\n if (!writerProjection) {\n input.onSyncAbandoned?.(\n \"the document writer projection could not be fetched\",\n );\n return null;\n }\n return writerProjection;\n}\n\nexport async function refreshSyncAttemptWriterProjection(\n input: Omit<\n Parameters<typeof resolveSyncAttemptWriterProjection>[0],\n \"reusableWriterProjection\"\n > & { unavailableError?: unknown },\n): Promise<DocumentWriterProjectionResponse | null> {\n const { onRemoteDocumentDeleted, unavailableError, ...resolutionInput } =\n input;\n if (input.stillCurrent?.() === false) return null;\n if (input.apiClient.evictDocumentWriterProjection) {\n input.apiClient.evictDocumentWriterProjection(input.documentId);\n } else {\n input.apiClient.clearWriterProjectionCaches?.();\n }\n let remoteDocumentDeleted = false;\n const writerProjection = await resolveSyncAttemptWriterProjection({\n ...resolutionInput,\n onRemoteDocumentDeleted: async (deleted) => {\n remoteDocumentDeleted = true;\n await onRemoteDocumentDeleted?.(deleted);\n },\n reusableWriterProjection: null,\n });\n if (\n !writerProjection &&\n unavailableError !== undefined &&\n !remoteDocumentDeleted &&\n input.stillCurrent?.() !== false\n ) {\n throw unavailableError;\n }\n return writerProjection;\n}\n\nexport async function retrySyncPlanOrAbandon(input: {\n apiClient: DocumentSyncApi;\n buildWithProjection: (\n projection: DocumentWriterProjectionResponse,\n ) => Promise<MaterializedDocumentSyncPlan>;\n documentId: string;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n onSyncAbandoned?: ((reason: string) => void) | undefined;\n onSyncTrace?: DocumentSyncTraceEmitter | undefined;\n onTerminalFailure?: TerminalSubmitFailureHandler | undefined;\n stillCurrent?: (() => boolean) | undefined;\n writerProjection: DocumentWriterProjectionResponse;\n}): Promise<\n | readonly [MaterializedDocumentSyncPlan, DocumentWriterProjectionResponse]\n | null\n> {\n const planned = await retrySyncPlan(input);\n if (!planned && input.stillCurrent?.() !== false) {\n input.onSyncAbandoned?.(\n \"a sync plan could not be built against the current projection\",\n );\n }\n return planned;\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"syncAbandon.js","sourceRoot":"","sources":["syncAbandon.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,4BAA4B,EAAE,MAAM,mBAAmB,CAAC;AACjE,OAAO,EAAE,oCAAoC,EAAE,MAAM,qBAAqB,CAAC;AAQ3E,MAAM,UAAU,kBAAkB,CAAC,KAAyB;IAC1D,KAAK,CAAC,WAAW,EAAE,CAAC,kCAAkC,KAAK,CAAC,UAAU,EAAE,CAAC,CAAC;IAC1E,KAAK,CAAC,eAAe,EAAE,CAAC,SAAS,CAAC,CAAC;IACnC,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,UAAU,qBAAqB,CACnC,KAAyB,EACzB,KAA2C;IAE3C,uEAAuE;IACvE,yEAAyE;IACzE,yEAAyE;IACzE,4BAA4B,CAAC,KAAK,CAAC,WAAW,EAAE;QAC9C,UAAU,EAAE,KAAK,CAAC,UAAU;QAC5B,MAAM,EAAE,KAAK,CAAC,MAAM;KACrB,CAAC,CAAC;IACH,KAAK,CAAC,eAAe,EAAE,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;IACtC,OAAO,IAAI,CAAC;AACd,CAAC;AAED;;;;;GAKG;AACH,MAAM,CAAC,KAAK,UAAU,iCAAiC,CACrD,KAAyB,EACzB,KAA0C;IAE1C,MAAM,KAAK,CAAC,uBAAuB,EAAE,CAAC;QACpC,IAAI,EAAE,uCAAuC;QAC7C,OAAO,EAAE,KAAK,CAAC,OAAO;QACtB,EAAE,EAAE,KAAK;QACT,MAAM,EAAE,GAAG,EAAE,CAAC,SAAS;QACvB,MAAM,EAAE,IAAI;KACb,CAAC,CAAC;IACH,OAAO,qBAAqB,CAC1B,KAAK,EACL,IAAI,oCAAoC,CAAC,cAAc,CAAC,CACzD,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,8BAA8B,CAC5C,KAAyB;IAEzB,KAAK,CAAC,eAAe,EAAE,CAAC,6CAA6C,CAAC,CAAC;IACvE,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,wBAAwB,CAC5C,KAAyB,EACzB,KAAY;IAEZ,MAAM,OAAO,GAA8B;QACzC,IAAI,EAAE,iCAAiC;QACvC,OAAO,EAAE,KAAK,CAAC,OAAO;QACtB,EAAE,EAAE,KAAK;QACT,MAAM,EAAE,GAAG,EAAE,CAAC,SAAS;QACvB,MAAM,EAAE,IAAI;KACb,CAAC;IACF,MAAM,KAAK,CAAC,uBAAuB,EAAE,CAAC,OAAO,CAAC,CAAC;IAC/C,KAAK,CAAC,eAAe,EAAE,CACrB,mEAAmE,CACpE,CAAC;IACF,OAAO,IAAI,CAAC;AACd,CAAC","sourcesContent":["import type { ContainerKekRepairInaccessibleError } from \"../../../data/documents/shared/containerKekCurrency\";\nimport type { DocumentSyncSubmitFailure } from \"../../../data/documents/shared/types\";\nimport type { SyncRemoteDocumentInput } from \"../sync/readOnlySync\";\nimport { traceAncestorRepairAbandoned } from \"../sync/syncTrace\";\nimport { DocumentAncestorRepairAbandonedError } from \"./syncRepairAbandon\";\n\n/** The ways a sync pass gives up without failing: writes stay queued. */\ntype AbandonedSyncInput = Pick<\n SyncRemoteDocumentInput,\n \"documentId\" | \"onSyncAbandoned\" | \"onSyncTrace\" | \"onTerminalSubmitFailure\"\n>;\n\nexport function abandonBlockedSync(input: AbandonedSyncInput): null {\n input.onSyncTrace?.(`document sync blocked document=${input.documentId}`);\n input.onSyncAbandoned?.(\"blocked\");\n return null;\n}\n\nexport function abandonAncestorRepair(\n input: AbandonedSyncInput,\n error: DocumentAncestorRepairAbandonedError,\n): null {\n // Trace as well as abandon: the store's onSyncAbandoned only parks the\n // document, and this path may already have issued server-side rekeys, so\n // abandoning untraced would leave a retrying loop with no way to see it.\n traceAncestorRepairAbandoned(input.onSyncTrace, {\n documentId: input.documentId,\n reason: error.reason,\n });\n input.onSyncAbandoned?.(error.reason);\n return null;\n}\n\n/**\n * The stale ancestor is one this writer can neither re-key nor be given the\n * key for, and one refetch has already confirmed nobody repaired it yet. The\n * writes stay queued; the durable row tells the write queue why, and the\n * dependent-path hint that follows the repair re-arms the pass.\n */\nexport async function abandonInaccessibleAncestorRepair(\n input: AbandonedSyncInput,\n error: ContainerKekRepairInaccessibleError,\n): Promise<null> {\n await input.onTerminalSubmitFailure?.({\n code: \"document_ancestor_repair_inaccessible\",\n message: error.message,\n ok: false,\n report: () => undefined,\n status: null,\n });\n return abandonAncestorRepair(\n input,\n new DocumentAncestorRepairAbandonedError(\"inaccessible\"),\n );\n}\n\nexport function abandonAfterRetryableConflicts(\n input: AbandonedSyncInput,\n): null {\n input.onSyncAbandoned?.(\"every sync attempt hit a retryable conflict\");\n return null;\n}\n\nexport async function abandonOversizedSyncPlan(\n input: AbandonedSyncInput,\n error: Error,\n): Promise<null> {\n const failure: DocumentSyncSubmitFailure = {\n code: \"document_sync_request_too_large\",\n message: error.message,\n ok: false,\n report: () => undefined,\n status: null,\n };\n await input.onTerminalSubmitFailure?.(failure);\n input.onSyncAbandoned?.(\n \"a queued update cannot fit within the document sync request limit\",\n );\n return null;\n}\n"]}
|
|
1
|
+
{"version":3,"file":"syncAbandon.js","sourceRoot":"","sources":["syncAbandon.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,4BAA4B,EAAE,MAAM,mBAAmB,CAAC;AACjE,OAAO,EAAE,oCAAoC,EAAE,MAAM,qBAAqB,CAAC;AAQ3E,MAAM,UAAU,kBAAkB,CAAC,KAAyB;IAC1D,KAAK,CAAC,WAAW,EAAE,CAAC,kCAAkC,KAAK,CAAC,UAAU,EAAE,CAAC,CAAC;IAC1E,KAAK,CAAC,eAAe,EAAE,CAAC,SAAS,CAAC,CAAC;IACnC,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,UAAU,qBAAqB,CACnC,KAAyB,EACzB,KAA2C;IAE3C,uEAAuE;IACvE,yEAAyE;IACzE,yEAAyE;IACzE,4BAA4B,CAAC,KAAK,CAAC,WAAW,EAAE;QAC9C,UAAU,EAAE,KAAK,CAAC,UAAU;QAC5B,MAAM,EAAE,KAAK,CAAC,MAAM;KACrB,CAAC,CAAC;IACH,KAAK,CAAC,eAAe,EAAE,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;IACtC,OAAO,IAAI,CAAC;AACd,CAAC;AAED;;;;;GAKG;AACH,MAAM,CAAC,KAAK,UAAU,iCAAiC,CACrD,KAAyB,EACzB,KAA0C;IAE1C,MAAM,KAAK,CAAC,uBAAuB,EAAE,CAAC;QACpC,IAAI,EAAE,uCAAuC;QAC7C,OAAO,EAAE,KAAK,CAAC,OAAO;QACtB,EAAE,EAAE,KAAK;QACT,MAAM,EAAE,GAAG,EAAE,CAAC,SAAS;QACvB,MAAM,EAAE,IAAI;KACb,CAAC,CAAC;IACH,OAAO,qBAAqB,CAC1B,KAAK,EACL,IAAI,oCAAoC,CAAC,cAAc,CAAC,CACzD,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,8BAA8B,CAC5C,KAAyB;IAEzB,KAAK,CAAC,eAAe,EAAE,CAAC,6CAA6C,CAAC,CAAC;IACvE,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,wBAAwB,CAC5C,KAAyB,EACzB,KAAY;IAEZ,MAAM,OAAO,GAA8B;QACzC,IAAI,EAAE,iCAAiC;QACvC,OAAO,EAAE,KAAK,CAAC,OAAO;QACtB,EAAE,EAAE,KAAK;QACT,MAAM,EAAE,GAAG,EAAE,CAAC,SAAS;QACvB,MAAM,EAAE,IAAI;KACb,CAAC;IACF,MAAM,KAAK,CAAC,uBAAuB,EAAE,CAAC,OAAO,CAAC,CAAC;IAC/C,KAAK,CAAC,eAAe,EAAE,CACrB,mEAAmE,CACpE,CAAC;IACF,OAAO,IAAI,CAAC;AACd,CAAC","sourcesContent":["import type { ContainerKekRepairInaccessibleError } from \"../../../data/documents/shared/containerKek/containerKekCurrency\";\nimport type { DocumentSyncSubmitFailure } from \"../../../data/documents/shared/types\";\nimport type { SyncRemoteDocumentInput } from \"../sync/readOnlySync\";\nimport { traceAncestorRepairAbandoned } from \"../sync/syncTrace\";\nimport { DocumentAncestorRepairAbandonedError } from \"./syncRepairAbandon\";\n\n/** The ways a sync pass gives up without failing: writes stay queued. */\ntype AbandonedSyncInput = Pick<\n SyncRemoteDocumentInput,\n \"documentId\" | \"onSyncAbandoned\" | \"onSyncTrace\" | \"onTerminalSubmitFailure\"\n>;\n\nexport function abandonBlockedSync(input: AbandonedSyncInput): null {\n input.onSyncTrace?.(`document sync blocked document=${input.documentId}`);\n input.onSyncAbandoned?.(\"blocked\");\n return null;\n}\n\nexport function abandonAncestorRepair(\n input: AbandonedSyncInput,\n error: DocumentAncestorRepairAbandonedError,\n): null {\n // Trace as well as abandon: the store's onSyncAbandoned only parks the\n // document, and this path may already have issued server-side rekeys, so\n // abandoning untraced would leave a retrying loop with no way to see it.\n traceAncestorRepairAbandoned(input.onSyncTrace, {\n documentId: input.documentId,\n reason: error.reason,\n });\n input.onSyncAbandoned?.(error.reason);\n return null;\n}\n\n/**\n * The stale ancestor is one this writer can neither re-key nor be given the\n * key for, and one refetch has already confirmed nobody repaired it yet. The\n * writes stay queued; the durable row tells the write queue why, and the\n * dependent-path hint that follows the repair re-arms the pass.\n */\nexport async function abandonInaccessibleAncestorRepair(\n input: AbandonedSyncInput,\n error: ContainerKekRepairInaccessibleError,\n): Promise<null> {\n await input.onTerminalSubmitFailure?.({\n code: \"document_ancestor_repair_inaccessible\",\n message: error.message,\n ok: false,\n report: () => undefined,\n status: null,\n });\n return abandonAncestorRepair(\n input,\n new DocumentAncestorRepairAbandonedError(\"inaccessible\"),\n );\n}\n\nexport function abandonAfterRetryableConflicts(\n input: AbandonedSyncInput,\n): null {\n input.onSyncAbandoned?.(\"every sync attempt hit a retryable conflict\");\n return null;\n}\n\nexport async function abandonOversizedSyncPlan(\n input: AbandonedSyncInput,\n error: Error,\n): Promise<null> {\n const failure: DocumentSyncSubmitFailure = {\n code: \"document_sync_request_too_large\",\n message: error.message,\n ok: false,\n report: () => undefined,\n status: null,\n };\n await input.onTerminalSubmitFailure?.(failure);\n input.onSyncAbandoned?.(\n \"a queued update cannot fit within the document sync request limit\",\n );\n return null;\n}\n"]}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { KeyingVerificationError } from "../../../internal/crypto/index.js";
|
|
2
2
|
import { DOCUMENT_MUTATION_ERROR_CODES, DOCUMENT_SYNC_ERROR_CODES, } from "../../../internal/validators/response/index.js";
|
|
3
|
-
import { ContainerKekRepairRequiredError } from "../../../data/documents/shared/containerKekCurrency.js";
|
|
3
|
+
import { ContainerKekRepairRequiredError } from "../../../data/documents/shared/containerKek/containerKekCurrency.js";
|
|
4
4
|
import { isRetryableDocumentSyncConflict, isUpstreamDeletedDocumentSyncFailure, } from "../../../data/documents/shared/responses.js";
|
|
5
5
|
import { ProjectionDependencyUnavailableError } from "../../../data/keyingProjectionVerification/dependencyUnavailable.js";
|
|
6
6
|
import { isKeyingVerificationError } from "../../../data/keyingProjectionVerification/error.js";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"syncFailureClassification.js","sourceRoot":"","sources":["syncFailureClassification.ts"],"names":[],"mappings":"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","sourcesContent":["import { KeyingVerificationError } from \"@tearleads/crypto\";\nimport {\n DOCUMENT_MUTATION_ERROR_CODES,\n DOCUMENT_SYNC_ERROR_CODES,\n} from \"@tearleads/validators/response\";\nimport { ContainerKekRepairRequiredError } from \"../../../data/documents/shared/containerKekCurrency\";\nimport {\n isRetryableDocumentSyncConflict,\n isUpstreamDeletedDocumentSyncFailure,\n} from \"../../../data/documents/shared/responses\";\nimport type { DocumentSyncSubmitFailure } from \"../../../data/documents/shared/types\";\nimport { ProjectionDependencyUnavailableError } from \"../../../data/keyingProjectionVerification/dependencyUnavailable\";\nimport { isKeyingVerificationError } from \"../../../data/keyingProjectionVerification/error\";\nimport type { ExecSql } from \"../../../data/sqlite/sqlSchema\";\n\nexport type RemoteDocumentDeletionHandler = (input: {\n /** Present only after the SDK has verified the signed terminal purge proof. */\n readonly commitPurgeProof?:\n | ((transactionExecSql: ExecSql) => Promise<void>)\n | undefined;\n readonly documentId: string;\n}) => Promise<void> | void;\n\n/**\n * Invoked when a submission fails terminally — the failure is neither a\n * retryable conflict nor a recoverable update-id conflict, so the sync pass\n * stops and the pending writes stay queued (e.g. a 403 after write access was\n * revoked). Callers persist the failure so the write queue can surface it.\n */\nexport type TerminalSubmitFailureHandler = (\n failure: DocumentSyncSubmitFailure,\n) => Promise<void> | void;\n\n/**\n * Read-only counterpart to describeDocumentSyncSubmitFailure: names a refused\n * revalidation without implying a blocked write. 403s never reach this — a\n * read-only 403 is deliberately suppressed (edge-case row 9) so unattempted\n * local edits are never flagged.\n */\nexport function describeDocumentRevalidationFailure(\n failure: Pick<DocumentSyncSubmitFailure, \"message\" | \"status\">,\n): string {\n const detail =\n failure.message.trim().length > 0\n ? failure.message.trim()\n : \"the server refused the read\";\n const suffix = failure.status === null ? \"\" : ` (${failure.status})`;\n return `Remote revalidation failed: ${detail}${suffix}`;\n}\n\n/** Human-readable description of a terminal submit failure for queue display. */\nexport function describeDocumentSyncSubmitFailure(\n failure: Pick<DocumentSyncSubmitFailure, \"message\" | \"status\">,\n): string {\n if (failure.status === 403) {\n return \"Write access denied by the server (403)\";\n }\n const message =\n failure.message.trim().length > 0 ? failure.message.trim() : \"Sync failed\";\n return failure.status === null ? message : `${message} (${failure.status})`;\n}\n\ntype ProjectionIntegrityErrorCode =\n | \"equivocation\"\n | \"rollback\"\n | \"stale_predecessor\";\n\nfunction keyingVerificationErrorCode(error: unknown): string | null {\n if (!isKeyingVerificationError(error) || !(error instanceof Error)) {\n return null;\n }\n const code = Reflect.get(error, \"code\");\n return typeof code === \"string\" ? code : null;\n}\n\nexport function projectionIntegrityErrorCode(\n error: unknown,\n): ProjectionIntegrityErrorCode | null {\n if (\n !(error instanceof KeyingVerificationError) &&\n !(error instanceof Error && error.name === \"KeyingVerificationError\")\n ) {\n return null;\n }\n\n const code = keyingVerificationErrorCode(error);\n return code === \"rollback\" ||\n code === \"equivocation\" ||\n code === \"stale_predecessor\"\n ? code\n : null;\n}\n\n/**\n * Shared shell for the stale-projection retry classifiers. A cached\n * projection older than a checkpoint we already recorded (\"rollback\") —\n * typical right after a peer shared/rotated a linked container — is resolved\n * by refetching the current projection. The refetch is safe: it cannot\n * bypass the anti-rollback check, because a genuinely rolled-back server\n * response re-throws on the rebuilt plan. Any other keying-verification\n * failure is terminal; anything else defers to the caller's message\n * predicate for its unwrap-failure shape.\n */\nexport function shouldRetryWithFreshProjection(\n error: unknown,\n messageMatches: (message: string) => boolean,\n): boolean {\n // A peer may already have repaired the chain. Refetch once; the same guard\n // rejects a still-stale response before any new ciphertext is produced.\n if (\n error instanceof ContainerKekRepairRequiredError ||\n error instanceof ProjectionDependencyUnavailableError\n )\n return true;\n const integrityErrorCode = projectionIntegrityErrorCode(error);\n if (integrityErrorCode) {\n return integrityErrorCode === \"rollback\";\n }\n if (keyingVerificationErrorCode(error) === \"invalid_shape\") {\n // Verification boundaries normalize malformed/stale projection data to a\n // terminal error. One cache eviction is still safe: a dishonest or broken\n // fresh response fails again outside this retry boundary.\n return true;\n }\n if (isKeyingVerificationError(error)) {\n return false;\n }\n\n return error instanceof Error && messageMatches(error.message);\n}\n\nexport function shouldRetrySyncWithFreshWriterProjection(\n error: unknown,\n): boolean {\n return shouldRetryWithFreshProjection(\n error,\n (message) =>\n message.startsWith(\n \"Document authorizing container KEK path could not be unwrapped\",\n ) && message.includes(\"Container writer projection KEK\"),\n );\n}\n\nexport function isRecoverableDocumentUpdateIdConflict(\n failure: DocumentSyncSubmitFailure,\n): boolean {\n return (\n failure.status === 409 &&\n failure.code === DOCUMENT_SYNC_ERROR_CODES.updateIdConflict\n );\n}\n\n/**\n * The server's covering-baseline gate refused a queued rotation checkpoint\n * (e.g. a leftover from an interrupted recovery or a lost heal ack) because\n * it no longer covers the committed frontier. The pass can repair itself by\n * regenerating a fresh covering baseline from the live document instead of\n * resubmitting the stale payload — which would fail terminally forever.\n */\nexport function isCheckpointCoverageConflict(\n failure: DocumentSyncSubmitFailure,\n): boolean {\n return (\n failure.status === 409 &&\n failure.code === DOCUMENT_SYNC_ERROR_CODES.checkpointCoverageConflict\n );\n}\n\n/**\n * A create submitted with a stable documentId whose first attempt already\n * committed server-side comes back as this 409 (see the server's\n * `assertCreateCanAdvanceDocumentHead`). It is not a failure — the caller adopts\n * the existing remote document instead of creating a duplicate.\n */\nexport function isDocumentManifestAlreadyExistsConflict(failure: {\n readonly code?: string | undefined;\n readonly message: string;\n readonly status: number | null;\n}): boolean {\n return (\n failure.status === 409 &&\n failure.code === DOCUMENT_MUTATION_ERROR_CODES.manifestAlreadyExists\n );\n}\n\nexport function canRetryDocumentSyncConflict(input: {\n attempt: number;\n failure: DocumentSyncSubmitFailure;\n maxAttempts: number;\n}): boolean {\n return (\n input.attempt < input.maxAttempts &&\n isRetryableDocumentSyncConflict(input.failure)\n );\n}\n\nexport function canRecoverDocumentUpdateIdConflict(input: {\n attempt: number;\n failure: DocumentSyncSubmitFailure;\n maxAttempts: number;\n pendingUpdateCount: number;\n}): boolean {\n return (\n input.attempt < input.maxAttempts &&\n input.pendingUpdateCount > 0 &&\n isRecoverableDocumentUpdateIdConflict(input.failure)\n );\n}\n\nexport async function handleUpstreamDeletedDocumentSyncFailure(input: {\n documentId: string;\n failure: DocumentSyncSubmitFailure;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n}): Promise<boolean> {\n if (!isUpstreamDeletedDocumentSyncFailure(input.failure)) {\n return false;\n }\n\n await input.onRemoteDocumentDeleted?.({ documentId: input.documentId });\n return true;\n}\n"]}
|
|
1
|
+
{"version":3,"file":"syncFailureClassification.js","sourceRoot":"","sources":["syncFailureClassification.ts"],"names":[],"mappings":"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","sourcesContent":["import { KeyingVerificationError } from \"@tearleads/crypto\";\nimport {\n DOCUMENT_MUTATION_ERROR_CODES,\n DOCUMENT_SYNC_ERROR_CODES,\n} from \"@tearleads/validators/response\";\nimport { ContainerKekRepairRequiredError } from \"../../../data/documents/shared/containerKek/containerKekCurrency\";\nimport {\n isRetryableDocumentSyncConflict,\n isUpstreamDeletedDocumentSyncFailure,\n} from \"../../../data/documents/shared/responses\";\nimport type { DocumentSyncSubmitFailure } from \"../../../data/documents/shared/types\";\nimport { ProjectionDependencyUnavailableError } from \"../../../data/keyingProjectionVerification/dependencyUnavailable\";\nimport { isKeyingVerificationError } from \"../../../data/keyingProjectionVerification/error\";\nimport type { ExecSql } from \"../../../data/sqlite/sqlSchema\";\n\nexport type RemoteDocumentDeletionHandler = (input: {\n /** Present only after the SDK has verified the signed terminal purge proof. */\n readonly commitPurgeProof?:\n | ((transactionExecSql: ExecSql) => Promise<void>)\n | undefined;\n readonly documentId: string;\n}) => Promise<void> | void;\n\n/**\n * Invoked when a submission fails terminally — the failure is neither a\n * retryable conflict nor a recoverable update-id conflict, so the sync pass\n * stops and the pending writes stay queued (e.g. a 403 after write access was\n * revoked). Callers persist the failure so the write queue can surface it.\n */\nexport type TerminalSubmitFailureHandler = (\n failure: DocumentSyncSubmitFailure,\n) => Promise<void> | void;\n\n/**\n * Read-only counterpart to describeDocumentSyncSubmitFailure: names a refused\n * revalidation without implying a blocked write. 403s never reach this — a\n * read-only 403 is deliberately suppressed (edge-case row 9) so unattempted\n * local edits are never flagged.\n */\nexport function describeDocumentRevalidationFailure(\n failure: Pick<DocumentSyncSubmitFailure, \"message\" | \"status\">,\n): string {\n const detail =\n failure.message.trim().length > 0\n ? failure.message.trim()\n : \"the server refused the read\";\n const suffix = failure.status === null ? \"\" : ` (${failure.status})`;\n return `Remote revalidation failed: ${detail}${suffix}`;\n}\n\n/** Human-readable description of a terminal submit failure for queue display. */\nexport function describeDocumentSyncSubmitFailure(\n failure: Pick<DocumentSyncSubmitFailure, \"message\" | \"status\">,\n): string {\n if (failure.status === 403) {\n return \"Write access denied by the server (403)\";\n }\n const message =\n failure.message.trim().length > 0 ? failure.message.trim() : \"Sync failed\";\n return failure.status === null ? message : `${message} (${failure.status})`;\n}\n\ntype ProjectionIntegrityErrorCode =\n | \"equivocation\"\n | \"rollback\"\n | \"stale_predecessor\";\n\nfunction keyingVerificationErrorCode(error: unknown): string | null {\n if (!isKeyingVerificationError(error) || !(error instanceof Error)) {\n return null;\n }\n const code = Reflect.get(error, \"code\");\n return typeof code === \"string\" ? code : null;\n}\n\nexport function projectionIntegrityErrorCode(\n error: unknown,\n): ProjectionIntegrityErrorCode | null {\n if (\n !(error instanceof KeyingVerificationError) &&\n !(error instanceof Error && error.name === \"KeyingVerificationError\")\n ) {\n return null;\n }\n\n const code = keyingVerificationErrorCode(error);\n return code === \"rollback\" ||\n code === \"equivocation\" ||\n code === \"stale_predecessor\"\n ? code\n : null;\n}\n\n/**\n * Shared shell for the stale-projection retry classifiers. A cached\n * projection older than a checkpoint we already recorded (\"rollback\") —\n * typical right after a peer shared/rotated a linked container — is resolved\n * by refetching the current projection. The refetch is safe: it cannot\n * bypass the anti-rollback check, because a genuinely rolled-back server\n * response re-throws on the rebuilt plan. Any other keying-verification\n * failure is terminal; anything else defers to the caller's message\n * predicate for its unwrap-failure shape.\n */\nexport function shouldRetryWithFreshProjection(\n error: unknown,\n messageMatches: (message: string) => boolean,\n): boolean {\n // A peer may already have repaired the chain. Refetch once; the same guard\n // rejects a still-stale response before any new ciphertext is produced.\n if (\n error instanceof ContainerKekRepairRequiredError ||\n error instanceof ProjectionDependencyUnavailableError\n )\n return true;\n const integrityErrorCode = projectionIntegrityErrorCode(error);\n if (integrityErrorCode) {\n return integrityErrorCode === \"rollback\";\n }\n if (keyingVerificationErrorCode(error) === \"invalid_shape\") {\n // Verification boundaries normalize malformed/stale projection data to a\n // terminal error. One cache eviction is still safe: a dishonest or broken\n // fresh response fails again outside this retry boundary.\n return true;\n }\n if (isKeyingVerificationError(error)) {\n return false;\n }\n\n return error instanceof Error && messageMatches(error.message);\n}\n\nexport function shouldRetrySyncWithFreshWriterProjection(\n error: unknown,\n): boolean {\n return shouldRetryWithFreshProjection(\n error,\n (message) =>\n message.startsWith(\n \"Document authorizing container KEK path could not be unwrapped\",\n ) && message.includes(\"Container writer projection KEK\"),\n );\n}\n\nexport function isRecoverableDocumentUpdateIdConflict(\n failure: DocumentSyncSubmitFailure,\n): boolean {\n return (\n failure.status === 409 &&\n failure.code === DOCUMENT_SYNC_ERROR_CODES.updateIdConflict\n );\n}\n\n/**\n * The server's covering-baseline gate refused a queued rotation checkpoint\n * (e.g. a leftover from an interrupted recovery or a lost heal ack) because\n * it no longer covers the committed frontier. The pass can repair itself by\n * regenerating a fresh covering baseline from the live document instead of\n * resubmitting the stale payload — which would fail terminally forever.\n */\nexport function isCheckpointCoverageConflict(\n failure: DocumentSyncSubmitFailure,\n): boolean {\n return (\n failure.status === 409 &&\n failure.code === DOCUMENT_SYNC_ERROR_CODES.checkpointCoverageConflict\n );\n}\n\n/**\n * A create submitted with a stable documentId whose first attempt already\n * committed server-side comes back as this 409 (see the server's\n * `assertCreateCanAdvanceDocumentHead`). It is not a failure — the caller adopts\n * the existing remote document instead of creating a duplicate.\n */\nexport function isDocumentManifestAlreadyExistsConflict(failure: {\n readonly code?: string | undefined;\n readonly message: string;\n readonly status: number | null;\n}): boolean {\n return (\n failure.status === 409 &&\n failure.code === DOCUMENT_MUTATION_ERROR_CODES.manifestAlreadyExists\n );\n}\n\nexport function canRetryDocumentSyncConflict(input: {\n attempt: number;\n failure: DocumentSyncSubmitFailure;\n maxAttempts: number;\n}): boolean {\n return (\n input.attempt < input.maxAttempts &&\n isRetryableDocumentSyncConflict(input.failure)\n );\n}\n\nexport function canRecoverDocumentUpdateIdConflict(input: {\n attempt: number;\n failure: DocumentSyncSubmitFailure;\n maxAttempts: number;\n pendingUpdateCount: number;\n}): boolean {\n return (\n input.attempt < input.maxAttempts &&\n input.pendingUpdateCount > 0 &&\n isRecoverableDocumentUpdateIdConflict(input.failure)\n );\n}\n\nexport async function handleUpstreamDeletedDocumentSyncFailure(input: {\n documentId: string;\n failure: DocumentSyncSubmitFailure;\n onRemoteDocumentDeleted?: RemoteDocumentDeletionHandler | undefined;\n}): Promise<boolean> {\n if (!isUpstreamDeletedDocumentSyncFailure(input.failure)) {\n return false;\n }\n\n await input.onRemoteDocumentDeleted?.({ documentId: input.documentId });\n return true;\n}\n"]}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import type { DocumentSyncResponse, DocumentWriterProjectionResponse } from "../../../internal/validators/response/index.js";
|
|
2
2
|
import type { DocumentSyncPreparedUpdate, ProjectionVerificationOptions } from "../../../data/documents/shared/types.js";
|
|
3
|
-
import type { PendingUpdateRecord } from "../../../data/sqlite/documentPersistence.js";
|
|
3
|
+
import type { PendingUpdateRecord } from "../../../data/sqlite/documentPersistence/index.js";
|
|
4
4
|
import type { ExecSql } from "../../../data/sqlite/sqlSchema.js";
|
|
5
5
|
type SyncResponseUpdate = DocumentSyncResponse["updates"][number];
|
|
6
6
|
type RawHistoryUnavailableValidator = (input: {
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { importContentKeyMaterial } from "../../../data/documents/shared/contentRecordKeys.js";
|
|
2
2
|
import { encryptDocumentPendingUpdate } from "../../../data/documents/shared/crypto.js";
|
|
3
|
-
import {
|
|
4
|
-
import { isDocumentSyncUpdateIsolationError, isolateDocumentSyncBatchError, isolateDocumentSyncUpdateError, } from "../../../data/documents/shared/documentSyncUpdateIsolation.js";
|
|
5
|
-
import { ContainerKekHistoryUnavailableError, collectContainerKeksForDocumentSync, DocumentContentKeyUnavailableError, DocumentHistoryUnavailableError, unwrapDocumentContentKeyFromBundle, } from "../../../data/documents/shared/projection.js";
|
|
3
|
+
import { ContainerKekHistoryUnavailableError, collectContainerKeksForDocumentSync, DocumentContentKeyUnavailableError, DocumentHistoryUnavailableError, unwrapDocumentContentKeyFromBundle, } from "../../../data/documents/shared/projection/index.js";
|
|
6
4
|
import { readWriteHeader } from "../../../data/documents/shared/readers.js";
|
|
5
|
+
import { assertDocumentSyncUpdateEncryptedRecord } from "../../../data/documents/shared/sync/documentSyncUpdateDecryption.js";
|
|
6
|
+
import { isDocumentSyncUpdateIsolationError, isolateDocumentSyncBatchError, isolateDocumentSyncUpdateError, } from "../../../data/documents/shared/sync/documentSyncUpdateIsolation.js";
|
|
7
7
|
import { projectionVerificationOptions } from "../../../data/documents/shared/types.js";
|
|
8
8
|
import { isKeyingVerificationError } from "../../../data/keyingProjectionVerification/error.js";
|
|
9
9
|
function isRawHistoryUnavailableCause(error) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"syncContentKeys.js","sourceRoot":"","sources":["syncContentKeys.ts"],"names":[],"mappings":"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","sourcesContent":["import type {\n DocumentSyncResponse,\n DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport { importContentKeyMaterial } from \"../../../data/documents/shared/contentRecordKeys\";\nimport { encryptDocumentPendingUpdate } from \"../../../data/documents/shared/crypto\";\nimport { assertDocumentSyncUpdateEncryptedRecord } from \"../../../data/documents/shared/documentSyncUpdateDecryption\";\nimport {\n isDocumentSyncUpdateIsolationError,\n isolateDocumentSyncBatchError,\n isolateDocumentSyncUpdateError,\n} from \"../../../data/documents/shared/documentSyncUpdateIsolation\";\nimport {\n ContainerKekHistoryUnavailableError,\n collectContainerKeksForDocumentSync,\n DocumentContentKeyUnavailableError,\n DocumentHistoryUnavailableError,\n unwrapDocumentContentKeyFromBundle,\n} from \"../../../data/documents/shared/projection\";\nimport { readWriteHeader } from \"../../../data/documents/shared/readers\";\nimport type {\n DocumentSyncPreparedUpdate,\n ProjectionVerificationOptions,\n} from \"../../../data/documents/shared/types\";\nimport { projectionVerificationOptions } from \"../../../data/documents/shared/types\";\nimport { isKeyingVerificationError } from \"../../../data/keyingProjectionVerification/error\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport type { ExecSql } from \"../../../data/sqlite/sqlSchema\";\n\ntype SyncResponseUpdate = DocumentSyncResponse[\"updates\"][number];\ntype RawHistoryUnavailableCause =\n | DocumentContentKeyUnavailableError\n | DocumentHistoryUnavailableError;\n\nfunction isRawHistoryUnavailableCause(\n error: unknown,\n): error is RawHistoryUnavailableCause {\n return (\n error instanceof DocumentContentKeyUnavailableError ||\n (error instanceof DocumentHistoryUnavailableError &&\n error.historyCause instanceof ContainerKekHistoryUnavailableError)\n );\n}\n\ntype RawHistoryUnavailableValidator = (input: {\n contentKeysByEpoch: ReadonlyMap<number, Uint8Array>;\n updates: readonly SyncResponseUpdate[];\n}) => void | Promise<void>;\n\n/** A raw recovery cannot reconstruct history without this retained epoch. */\nexport class DocumentRawHistoryUnavailableError extends Error {\n readonly code = \"document_raw_history_epoch_unavailable\";\n\n constructor(\n readonly contentKeyEpoch: number,\n cause: unknown,\n ) {\n super(\n `Document raw-history recovery cannot decrypt content-key epoch ${contentKeyEpoch}`,\n { cause },\n );\n this.name = \"DocumentRawHistoryUnavailableError\";\n }\n}\n\nasync function assertResponseEncryptedRecords(\n updates: readonly SyncResponseUpdate[],\n): Promise<void> {\n const inspections = await Promise.allSettled(\n updates.map(assertDocumentSyncUpdateEncryptedRecord),\n );\n const failures = inspections.flatMap((inspection, index) =>\n inspection.status === \"rejected\"\n ? [{ index, reason: inspection.reason }]\n : [],\n );\n const firstFailure = failures[0];\n if (failures.length === 1 && firstFailure) {\n throw firstFailure.reason;\n }\n if (failures.length > 1 && firstFailure) {\n const stage =\n isDocumentSyncUpdateIsolationError(firstFailure.reason) &&\n failures.every(\n ({ reason }) =>\n isDocumentSyncUpdateIsolationError(reason) &&\n reason.stage === firstFailure.reason.stage,\n )\n ? firstFailure.reason.stage\n : \"encrypted_record\";\n throw isolateDocumentSyncBatchError({\n cause: new Error(\"Multiple document encrypted records are invalid\"),\n stage,\n updateIds: failures.map(({ index }) => updates[index]?.id ?? \"unknown\"),\n });\n }\n}\n\nasync function throwRawHistoryUnavailable(input: {\n contentKeysByEpoch: ReadonlyMap<number, Uint8Array>;\n response: DocumentSyncResponse;\n unavailable: { cause: RawHistoryUnavailableCause; contentKeyEpoch: number };\n validate?: RawHistoryUnavailableValidator | undefined;\n}): Promise<never> {\n await assertResponseEncryptedRecords(input.response.updates);\n await input.validate?.({\n contentKeysByEpoch: input.contentKeysByEpoch,\n updates: input.response.updates.filter((update) =>\n input.contentKeysByEpoch.has(\n readWriteHeader(\n update.writeHeader,\n \"Document sync response write header\",\n ).contentKeyEpoch,\n ),\n ),\n });\n throw new DocumentRawHistoryUnavailableError(\n input.unavailable.contentKeyEpoch,\n input.unavailable.cause,\n );\n}\n\nexport async function prepareDocumentOutgoingUpdates(input: {\n contentKey: Uint8Array;\n contentKeyEpoch: number;\n documentId: string;\n organizationId: string;\n pendingUpdates: readonly PendingUpdateRecord[];\n}): Promise<DocumentSyncPreparedUpdate[]> {\n if (input.pendingUpdates.length === 0) {\n return [];\n }\n const contentKeyMaterial = await importContentKeyMaterial(input.contentKey);\n\n return Promise.all(\n input.pendingUpdates.map(async (update) => {\n const encrypted = await encryptDocumentPendingUpdate({\n contentKeyMaterial,\n contentKeyEpoch: input.contentKeyEpoch,\n documentId: input.documentId,\n organizationId: input.organizationId,\n update,\n });\n\n return {\n contentRecordId: encrypted.contentRecordId,\n encryptedData: encrypted.encryptedData,\n id: update.id,\n partialStartVersionVector: update.partialStartVersionVector,\n partialEndVersionVector: update.partialEndVersionVector,\n metadataHash: encrypted.metadataHash,\n ciphertextHash: encrypted.ciphertextHash,\n plaintextHash: encrypted.plaintextHash,\n ...(update.sourceVersionVector\n ? {\n checkpointKind: \"rotate_baseline\" as const,\n checkpointPayloadKind: \"full_history_snapshot\" as const,\n sourceVersionVector: update.sourceVersionVector,\n }\n : {}),\n };\n }),\n );\n}\n\nfunction syncResponseContentKeyBundlesByEpoch(\n response: DocumentSyncResponse,\n): ReadonlyMap<number, DocumentSyncResponse[\"contentKeyBundle\"]> {\n const byEpoch = new Map<number, DocumentSyncResponse[\"contentKeyBundle\"]>();\n\n for (const bundle of [\n response.contentKeyBundle,\n ...response.contentKeyBundles,\n ]) {\n if (byEpoch.has(bundle.contentKeyEpoch)) {\n throw new Error(\"Document sync response repeats a content-key epoch\");\n }\n byEpoch.set(bundle.contentKeyEpoch, bundle);\n }\n\n return byEpoch;\n}\n\nfunction syncResponseUpdatesByContentKeyEpoch(\n response: DocumentSyncResponse,\n): ReadonlyMap<number, readonly SyncResponseUpdate[]> {\n const updatesByEpoch = new Map<number, SyncResponseUpdate[]>();\n for (const update of response.updates) {\n let contentKeyEpoch: number;\n try {\n contentKeyEpoch = readWriteHeader(\n update.writeHeader,\n \"Document sync response write header\",\n ).contentKeyEpoch;\n } catch (error) {\n throw isolateDocumentSyncUpdateError({\n cause: error,\n responseUpdate: update,\n stage: \"write_header\",\n updateId: update.id,\n });\n }\n const epochUpdates = updatesByEpoch.get(contentKeyEpoch);\n if (epochUpdates) epochUpdates.push(update);\n else updatesByEpoch.set(contentKeyEpoch, [update]);\n }\n return updatesByEpoch;\n}\n\nfunction assertBundleMatchesUpdateHeaders(input: {\n bundle: DocumentSyncResponse[\"contentKeyBundle\"];\n requireOriginalTargets: boolean;\n updates: readonly SyncResponseUpdate[];\n}): void {\n for (const update of input.updates) {\n const header = readWriteHeader(\n update.writeHeader,\n \"Document sync response write header\",\n );\n if (\n header.objectId !== input.bundle.documentId ||\n header.contentKeyEpoch !== input.bundle.contentKeyEpoch ||\n (input.requireOriginalTargets &&\n (header.accessManifestHash !== input.bundle.linkSetManifestHash ||\n header.targetHash !== input.bundle.targetHash))\n ) {\n throw new Error(\n input.requireOriginalTargets\n ? \"Document sync response content key is unavailable and its bundle differs from the original update headers\"\n : \"Document sync response content-key bundle does not match its update headers\",\n );\n }\n }\n}\n\n/**\n * Linking can rewrap a retained key at the same content epoch. Its latest bundle\n * then has newer targets than older signed updates. A usable key is validated\n * by the caller's authenticated record decryption; the update's own historical\n * manifest, targets and signature are verified independently before this step.\n *\n * If the key cannot be recovered, require the original target commitments before\n * calling that an availability failure. Substituted unavailable targets must\n * still be quarantined, never disguised as legitimate missing history.\n */\nasync function unwrapHistoricalContentKey(input: {\n bundle: DocumentSyncResponse[\"contentKeyBundle\"];\n documentId: string;\n collectedKeks: Awaited<\n ReturnType<typeof collectContainerKeksForDocumentSync>\n >;\n updates: readonly SyncResponseUpdate[];\n}): Promise<Uint8Array> {\n assertBundleMatchesUpdateHeaders({ ...input, requireOriginalTargets: false });\n try {\n return await unwrapDocumentContentKeyFromBundle(\n input.bundle,\n input.documentId,\n input.collectedKeks.keksByEpochId,\n input.collectedKeks.predecessorFailuresByEpochId,\n input.collectedKeks.unattributedPredecessorFailuresByContainerId,\n );\n } catch (error) {\n if (isRawHistoryUnavailableCause(error)) {\n assertBundleMatchesUpdateHeaders({\n ...input,\n requireOriginalTargets: true,\n });\n }\n throw error;\n }\n}\n\n/** @internal Keeps epoch-wide failures anonymous and integrity failures typed. */\nexport function throwDocumentSyncContentKeyFailure(input: {\n cause: unknown;\n updates: readonly SyncResponseUpdate[];\n}): never {\n if (isKeyingVerificationError(input.cause)) {\n throw input.cause;\n }\n if (\n input.cause instanceof DocumentHistoryUnavailableError &&\n isKeyingVerificationError(input.cause.historyCause)\n ) {\n throw input.cause.historyCause;\n }\n throw isolateDocumentSyncBatchError({\n cause: input.cause,\n stage: \"content_key\",\n updateIds: input.updates.map((update) => update.id),\n });\n}\n\nexport async function unwrapDocumentSyncResponseContentKeys(\n input: {\n currentContentKey: Uint8Array;\n currentContentKeyEpoch: number;\n execSql?: ExecSql | undefined;\n historyMode?: \"raw\" | undefined;\n /** @internal Validate every decryptable sibling before raw availability wins. */\n onRawHistoryUnavailable?: RawHistoryUnavailableValidator | undefined;\n response: DocumentSyncResponse;\n targetSecretKey: Uint8Array;\n writerProjection: DocumentWriterProjectionResponse;\n } & ProjectionVerificationOptions,\n): Promise<ReadonlyMap<number, Uint8Array>> {\n // A stale read-only pass can carry an empty placeholder when none of its\n // authorizing paths reaches the bundle target. Do not mark that epoch as\n // resolved: every served update must instead unwrap its bundle through the\n // verified predecessor KEK chain or fail with an honest error.\n const contentKeysByEpoch = new Map<number, Uint8Array>(\n input.currentContentKey.byteLength > 0\n ? [[input.currentContentKeyEpoch, input.currentContentKey]]\n : [],\n );\n const updatesByContentKeyEpoch = syncResponseUpdatesByContentKeyEpoch(\n input.response,\n );\n const missingContentKeyEpochs = [...updatesByContentKeyEpoch.keys()].filter(\n (contentKeyEpoch) => !contentKeysByEpoch.has(contentKeyEpoch),\n );\n missingContentKeyEpochs.sort((left, right) => left - right);\n if (missingContentKeyEpochs.length === 0) {\n return contentKeysByEpoch;\n }\n const missingUpdates = missingContentKeyEpochs.flatMap(\n (contentKeyEpoch) => updatesByContentKeyEpoch.get(contentKeyEpoch) ?? [],\n );\n let bundlesByEpoch: ReturnType<typeof syncResponseContentKeyBundlesByEpoch>;\n try {\n bundlesByEpoch = syncResponseContentKeyBundlesByEpoch(input.response);\n } catch (error) {\n throwDocumentSyncContentKeyFailure({\n cause: error,\n updates: missingUpdates,\n });\n }\n const absentBundleEpoch = missingContentKeyEpochs.find(\n (contentKeyEpoch) => !bundlesByEpoch.has(contentKeyEpoch),\n );\n if (absentBundleEpoch !== undefined) {\n throwDocumentSyncContentKeyFailure({\n cause: new Error(\"Document sync response content-key bundle missing\"),\n updates:\n updatesByContentKeyEpoch.get(absentBundleEpoch) ?? missingUpdates,\n });\n }\n const collectedKeks = await collectContainerKeksForDocumentSync({\n execSql: input.execSql,\n secretKey: input.targetSecretKey,\n writerProjection: input.writerProjection,\n ...projectionVerificationOptions(input),\n });\n let unavailableRawHistory:\n | { cause: RawHistoryUnavailableCause; contentKeyEpoch: number }\n | undefined;\n\n for (const contentKeyEpoch of missingContentKeyEpochs) {\n const bundle = bundlesByEpoch.get(contentKeyEpoch);\n const responseUpdates =\n updatesByContentKeyEpoch.get(contentKeyEpoch) ?? missingUpdates;\n if (!bundle) {\n const error = new Error(\n \"Document sync response content-key bundle missing\",\n );\n throwDocumentSyncContentKeyFailure({\n cause: error,\n updates: responseUpdates,\n });\n }\n try {\n contentKeysByEpoch.set(\n bundle.contentKeyEpoch,\n await unwrapHistoricalContentKey({\n bundle,\n collectedKeks,\n documentId: input.writerProjection.documentId,\n updates: responseUpdates,\n }),\n );\n } catch (error) {\n if (input.historyMode === \"raw\" && isRawHistoryUnavailableCause(error)) {\n unavailableRawHistory ??= { cause: error, contentKeyEpoch };\n continue;\n }\n throwDocumentSyncContentKeyFailure({\n cause: error,\n updates: responseUpdates,\n });\n }\n }\n\n if (unavailableRawHistory) {\n await throwRawHistoryUnavailable({\n contentKeysByEpoch,\n response: input.response,\n unavailable: unavailableRawHistory,\n validate: input.onRawHistoryUnavailable,\n });\n }\n\n return contentKeysByEpoch;\n}\n"]}
|
|
1
|
+
{"version":3,"file":"syncContentKeys.js","sourceRoot":"","sources":["syncContentKeys.ts"],"names":[],"mappings":"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","sourcesContent":["import type {\n DocumentSyncResponse,\n DocumentWriterProjectionResponse,\n} from \"@tearleads/validators/response\";\nimport { importContentKeyMaterial } from \"../../../data/documents/shared/contentRecordKeys\";\nimport { encryptDocumentPendingUpdate } from \"../../../data/documents/shared/crypto\";\nimport {\n ContainerKekHistoryUnavailableError,\n collectContainerKeksForDocumentSync,\n DocumentContentKeyUnavailableError,\n DocumentHistoryUnavailableError,\n unwrapDocumentContentKeyFromBundle,\n} from \"../../../data/documents/shared/projection\";\nimport { readWriteHeader } from \"../../../data/documents/shared/readers\";\nimport { assertDocumentSyncUpdateEncryptedRecord } from \"../../../data/documents/shared/sync/documentSyncUpdateDecryption\";\nimport {\n isDocumentSyncUpdateIsolationError,\n isolateDocumentSyncBatchError,\n isolateDocumentSyncUpdateError,\n} from \"../../../data/documents/shared/sync/documentSyncUpdateIsolation\";\nimport type {\n DocumentSyncPreparedUpdate,\n ProjectionVerificationOptions,\n} from \"../../../data/documents/shared/types\";\nimport { projectionVerificationOptions } from \"../../../data/documents/shared/types\";\nimport { isKeyingVerificationError } from \"../../../data/keyingProjectionVerification/error\";\nimport type { PendingUpdateRecord } from \"../../../data/sqlite/documentPersistence\";\nimport type { ExecSql } from \"../../../data/sqlite/sqlSchema\";\n\ntype SyncResponseUpdate = DocumentSyncResponse[\"updates\"][number];\ntype RawHistoryUnavailableCause =\n | DocumentContentKeyUnavailableError\n | DocumentHistoryUnavailableError;\n\nfunction isRawHistoryUnavailableCause(\n error: unknown,\n): error is RawHistoryUnavailableCause {\n return (\n error instanceof DocumentContentKeyUnavailableError ||\n (error instanceof DocumentHistoryUnavailableError &&\n error.historyCause instanceof ContainerKekHistoryUnavailableError)\n );\n}\n\ntype RawHistoryUnavailableValidator = (input: {\n contentKeysByEpoch: ReadonlyMap<number, Uint8Array>;\n updates: readonly SyncResponseUpdate[];\n}) => void | Promise<void>;\n\n/** A raw recovery cannot reconstruct history without this retained epoch. */\nexport class DocumentRawHistoryUnavailableError extends Error {\n readonly code = \"document_raw_history_epoch_unavailable\";\n\n constructor(\n readonly contentKeyEpoch: number,\n cause: unknown,\n ) {\n super(\n `Document raw-history recovery cannot decrypt content-key epoch ${contentKeyEpoch}`,\n { cause },\n );\n this.name = \"DocumentRawHistoryUnavailableError\";\n }\n}\n\nasync function assertResponseEncryptedRecords(\n updates: readonly SyncResponseUpdate[],\n): Promise<void> {\n const inspections = await Promise.allSettled(\n updates.map(assertDocumentSyncUpdateEncryptedRecord),\n );\n const failures = inspections.flatMap((inspection, index) =>\n inspection.status === \"rejected\"\n ? [{ index, reason: inspection.reason }]\n : [],\n );\n const firstFailure = failures[0];\n if (failures.length === 1 && firstFailure) {\n throw firstFailure.reason;\n }\n if (failures.length > 1 && firstFailure) {\n const stage =\n isDocumentSyncUpdateIsolationError(firstFailure.reason) &&\n failures.every(\n ({ reason }) =>\n isDocumentSyncUpdateIsolationError(reason) &&\n reason.stage === firstFailure.reason.stage,\n )\n ? firstFailure.reason.stage\n : \"encrypted_record\";\n throw isolateDocumentSyncBatchError({\n cause: new Error(\"Multiple document encrypted records are invalid\"),\n stage,\n updateIds: failures.map(({ index }) => updates[index]?.id ?? \"unknown\"),\n });\n }\n}\n\nasync function throwRawHistoryUnavailable(input: {\n contentKeysByEpoch: ReadonlyMap<number, Uint8Array>;\n response: DocumentSyncResponse;\n unavailable: { cause: RawHistoryUnavailableCause; contentKeyEpoch: number };\n validate?: RawHistoryUnavailableValidator | undefined;\n}): Promise<never> {\n await assertResponseEncryptedRecords(input.response.updates);\n await input.validate?.({\n contentKeysByEpoch: input.contentKeysByEpoch,\n updates: input.response.updates.filter((update) =>\n input.contentKeysByEpoch.has(\n readWriteHeader(\n update.writeHeader,\n \"Document sync response write header\",\n ).contentKeyEpoch,\n ),\n ),\n });\n throw new DocumentRawHistoryUnavailableError(\n input.unavailable.contentKeyEpoch,\n input.unavailable.cause,\n );\n}\n\nexport async function prepareDocumentOutgoingUpdates(input: {\n contentKey: Uint8Array;\n contentKeyEpoch: number;\n documentId: string;\n organizationId: string;\n pendingUpdates: readonly PendingUpdateRecord[];\n}): Promise<DocumentSyncPreparedUpdate[]> {\n if (input.pendingUpdates.length === 0) {\n return [];\n }\n const contentKeyMaterial = await importContentKeyMaterial(input.contentKey);\n\n return Promise.all(\n input.pendingUpdates.map(async (update) => {\n const encrypted = await encryptDocumentPendingUpdate({\n contentKeyMaterial,\n contentKeyEpoch: input.contentKeyEpoch,\n documentId: input.documentId,\n organizationId: input.organizationId,\n update,\n });\n\n return {\n contentRecordId: encrypted.contentRecordId,\n encryptedData: encrypted.encryptedData,\n id: update.id,\n partialStartVersionVector: update.partialStartVersionVector,\n partialEndVersionVector: update.partialEndVersionVector,\n metadataHash: encrypted.metadataHash,\n ciphertextHash: encrypted.ciphertextHash,\n plaintextHash: encrypted.plaintextHash,\n ...(update.sourceVersionVector\n ? {\n checkpointKind: \"rotate_baseline\" as const,\n checkpointPayloadKind: \"full_history_snapshot\" as const,\n sourceVersionVector: update.sourceVersionVector,\n }\n : {}),\n };\n }),\n );\n}\n\nfunction syncResponseContentKeyBundlesByEpoch(\n response: DocumentSyncResponse,\n): ReadonlyMap<number, DocumentSyncResponse[\"contentKeyBundle\"]> {\n const byEpoch = new Map<number, DocumentSyncResponse[\"contentKeyBundle\"]>();\n\n for (const bundle of [\n response.contentKeyBundle,\n ...response.contentKeyBundles,\n ]) {\n if (byEpoch.has(bundle.contentKeyEpoch)) {\n throw new Error(\"Document sync response repeats a content-key epoch\");\n }\n byEpoch.set(bundle.contentKeyEpoch, bundle);\n }\n\n return byEpoch;\n}\n\nfunction syncResponseUpdatesByContentKeyEpoch(\n response: DocumentSyncResponse,\n): ReadonlyMap<number, readonly SyncResponseUpdate[]> {\n const updatesByEpoch = new Map<number, SyncResponseUpdate[]>();\n for (const update of response.updates) {\n let contentKeyEpoch: number;\n try {\n contentKeyEpoch = readWriteHeader(\n update.writeHeader,\n \"Document sync response write header\",\n ).contentKeyEpoch;\n } catch (error) {\n throw isolateDocumentSyncUpdateError({\n cause: error,\n responseUpdate: update,\n stage: \"write_header\",\n updateId: update.id,\n });\n }\n const epochUpdates = updatesByEpoch.get(contentKeyEpoch);\n if (epochUpdates) epochUpdates.push(update);\n else updatesByEpoch.set(contentKeyEpoch, [update]);\n }\n return updatesByEpoch;\n}\n\nfunction assertBundleMatchesUpdateHeaders(input: {\n bundle: DocumentSyncResponse[\"contentKeyBundle\"];\n requireOriginalTargets: boolean;\n updates: readonly SyncResponseUpdate[];\n}): void {\n for (const update of input.updates) {\n const header = readWriteHeader(\n update.writeHeader,\n \"Document sync response write header\",\n );\n if (\n header.objectId !== input.bundle.documentId ||\n header.contentKeyEpoch !== input.bundle.contentKeyEpoch ||\n (input.requireOriginalTargets &&\n (header.accessManifestHash !== input.bundle.linkSetManifestHash ||\n header.targetHash !== input.bundle.targetHash))\n ) {\n throw new Error(\n input.requireOriginalTargets\n ? \"Document sync response content key is unavailable and its bundle differs from the original update headers\"\n : \"Document sync response content-key bundle does not match its update headers\",\n );\n }\n }\n}\n\n/**\n * Linking can rewrap a retained key at the same content epoch. Its latest bundle\n * then has newer targets than older signed updates. A usable key is validated\n * by the caller's authenticated record decryption; the update's own historical\n * manifest, targets and signature are verified independently before this step.\n *\n * If the key cannot be recovered, require the original target commitments before\n * calling that an availability failure. Substituted unavailable targets must\n * still be quarantined, never disguised as legitimate missing history.\n */\nasync function unwrapHistoricalContentKey(input: {\n bundle: DocumentSyncResponse[\"contentKeyBundle\"];\n documentId: string;\n collectedKeks: Awaited<\n ReturnType<typeof collectContainerKeksForDocumentSync>\n >;\n updates: readonly SyncResponseUpdate[];\n}): Promise<Uint8Array> {\n assertBundleMatchesUpdateHeaders({ ...input, requireOriginalTargets: false });\n try {\n return await unwrapDocumentContentKeyFromBundle(\n input.bundle,\n input.documentId,\n input.collectedKeks.keksByEpochId,\n input.collectedKeks.predecessorFailuresByEpochId,\n input.collectedKeks.unattributedPredecessorFailuresByContainerId,\n );\n } catch (error) {\n if (isRawHistoryUnavailableCause(error)) {\n assertBundleMatchesUpdateHeaders({\n ...input,\n requireOriginalTargets: true,\n });\n }\n throw error;\n }\n}\n\n/** @internal Keeps epoch-wide failures anonymous and integrity failures typed. */\nexport function throwDocumentSyncContentKeyFailure(input: {\n cause: unknown;\n updates: readonly SyncResponseUpdate[];\n}): never {\n if (isKeyingVerificationError(input.cause)) {\n throw input.cause;\n }\n if (\n input.cause instanceof DocumentHistoryUnavailableError &&\n isKeyingVerificationError(input.cause.historyCause)\n ) {\n throw input.cause.historyCause;\n }\n throw isolateDocumentSyncBatchError({\n cause: input.cause,\n stage: \"content_key\",\n updateIds: input.updates.map((update) => update.id),\n });\n}\n\nexport async function unwrapDocumentSyncResponseContentKeys(\n input: {\n currentContentKey: Uint8Array;\n currentContentKeyEpoch: number;\n execSql?: ExecSql | undefined;\n historyMode?: \"raw\" | undefined;\n /** @internal Validate every decryptable sibling before raw availability wins. */\n onRawHistoryUnavailable?: RawHistoryUnavailableValidator | undefined;\n response: DocumentSyncResponse;\n targetSecretKey: Uint8Array;\n writerProjection: DocumentWriterProjectionResponse;\n } & ProjectionVerificationOptions,\n): Promise<ReadonlyMap<number, Uint8Array>> {\n // A stale read-only pass can carry an empty placeholder when none of its\n // authorizing paths reaches the bundle target. Do not mark that epoch as\n // resolved: every served update must instead unwrap its bundle through the\n // verified predecessor KEK chain or fail with an honest error.\n const contentKeysByEpoch = new Map<number, Uint8Array>(\n input.currentContentKey.byteLength > 0\n ? [[input.currentContentKeyEpoch, input.currentContentKey]]\n : [],\n );\n const updatesByContentKeyEpoch = syncResponseUpdatesByContentKeyEpoch(\n input.response,\n );\n const missingContentKeyEpochs = [...updatesByContentKeyEpoch.keys()].filter(\n (contentKeyEpoch) => !contentKeysByEpoch.has(contentKeyEpoch),\n );\n missingContentKeyEpochs.sort((left, right) => left - right);\n if (missingContentKeyEpochs.length === 0) {\n return contentKeysByEpoch;\n }\n const missingUpdates = missingContentKeyEpochs.flatMap(\n (contentKeyEpoch) => updatesByContentKeyEpoch.get(contentKeyEpoch) ?? [],\n );\n let bundlesByEpoch: ReturnType<typeof syncResponseContentKeyBundlesByEpoch>;\n try {\n bundlesByEpoch = syncResponseContentKeyBundlesByEpoch(input.response);\n } catch (error) {\n throwDocumentSyncContentKeyFailure({\n cause: error,\n updates: missingUpdates,\n });\n }\n const absentBundleEpoch = missingContentKeyEpochs.find(\n (contentKeyEpoch) => !bundlesByEpoch.has(contentKeyEpoch),\n );\n if (absentBundleEpoch !== undefined) {\n throwDocumentSyncContentKeyFailure({\n cause: new Error(\"Document sync response content-key bundle missing\"),\n updates:\n updatesByContentKeyEpoch.get(absentBundleEpoch) ?? missingUpdates,\n });\n }\n const collectedKeks = await collectContainerKeksForDocumentSync({\n execSql: input.execSql,\n secretKey: input.targetSecretKey,\n writerProjection: input.writerProjection,\n ...projectionVerificationOptions(input),\n });\n let unavailableRawHistory:\n | { cause: RawHistoryUnavailableCause; contentKeyEpoch: number }\n | undefined;\n\n for (const contentKeyEpoch of missingContentKeyEpochs) {\n const bundle = bundlesByEpoch.get(contentKeyEpoch);\n const responseUpdates =\n updatesByContentKeyEpoch.get(contentKeyEpoch) ?? missingUpdates;\n if (!bundle) {\n const error = new Error(\n \"Document sync response content-key bundle missing\",\n );\n throwDocumentSyncContentKeyFailure({\n cause: error,\n updates: responseUpdates,\n });\n }\n try {\n contentKeysByEpoch.set(\n bundle.contentKeyEpoch,\n await unwrapHistoricalContentKey({\n bundle,\n collectedKeks,\n documentId: input.writerProjection.documentId,\n updates: responseUpdates,\n }),\n );\n } catch (error) {\n if (input.historyMode === \"raw\" && isRawHistoryUnavailableCause(error)) {\n unavailableRawHistory ??= { cause: error, contentKeyEpoch };\n continue;\n }\n throwDocumentSyncContentKeyFailure({\n cause: error,\n updates: responseUpdates,\n });\n }\n }\n\n if (unavailableRawHistory) {\n await throwRawHistoryUnavailable({\n contentKeysByEpoch,\n response: input.response,\n unavailable: unavailableRawHistory,\n validate: input.onRawHistoryUnavailable,\n });\n }\n\n return contentKeysByEpoch;\n}\n"]}
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { emptyVersionVector, getImportBlobMetadata, satisfiesVersionVector, versionVectorsEqual, } from "../../../internal/loro/index.js";
|
|
2
2
|
import { documentKekTargetsFromContentKeyBundle } from "../../../internal/validators/response/index.js";
|
|
3
3
|
import { createPendingUpdateFields } from "../../../data/documents/documentSync.js";
|
|
4
|
-
import { assertDocumentKekPathsCurrent } from "../../../data/documents/shared/containerKekCurrency.js";
|
|
5
|
-
import { assertDocumentWriterProjectionConsistent, authorizingContainerPathRefs, buildRotatedDocumentContentKeyBundle, ContainerKekHistoryUnavailableError, collectContainerKeksForDocumentSync, DocumentHistoryUnavailableError, unwrapDocumentContentKeyFromBundle, } from "../../../data/documents/shared/projection.js";
|
|
4
|
+
import { assertDocumentKekPathsCurrent } from "../../../data/documents/shared/containerKek/containerKekCurrency.js";
|
|
5
|
+
import { assertDocumentWriterProjectionConsistent, authorizingContainerPathRefs, buildRotatedDocumentContentKeyBundle, ContainerKekHistoryUnavailableError, collectContainerKeksForDocumentSync, DocumentHistoryUnavailableError, unwrapDocumentContentKeyFromBundle, } from "../../../data/documents/shared/projection/index.js";
|
|
6
6
|
import { assertDocumentManifestBundleConsistent } from "../../../data/documents/shared/readers.js";
|
|
7
7
|
import { projectionVerificationOptions } from "../../../data/documents/shared/types.js";
|
|
8
8
|
import { selectDocumentSyncOutgoingBatch } from "../../../data/sync/documentSyncOutgoingBatch.js";
|