@procedures/mongo 0.54.0 → 0.54.1

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/CHANGELOG.md CHANGED
@@ -1,5 +1,23 @@
1
1
  # @procedures/mongo
2
2
 
3
+ ## 0.54.1
4
+
5
+ ### Patch Changes
6
+
7
+ - 3914b5f: `MongoDocumentStorage` has the new option `sequence` (CLI-96). The default `collection` keeps one counter of the numbers for the collection. With `partition`, each partition has its own counter and its own write queue, so the writes of two partitions share no document.
8
+
9
+ - The gain is for the other partitions. One tenant wrote a burst in the CI tests of CLI-96. The p99 of the writes of the other tenants went from 316 to 758 ms to 12 to 51 ms.
10
+ - The rate of one partition does not change: approximately 400 writes a second. The stated limit of a partition is 200 writes a second.
11
+ - A live collection gains nothing. A store with the option refuses a collection with numbers on its counter of the collection, with a clear error. Use the option for a new collection. The move of a live collection is a step with all processes stopped.
12
+ - A store with the default refuses a collection whose stores have the option. Give the same `sequence` to each store of a collection, and to the storage of a view target.
13
+ - A first load of many tenants does not hold each schedule on each CPU model of the runners. The tail of the other tenants is the claim. A host that wants a warm pool for a first load sets `minPoolSize` of its client.
14
+ - The new option `writesInFlight` bounds the writes of each client at one time, over the stores with the same value. The default is 8. Before it, each partition of a process kept a transaction open at once, and the server queue reached 152 tickets with 20,000 partitions.
15
+ - The bound covers each store of a client, also with the default `sequence`. A client that writes more than 8 collections at once gets a queue for the permits. Set `writesInFlight: Infinity` to keep no bound.
16
+ - A watcher notes the writes of this process that it skips with their partition, because two partitions can have the same number.
17
+ - Updated dependencies [13c3a8b]
18
+ - @procedures/client@0.54.1
19
+ - @procedures/collections@0.54.1
20
+
3
21
  ## 0.54.0
4
22
 
5
23
  ### Patch Changes
