From f4f1e1a5820390113cdbfbe5c3d281853c332a8a Mon Sep 17 00:00:00 2001 From: Ruben Bartelink Date: Wed, 21 Oct 2020 08:51:19 +0100 Subject: [PATCH] Final Stored Proc diff reduction vs 3.0 as v2 --- src/Equinox.CosmosStore/CosmosStore.fs | 14 ++------------ 1 file changed, 2 insertions(+), 12 deletions(-) diff --git a/src/Equinox.CosmosStore/CosmosStore.fs b/src/Equinox.CosmosStore/CosmosStore.fs index 44e310db0..3651ba26f 100644 --- a/src/Equinox.CosmosStore/CosmosStore.fs +++ b/src/Equinox.CosmosStore/CosmosStore.fs @@ -392,20 +392,16 @@ module private MicrosoftAzureCosmosWrappers = type SyncResponse = { etag: string; n: int64; conflicts: Unfold[] } module internal SyncStoredProc = - let [] name = "EquinoxRollingUnfolds5" // NB need to rename/number for any breaking change - let [] body = """ + let [] private name = "EquinoxRollingUnfolds5" // NB need to rename/number for any breaking change + let [] private body = """ // Manages the merging of the supplied Request Batch into the stream // 0 perform concurrency check (index=-1 -> always append; index=-2 -> check based on .etag; _ -> check .n=.index) - // High level end-states: - // 1a if there is a Tip, but are only changes to the `u`nfolds (and no `e`vents) -> update Tip only // 1b if there is a Tip, but incoming request includes an event -> generate a batch document + create empty Tip - // 2a if stream empty, but incoming request includes an event -> generate a batch document + create empty Tip // 2b if no current Tip, and no events being written -> the incoming `req` becomes the Tip batch - function sync(req, expIndex, expEtag) { if (!req) throw new Error("Missing req argument"); const collectionLink = __.getSelfLink(); @@ -423,7 +419,6 @@ function sync(req, expIndex, expEtag) { } else if (current && ((expIndex === -2 && expEtag !== current._etag) || (expIndex !== -2 && expIndex !== current.n))) { // Where possible, we extract conflicting events from e and/or u in order to avoid another read cycle; // yielding [] triggers the client to go loading the events itself - // if we're working based on etags, the `u`nfolds likely bear relevant info as state-bearing unfolds response.setBody({ etag: current._etag, n: current.n, conflicts: current.u || [] }); } else { @@ -431,7 +426,6 @@ function sync(req, expIndex, expEtag) { } }); if (!isAccepted) throw new Error("readDocument not Accepted"); - function executeUpsert(tip) { function callback(err, doc) { if (err) throw err; @@ -448,13 +442,10 @@ function sync(req, expIndex, expEtag) { const batch = { id: tip.i.toString(), p: tip.p, i: tip.i, n: tip.n, e: tip.e } const batchAccepted = __.createDocument(collectionLink, batch, { disableAutomaticIdGeneration: true }); if (!batchAccepted) throw new Error("Unable to remove Tip markings."); - tip.i = tip.n; tip.e = []; } - // TODO Carry forward `u` items not present in `batch`, together with supporting catchup events from preceding batches - // Replace all the unfolds // TODO: should remove only unfolds being superseded tip.u = req.u; // As we've mutated the document in a manner that can conflict with other writers, our write needs to be contingent on no competing updates having taken place @@ -466,7 +457,6 @@ function sync(req, expIndex, expEtag) { const batch = { id: "0", p: req.p, i: 0, n: req.e.length, e: req.e }; const batchAccepted = __.createDocument(collectionLink, batch, { disableAutomaticIdGeneration: true }); if (!batchAccepted) throw new Error("Unable to create Batch 0."); - req.i = batch.n; req.e = []; } else {