import { Db, Document, MongoServerError } from "mongodb"; import { getDb } from "../index"; import { MUNI_ISSUES_COLLECTION, NAMESPACE_EXISTS, VALIDATION_LEVEL, VALIDATION_ACTION, } from "./muniIssues.constants"; import { muniIssuesIndexes, muniIssuesJsonSchema } from "./muniIssues.schema"; const applyValidator = (db: Db, validator: Document): Promise => db.command({ collMod: MUNI_ISSUES_COLLECTION, validator, validationLevel: VALIDATION_LEVEL, validationAction: VALIDATION_ACTION, }); // Provisions validator and indexes: createCollection first, collMod if already exists. export const ensureMuniIssuesCollection = async (): Promise => { const db = getDb(); const validator = { $jsonSchema: muniIssuesJsonSchema }; const existing = await db .listCollections({ name: MUNI_ISSUES_COLLECTION }) .toArray(); if (existing.length === 0) { try { await db.createCollection(MUNI_ISSUES_COLLECTION, { validator, validationLevel: VALIDATION_LEVEL, validationAction: VALIDATION_ACTION, }); } catch (err) { // NamespaceExists race: collection exists — apply validator via collMod. if (err instanceof MongoServerError && err.code === NAMESPACE_EXISTS) { await applyValidator(db, validator); } else { throw err; } } } else { await applyValidator(db, validator); } await db.collection(MUNI_ISSUES_COLLECTION).createIndexes(muniIssuesIndexes); }; // Per-Db cache so each test's in-memory Db re-provisions. const provisioningByDb = new WeakMap>(); // Once per Db; evicts failed run so the next call retries. export const ensureMuniIssuesCollectionOnce = (): Promise => { const db = getDb(); let provisioning = provisioningByDb.get(db); if (!provisioning) { provisioning = ensureMuniIssuesCollection().catch((err) => { provisioningByDb.delete(db); throw err; }); provisioningByDb.set(db, provisioning); } return provisioning; };