package/README.md CHANGED
@@ -666,6 +666,7 @@ server.usePartitions("notes", { storageOf: (partition) => notes.forPartition(par
666
666
  | `maxTombstones` | The most deletes that the change log keeps in each partition (default 10000) |
667
667
  | `queryPolicy` | The query policy of `query()` without a policy of the call |
668
668
  | `counters` | The collection of the sequence counters (default `__storage_counters`) |
669
+ | `sequence` | `collection` (the default): one counter of the numbers for the collection. `partition`: one counter and one write queue for each partition (roadmap CLI-96). The next section tells when to use it. |
669
670
  | `writeLease` | The time after which a pending number of a write that stopped no longer holds the readers (default `seconds(60)`). A plain number is a `TypeError`. |
670
671
  | `client` | The client of the database, for the transactions. The default is the client of the default connection when `db` is absent. With `db` and no `client`, a write is not a transaction, also on a replica set: it uses the watermark. |
671
672
  | `transactions` | `auto` (the default): a transaction for each write on a replica set or a sharded cluster. `never`: the watermark only. |
@@ -677,6 +678,11 @@ server.usePartitions("notes", { storageOf: (partition) => notes.forPartition(par
677
678
  - **The change log.** Each write gets the next number of the sequence of the collection, and a delete leaves a tombstone. `getChangesSince()` thus gives the exact changes and deletes. A version of another epoch, or a version before the oldest dropped tombstone, gives a full result.
678
679
  - **The versions.** `versionOf(id)` gives the number of the last write of an item.
679
680
  - **The queries.** `query()` sends the equality of a string, a number or a boolean, and `$in` of them, to MongoDB as a filter. `queryEntries()` of the core then gives the exact result, so a query gives the result of the reference.
681
+ - **A counter for each partition.** With `sequence: "partition"`, the writes of two partitions share no document, so they do not wait for each other. The numbers of two partitions can be equal. A store reads only its partition, so the numbers stay in order in each partition.
682
+ - Give the same `sequence` to each store of a collection, and to the storage of a view target. A store refuses a collection that has the other sequence, with a clear error.
683
+ - Use the option only for a new collection. A store with the option refuses a collection with numbers on its counter of the collection. Thus a live collection gains nothing. Its move is a step with all processes stopped.
684
+ - One partition keeps the limit of one collection with the default: approximately 400 writes a second. The stated limit of a partition is 200 writes a second.
685
+ - The gain is for the other partitions. One tenant wrote a burst in the CI tests of CLI-96. The p99 of the writes of the other tenants went from 316 to 758 ms to 12 to 51 ms.
680
686
  - **Several writers.** On a replica set, a write takes its numbers and writes in one transaction. On a single server, a watermark keeps the log exact. Each write keeps its numbers pending until it ends, and a version stops below the lowest pending number. A write that ends after its lease moves its documents to new numbers.
681
687
  - **The cases that stay on a single server.** A process that stops between a late write and the move of its documents leaves that change below the watermark. A reader that passed those numbers does not get the change. And a precondition (`expectedVersion`) of a document without `_seq` has the guard `{ _seq: { $exists: false } }`: a writer outside the storage between the test and the write is not seen. On a replica set, the test and the write are one transaction, and these cases do not occur.
682
688
  - **The partitions.** An id cannot have the character U+001F, and each write filter has the partition. A write cannot change a document of another partition.
@@ -166,6 +166,26 @@ export interface MongoDocumentStorageOptions<T = unknown> {
166
166
  queryPolicy?: StorageQueryPolicy | undefined;
167
167
  /** The collection of the sequence counters (default `__storage_counters`). */
168
168
  counters?: string | undefined;
169
+ /**
170
+ * The sequence of the numbers of the writes (roadmap CLI-96). `collection` (the default): one counter for the collection.
171
+ * `partition`: one counter and one write queue for each partition, so the writes of two partitions share no document.
172
+ *
173
+ * - Give the same value to each store of a collection. A store refuses a collection that has the other sequence, with a clear error.
174
+ * - A store with `partition` refuses a collection with numbers on its counter of the collection. Use it for a new collection.
175
+ * - One partition keeps the limit of one collection with the default: approximately 400 writes a second, and a stated limit of 200.
176
+ */
177
+ sequence?: "collection" | "partition" | undefined;
178
+ /**
179
+ * The most writes of each client at one time, over the stores with the same value (roadmap CLI-96). The default is 8.
180
+ * A write waits for a permit after its turn in the write queue of its counter.
181
+ *
182
+ * - With `sequence: "partition"`, each partition has its own queue. Without this bound, each partition of a process has a transaction open at once.
183
+ * - A whole number of 1 or more, or `Infinity` for no bound. Another value is a `RangeError`.
184
+ * - The sweeps of 2, 4, 8, 16 and `Infinity` at the bench cases `400-p2` and `4000-p2` set the default of 8.
185
+ * - With `sequence: "partition"`, `Infinity` costs approximately 30 % of the writes a second. The bench run 42428048767
186
+ * gives 638.5 against 916.5 of the default sequence at `4000-p2`. The store emits a process warning one time for it.
187
+ */
188
+ writesInFlight?: number | undefined;
169
189
  /**
170
190
  * The time after which a pending number of a write no longer holds the watermark (default 60 s):
171
191
  * a writer that stopped does not stop the change reads. A plain number is a `TypeError`.
@@ -196,6 +216,10 @@ export interface MongoDocumentStorageOptions<T = unknown> {
196
216
  */
197
217
  form?: StoredForm | undefined;
198
218
  }
219
+ /** The default of the option `writesInFlight`: the most writes of each client at one time (roadmap CLI-96). */
220
+ export declare const DEFAULT_WRITES_IN_FLIGHT = 8;
221
+ /** The code of the process warning for a store with `sequence: "partition"` and no bound on its writes. */
222
+ export declare const UNBOUNDED_PARTITION_WARNING = "PROCEDURES_MONGO_UNBOUNDED_PARTITION";
199
223
  /** The options of `decodeStoredDocument`. */
200
224
  export interface DecodeStoredDocumentOptions {
201
225
  /** The stored form of the storage, for example `storage.form` (default `DEFAULT_STORED_FORM`). */
@@ -363,6 +387,8 @@ export interface StorageWriteTarget {
363
387
  withPendingNumbers<R>(db: Db, count: number, write: (first: number) => Promise<R>): Promise<R>;
364
388
  /** This method writes the floor document of the partition once (roadmap O66). */
365
389
  noteFloor(db: Db): Promise<void>;
390
+ /** The sequence of the numbers: one counter for the collection, or one for each partition (roadmap CLI-96). */
391
+ readonly sequence: "collection" | "partition";
366
392
  /** This method drops the oldest tombstones over the limit, and raises the floor of the change log. */
367
393
  prune(db: Db): Promise<void>;
368
394
  }
@@ -400,6 +426,8 @@ export declare class MongoDocumentStorage<T> implements CollectionStorage<T> {
400
426
  private readonly maxTombstones;
401
427
  private readonly countersName;
402
428
  private readonly writeLeaseMs;
429
+ /** The most writes of each client at one time, over the stores with this value. `Infinity` is no bound. */
430
+ private readonly writesInFlight;
403
431
  /** The storages of the partitions, for `forPartition`: the same storage for the same partition. */
404
432
  private readonly partitions;
405
433
  /** The stored form of the documents (roadmap CLI-76). A `ViewMaterializer` of the collection takes the same form. */
@@ -413,6 +441,12 @@ export declare class MongoDocumentStorage<T> implements CollectionStorage<T> {
413
441
  private indexes;
414
442
  /** True after this storage wrote (or found) the floor document of its partition (roadmap O66). A failed write leaves it false. */
415
443
  private floorNoted;
444
+ /** The sequence of the numbers (roadmap CLI-96). */
445
+ private readonly sequence;
446
+ /** The `_id` of the counter of the numbers: the collection, or the partition with the option `sequence: "partition"`. */
447
+ private readonly counterId;
448
+ /** The partition of the notes of the own numbers with a counter for each partition, else `undefined` (roadmap CLI-96). */
449
+ private readonly ownScope;
416
450
  private closed;
417
451
  constructor(options: MongoDocumentStorageOptions<T>, partitions?: Map<string, MongoDocumentStorage<T>>);
418
452
  /** The storage of a partition of the same collection. It gives the same storage for the same partition. */
@@ -480,9 +514,16 @@ export declare class MongoDocumentStorage<T> implements CollectionStorage<T> {
480
514
  /**
481
515
  * The watermark of the collection: the highest number below each pending number of a write whose
482
516
  * lease has not ended, the epoch, and the floor of the partition. Each number up to it is written
483
- * or abandoned. One command reads them. Only the first read of a collection writes: it makes the counter.
517
+ * or abandoned. One command reads them. Only the first read of a store writes: it makes the counter. With the
518
+ * option `sequence: "partition"`, the first read of each process also marks the counter of the collection.
484
519
  */
485
520
  private watermark;
521
+ /**
522
+ * This method checks once for each collection that a store with the option `sequence: "partition"` can use it (roadmap
523
+ * CLI-96). One atomic step marks the counter of the collection, unless that counter has numbers. A store with the default
524
+ * reads the mark in its own steps on that counter, so it needs no check of its own.
525
+ */
526
+ private checkSequence;
486
527
  /** The id of the document of the oldest kept change of the partition. */
487
528
  private floorOf;
488
529
  private floorId;
@@ -1 +1 @@
1
- {"version":3,"file":"document-storage.d.ts","sourceRoot":"","sources":["../../src/storage/document-storage.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"document-storage.d.ts","sourceRoot":"","sources":["../../src/storage/document-storage.ts"],"names":[],"mappings":"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"}
@@ -170,6 +170,18 @@ function duplicateIndex(error) {
170
170
  const stopped = [writeErrors].flat().find((entry) => entry?.code === 11000);
171
171
  return typeof stopped?.index === "number" ? stopped.index : undefined;
172
172
  }
173
+ /**
174
+ * The checks of the sequence of each collection (roadmap CLI-96): by the client, then by the names of the database, the
175
+ * counters and the collection. A check that fails leaves no entry, so the next call tries again.
176
+ */
177
+ const SEQUENCE_CHECKS = new WeakMap();
178
+ /** The error of a store whose sequence is not the sequence of its collection (roadmap CLI-96). */
179
+ function sequenceMismatch(collection, sequence) {
180
+ return sequence === "partition"
181
+ ? new Error(`The collection ${collection} has numbers on its counter of the collection, so the option sequence "partition" refuses it. ` +
182
+ "The option is for a collection with no writes. The move of a live collection is a step with all processes stopped.")
183
+ : new Error(`The collection ${collection} has a counter for each partition. Give the option sequence "partition" to each store of it.`);
184
+ }
173
185
  /** True when a client is on a replica set or a sharded cluster: it has transactions. */
174
186
  const TRANSACTIONAL = new WeakMap();
175
187
  function hasTransactions(db) {
@@ -198,6 +210,31 @@ const MOST_FULL_TRIES = 3;
198
210
  const QUEUES = new WeakMap();
199
211
  /** The change reads of each client at one time. A burst of reads leaves the pool to the other operations. */
200
212
  const READS = new WeakMap();
213
+ /** The default of the option `writesInFlight`: the most writes of each client at one time (roadmap CLI-96). */
214
+ export const DEFAULT_WRITES_IN_FLIGHT = 8;
215
+ /** The code of the process warning for a store with `sequence: "partition"` and no bound on its writes. */
216
+ export const UNBOUNDED_PARTITION_WARNING = "PROCEDURES_MONGO_UNBOUNDED_PARTITION";
217
+ let warnedUnboundedPartition = false;
218
+ /** This function emits the process warning of an unbounded store with a counter for each partition, one time. */
219
+ function warnUnboundedPartition() {
220
+ if (warnedUnboundedPartition)
221
+ return;
222
+ warnedUnboundedPartition = true;
223
+ process.emitWarning('writesInFlight: Infinity with sequence: "partition" costs approximately 30 % of the writes a second. Use the default bound of 8.', { code: UNBOUNDED_PARTITION_WARNING });
224
+ }
225
+ /** The permits of the writes of each client, by the value of `writesInFlight`: the stores with one value share the permits. */
226
+ const WRITES = new WeakMap();
227
+ /** This function gives the permits of the writes of a client for a bound. */
228
+ function writePermitsOf(db, bound) {
229
+ const owner = ownerOf(db);
230
+ let byBound = WRITES.get(owner);
231
+ if (!byBound)
232
+ WRITES.set(owner, (byBound = new Map()));
233
+ let permits = byBound.get(bound);
234
+ if (!permits)
235
+ byBound.set(bound, (permits = semaphore(bound)));
236
+ return permits;
237
+ }
201
238
  /** This function starts a write after each earlier write of the collection. */
202
239
  function enqueueWrite(db, name, task) {
203
240
  const owner = ownerOf(db);
@@ -500,6 +537,8 @@ export class MongoDocumentStorage {
500
537
  maxTombstones;
501
538
  countersName;
502
539
  writeLeaseMs;
540
+ /** The most writes of each client at one time, over the stores with this value. `Infinity` is no bound. */
541
+ writesInFlight;
503
542
  /** The storages of the partitions, for `forPartition`: the same storage for the same partition. */
504
543
  partitions;
505
544
  /** The stored form of the documents (roadmap CLI-76). A `ViewMaterializer` of the collection takes the same form. */
@@ -513,6 +552,12 @@ export class MongoDocumentStorage {
513
552
  indexes;
514
553
  /** True after this storage wrote (or found) the floor document of its partition (roadmap O66). A failed write leaves it false. */
515
554
  floorNoted = false;
555
+ /** The sequence of the numbers (roadmap CLI-96). */
556
+ sequence;
557
+ /** The `_id` of the counter of the numbers: the collection, or the partition with the option `sequence: "partition"`. */
558
+ counterId;
559
+ /** The partition of the notes of the own numbers with a counter for each partition, else `undefined` (roadmap CLI-96). */
560
+ ownScope;
516
561
  closed = false;
517
562
  static {
518
563
  sourceOfStorage = (storage) => ({
@@ -530,6 +575,7 @@ export class MongoDocumentStorage {
530
575
  writeTargetOfStorage = (storage) => ({
531
576
  collection: storage.collectionName,
532
577
  counters: storage.countersName,
578
+ sequence: storage.sequence,
533
579
  form: storage.form,
534
580
  partition: storage.partition,
535
581
  writeLeaseMs: storage.writeLeaseMs,
@@ -576,9 +622,21 @@ export class MongoDocumentStorage {
576
622
  if (!Number.isSafeInteger(this.maxTombstones) || this.maxTombstones < 0)
577
623
  throw new Error("maxTombstones must be a whole number of 0 or more");
578
624
  this.countersName = options.counters ?? "__storage_counters";
625
+ const sequence = options.sequence ?? "collection";
626
+ if (sequence !== "collection" && sequence !== "partition")
627
+ throw new TypeError(`sequence must be "collection" or "partition", not ${JSON.stringify(sequence)}`);
628
+ this.sequence = sequence;
629
+ this.counterId = sequence === "partition" ? `seq${SEPARATOR}${this.collectionName}${SEPARATOR}${this.partition ?? ""}` : this.collectionName;
630
+ this.ownScope = sequence === "partition" ? (this.partition ?? "") : undefined;
579
631
  this.writeLeaseMs = Math.round(optionalMs(options.writeLease, "writeLease") ?? 60_000);
580
632
  if (!Number.isSafeInteger(this.writeLeaseMs) || this.writeLeaseMs < 1)
581
633
  throw new Error("writeLease must be 1 ms or more");
634
+ this.writesInFlight = options.writesInFlight ?? DEFAULT_WRITES_IN_FLIGHT;
635
+ if (!(this.writesInFlight === Infinity || (Number.isSafeInteger(this.writesInFlight) && this.writesInFlight >= 1))) {
636
+ throw new RangeError(`writesInFlight must be a whole number of 1 or more, or Infinity, not ${String(options.writesInFlight)}`);
637
+ }
638
+ if (this.writesInFlight === Infinity && this.sequence === "partition")
639
+ warnUnboundedPartition();
582
640
  this.partitions = partitions ?? new Map();
583
641
  }
584
642
  /** The storage of a partition of the same collection. It gives the same storage for the same partition. */
@@ -728,7 +786,7 @@ export class MongoDocumentStorage {
728
786
  * document until `release()`, so the watermark of the readers stays below them.
729
787
  */
730
788
  async allocate(db, count) {
731
- const counter = (await db.collection(this.countersName).findOneAndUpdate({ _id: this.collectionName }, [
789
+ const counter = (await db.collection(this.countersName).findOneAndUpdate({ _id: this.counterId }, [
732
790
  { $set: { seq: { $add: [{ $ifNull: ["$seq", 0] }, count] }, epoch: { $ifNull: ["$epoch", randomUUID()] } } },
733
791
  {
734
792
  $set: {
@@ -740,7 +798,12 @@ export class MongoDocumentStorage {
740
798
  ], { upsert: true, returnDocument: "after" }));
741
799
  if (!counter)
742
800
  throw new Error(`The sequence of ${this.collectionName} is not available`);
743
- return { first: counter.seq - count + 1, epoch: counter.epoch };
801
+ const first = counter.seq - count + 1;
802
+ if (this.sequence === "collection" && counter.sequence === "partition") {
803
+ await this.release(db, first).catch(() => undefined);
804
+ throw sequenceMismatch(this.collectionName, "collection");
805
+ }
806
+ return { first, epoch: counter.epoch };
744
807
  }
745
808
  /**
746
809
  * This method ends the pending numbers of a write, and drops the pending numbers whose lease
@@ -750,7 +813,7 @@ export class MongoDocumentStorage {
750
813
  */
751
814
  async release(db, first) {
752
815
  const live = { $gt: ["$$this.at", { $subtract: ["$$NOW", this.writeLeaseMs] }] };
753
- const after = (await db.collection(this.countersName).findOneAndUpdate({ _id: this.collectionName }, [
816
+ const after = (await db.collection(this.countersName).findOneAndUpdate({ _id: this.counterId }, [
754
817
  {
755
818
  $set: {
756
819
  lastRelease: {
@@ -795,16 +858,20 @@ export class MongoDocumentStorage {
795
858
  */
796
859
  async withNumbers(db, collection, count, write, own = true) {
797
860
  const noteOwn = own ? noteOwnNumbers : () => undefined;
861
+ await this.checkSequence(db);
798
862
  const client = await this.transactionClient(db);
799
863
  if (client) {
800
864
  const session = client.startSession();
801
865
  try {
802
866
  return await session.withTransaction(async () => {
803
- const counter = (await db.collection(this.countersName).findOneAndUpdate({ _id: this.collectionName }, { $inc: { seq: count }, $setOnInsert: { epoch: randomUUID() } }, { upsert: true, returnDocument: "after", session }));
867
+ const counter = (await db.collection(this.countersName).findOneAndUpdate({ _id: this.counterId }, { $inc: { seq: count }, $setOnInsert: { epoch: randomUUID() } }, { upsert: true, returnDocument: "after", session }));
804
868
  if (!counter)
805
869
  throw new Error(`The sequence of ${this.collectionName} is not available`);
870
+ // The error aborts the transaction, so the counter keeps its number
871
+ if (this.sequence === "collection" && counter.sequence === "partition")
872
+ throw sequenceMismatch(this.collectionName, "collection");
806
873
  // A watcher of the collection in this process skips the events of these numbers (roadmap CLI-77)
807
- noteOwn(db, this.collectionName, counter.seq - count + 1, count);
874
+ noteOwn(db, this.collectionName, counter.seq - count + 1, count, this.ownScope);
808
875
  return write(counter.seq - count + 1, session);
809
876
  });
810
877
  }
@@ -821,8 +888,9 @@ export class MongoDocumentStorage {
821
888
  * the numbers for a watcher of this process (roadmap CLI-77).
822
889
  */
823
890
  async withPendingNumbers(db, collection, count, write, noteOwn) {
891
+ await this.checkSequence(db);
824
892
  let { first } = await this.allocate(db, count);
825
- noteOwn(db, this.collectionName, first, count);
893
+ noteOwn(db, this.collectionName, first, count, this.ownScope);
826
894
  let result;
827
895
  try {
828
896
  result = await write(first);
@@ -836,7 +904,7 @@ export class MongoDocumentStorage {
836
904
  throw new Error(`A write of ${this.collectionName} stayed late after ${MAX_MOVES} moves to new numbers`);
837
905
  // Late: a reader can have passed these numbers. The write takes new ones.
838
906
  const next = (await this.allocate(db, count)).first;
839
- noteOwn(db, this.collectionName, next, count);
907
+ noteOwn(db, this.collectionName, next, count, this.ownScope);
840
908
  await this.move(collection, first, count, next);
841
909
  first = next;
842
910
  }
@@ -845,19 +913,22 @@ export class MongoDocumentStorage {
845
913
  /**
846
914
  * The watermark of the collection: the highest number below each pending number of a write whose
847
915
  * lease has not ended, the epoch, and the floor of the partition. Each number up to it is written
848
- * or abandoned. One command reads them. Only the first read of a collection writes: it makes the counter.
916
+ * or abandoned. One command reads them. Only the first read of a store writes: it makes the counter. With the
917
+ * option `sequence: "partition"`, the first read of each process also marks the counter of the collection.
849
918
  */
850
919
  async watermark(db) {
920
+ await this.checkSequence(db);
851
921
  const counters = db.collection(this.countersName);
852
922
  const floorId = this.floorId();
853
923
  const read = () => counters
854
924
  .aggregate([
855
- { $match: { _id: { $in: [this.collectionName, floorId] } } },
925
+ { $match: { _id: { $in: [this.counterId, floorId] } } },
856
926
  {
857
927
  $project: {
858
928
  seq: 1,
859
929
  epoch: 1,
860
930
  floor: 1,
931
+ sequence: 1,
861
932
  low: {
862
933
  $min: {
863
934
  $map: {
@@ -873,21 +944,56 @@ export class MongoDocumentStorage {
873
944
  ])
874
945
  .toArray();
875
946
  let docs = await read();
876
- if (!docs.some((doc) => doc._id === this.collectionName)) {
947
+ if (!docs.some((doc) => doc._id === this.counterId)) {
877
948
  // A duplicate key: another read made the counter at the same time
878
- await counters.updateOne({ _id: this.collectionName }, { $setOnInsert: { seq: 0, epoch: randomUUID() } }, { upsert: true }).catch((error) => {
949
+ await counters.updateOne({ _id: this.counterId }, { $setOnInsert: { seq: 0, epoch: randomUUID() } }, { upsert: true }).catch((error) => {
879
950
  if (!isDuplicateKey(error))
880
951
  throw error;
881
952
  });
882
953
  docs = await read();
883
954
  }
884
- const mark = docs.find((doc) => doc._id === this.collectionName);
955
+ const mark = docs.find((doc) => doc._id === this.counterId);
885
956
  if (!mark)
886
957
  throw new Error(`The sequence of ${this.collectionName} is not available`);
958
+ if (this.sequence === "collection" && mark.sequence === "partition")
959
+ throw sequenceMismatch(this.collectionName, "collection");
887
960
  const seq = typeof mark.low === "number" ? Math.min(mark.seq, mark.low - 1) : mark.seq;
888
961
  const floor = docs.find((doc) => doc._id === floorId)?.floor;
889
962
  return { seq, epoch: mark.epoch, floor: typeof floor === "number" ? floor : 0, held: seq < mark.seq };
890
963
  }
964
+ /**
965
+ * This method checks once for each collection that a store with the option `sequence: "partition"` can use it (roadmap
966
+ * CLI-96). One atomic step marks the counter of the collection, unless that counter has numbers. A store with the default
967
+ * reads the mark in its own steps on that counter, so it needs no check of its own.
968
+ */
969
+ checkSequence(db) {
970
+ if (this.sequence === "collection")
971
+ return Promise.resolve();
972
+ const owner = ownerOf(db);
973
+ let checks = SEQUENCE_CHECKS.get(owner);
974
+ if (!checks)
975
+ SEQUENCE_CHECKS.set(owner, (checks = new Map()));
976
+ const key = `${db.databaseName}\u0000${this.countersName}\u0000${this.collectionName}`;
977
+ let check = checks.get(key);
978
+ if (!check) {
979
+ const mark = async () => {
980
+ const counter = await db.collection(this.countersName).findOneAndUpdate({ _id: this.collectionName },
981
+ // A counter with numbers keeps its mark as it is: absent for a collection of the default sequence
982
+ [{ $set: { sequence: { $cond: [{ $gt: [{ $ifNull: ["$seq", 0] }, 0] }, "$sequence", "partition"] } } }], { upsert: true, returnDocument: "after" });
983
+ if (counter?.sequence !== "partition")
984
+ throw sequenceMismatch(this.collectionName, "partition");
985
+ };
986
+ // Two processes can insert the counter at the same time: the second finds it at its next try
987
+ check = mark().catch((error) => (isDuplicateKey(error) ? mark() : Promise.reject(error)));
988
+ checks.set(key, check);
989
+ const own = checks;
990
+ check.catch(() => {
991
+ if (own.get(key) === check)
992
+ own.delete(key);
993
+ });
994
+ }
995
+ return check;
996
+ }
891
997
  /** The id of the document of the oldest kept change of the partition. */
892
998
  async floorOf(db) {
893
999
  const doc = await db.collection(this.countersName).findOne({ _id: this.floorId() });
@@ -1154,11 +1260,16 @@ export class MongoDocumentStorage {
1154
1260
  // ===========================================================================
1155
1261
  async write(task) {
1156
1262
  const { db, items } = await this.collection();
1157
- return enqueueWrite(db, this.collectionName, async () => {
1263
+ const run = async () => {
1158
1264
  // The floor document of the partition, outside each transaction of the task (roadmap O66)
1159
1265
  await this.noteFloor(db);
1160
1266
  return task(db, items);
1161
- });
1267
+ };
1268
+ // The permit comes after the turn in the queue, so a write that waits for an earlier write of its counter holds no permit
1269
+ if (this.writesInFlight === Infinity)
1270
+ return enqueueWrite(db, this.counterId, run);
1271
+ const permits = writePermitsOf(db, this.writesInFlight);
1272
+ return enqueueWrite(db, this.counterId, () => permits.run(run));
1162
1273
  }
1163
1274
  async set(id, value, options) {
1164
1275
  await this.setBatch([[id, value]], options?.expectedVersion === undefined ? undefined : { expectedVersions: [[id, options.expectedVersion]] });