@prisma-next/adapter-mongo 0.4.0-dev.1 → 0.4.0-dev.3
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/dist/{codecs-9xSaT_DN.mjs → codecs-DGN3pWRt.mjs} +2 -2
- package/dist/codecs-DGN3pWRt.mjs.map +1 -0
- package/dist/control.d.mts +6 -45
- package/dist/control.d.mts.map +1 -1
- package/dist/control.mjs +30 -795
- package/dist/control.mjs.map +1 -1
- package/dist/index.mjs +1 -1
- package/package.json +14 -14
- package/src/core/codecs.ts +1 -1
- package/src/core/runner-deps.ts +37 -0
- package/src/exports/control.ts +9 -11
- package/dist/codecs-9xSaT_DN.mjs.map +0 -1
- package/src/core/contract-to-schema.ts +0 -63
- package/src/core/ddl-formatter.ts +0 -112
- package/src/core/filter-evaluator.ts +0 -84
- package/src/core/mongo-ops-serializer.ts +0 -275
- package/src/core/mongo-planner.ts +0 -470
- package/src/core/mongo-runner.ts +0 -277
package/dist/control.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"control.mjs","names":["db: Db","keySpec: Document","options: Record<string, unknown>","command: Record<string, unknown>","error: unknown","parts: string[]","statements: string[]","keys: MongoIndexKey[]","collections: MongoSchemaCollection[]","type","#client","collCreates: MongoMigrationPlanOperation[]","drops: MongoMigrationPlanOperation[]","creates: MongoMigrationPlanOperation[]","validatorOps: MongoMigrationPlanOperation[]","mutableOptionOps: MongoMigrationPlanOperation[]","collDrops: MongoMigrationPlanOperation[]","conflicts: MigrationPlannerConflict[]","current: unknown","readMarker","updateMarker","initMarker","writeLedgerEntry","mongoAdapterDescriptor: ControlAdapterDescriptor<'mongo', 'mongo'>"],"sources":["../src/core/command-executor.ts","../src/core/contract-to-schema.ts","../src/core/ddl-formatter.ts","../src/core/introspect-schema.ts","../src/core/mongo-control-driver.ts","../src/core/mongo-ops-serializer.ts","../src/core/mongo-planner.ts","../src/core/filter-evaluator.ts","../src/core/mongo-runner.ts","../src/exports/control.ts"],"sourcesContent":["import type {\n CollModCommand,\n CreateCollectionCommand,\n CreateIndexCommand,\n DropCollectionCommand,\n DropIndexCommand,\n ListCollectionsCommand,\n ListIndexesCommand,\n MongoDdlCommandVisitor,\n MongoInspectionCommandVisitor,\n} from '@prisma-next/mongo-query-ast/control';\nimport { keysToKeySpec } from '@prisma-next/mongo-query-ast/control';\nimport { type Db, type Document, MongoServerError } from 'mongodb';\n\nexport class MongoCommandExecutor implements MongoDdlCommandVisitor<Promise<void>> {\n constructor(private readonly db: Db) {}\n\n async createIndex(cmd: CreateIndexCommand): Promise<void> {\n const keySpec: Document = keysToKeySpec(cmd.keys);\n const options: Record<string, unknown> = {};\n if (cmd.unique !== undefined) options['unique'] = cmd.unique;\n if (cmd.sparse !== undefined) options['sparse'] = cmd.sparse;\n if (cmd.expireAfterSeconds !== undefined)\n options['expireAfterSeconds'] = cmd.expireAfterSeconds;\n if (cmd.partialFilterExpression !== undefined)\n options['partialFilterExpression'] = cmd.partialFilterExpression;\n if (cmd.name !== undefined) options['name'] = cmd.name;\n if (cmd.wildcardProjection !== undefined)\n options['wildcardProjection'] = cmd.wildcardProjection;\n if (cmd.collation !== undefined) options['collation'] = cmd.collation;\n if (cmd.weights !== undefined) options['weights'] = cmd.weights;\n if (cmd.default_language !== undefined) options['default_language'] = cmd.default_language;\n if (cmd.language_override !== undefined) options['language_override'] = cmd.language_override;\n await this.db.collection(cmd.collection).createIndex(keySpec, options);\n }\n\n async dropIndex(cmd: DropIndexCommand): Promise<void> {\n await this.db.collection(cmd.collection).dropIndex(cmd.name);\n }\n\n async createCollection(cmd: CreateCollectionCommand): Promise<void> {\n const options: Record<string, unknown> = {};\n if (cmd.capped !== undefined) options['capped'] = cmd.capped;\n if (cmd.size !== undefined) options['size'] = cmd.size;\n if (cmd.max !== undefined) options['max'] = cmd.max;\n if (cmd.timeseries !== undefined) options['timeseries'] = cmd.timeseries;\n if (cmd.collation !== undefined) options['collation'] = cmd.collation;\n if (cmd.clusteredIndex !== undefined) options['clusteredIndex'] = cmd.clusteredIndex;\n if (cmd.validator !== undefined) options['validator'] = cmd.validator;\n if (cmd.validationLevel !== undefined) options['validationLevel'] = cmd.validationLevel;\n if (cmd.validationAction !== undefined) options['validationAction'] = cmd.validationAction;\n if (cmd.changeStreamPreAndPostImages !== undefined)\n options['changeStreamPreAndPostImages'] = cmd.changeStreamPreAndPostImages;\n await this.db.createCollection(cmd.collection, options);\n }\n\n async dropCollection(cmd: DropCollectionCommand): Promise<void> {\n await this.db.collection(cmd.collection).drop();\n }\n\n async collMod(cmd: CollModCommand): Promise<void> {\n const command: Record<string, unknown> = { collMod: cmd.collection };\n if (cmd.validator !== undefined) command['validator'] = cmd.validator;\n if (cmd.validationLevel !== undefined) command['validationLevel'] = cmd.validationLevel;\n if (cmd.validationAction !== undefined) command['validationAction'] = cmd.validationAction;\n if (cmd.changeStreamPreAndPostImages !== undefined)\n command['changeStreamPreAndPostImages'] = cmd.changeStreamPreAndPostImages;\n await this.db.command(command);\n }\n}\n\nexport class MongoInspectionExecutor implements MongoInspectionCommandVisitor<Promise<Document[]>> {\n constructor(private readonly db: Db) {}\n\n async listIndexes(cmd: ListIndexesCommand): Promise<Document[]> {\n try {\n return await this.db.collection(cmd.collection).listIndexes().toArray();\n } catch (error: unknown) {\n if (error instanceof MongoServerError && error.code === 26) {\n return [];\n }\n throw error;\n }\n }\n\n async listCollections(_cmd: ListCollectionsCommand): Promise<Document[]> {\n return this.db.listCollections().toArray();\n }\n}\n","import type {\n MongoContract,\n MongoStorageCollection,\n MongoStorageCollectionOptions,\n MongoStorageIndex,\n MongoStorageValidator,\n} from '@prisma-next/mongo-contract';\nimport {\n MongoSchemaCollection,\n MongoSchemaCollectionOptions,\n MongoSchemaIndex,\n MongoSchemaIR,\n MongoSchemaValidator,\n} from '@prisma-next/mongo-schema-ir';\n\nfunction convertIndex(index: MongoStorageIndex): MongoSchemaIndex {\n return new MongoSchemaIndex({\n keys: index.keys,\n unique: index.unique,\n sparse: index.sparse,\n expireAfterSeconds: index.expireAfterSeconds,\n partialFilterExpression: index.partialFilterExpression,\n wildcardProjection: index.wildcardProjection,\n collation: index.collation,\n weights: index.weights,\n default_language: index.default_language,\n language_override: index.language_override,\n });\n}\n\nfunction convertValidator(v: MongoStorageValidator): MongoSchemaValidator {\n return new MongoSchemaValidator({\n jsonSchema: v.jsonSchema,\n validationLevel: v.validationLevel,\n validationAction: v.validationAction,\n });\n}\n\nfunction convertOptions(o: MongoStorageCollectionOptions): MongoSchemaCollectionOptions {\n return new MongoSchemaCollectionOptions(o);\n}\n\nfunction convertCollection(name: string, def: MongoStorageCollection): MongoSchemaCollection {\n const indexes = (def.indexes ?? []).map(convertIndex);\n return new MongoSchemaCollection({\n name,\n indexes,\n ...(def.validator != null && { validator: convertValidator(def.validator) }),\n ...(def.options != null && { options: convertOptions(def.options) }),\n });\n}\n\nexport function contractToMongoSchemaIR(contract: MongoContract | null): MongoSchemaIR {\n if (!contract) {\n return new MongoSchemaIR([]);\n }\n\n const collections = Object.entries(contract.storage.collections).map(([name, def]) =>\n convertCollection(name, def),\n );\n\n return new MongoSchemaIR(collections);\n}\n","import type { MigrationPlanOperation } from '@prisma-next/framework-components/control';\nimport type {\n CollModCommand,\n CreateCollectionCommand,\n CreateIndexCommand,\n DropCollectionCommand,\n DropIndexCommand,\n MongoDdlCommandVisitor,\n MongoIndexKey,\n} from '@prisma-next/mongo-query-ast/control';\n\nfunction formatKeySpec(keys: ReadonlyArray<MongoIndexKey>): string {\n const entries = keys.map((k) => `${JSON.stringify(k.field)}: ${JSON.stringify(k.direction)}`);\n return `{ ${entries.join(', ')} }`;\n}\n\nfunction formatOptions(cmd: CreateIndexCommand): string | undefined {\n const parts: string[] = [];\n if (cmd.unique) parts.push('unique: true');\n if (cmd.sparse) parts.push('sparse: true');\n if (cmd.expireAfterSeconds !== undefined)\n parts.push(`expireAfterSeconds: ${cmd.expireAfterSeconds}`);\n if (cmd.name) parts.push(`name: ${JSON.stringify(cmd.name)}`);\n if (cmd.collation) parts.push(`collation: ${JSON.stringify(cmd.collation)}`);\n if (cmd.weights) parts.push(`weights: ${JSON.stringify(cmd.weights)}`);\n if (cmd.default_language) parts.push(`default_language: ${JSON.stringify(cmd.default_language)}`);\n if (cmd.language_override)\n parts.push(`language_override: ${JSON.stringify(cmd.language_override)}`);\n if (cmd.wildcardProjection)\n parts.push(`wildcardProjection: ${JSON.stringify(cmd.wildcardProjection)}`);\n if (cmd.partialFilterExpression)\n parts.push(`partialFilterExpression: ${JSON.stringify(cmd.partialFilterExpression)}`);\n if (parts.length === 0) return undefined;\n return `{ ${parts.join(', ')} }`;\n}\n\nfunction formatCreateCollectionOptions(cmd: CreateCollectionCommand): string | undefined {\n const parts: string[] = [];\n if (cmd.capped) parts.push('capped: true');\n if (cmd.size !== undefined) parts.push(`size: ${cmd.size}`);\n if (cmd.max !== undefined) parts.push(`max: ${cmd.max}`);\n if (cmd.timeseries) parts.push(`timeseries: ${JSON.stringify(cmd.timeseries)}`);\n if (cmd.collation) parts.push(`collation: ${JSON.stringify(cmd.collation)}`);\n if (cmd.clusteredIndex) parts.push(`clusteredIndex: ${JSON.stringify(cmd.clusteredIndex)}`);\n if (cmd.validator) parts.push(`validator: ${JSON.stringify(cmd.validator)}`);\n if (cmd.validationLevel) parts.push(`validationLevel: ${JSON.stringify(cmd.validationLevel)}`);\n if (cmd.validationAction) parts.push(`validationAction: ${JSON.stringify(cmd.validationAction)}`);\n if (cmd.changeStreamPreAndPostImages)\n parts.push(`changeStreamPreAndPostImages: ${JSON.stringify(cmd.changeStreamPreAndPostImages)}`);\n if (parts.length === 0) return undefined;\n return `{ ${parts.join(', ')} }`;\n}\n\nclass MongoDdlCommandFormatter implements MongoDdlCommandVisitor<string> {\n createIndex(cmd: CreateIndexCommand): string {\n const keySpec = formatKeySpec(cmd.keys);\n const opts = formatOptions(cmd);\n return opts\n ? `db.${cmd.collection}.createIndex(${keySpec}, ${opts})`\n : `db.${cmd.collection}.createIndex(${keySpec})`;\n }\n\n dropIndex(cmd: DropIndexCommand): string {\n return `db.${cmd.collection}.dropIndex(${JSON.stringify(cmd.name)})`;\n }\n\n createCollection(cmd: CreateCollectionCommand): string {\n const opts = formatCreateCollectionOptions(cmd);\n return opts\n ? `db.createCollection(${JSON.stringify(cmd.collection)}, ${opts})`\n : `db.createCollection(${JSON.stringify(cmd.collection)})`;\n }\n\n dropCollection(cmd: DropCollectionCommand): string {\n return `db.${cmd.collection}.drop()`;\n }\n\n collMod(cmd: CollModCommand): string {\n const parts: string[] = [`collMod: ${JSON.stringify(cmd.collection)}`];\n if (cmd.validator) parts.push(`validator: ${JSON.stringify(cmd.validator)}`);\n if (cmd.validationLevel) parts.push(`validationLevel: ${JSON.stringify(cmd.validationLevel)}`);\n if (cmd.validationAction)\n parts.push(`validationAction: ${JSON.stringify(cmd.validationAction)}`);\n if (cmd.changeStreamPreAndPostImages)\n parts.push(\n `changeStreamPreAndPostImages: ${JSON.stringify(cmd.changeStreamPreAndPostImages)}`,\n );\n return `db.runCommand({ ${parts.join(', ')} })`;\n }\n}\n\nconst formatter = new MongoDdlCommandFormatter();\n\ninterface MongoExecuteStep {\n readonly command: { readonly accept: <R>(visitor: MongoDdlCommandVisitor<R>) => R };\n}\n\nexport function formatMongoOperations(operations: readonly MigrationPlanOperation[]): string[] {\n const statements: string[] = [];\n for (const operation of operations) {\n const candidate = operation as unknown as Record<string, unknown>;\n if (!('execute' in candidate) || !Array.isArray(candidate['execute'])) {\n continue;\n }\n for (const step of candidate['execute'] as MongoExecuteStep[]) {\n if (step.command && typeof step.command.accept === 'function') {\n statements.push(step.command.accept(formatter));\n }\n }\n }\n return statements;\n}\n","import type { MongoIndexKey, MongoIndexKeyDirection } from '@prisma-next/mongo-contract';\nimport {\n MongoSchemaCollection,\n MongoSchemaCollectionOptions,\n MongoSchemaIndex,\n MongoSchemaIR,\n MongoSchemaValidator,\n} from '@prisma-next/mongo-schema-ir';\nimport type { Db, Document } from 'mongodb';\n\nconst PRISMA_MIGRATIONS_COLLECTION = '_prisma_migrations';\n\nfunction parseIndexKeys(keySpec: Record<string, unknown>): MongoIndexKey[] {\n const keys: MongoIndexKey[] = [];\n for (const [field, direction] of Object.entries(keySpec)) {\n keys.push({ field, direction: direction as MongoIndexKeyDirection });\n }\n return keys;\n}\n\nfunction isDefaultIdIndex(doc: Document): boolean {\n const key = doc['key'] as Record<string, unknown> | undefined;\n if (!key) return false;\n const entries = Object.entries(key);\n return entries.length === 1 && entries[0]?.[0] === '_id' && entries[0]?.[1] === 1;\n}\n\nfunction parseIndex(doc: Document): MongoSchemaIndex {\n const keySpec = doc['key'] as Record<string, unknown>;\n return new MongoSchemaIndex({\n keys: parseIndexKeys(keySpec),\n unique: doc['unique'] as boolean | undefined,\n sparse: doc['sparse'] as boolean | undefined,\n expireAfterSeconds: doc['expireAfterSeconds'] as number | undefined,\n partialFilterExpression: doc['partialFilterExpression'] as Record<string, unknown> | undefined,\n wildcardProjection: doc['wildcardProjection'] as Record<string, 0 | 1> | undefined,\n collation: doc['collation'] as Record<string, unknown> | undefined,\n weights: doc['weights'] as Record<string, number> | undefined,\n default_language: doc['default_language'] as string | undefined,\n language_override: doc['language_override'] as string | undefined,\n });\n}\n\nfunction parseValidator(options: Document): MongoSchemaValidator | undefined {\n const validator = options['validator'] as Record<string, unknown> | undefined;\n if (!validator) return undefined;\n\n const jsonSchema = validator['$jsonSchema'] as Record<string, unknown> | undefined;\n if (!jsonSchema) return undefined;\n\n return new MongoSchemaValidator({\n jsonSchema,\n validationLevel: (options['validationLevel'] as 'strict' | 'moderate') ?? 'strict',\n validationAction: (options['validationAction'] as 'error' | 'warn') ?? 'error',\n });\n}\n\nfunction parseCollectionOptions(info: Document): MongoSchemaCollectionOptions | undefined {\n const options = info['options'] as Record<string, unknown> | undefined;\n if (!options) return undefined;\n\n const capped = options['capped'] as boolean | undefined;\n const size = options['size'] as number | undefined;\n const max = options['max'] as number | undefined;\n const timeseries = options['timeseries'] as\n | { timeField: string; metaField?: string; granularity?: 'seconds' | 'minutes' | 'hours' }\n | undefined;\n const collation = options['collation'] as Record<string, unknown> | undefined;\n const changeStreamPreAndPostImages = options['changeStreamPreAndPostImages'] as\n | { enabled: boolean }\n | undefined;\n const clusteredIndex = options['clusteredIndex'] as { name?: string } | undefined;\n\n const hasMeaningfulOptions =\n capped || timeseries || collation || changeStreamPreAndPostImages || clusteredIndex;\n if (!hasMeaningfulOptions) return undefined;\n\n return new MongoSchemaCollectionOptions({\n ...(capped ? { capped: { size: size ?? 0, ...(max != null ? { max } : {}) } } : {}),\n ...(timeseries ? { timeseries } : {}),\n ...(collation ? { collation } : {}),\n ...(changeStreamPreAndPostImages ? { changeStreamPreAndPostImages } : {}),\n ...(clusteredIndex ? { clusteredIndex } : {}),\n });\n}\n\nexport async function introspectSchema(db: Db): Promise<MongoSchemaIR> {\n const collectionInfos = await db.listCollections().toArray();\n\n const collections: MongoSchemaCollection[] = [];\n\n for (const info of collectionInfos) {\n const name = info['name'] as string;\n const type = info['type'] as string | undefined;\n\n if (name === PRISMA_MIGRATIONS_COLLECTION) continue;\n if (name.startsWith('system.')) continue;\n if (type === 'view') continue;\n\n const indexDocs = await db.collection(name).listIndexes().toArray();\n const indexes = indexDocs.filter((doc) => !isDefaultIdIndex(doc)).map(parseIndex);\n\n const infoOptions = 'options' in info ? (info['options'] as Record<string, unknown>) : {};\n const validator = parseValidator(infoOptions);\n const options = parseCollectionOptions(info);\n\n collections.push(\n new MongoSchemaCollection({\n name,\n indexes,\n ...(validator ? { validator } : {}),\n ...(options ? { options } : {}),\n }),\n );\n }\n\n return new MongoSchemaIR(collections);\n}\n","import type { ControlDriverInstance } from '@prisma-next/framework-components/control';\nimport type { Db, MongoClient } from 'mongodb';\n\nexport interface MongoControlDriverInstance extends ControlDriverInstance<'mongo', 'mongo'> {\n readonly db: Db;\n}\n\nclass MongoControlDriverImpl implements MongoControlDriverInstance {\n readonly familyId = 'mongo' as const;\n readonly targetId = 'mongo' as const;\n readonly db: Db;\n readonly #client: MongoClient;\n\n constructor(db: Db, client: MongoClient) {\n this.db = db;\n this.#client = client;\n }\n\n query(): Promise<never> {\n throw new Error('MongoDB control driver does not support SQL queries');\n }\n\n async close(): Promise<void> {\n await this.#client.close();\n }\n}\n\nexport function createMongoControlDriver(db: Db, client: MongoClient): MongoControlDriverInstance {\n return new MongoControlDriverImpl(db, client);\n}\n","import type { MigrationOperationClass } from '@prisma-next/framework-components/control';\nimport {\n type AnyMongoDdlCommand,\n type AnyMongoInspectionCommand,\n CollModCommand,\n CreateCollectionCommand,\n CreateIndexCommand,\n DropCollectionCommand,\n DropIndexCommand,\n ListCollectionsCommand,\n ListIndexesCommand,\n MongoAndExpr,\n MongoExistsExpr,\n MongoFieldFilter,\n type MongoFilterExpr,\n type MongoMigrationCheck,\n type MongoMigrationPlanOperation,\n type MongoMigrationStep,\n MongoNotExpr,\n MongoOrExpr,\n} from '@prisma-next/mongo-query-ast/control';\nimport { type } from 'arktype';\n\nconst IndexKeyDirection = type('1 | -1 | \"text\" | \"2dsphere\" | \"2d\" | \"hashed\"');\nconst IndexKeyJson = type({ field: 'string', direction: IndexKeyDirection });\n\nconst CreateIndexJson = type({\n kind: '\"createIndex\"',\n collection: 'string',\n keys: IndexKeyJson.array().atLeastLength(1),\n 'unique?': 'boolean',\n 'sparse?': 'boolean',\n 'expireAfterSeconds?': 'number',\n 'partialFilterExpression?': 'Record<string, unknown>',\n 'name?': 'string',\n 'wildcardProjection?': 'Record<string, unknown>',\n 'collation?': 'Record<string, unknown>',\n 'weights?': 'Record<string, unknown>',\n 'default_language?': 'string',\n 'language_override?': 'string',\n});\n\nconst DropIndexJson = type({\n kind: '\"dropIndex\"',\n collection: 'string',\n name: 'string',\n});\n\nconst CreateCollectionJson = type({\n kind: '\"createCollection\"',\n collection: 'string',\n 'validator?': 'Record<string, unknown>',\n 'validationLevel?': '\"strict\" | \"moderate\"',\n 'validationAction?': '\"error\" | \"warn\"',\n 'capped?': 'boolean',\n 'size?': 'number',\n 'max?': 'number',\n 'timeseries?': 'Record<string, unknown>',\n 'collation?': 'Record<string, unknown>',\n 'changeStreamPreAndPostImages?': 'Record<string, unknown>',\n 'clusteredIndex?': 'Record<string, unknown>',\n});\n\nconst DropCollectionJson = type({\n kind: '\"dropCollection\"',\n collection: 'string',\n});\n\nconst CollModJson = type({\n kind: '\"collMod\"',\n collection: 'string',\n 'validator?': 'Record<string, unknown>',\n 'validationLevel?': '\"strict\" | \"moderate\"',\n 'validationAction?': '\"error\" | \"warn\"',\n 'changeStreamPreAndPostImages?': 'Record<string, unknown>',\n});\n\nconst ListIndexesJson = type({\n kind: '\"listIndexes\"',\n collection: 'string',\n});\n\nconst ListCollectionsJson = type({\n kind: '\"listCollections\"',\n});\n\nconst FieldFilterJson = type({\n kind: '\"field\"',\n field: 'string',\n op: 'string',\n value: 'unknown',\n});\n\nconst ExistsFilterJson = type({\n kind: '\"exists\"',\n field: 'string',\n exists: 'boolean',\n});\n\nconst CheckJson = type({\n description: 'string',\n source: 'Record<string, unknown>',\n filter: 'Record<string, unknown>',\n expect: '\"exists\" | \"notExists\"',\n});\n\nconst StepJson = type({\n description: 'string',\n command: 'Record<string, unknown>',\n});\n\nconst OperationJson = type({\n id: 'string',\n label: 'string',\n operationClass: '\"additive\" | \"widening\" | \"destructive\"',\n precheck: 'Record<string, unknown>[]',\n execute: 'Record<string, unknown>[]',\n postcheck: 'Record<string, unknown>[]',\n});\n\nfunction validate<T>(schema: { assert: (data: unknown) => T }, data: unknown, context: string): T {\n try {\n return schema.assert(data);\n } catch (error) {\n const message = error instanceof Error ? error.message : String(error);\n throw new Error(`Invalid ${context}: ${message}`);\n }\n}\n\nfunction deserializeFilterExpr(json: unknown): MongoFilterExpr {\n const record = json as Record<string, unknown>;\n const kind = record['kind'] as string;\n switch (kind) {\n case 'field': {\n const data = validate(FieldFilterJson, json, 'field filter');\n return MongoFieldFilter.of(data.field, data.op, data.value as never);\n }\n case 'and': {\n const exprs = record['exprs'];\n if (!Array.isArray(exprs)) throw new Error('Invalid and filter: missing exprs array');\n return MongoAndExpr.of(exprs.map(deserializeFilterExpr));\n }\n case 'or': {\n const exprs = record['exprs'];\n if (!Array.isArray(exprs)) throw new Error('Invalid or filter: missing exprs array');\n return MongoOrExpr.of(exprs.map(deserializeFilterExpr));\n }\n case 'not': {\n const expr = record['expr'];\n if (!expr || typeof expr !== 'object') throw new Error('Invalid not filter: missing expr');\n return new MongoNotExpr(deserializeFilterExpr(expr));\n }\n case 'exists': {\n const data = validate(ExistsFilterJson, json, 'exists filter');\n return new MongoExistsExpr(data.field, data.exists);\n }\n default:\n throw new Error(`Unknown filter expression kind: ${kind}`);\n }\n}\n\nfunction deserializeDdlCommand(json: unknown): AnyMongoDdlCommand {\n const record = json as Record<string, unknown>;\n const kind = record['kind'] as string;\n switch (kind) {\n case 'createIndex': {\n const data = validate(CreateIndexJson, json, 'createIndex command');\n return new CreateIndexCommand(data.collection, data.keys, {\n unique: data.unique,\n sparse: data.sparse,\n expireAfterSeconds: data.expireAfterSeconds,\n partialFilterExpression: data.partialFilterExpression,\n name: data.name,\n wildcardProjection: data.wildcardProjection as Record<string, 0 | 1> | undefined,\n collation: data.collation,\n weights: data.weights as Record<string, number> | undefined,\n default_language: data.default_language,\n language_override: data.language_override,\n });\n }\n case 'dropIndex': {\n const data = validate(DropIndexJson, json, 'dropIndex command');\n return new DropIndexCommand(data.collection, data.name);\n }\n case 'createCollection': {\n const data = validate(CreateCollectionJson, json, 'createCollection command');\n return new CreateCollectionCommand(data.collection, {\n validator: data.validator,\n validationLevel: data.validationLevel,\n validationAction: data.validationAction,\n capped: data.capped,\n size: data.size,\n max: data.max,\n timeseries: data.timeseries as CreateCollectionCommand['timeseries'],\n collation: data.collation,\n changeStreamPreAndPostImages: data.changeStreamPreAndPostImages as\n | { enabled: boolean }\n | undefined,\n clusteredIndex: data.clusteredIndex as CreateCollectionCommand['clusteredIndex'],\n });\n }\n case 'dropCollection': {\n const data = validate(DropCollectionJson, json, 'dropCollection command');\n return new DropCollectionCommand(data.collection);\n }\n case 'collMod': {\n const data = validate(CollModJson, json, 'collMod command');\n return new CollModCommand(data.collection, {\n validator: data.validator,\n validationLevel: data.validationLevel,\n validationAction: data.validationAction,\n changeStreamPreAndPostImages: data.changeStreamPreAndPostImages as\n | { enabled: boolean }\n | undefined,\n });\n }\n default:\n throw new Error(`Unknown DDL command kind: ${kind}`);\n }\n}\n\nfunction deserializeInspectionCommand(json: unknown): AnyMongoInspectionCommand {\n const record = json as Record<string, unknown>;\n const kind = record['kind'] as string;\n switch (kind) {\n case 'listIndexes': {\n const data = validate(ListIndexesJson, json, 'listIndexes command');\n return new ListIndexesCommand(data.collection);\n }\n case 'listCollections': {\n validate(ListCollectionsJson, json, 'listCollections command');\n return new ListCollectionsCommand();\n }\n default:\n throw new Error(`Unknown inspection command kind: ${kind}`);\n }\n}\n\nfunction deserializeCheck(json: unknown): MongoMigrationCheck {\n const data = validate(CheckJson, json, 'migration check');\n return {\n description: data.description,\n source: deserializeInspectionCommand(data.source),\n filter: deserializeFilterExpr(data.filter),\n expect: data.expect,\n };\n}\n\nfunction deserializeStep(json: unknown): MongoMigrationStep {\n const data = validate(StepJson, json, 'migration step');\n return {\n description: data.description,\n command: deserializeDdlCommand(data.command),\n };\n}\n\nexport function deserializeMongoOp(json: unknown): MongoMigrationPlanOperation {\n const data = validate(OperationJson, json, 'migration operation');\n return {\n id: data.id,\n label: data.label,\n operationClass: data.operationClass as MigrationOperationClass,\n precheck: data.precheck.map(deserializeCheck),\n execute: data.execute.map(deserializeStep),\n postcheck: data.postcheck.map(deserializeCheck),\n };\n}\n\nexport function deserializeMongoOps(json: readonly unknown[]): MongoMigrationPlanOperation[] {\n return json.map(deserializeMongoOp);\n}\n\nexport function serializeMongoOps(ops: readonly MongoMigrationPlanOperation[]): string {\n return JSON.stringify(ops, null, 2);\n}\n","import type { TargetBoundComponentDescriptor } from '@prisma-next/framework-components/components';\nimport type {\n MigrationOperationPolicy,\n MigrationPlanner,\n MigrationPlannerConflict,\n MigrationPlannerResult,\n} from '@prisma-next/framework-components/control';\nimport type { MongoContract, MongoIndexKey } from '@prisma-next/mongo-contract';\nimport {\n buildIndexOpId,\n CollModCommand,\n CreateCollectionCommand,\n CreateIndexCommand,\n DropCollectionCommand,\n DropIndexCommand,\n defaultMongoIndexName,\n keysToKeySpec,\n ListCollectionsCommand,\n ListIndexesCommand,\n MongoAndExpr,\n MongoFieldFilter,\n type MongoMigrationPlanOperation,\n} from '@prisma-next/mongo-query-ast/control';\nimport {\n canonicalize,\n deepEqual,\n type MongoSchemaCollection,\n type MongoSchemaCollectionOptions,\n type MongoSchemaIndex,\n type MongoSchemaIR,\n type MongoSchemaValidator,\n} from '@prisma-next/mongo-schema-ir';\nimport { contractToMongoSchemaIR } from './contract-to-schema';\n\nfunction buildIndexLookupKey(index: MongoSchemaIndex): string {\n const keys = index.keys.map((k) => `${k.field}:${k.direction}`).join(',');\n const opts = [\n index.unique ? 'unique' : '',\n index.sparse ? 'sparse' : '',\n index.expireAfterSeconds != null ? `ttl:${index.expireAfterSeconds}` : '',\n index.partialFilterExpression ? `pfe:${canonicalize(index.partialFilterExpression)}` : '',\n index.wildcardProjection ? `wp:${canonicalize(index.wildcardProjection)}` : '',\n index.collation ? `col:${canonicalize(index.collation)}` : '',\n index.weights ? `wt:${canonicalize(index.weights)}` : '',\n index.default_language ? `dl:${index.default_language}` : '',\n index.language_override ? `lo:${index.language_override}` : '',\n ]\n .filter(Boolean)\n .join(';');\n return opts ? `${keys}|${opts}` : keys;\n}\n\nfunction formatKeys(keys: ReadonlyArray<MongoIndexKey>): string {\n return keys.map((k) => `${k.field}:${k.direction}`).join(', ');\n}\n\nfunction isTextIndex(keys: ReadonlyArray<MongoIndexKey>): boolean {\n return keys.some((k) => k.direction === 'text');\n}\n\nfunction planCreateIndex(collection: string, index: MongoSchemaIndex): MongoMigrationPlanOperation {\n const { keys } = index;\n const name = defaultMongoIndexName(keys);\n\n const textIndex = isTextIndex(keys);\n const keyFilter = textIndex\n ? MongoFieldFilter.eq('key._fts', 'text')\n : MongoFieldFilter.eq('key', keysToKeySpec(keys));\n const fullFilter = index.unique\n ? MongoAndExpr.of([keyFilter, MongoFieldFilter.eq('unique', true)])\n : keyFilter;\n\n return {\n id: buildIndexOpId('create', collection, keys),\n label: `Create index on ${collection} (${formatKeys(keys)})`,\n operationClass: 'additive',\n precheck: [\n {\n description: `index does not already exist on ${collection}`,\n source: new ListIndexesCommand(collection),\n filter: keyFilter,\n expect: 'notExists',\n },\n ],\n execute: [\n {\n description: `create index on ${collection}`,\n command: new CreateIndexCommand(collection, keys, {\n unique: index.unique || undefined,\n sparse: index.sparse,\n expireAfterSeconds: index.expireAfterSeconds,\n partialFilterExpression: index.partialFilterExpression,\n wildcardProjection: index.wildcardProjection,\n collation: index.collation,\n weights: index.weights,\n default_language: index.default_language,\n language_override: index.language_override,\n name,\n }),\n },\n ],\n postcheck: [\n {\n description: `index exists on ${collection}`,\n source: new ListIndexesCommand(collection),\n filter: fullFilter,\n expect: 'exists',\n },\n ],\n };\n}\n\nfunction planDropIndex(collection: string, index: MongoSchemaIndex): MongoMigrationPlanOperation {\n const { keys } = index;\n const indexName = defaultMongoIndexName(keys);\n const textIndex = isTextIndex(keys);\n const keyFilter = textIndex\n ? MongoFieldFilter.eq('key._fts', 'text')\n : MongoFieldFilter.eq('key', keysToKeySpec(keys));\n\n return {\n id: buildIndexOpId('drop', collection, keys),\n label: `Drop index on ${collection} (${formatKeys(keys)})`,\n operationClass: 'destructive',\n precheck: [\n {\n description: `index exists on ${collection}`,\n source: new ListIndexesCommand(collection),\n filter: keyFilter,\n expect: 'exists',\n },\n ],\n execute: [\n {\n description: `drop index on ${collection}`,\n command: new DropIndexCommand(collection, indexName),\n },\n ],\n postcheck: [\n {\n description: `index no longer exists on ${collection}`,\n source: new ListIndexesCommand(collection),\n filter: keyFilter,\n expect: 'notExists',\n },\n ],\n };\n}\n\nfunction validatorsEqual(\n a: MongoSchemaValidator | undefined,\n b: MongoSchemaValidator | undefined,\n): boolean {\n if (!a && !b) return true;\n if (!a || !b) return false;\n return (\n a.validationLevel === b.validationLevel &&\n a.validationAction === b.validationAction &&\n canonicalize(a.jsonSchema) === canonicalize(b.jsonSchema)\n );\n}\n\nfunction classifyValidatorUpdate(\n origin: MongoSchemaValidator,\n dest: MongoSchemaValidator,\n): 'widening' | 'destructive' {\n let hasDestructive = false;\n\n if (canonicalize(origin.jsonSchema) !== canonicalize(dest.jsonSchema)) {\n hasDestructive = true;\n }\n\n if (origin.validationAction !== dest.validationAction) {\n if (dest.validationAction === 'error') hasDestructive = true;\n }\n\n if (origin.validationLevel !== dest.validationLevel) {\n if (dest.validationLevel === 'strict') hasDestructive = true;\n }\n\n return hasDestructive ? 'destructive' : 'widening';\n}\n\nfunction planValidatorDiff(\n collName: string,\n originValidator: MongoSchemaValidator | undefined,\n destValidator: MongoSchemaValidator | undefined,\n): MongoMigrationPlanOperation | undefined {\n if (validatorsEqual(originValidator, destValidator)) return undefined;\n\n const collExistsPrecheck = {\n description: `collection ${collName} exists`,\n source: new ListCollectionsCommand(),\n filter: MongoFieldFilter.eq('name', collName),\n expect: 'exists' as const,\n };\n\n if (destValidator) {\n const operationClass = originValidator\n ? classifyValidatorUpdate(originValidator, destValidator)\n : 'destructive';\n return {\n id: `validator.${collName}.${originValidator ? 'update' : 'add'}`,\n label: `${originValidator ? 'Update' : 'Add'} validator on ${collName}`,\n operationClass,\n precheck: [collExistsPrecheck],\n execute: [\n {\n description: `set validator on ${collName}`,\n command: new CollModCommand(collName, {\n validator: { $jsonSchema: destValidator.jsonSchema },\n validationLevel: destValidator.validationLevel,\n validationAction: destValidator.validationAction,\n }),\n },\n ],\n postcheck: [\n {\n description: `validator applied on ${collName}`,\n source: new ListCollectionsCommand(),\n filter: MongoAndExpr.of([\n MongoFieldFilter.eq('name', collName),\n MongoFieldFilter.eq('options.validationLevel', destValidator.validationLevel),\n MongoFieldFilter.eq('options.validationAction', destValidator.validationAction),\n ]),\n expect: 'exists' as const,\n },\n ],\n };\n }\n\n return {\n id: `validator.${collName}.remove`,\n label: `Remove validator on ${collName}`,\n operationClass: 'widening',\n precheck: [collExistsPrecheck],\n execute: [\n {\n description: `remove validator on ${collName}`,\n command: new CollModCommand(collName, {\n validator: {},\n validationLevel: 'strict',\n validationAction: 'error',\n }),\n },\n ],\n postcheck: [],\n };\n}\n\nfunction hasImmutableOptionChange(\n origin: MongoSchemaCollectionOptions | undefined,\n dest: MongoSchemaCollectionOptions | undefined,\n): string | undefined {\n if (canonicalize(origin?.capped) !== canonicalize(dest?.capped)) return 'capped';\n if (canonicalize(origin?.timeseries) !== canonicalize(dest?.timeseries)) return 'timeseries';\n if (canonicalize(origin?.collation) !== canonicalize(dest?.collation)) return 'collation';\n if (canonicalize(origin?.clusteredIndex) !== canonicalize(dest?.clusteredIndex))\n return 'clusteredIndex';\n return undefined;\n}\n\nfunction planCreateCollection(\n collName: string,\n dest: MongoSchemaCollection,\n): MongoMigrationPlanOperation {\n const opts = dest.options;\n const validator = dest.validator;\n return {\n id: `collection.${collName}.create`,\n label: `Create collection ${collName}`,\n operationClass: 'additive',\n precheck: [\n {\n description: `collection ${collName} does not exist`,\n source: new ListCollectionsCommand(),\n filter: MongoFieldFilter.eq('name', collName),\n expect: 'notExists',\n },\n ],\n execute: [\n {\n description: `create collection ${collName}`,\n command: new CreateCollectionCommand(collName, {\n capped: opts?.capped ? true : undefined,\n size: opts?.capped?.size,\n max: opts?.capped?.max,\n timeseries: opts?.timeseries,\n collation: opts?.collation,\n clusteredIndex: opts?.clusteredIndex\n ? {\n key: { _id: 1 } as Record<string, number>,\n unique: true as boolean,\n ...(opts.clusteredIndex.name != null ? { name: opts.clusteredIndex.name } : {}),\n }\n : undefined,\n validator: validator ? { $jsonSchema: validator.jsonSchema } : undefined,\n validationLevel: validator?.validationLevel,\n validationAction: validator?.validationAction,\n changeStreamPreAndPostImages: opts?.changeStreamPreAndPostImages,\n }),\n },\n ],\n postcheck: [],\n };\n}\n\nfunction planDropCollection(collName: string): MongoMigrationPlanOperation {\n return {\n id: `collection.${collName}.drop`,\n label: `Drop collection ${collName}`,\n operationClass: 'destructive',\n precheck: [],\n execute: [\n {\n description: `drop collection ${collName}`,\n command: new DropCollectionCommand(collName),\n },\n ],\n postcheck: [],\n };\n}\n\nfunction planMutableOptionsDiff(\n collName: string,\n origin: MongoSchemaCollectionOptions | undefined,\n dest: MongoSchemaCollectionOptions | undefined,\n): MongoMigrationPlanOperation | undefined {\n const originCSPPI = origin?.changeStreamPreAndPostImages;\n const destCSPPI = dest?.changeStreamPreAndPostImages;\n if (deepEqual(originCSPPI, destCSPPI)) return undefined;\n\n return {\n id: `options.${collName}.update`,\n label: `Update mutable options on ${collName}`,\n operationClass: destCSPPI?.enabled ? 'widening' : 'destructive',\n precheck: [],\n execute: [\n {\n description: `update options on ${collName}`,\n command: new CollModCommand(collName, {\n changeStreamPreAndPostImages: destCSPPI,\n }),\n },\n ],\n postcheck: [],\n };\n}\n\nfunction collectionHasOptions(coll: MongoSchemaCollection): boolean {\n return !!(coll.options || coll.validator);\n}\n\nexport class MongoMigrationPlanner implements MigrationPlanner<'mongo', 'mongo'> {\n plan(options: {\n readonly contract: unknown;\n readonly schema: unknown;\n readonly policy: MigrationOperationPolicy;\n readonly frameworkComponents: ReadonlyArray<TargetBoundComponentDescriptor<'mongo', 'mongo'>>;\n }): MigrationPlannerResult {\n const contract = options.contract as MongoContract;\n const originIR = options.schema as MongoSchemaIR;\n const destinationIR = contractToMongoSchemaIR(contract);\n\n const collCreates: MongoMigrationPlanOperation[] = [];\n const drops: MongoMigrationPlanOperation[] = [];\n const creates: MongoMigrationPlanOperation[] = [];\n const validatorOps: MongoMigrationPlanOperation[] = [];\n const mutableOptionOps: MongoMigrationPlanOperation[] = [];\n const collDrops: MongoMigrationPlanOperation[] = [];\n const conflicts: MigrationPlannerConflict[] = [];\n\n const allCollectionNames = new Set([\n ...originIR.collectionNames,\n ...destinationIR.collectionNames,\n ]);\n\n for (const collName of [...allCollectionNames].sort()) {\n const originColl = originIR.collection(collName);\n const destColl = destinationIR.collection(collName);\n\n if (!originColl && destColl) {\n if (collectionHasOptions(destColl)) {\n collCreates.push(planCreateCollection(collName, destColl));\n }\n } else if (originColl && !destColl) {\n collDrops.push(planDropCollection(collName));\n } else if (originColl && destColl) {\n const immutableChange = hasImmutableOptionChange(originColl.options, destColl.options);\n if (immutableChange) {\n conflicts.push({\n kind: 'policy-violation',\n summary: `Cannot change immutable collection option '${immutableChange}' on ${collName}`,\n why: `MongoDB does not support modifying the '${immutableChange}' option after collection creation`,\n });\n }\n\n const mutableOp = planMutableOptionsDiff(collName, originColl.options, destColl.options);\n if (mutableOp) mutableOptionOps.push(mutableOp);\n\n const validatorOp = planValidatorDiff(collName, originColl.validator, destColl.validator);\n if (validatorOp) validatorOps.push(validatorOp);\n }\n\n const originLookup = new Map<string, MongoSchemaIndex>();\n if (originColl) {\n for (const idx of originColl.indexes) {\n originLookup.set(buildIndexLookupKey(idx), idx);\n }\n }\n\n const destLookup = new Map<string, MongoSchemaIndex>();\n if (destColl) {\n for (const idx of destColl.indexes) {\n destLookup.set(buildIndexLookupKey(idx), idx);\n }\n }\n\n for (const [lookupKey, idx] of originLookup) {\n if (!destLookup.has(lookupKey)) {\n drops.push(planDropIndex(collName, idx));\n }\n }\n\n for (const [lookupKey, idx] of destLookup) {\n if (!originLookup.has(lookupKey)) {\n creates.push(planCreateIndex(collName, idx));\n }\n }\n }\n\n if (conflicts.length > 0) {\n return { kind: 'failure', conflicts };\n }\n\n const allOps = [\n ...collCreates,\n ...drops,\n ...creates,\n ...validatorOps,\n ...mutableOptionOps,\n ...collDrops,\n ];\n\n for (const op of allOps) {\n if (!options.policy.allowedOperationClasses.includes(op.operationClass)) {\n conflicts.push({\n kind: 'policy-violation',\n summary: `${op.operationClass} operation disallowed: ${op.label}`,\n why: `Policy does not allow '${op.operationClass}' operations`,\n });\n }\n }\n\n if (conflicts.length > 0) {\n return { kind: 'failure', conflicts };\n }\n\n return {\n kind: 'success',\n plan: {\n targetId: 'mongo',\n destination: {\n storageHash: contract.storage.storageHash,\n },\n operations: allOps,\n },\n };\n }\n}\n","import type {\n MongoAndExpr,\n MongoExistsExpr,\n MongoExprFilter,\n MongoFieldFilter,\n MongoFilterExpr,\n MongoFilterVisitor,\n MongoNotExpr,\n MongoOrExpr,\n} from '@prisma-next/mongo-query-ast/control';\nimport { deepEqual } from '@prisma-next/mongo-schema-ir';\nimport type { MongoValue } from '@prisma-next/mongo-value';\n\nfunction getNestedField(doc: Record<string, unknown>, path: string): unknown {\n const parts = path.split('.');\n let current: unknown = doc;\n for (const part of parts) {\n if (current === null || current === undefined || typeof current !== 'object') {\n return undefined;\n }\n const record = current as Record<string, unknown>;\n if (!Object.hasOwn(record, part)) {\n return undefined;\n }\n current = record[part];\n }\n return current;\n}\n\nfunction evaluateFieldOp(op: string, actual: unknown, expected: MongoValue): boolean {\n switch (op) {\n case '$eq':\n return deepEqual(actual, expected);\n case '$ne':\n return !deepEqual(actual, expected);\n case '$gt':\n return typeof actual === typeof expected && (actual as number) > (expected as number);\n case '$gte':\n return typeof actual === typeof expected && (actual as number) >= (expected as number);\n case '$lt':\n return typeof actual === typeof expected && (actual as number) < (expected as number);\n case '$lte':\n return typeof actual === typeof expected && (actual as number) <= (expected as number);\n case '$in':\n return Array.isArray(expected) && expected.some((v) => deepEqual(actual, v));\n default:\n throw new Error(`Unsupported filter operator in migration check: ${op}`);\n }\n}\n\nexport class FilterEvaluator implements MongoFilterVisitor<boolean> {\n private doc: Record<string, unknown> = {};\n\n evaluate(filter: MongoFilterExpr, doc: Record<string, unknown>): boolean {\n this.doc = doc;\n return filter.accept(this);\n }\n\n field(expr: MongoFieldFilter): boolean {\n const value = getNestedField(this.doc, expr.field);\n return evaluateFieldOp(expr.op, value, expr.value);\n }\n\n and(expr: MongoAndExpr): boolean {\n return expr.exprs.every((child) => child.accept(this));\n }\n\n or(expr: MongoOrExpr): boolean {\n return expr.exprs.some((child) => child.accept(this));\n }\n\n not(expr: MongoNotExpr): boolean {\n return !expr.expr.accept(this);\n }\n\n exists(expr: MongoExistsExpr): boolean {\n const has = getNestedField(this.doc, expr.field) !== undefined;\n return expr.exists ? has : !has;\n }\n\n expr(_expr: MongoExprFilter): boolean {\n throw new Error('Aggregation expression filters are not supported in migration checks');\n }\n}\n","import type { TargetBoundComponentDescriptor } from '@prisma-next/framework-components/components';\nimport type {\n ControlDriverInstance,\n MigrationOperationPolicy,\n MigrationPlan,\n MigrationPlanOperation,\n MigrationRunner,\n MigrationRunnerExecutionChecks,\n MigrationRunnerFailure,\n MigrationRunnerResult,\n} from '@prisma-next/framework-components/control';\nimport type {\n MongoMigrationCheck,\n MongoMigrationPlanOperation,\n} from '@prisma-next/mongo-query-ast/control';\nimport {\n initMarker,\n readMarker,\n updateMarker,\n writeLedgerEntry,\n} from '@prisma-next/target-mongo/control';\nimport { notOk, ok } from '@prisma-next/utils/result';\nimport type { Db } from 'mongodb';\nimport { MongoCommandExecutor, MongoInspectionExecutor } from './command-executor';\nimport { FilterEvaluator } from './filter-evaluator';\nimport type { MongoControlDriverInstance } from './mongo-control-driver';\nimport { deserializeMongoOps } from './mongo-ops-serializer';\n\nfunction runnerFailure(\n code: string,\n summary: string,\n opts?: { why?: string; meta?: Record<string, unknown> },\n): MigrationRunnerResult {\n return notOk<MigrationRunnerFailure>({\n code,\n summary,\n ...opts,\n });\n}\n\nfunction isMongoControlDriverInstance(\n driver: ControlDriverInstance<'mongo', 'mongo'>,\n): driver is MongoControlDriverInstance {\n return 'db' in driver && driver.db != null;\n}\n\nfunction extractDb(driver: ControlDriverInstance<'mongo', 'mongo'>): Db {\n if (!isMongoControlDriverInstance(driver)) {\n throw new Error(\n 'Mongo control driver does not expose a db property. ' +\n 'Use mongoControlDriver.create() from `@prisma-next/driver-mongo/control`.',\n );\n }\n return driver.db;\n}\n\nexport class MongoMigrationRunner implements MigrationRunner<'mongo', 'mongo'> {\n async execute(options: {\n readonly plan: MigrationPlan;\n readonly driver: ControlDriverInstance<'mongo', 'mongo'>;\n readonly destinationContract: unknown;\n readonly policy: MigrationOperationPolicy;\n readonly callbacks?: {\n onOperationStart?(op: MigrationPlanOperation): void;\n onOperationComplete?(op: MigrationPlanOperation): void;\n };\n readonly executionChecks?: MigrationRunnerExecutionChecks;\n readonly frameworkComponents: ReadonlyArray<TargetBoundComponentDescriptor<'mongo', 'mongo'>>;\n }): Promise<MigrationRunnerResult> {\n const db = extractDb(options.driver);\n const operations = deserializeMongoOps(options.plan.operations as readonly unknown[]);\n\n const policyCheck = this.enforcePolicyCompatibility(options.policy, operations);\n if (policyCheck) return policyCheck;\n\n const existingMarker = await readMarker(db);\n\n const markerCheck = this.ensureMarkerCompatibility(existingMarker, options.plan);\n if (markerCheck) return markerCheck;\n\n const checks = options.executionChecks;\n const runPrechecks = checks?.prechecks !== false;\n const runPostchecks = checks?.postchecks !== false;\n const runIdempotency = checks?.idempotencyChecks !== false;\n\n const commandExecutor = new MongoCommandExecutor(db);\n const inspectionExecutor = new MongoInspectionExecutor(db);\n const filterEvaluator = new FilterEvaluator();\n\n let operationsExecuted = 0;\n\n for (const operation of operations) {\n options.callbacks?.onOperationStart?.(operation);\n try {\n if (runPostchecks && runIdempotency) {\n const allSatisfied = await this.allChecksSatisfied(\n operation.postcheck,\n inspectionExecutor,\n filterEvaluator,\n );\n if (allSatisfied) continue;\n }\n\n if (runPrechecks) {\n const precheckResult = await this.evaluateChecks(\n operation.precheck,\n inspectionExecutor,\n filterEvaluator,\n );\n if (!precheckResult) {\n return runnerFailure(\n 'PRECHECK_FAILED',\n `Operation ${operation.id} failed during precheck`,\n { meta: { operationId: operation.id } },\n );\n }\n }\n\n for (const step of operation.execute) {\n await step.command.accept(commandExecutor);\n }\n\n if (runPostchecks) {\n const postcheckResult = await this.evaluateChecks(\n operation.postcheck,\n inspectionExecutor,\n filterEvaluator,\n );\n if (!postcheckResult) {\n return runnerFailure(\n 'POSTCHECK_FAILED',\n `Operation ${operation.id} failed during postcheck`,\n { meta: { operationId: operation.id } },\n );\n }\n }\n\n operationsExecuted += 1;\n } finally {\n options.callbacks?.onOperationComplete?.(operation);\n }\n }\n\n const destination = options.plan.destination;\n const contract = options.destinationContract as { profileHash?: string };\n const profileHash = contract.profileHash ?? destination.storageHash;\n\n if (\n operationsExecuted === 0 &&\n existingMarker?.storageHash === destination.storageHash &&\n existingMarker.profileHash === profileHash\n ) {\n return ok({ operationsPlanned: operations.length, operationsExecuted });\n }\n\n if (existingMarker) {\n const updated = await updateMarker(db, existingMarker.storageHash, {\n storageHash: destination.storageHash,\n profileHash,\n });\n if (!updated) {\n return runnerFailure(\n 'MARKER_CAS_FAILURE',\n 'Marker was modified by another process during migration execution.',\n {\n meta: {\n expectedStorageHash: existingMarker.storageHash,\n destinationStorageHash: destination.storageHash,\n },\n },\n );\n }\n } else {\n await initMarker(db, {\n storageHash: destination.storageHash,\n profileHash,\n });\n }\n\n const originHash = existingMarker?.storageHash ?? '';\n await writeLedgerEntry(db, {\n edgeId: `${originHash}->${destination.storageHash}`,\n from: originHash,\n to: destination.storageHash,\n });\n\n return ok({ operationsPlanned: operations.length, operationsExecuted });\n }\n\n private async evaluateChecks(\n checks: readonly MongoMigrationCheck[],\n inspectionExecutor: MongoInspectionExecutor,\n filterEvaluator: FilterEvaluator,\n ): Promise<boolean> {\n for (const check of checks) {\n const documents = await check.source.accept(inspectionExecutor);\n const matchFound = documents.some((doc) =>\n filterEvaluator.evaluate(check.filter, doc as Record<string, unknown>),\n );\n const passed = check.expect === 'exists' ? matchFound : !matchFound;\n if (!passed) return false;\n }\n return true;\n }\n\n private async allChecksSatisfied(\n checks: readonly MongoMigrationCheck[],\n inspectionExecutor: MongoInspectionExecutor,\n filterEvaluator: FilterEvaluator,\n ): Promise<boolean> {\n if (checks.length === 0) return false;\n return this.evaluateChecks(checks, inspectionExecutor, filterEvaluator);\n }\n\n private enforcePolicyCompatibility(\n policy: MigrationOperationPolicy,\n operations: readonly MongoMigrationPlanOperation[],\n ): MigrationRunnerResult | undefined {\n const allowedClasses = new Set(policy.allowedOperationClasses);\n for (const operation of operations) {\n if (!allowedClasses.has(operation.operationClass)) {\n return runnerFailure(\n 'POLICY_VIOLATION',\n `Operation ${operation.id} has class \"${operation.operationClass}\" which is not allowed by policy.`,\n {\n why: `Policy only allows: ${[...allowedClasses].join(', ')}.`,\n meta: {\n operationId: operation.id,\n operationClass: operation.operationClass,\n },\n },\n );\n }\n }\n return undefined;\n }\n\n private ensureMarkerCompatibility(\n marker: Awaited<ReturnType<typeof readMarker>>,\n plan: MigrationPlan,\n ): MigrationRunnerResult | undefined {\n const origin = plan.origin ?? null;\n if (!origin) {\n if (marker) {\n return runnerFailure(\n 'MARKER_ORIGIN_MISMATCH',\n 'Database already has a contract marker but the plan has no origin. This would silently overwrite the existing marker.',\n { meta: { markerStorageHash: marker.storageHash } },\n );\n }\n return undefined;\n }\n\n if (!marker) {\n return runnerFailure(\n 'MARKER_ORIGIN_MISMATCH',\n `Missing contract marker: expected origin storage hash ${origin.storageHash}.`,\n { meta: { expectedOriginStorageHash: origin.storageHash } },\n );\n }\n\n if (marker.storageHash !== origin.storageHash) {\n return runnerFailure(\n 'MARKER_ORIGIN_MISMATCH',\n `Existing contract marker (${marker.storageHash}) does not match plan origin (${origin.storageHash}).`,\n {\n meta: {\n markerStorageHash: marker.storageHash,\n expectedOriginStorageHash: origin.storageHash,\n },\n },\n );\n }\n\n return undefined;\n }\n}\n","import type { ControlAdapterDescriptor } from '@prisma-next/framework-components/control';\n\nexport {\n initMarker,\n readMarker,\n updateMarker,\n writeLedgerEntry,\n} from '@prisma-next/target-mongo/control';\nexport { MongoCommandExecutor, MongoInspectionExecutor } from '../core/command-executor';\nexport { contractToMongoSchemaIR } from '../core/contract-to-schema';\nexport { formatMongoOperations } from '../core/ddl-formatter';\nexport { introspectSchema } from '../core/introspect-schema';\nexport {\n createMongoControlDriver,\n type MongoControlDriverInstance,\n} from '../core/mongo-control-driver';\nexport { deserializeMongoOps, serializeMongoOps } from '../core/mongo-ops-serializer';\nexport { MongoMigrationPlanner } from '../core/mongo-planner';\nexport { MongoMigrationRunner } from '../core/mongo-runner';\n\nimport {\n mongoBooleanCodec,\n mongoDateCodec,\n mongoDoubleCodec,\n mongoInt32Codec,\n mongoObjectIdCodec,\n mongoStringCodec,\n mongoVectorCodec,\n} from '../core/codecs';\n\nconst mongoAdapterDescriptor: ControlAdapterDescriptor<'mongo', 'mongo'> = {\n kind: 'adapter',\n id: 'mongo',\n familyId: 'mongo',\n targetId: 'mongo',\n version: '0.0.1',\n types: {\n codecTypes: {\n codecInstances: [\n mongoObjectIdCodec,\n mongoStringCodec,\n mongoDoubleCodec,\n mongoInt32Codec,\n mongoBooleanCodec,\n mongoDateCodec,\n mongoVectorCodec,\n ],\n import: {\n package: '@prisma-next/adapter-mongo/codec-types',\n named: 'CodecTypes',\n alias: 'MongoCodecTypes',\n },\n typeImports: [\n {\n package: '@prisma-next/adapter-mongo/codec-types',\n named: 'Vector',\n alias: 'Vector',\n },\n ],\n },\n },\n create() {\n return { familyId: 'mongo' as const, targetId: 'mongo' as const };\n },\n};\n\nexport default mongoAdapterDescriptor;\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"control.mjs","names":["db: Db","keySpec: Document","options: Record<string, unknown>","command: Record<string, unknown>","error: unknown","keys: MongoIndexKey[]","collections: MongoSchemaCollection[]","#client","mongoAdapterDescriptor: ControlAdapterDescriptor<'mongo', 'mongo'>"],"sources":["../src/core/command-executor.ts","../src/core/introspect-schema.ts","../src/core/mongo-control-driver.ts","../src/core/runner-deps.ts","../src/exports/control.ts"],"sourcesContent":["import type {\n CollModCommand,\n CreateCollectionCommand,\n CreateIndexCommand,\n DropCollectionCommand,\n DropIndexCommand,\n ListCollectionsCommand,\n ListIndexesCommand,\n MongoDdlCommandVisitor,\n MongoInspectionCommandVisitor,\n} from '@prisma-next/mongo-query-ast/control';\nimport { keysToKeySpec } from '@prisma-next/mongo-query-ast/control';\nimport { type Db, type Document, MongoServerError } from 'mongodb';\n\nexport class MongoCommandExecutor implements MongoDdlCommandVisitor<Promise<void>> {\n constructor(private readonly db: Db) {}\n\n async createIndex(cmd: CreateIndexCommand): Promise<void> {\n const keySpec: Document = keysToKeySpec(cmd.keys);\n const options: Record<string, unknown> = {};\n if (cmd.unique !== undefined) options['unique'] = cmd.unique;\n if (cmd.sparse !== undefined) options['sparse'] = cmd.sparse;\n if (cmd.expireAfterSeconds !== undefined)\n options['expireAfterSeconds'] = cmd.expireAfterSeconds;\n if (cmd.partialFilterExpression !== undefined)\n options['partialFilterExpression'] = cmd.partialFilterExpression;\n if (cmd.name !== undefined) options['name'] = cmd.name;\n if (cmd.wildcardProjection !== undefined)\n options['wildcardProjection'] = cmd.wildcardProjection;\n if (cmd.collation !== undefined) options['collation'] = cmd.collation;\n if (cmd.weights !== undefined) options['weights'] = cmd.weights;\n if (cmd.default_language !== undefined) options['default_language'] = cmd.default_language;\n if (cmd.language_override !== undefined) options['language_override'] = cmd.language_override;\n await this.db.collection(cmd.collection).createIndex(keySpec, options);\n }\n\n async dropIndex(cmd: DropIndexCommand): Promise<void> {\n await this.db.collection(cmd.collection).dropIndex(cmd.name);\n }\n\n async createCollection(cmd: CreateCollectionCommand): Promise<void> {\n const options: Record<string, unknown> = {};\n if (cmd.capped !== undefined) options['capped'] = cmd.capped;\n if (cmd.size !== undefined) options['size'] = cmd.size;\n if (cmd.max !== undefined) options['max'] = cmd.max;\n if (cmd.timeseries !== undefined) options['timeseries'] = cmd.timeseries;\n if (cmd.collation !== undefined) options['collation'] = cmd.collation;\n if (cmd.clusteredIndex !== undefined) options['clusteredIndex'] = cmd.clusteredIndex;\n if (cmd.validator !== undefined) options['validator'] = cmd.validator;\n if (cmd.validationLevel !== undefined) options['validationLevel'] = cmd.validationLevel;\n if (cmd.validationAction !== undefined) options['validationAction'] = cmd.validationAction;\n if (cmd.changeStreamPreAndPostImages !== undefined)\n options['changeStreamPreAndPostImages'] = cmd.changeStreamPreAndPostImages;\n await this.db.createCollection(cmd.collection, options);\n }\n\n async dropCollection(cmd: DropCollectionCommand): Promise<void> {\n await this.db.collection(cmd.collection).drop();\n }\n\n async collMod(cmd: CollModCommand): Promise<void> {\n const command: Record<string, unknown> = { collMod: cmd.collection };\n if (cmd.validator !== undefined) command['validator'] = cmd.validator;\n if (cmd.validationLevel !== undefined) command['validationLevel'] = cmd.validationLevel;\n if (cmd.validationAction !== undefined) command['validationAction'] = cmd.validationAction;\n if (cmd.changeStreamPreAndPostImages !== undefined)\n command['changeStreamPreAndPostImages'] = cmd.changeStreamPreAndPostImages;\n await this.db.command(command);\n }\n}\n\nexport class MongoInspectionExecutor implements MongoInspectionCommandVisitor<Promise<Document[]>> {\n constructor(private readonly db: Db) {}\n\n async listIndexes(cmd: ListIndexesCommand): Promise<Document[]> {\n try {\n return await this.db.collection(cmd.collection).listIndexes().toArray();\n } catch (error: unknown) {\n if (error instanceof MongoServerError && error.code === 26) {\n return [];\n }\n throw error;\n }\n }\n\n async listCollections(_cmd: ListCollectionsCommand): Promise<Document[]> {\n return this.db.listCollections().toArray();\n }\n}\n","import type { MongoIndexKey, MongoIndexKeyDirection } from '@prisma-next/mongo-contract';\nimport {\n MongoSchemaCollection,\n MongoSchemaCollectionOptions,\n MongoSchemaIndex,\n MongoSchemaIR,\n MongoSchemaValidator,\n} from '@prisma-next/mongo-schema-ir';\nimport type { Db, Document } from 'mongodb';\n\nconst PRISMA_MIGRATIONS_COLLECTION = '_prisma_migrations';\n\nfunction parseIndexKeys(keySpec: Record<string, unknown>): MongoIndexKey[] {\n const keys: MongoIndexKey[] = [];\n for (const [field, direction] of Object.entries(keySpec)) {\n keys.push({ field, direction: direction as MongoIndexKeyDirection });\n }\n return keys;\n}\n\nfunction isDefaultIdIndex(doc: Document): boolean {\n const key = doc['key'] as Record<string, unknown> | undefined;\n if (!key) return false;\n const entries = Object.entries(key);\n return entries.length === 1 && entries[0]?.[0] === '_id' && entries[0]?.[1] === 1;\n}\n\nfunction parseIndex(doc: Document): MongoSchemaIndex {\n const keySpec = doc['key'] as Record<string, unknown>;\n return new MongoSchemaIndex({\n keys: parseIndexKeys(keySpec),\n unique: doc['unique'] as boolean | undefined,\n sparse: doc['sparse'] as boolean | undefined,\n expireAfterSeconds: doc['expireAfterSeconds'] as number | undefined,\n partialFilterExpression: doc['partialFilterExpression'] as Record<string, unknown> | undefined,\n wildcardProjection: doc['wildcardProjection'] as Record<string, 0 | 1> | undefined,\n collation: doc['collation'] as Record<string, unknown> | undefined,\n weights: doc['weights'] as Record<string, number> | undefined,\n default_language: doc['default_language'] as string | undefined,\n language_override: doc['language_override'] as string | undefined,\n });\n}\n\nfunction parseValidator(options: Document): MongoSchemaValidator | undefined {\n const validator = options['validator'] as Record<string, unknown> | undefined;\n if (!validator) return undefined;\n\n const jsonSchema = validator['$jsonSchema'] as Record<string, unknown> | undefined;\n if (!jsonSchema) return undefined;\n\n return new MongoSchemaValidator({\n jsonSchema,\n validationLevel: (options['validationLevel'] as 'strict' | 'moderate') ?? 'strict',\n validationAction: (options['validationAction'] as 'error' | 'warn') ?? 'error',\n });\n}\n\nfunction parseCollectionOptions(info: Document): MongoSchemaCollectionOptions | undefined {\n const options = info['options'] as Record<string, unknown> | undefined;\n if (!options) return undefined;\n\n const capped = options['capped'] as boolean | undefined;\n const size = options['size'] as number | undefined;\n const max = options['max'] as number | undefined;\n const timeseries = options['timeseries'] as\n | { timeField: string; metaField?: string; granularity?: 'seconds' | 'minutes' | 'hours' }\n | undefined;\n const collation = options['collation'] as Record<string, unknown> | undefined;\n const changeStreamPreAndPostImages = options['changeStreamPreAndPostImages'] as\n | { enabled: boolean }\n | undefined;\n const clusteredIndex = options['clusteredIndex'] as { name?: string } | undefined;\n\n const hasMeaningfulOptions =\n capped || timeseries || collation || changeStreamPreAndPostImages || clusteredIndex;\n if (!hasMeaningfulOptions) return undefined;\n\n return new MongoSchemaCollectionOptions({\n ...(capped ? { capped: { size: size ?? 0, ...(max != null ? { max } : {}) } } : {}),\n ...(timeseries ? { timeseries } : {}),\n ...(collation ? { collation } : {}),\n ...(changeStreamPreAndPostImages ? { changeStreamPreAndPostImages } : {}),\n ...(clusteredIndex ? { clusteredIndex } : {}),\n });\n}\n\nexport async function introspectSchema(db: Db): Promise<MongoSchemaIR> {\n const collectionInfos = await db.listCollections().toArray();\n\n const collections: MongoSchemaCollection[] = [];\n\n for (const info of collectionInfos) {\n const name = info['name'] as string;\n const type = info['type'] as string | undefined;\n\n if (name === PRISMA_MIGRATIONS_COLLECTION) continue;\n if (name.startsWith('system.')) continue;\n if (type === 'view') continue;\n\n const indexDocs = await db.collection(name).listIndexes().toArray();\n const indexes = indexDocs.filter((doc) => !isDefaultIdIndex(doc)).map(parseIndex);\n\n const infoOptions = 'options' in info ? (info['options'] as Record<string, unknown>) : {};\n const validator = parseValidator(infoOptions);\n const options = parseCollectionOptions(info);\n\n collections.push(\n new MongoSchemaCollection({\n name,\n indexes,\n ...(validator ? { validator } : {}),\n ...(options ? { options } : {}),\n }),\n );\n }\n\n return new MongoSchemaIR(collections);\n}\n","import type { ControlDriverInstance } from '@prisma-next/framework-components/control';\nimport type { Db, MongoClient } from 'mongodb';\n\nexport interface MongoControlDriverInstance extends ControlDriverInstance<'mongo', 'mongo'> {\n readonly db: Db;\n}\n\nclass MongoControlDriverImpl implements MongoControlDriverInstance {\n readonly familyId = 'mongo' as const;\n readonly targetId = 'mongo' as const;\n readonly db: Db;\n readonly #client: MongoClient;\n\n constructor(db: Db, client: MongoClient) {\n this.db = db;\n this.#client = client;\n }\n\n query(): Promise<never> {\n throw new Error('MongoDB control driver does not support SQL queries');\n }\n\n async close(): Promise<void> {\n await this.#client.close();\n }\n}\n\nexport function createMongoControlDriver(db: Db, client: MongoClient): MongoControlDriverInstance {\n return new MongoControlDriverImpl(db, client);\n}\n","import type { ControlDriverInstance } from '@prisma-next/framework-components/control';\nimport {\n initMarker,\n type MongoRunnerDependencies,\n readMarker,\n updateMarker,\n writeLedgerEntry,\n} from '@prisma-next/target-mongo/control';\nimport type { Db } from 'mongodb';\nimport { MongoCommandExecutor, MongoInspectionExecutor } from './command-executor';\n\nfunction extractDb(driver: ControlDriverInstance<'mongo', 'mongo'>): Db {\n const mongoDriver = driver as ControlDriverInstance<'mongo', 'mongo'> & { db?: Db };\n if (!mongoDriver.db) {\n throw new Error(\n 'Mongo control driver does not expose a db property. ' +\n 'Use mongoControlDriver.create() from `@prisma-next/driver-mongo/control`.',\n );\n }\n return mongoDriver.db;\n}\n\nexport function createMongoRunnerDeps(\n driver: ControlDriverInstance<'mongo', 'mongo'>,\n): MongoRunnerDependencies {\n const db = extractDb(driver);\n return {\n commandExecutor: new MongoCommandExecutor(db),\n inspectionExecutor: new MongoInspectionExecutor(db),\n markerOps: {\n readMarker: () => readMarker(db),\n initMarker: (dest) => initMarker(db, dest),\n updateMarker: (expectedFrom, dest) => updateMarker(db, expectedFrom, dest),\n writeLedgerEntry: (entry) => writeLedgerEntry(db, entry),\n },\n };\n}\n","import type { ControlAdapterDescriptor } from '@prisma-next/framework-components/control';\n\nexport { MongoCommandExecutor, MongoInspectionExecutor } from '../core/command-executor';\nexport { introspectSchema } from '../core/introspect-schema';\nexport {\n createMongoControlDriver,\n type MongoControlDriverInstance,\n} from '../core/mongo-control-driver';\nexport { createMongoRunnerDeps } from '../core/runner-deps';\n\nimport {\n mongoBooleanCodec,\n mongoDateCodec,\n mongoDoubleCodec,\n mongoInt32Codec,\n mongoObjectIdCodec,\n mongoStringCodec,\n mongoVectorCodec,\n} from '../core/codecs';\n\nconst mongoAdapterDescriptor: ControlAdapterDescriptor<'mongo', 'mongo'> = {\n kind: 'adapter',\n id: 'mongo',\n familyId: 'mongo',\n targetId: 'mongo',\n version: '0.0.1',\n scalarTypeDescriptors: new Map([\n ['String', 'mongo/string@1'],\n ['Int', 'mongo/int32@1'],\n ['Boolean', 'mongo/bool@1'],\n ['DateTime', 'mongo/date@1'],\n ['ObjectId', 'mongo/objectId@1'],\n ['Float', 'mongo/double@1'],\n ]),\n types: {\n codecTypes: {\n codecInstances: [\n mongoObjectIdCodec,\n mongoStringCodec,\n mongoDoubleCodec,\n mongoInt32Codec,\n mongoBooleanCodec,\n mongoDateCodec,\n mongoVectorCodec,\n ],\n import: {\n package: '@prisma-next/adapter-mongo/codec-types',\n named: 'CodecTypes',\n alias: 'MongoCodecTypes',\n },\n typeImports: [\n {\n package: '@prisma-next/adapter-mongo/codec-types',\n named: 'Vector',\n alias: 'Vector',\n },\n ],\n },\n },\n create() {\n return { familyId: 'mongo' as const, targetId: 'mongo' as const };\n },\n};\n\nexport default mongoAdapterDescriptor;\n"],"mappings":"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"}
|
package/dist/index.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { a as mongoObjectIdCodec, c as MONGO_INT32_CODEC_ID, i as mongoInt32Codec, l as MONGO_VECTOR_CODEC_ID, n as mongoDateCodec, o as mongoStringCodec, r as mongoDoubleCodec, s as mongoVectorCodec, t as mongoBooleanCodec } from "./codecs-
|
|
1
|
+
import { a as mongoObjectIdCodec, c as MONGO_INT32_CODEC_ID, i as mongoInt32Codec, l as MONGO_VECTOR_CODEC_ID, n as mongoDateCodec, o as mongoStringCodec, r as mongoDoubleCodec, s as mongoVectorCodec, t as mongoBooleanCodec } from "./codecs-DGN3pWRt.mjs";
|
|
2
2
|
import { isExprArray, isRecordArgs } from "@prisma-next/mongo-query-ast/execution";
|
|
3
3
|
import { MongoParamRef } from "@prisma-next/mongo-value";
|
|
4
4
|
import { createMongoCodecRegistry } from "@prisma-next/mongo-codec";
|
package/package.json
CHANGED
|
@@ -1,25 +1,25 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@prisma-next/adapter-mongo",
|
|
3
|
-
"version": "0.4.0-dev.
|
|
3
|
+
"version": "0.4.0-dev.3",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"sideEffects": false,
|
|
6
6
|
"description": "MongoDB adapter for Prisma Next (lowers commands to wire format)",
|
|
7
7
|
"dependencies": {
|
|
8
8
|
"arktype": "^2.1.29",
|
|
9
9
|
"mongodb": "^6.16.0",
|
|
10
|
-
"@prisma-next/config": "0.4.0-dev.
|
|
11
|
-
"@prisma-next/
|
|
12
|
-
"@prisma-next/
|
|
13
|
-
"@prisma-next/framework-components": "0.4.0-dev.
|
|
14
|
-
"@prisma-next/mongo-codec": "0.4.0-dev.
|
|
15
|
-
"@prisma-next/mongo-contract": "0.4.0-dev.
|
|
16
|
-
"@prisma-next/mongo-
|
|
17
|
-
"@prisma-next/mongo-
|
|
18
|
-
"@prisma-next/mongo-
|
|
19
|
-
"@prisma-next/mongo-
|
|
20
|
-
"@prisma-next/mongo-
|
|
21
|
-
"@prisma-next/operations": "0.4.0-dev.
|
|
22
|
-
"@prisma-next/utils": "0.4.0-dev.
|
|
10
|
+
"@prisma-next/config": "0.4.0-dev.3",
|
|
11
|
+
"@prisma-next/contract": "0.4.0-dev.3",
|
|
12
|
+
"@prisma-next/target-mongo": "0.4.0-dev.3",
|
|
13
|
+
"@prisma-next/framework-components": "0.4.0-dev.3",
|
|
14
|
+
"@prisma-next/mongo-codec": "0.4.0-dev.3",
|
|
15
|
+
"@prisma-next/mongo-contract": "0.4.0-dev.3",
|
|
16
|
+
"@prisma-next/mongo-lowering": "0.4.0-dev.3",
|
|
17
|
+
"@prisma-next/mongo-query-ast": "0.4.0-dev.3",
|
|
18
|
+
"@prisma-next/mongo-schema-ir": "0.4.0-dev.3",
|
|
19
|
+
"@prisma-next/mongo-wire": "0.4.0-dev.3",
|
|
20
|
+
"@prisma-next/mongo-value": "0.4.0-dev.3",
|
|
21
|
+
"@prisma-next/operations": "0.4.0-dev.3",
|
|
22
|
+
"@prisma-next/utils": "0.4.0-dev.3"
|
|
23
23
|
},
|
|
24
24
|
"devDependencies": {
|
|
25
25
|
"mongodb-memory-server": "10.4.3",
|
package/src/core/codecs.ts
CHANGED
|
@@ -28,7 +28,7 @@ export const mongoStringCodec = mongoCodec({
|
|
|
28
28
|
|
|
29
29
|
export const mongoDoubleCodec = mongoCodec({
|
|
30
30
|
typeId: MONGO_DOUBLE_CODEC_ID,
|
|
31
|
-
targetTypes: ['
|
|
31
|
+
targetTypes: ['double'],
|
|
32
32
|
traits: ['equality', 'order', 'numeric'],
|
|
33
33
|
decode: (wire: number) => wire,
|
|
34
34
|
encode: (value: number) => value,
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
import type { ControlDriverInstance } from '@prisma-next/framework-components/control';
|
|
2
|
+
import {
|
|
3
|
+
initMarker,
|
|
4
|
+
type MongoRunnerDependencies,
|
|
5
|
+
readMarker,
|
|
6
|
+
updateMarker,
|
|
7
|
+
writeLedgerEntry,
|
|
8
|
+
} from '@prisma-next/target-mongo/control';
|
|
9
|
+
import type { Db } from 'mongodb';
|
|
10
|
+
import { MongoCommandExecutor, MongoInspectionExecutor } from './command-executor';
|
|
11
|
+
|
|
12
|
+
function extractDb(driver: ControlDriverInstance<'mongo', 'mongo'>): Db {
|
|
13
|
+
const mongoDriver = driver as ControlDriverInstance<'mongo', 'mongo'> & { db?: Db };
|
|
14
|
+
if (!mongoDriver.db) {
|
|
15
|
+
throw new Error(
|
|
16
|
+
'Mongo control driver does not expose a db property. ' +
|
|
17
|
+
'Use mongoControlDriver.create() from `@prisma-next/driver-mongo/control`.',
|
|
18
|
+
);
|
|
19
|
+
}
|
|
20
|
+
return mongoDriver.db;
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
export function createMongoRunnerDeps(
|
|
24
|
+
driver: ControlDriverInstance<'mongo', 'mongo'>,
|
|
25
|
+
): MongoRunnerDependencies {
|
|
26
|
+
const db = extractDb(driver);
|
|
27
|
+
return {
|
|
28
|
+
commandExecutor: new MongoCommandExecutor(db),
|
|
29
|
+
inspectionExecutor: new MongoInspectionExecutor(db),
|
|
30
|
+
markerOps: {
|
|
31
|
+
readMarker: () => readMarker(db),
|
|
32
|
+
initMarker: (dest) => initMarker(db, dest),
|
|
33
|
+
updateMarker: (expectedFrom, dest) => updateMarker(db, expectedFrom, dest),
|
|
34
|
+
writeLedgerEntry: (entry) => writeLedgerEntry(db, entry),
|
|
35
|
+
},
|
|
36
|
+
};
|
|
37
|
+
}
|
package/src/exports/control.ts
CHANGED
|
@@ -1,22 +1,12 @@
|
|
|
1
1
|
import type { ControlAdapterDescriptor } from '@prisma-next/framework-components/control';
|
|
2
2
|
|
|
3
|
-
export {
|
|
4
|
-
initMarker,
|
|
5
|
-
readMarker,
|
|
6
|
-
updateMarker,
|
|
7
|
-
writeLedgerEntry,
|
|
8
|
-
} from '@prisma-next/target-mongo/control';
|
|
9
3
|
export { MongoCommandExecutor, MongoInspectionExecutor } from '../core/command-executor';
|
|
10
|
-
export { contractToMongoSchemaIR } from '../core/contract-to-schema';
|
|
11
|
-
export { formatMongoOperations } from '../core/ddl-formatter';
|
|
12
4
|
export { introspectSchema } from '../core/introspect-schema';
|
|
13
5
|
export {
|
|
14
6
|
createMongoControlDriver,
|
|
15
7
|
type MongoControlDriverInstance,
|
|
16
8
|
} from '../core/mongo-control-driver';
|
|
17
|
-
export {
|
|
18
|
-
export { MongoMigrationPlanner } from '../core/mongo-planner';
|
|
19
|
-
export { MongoMigrationRunner } from '../core/mongo-runner';
|
|
9
|
+
export { createMongoRunnerDeps } from '../core/runner-deps';
|
|
20
10
|
|
|
21
11
|
import {
|
|
22
12
|
mongoBooleanCodec,
|
|
@@ -34,6 +24,14 @@ const mongoAdapterDescriptor: ControlAdapterDescriptor<'mongo', 'mongo'> = {
|
|
|
34
24
|
familyId: 'mongo',
|
|
35
25
|
targetId: 'mongo',
|
|
36
26
|
version: '0.0.1',
|
|
27
|
+
scalarTypeDescriptors: new Map([
|
|
28
|
+
['String', 'mongo/string@1'],
|
|
29
|
+
['Int', 'mongo/int32@1'],
|
|
30
|
+
['Boolean', 'mongo/bool@1'],
|
|
31
|
+
['DateTime', 'mongo/date@1'],
|
|
32
|
+
['ObjectId', 'mongo/objectId@1'],
|
|
33
|
+
['Float', 'mongo/double@1'],
|
|
34
|
+
]),
|
|
37
35
|
types: {
|
|
38
36
|
codecTypes: {
|
|
39
37
|
codecInstances: [
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"codecs-9xSaT_DN.mjs","names":[],"sources":["../src/core/codec-ids.ts","../src/core/codecs.ts"],"sourcesContent":["export const MONGO_OBJECTID_CODEC_ID = 'mongo/objectId@1' as const;\nexport const MONGO_STRING_CODEC_ID = 'mongo/string@1' as const;\nexport const MONGO_DOUBLE_CODEC_ID = 'mongo/double@1' as const;\nexport const MONGO_INT32_CODEC_ID = 'mongo/int32@1' as const;\nexport const MONGO_BOOLEAN_CODEC_ID = 'mongo/bool@1' as const;\nexport const MONGO_DATE_CODEC_ID = 'mongo/date@1' as const;\nexport const MONGO_VECTOR_CODEC_ID = 'mongo/vector@1' as const;\n","import { mongoCodec } from '@prisma-next/mongo-codec';\nimport { ObjectId } from 'mongodb';\nimport {\n MONGO_BOOLEAN_CODEC_ID,\n MONGO_DATE_CODEC_ID,\n MONGO_DOUBLE_CODEC_ID,\n MONGO_INT32_CODEC_ID,\n MONGO_OBJECTID_CODEC_ID,\n MONGO_STRING_CODEC_ID,\n MONGO_VECTOR_CODEC_ID,\n} from './codec-ids';\n\nexport const mongoObjectIdCodec = mongoCodec({\n typeId: MONGO_OBJECTID_CODEC_ID,\n targetTypes: ['objectId'],\n traits: ['equality'],\n decode: (wire: ObjectId) => wire.toHexString(),\n encode: (value: string) => new ObjectId(value),\n});\n\nexport const mongoStringCodec = mongoCodec({\n typeId: MONGO_STRING_CODEC_ID,\n targetTypes: ['string'],\n traits: ['equality', 'order', 'textual'],\n decode: (wire: string) => wire,\n encode: (value: string) => value,\n});\n\nexport const mongoDoubleCodec = mongoCodec({\n typeId: MONGO_DOUBLE_CODEC_ID,\n targetTypes: ['float'],\n traits: ['equality', 'order', 'numeric'],\n decode: (wire: number) => wire,\n encode: (value: number) => value,\n});\n\nexport const mongoInt32Codec = mongoCodec({\n typeId: MONGO_INT32_CODEC_ID,\n targetTypes: ['int'],\n traits: ['equality', 'order', 'numeric'],\n decode: (wire: number) => wire,\n encode: (value: number) => value,\n});\n\nexport const mongoBooleanCodec = mongoCodec({\n typeId: MONGO_BOOLEAN_CODEC_ID,\n targetTypes: ['bool'],\n traits: ['equality', 'boolean'],\n decode: (wire: boolean) => wire,\n encode: (value: boolean) => value,\n});\n\nexport const mongoDateCodec = mongoCodec({\n typeId: MONGO_DATE_CODEC_ID,\n targetTypes: ['date'],\n traits: ['equality', 'order'],\n decode: (wire: Date) => wire,\n encode: (value: Date) => value,\n});\n\nexport const mongoVectorCodec = mongoCodec({\n typeId: MONGO_VECTOR_CODEC_ID,\n targetTypes: ['vector'],\n traits: ['equality'],\n decode: (wire: readonly number[]) => wire,\n encode: (value: readonly number[]) => value,\n renderOutputType: (typeParams) => {\n const length = typeParams['length'];\n if (length === undefined) return undefined;\n if (typeof length !== 'number' || !Number.isFinite(length) || !Number.isInteger(length)) {\n throw new Error('renderOutputType: expected positive integer \"length\" for Vector');\n }\n return `Vector<${length}>`;\n },\n});\n"],"mappings":";;;;AAAA,MAAa,0BAA0B;AACvC,MAAa,wBAAwB;AACrC,MAAa,wBAAwB;AACrC,MAAa,uBAAuB;AACpC,MAAa,yBAAyB;AACtC,MAAa,sBAAsB;AACnC,MAAa,wBAAwB;;;;ACMrC,MAAa,qBAAqB,WAAW;CAC3C,QAAQ;CACR,aAAa,CAAC,WAAW;CACzB,QAAQ,CAAC,WAAW;CACpB,SAAS,SAAmB,KAAK,aAAa;CAC9C,SAAS,UAAkB,IAAI,SAAS,MAAM;CAC/C,CAAC;AAEF,MAAa,mBAAmB,WAAW;CACzC,QAAQ;CACR,aAAa,CAAC,SAAS;CACvB,QAAQ;EAAC;EAAY;EAAS;EAAU;CACxC,SAAS,SAAiB;CAC1B,SAAS,UAAkB;CAC5B,CAAC;AAEF,MAAa,mBAAmB,WAAW;CACzC,QAAQ;CACR,aAAa,CAAC,QAAQ;CACtB,QAAQ;EAAC;EAAY;EAAS;EAAU;CACxC,SAAS,SAAiB;CAC1B,SAAS,UAAkB;CAC5B,CAAC;AAEF,MAAa,kBAAkB,WAAW;CACxC,QAAQ;CACR,aAAa,CAAC,MAAM;CACpB,QAAQ;EAAC;EAAY;EAAS;EAAU;CACxC,SAAS,SAAiB;CAC1B,SAAS,UAAkB;CAC5B,CAAC;AAEF,MAAa,oBAAoB,WAAW;CAC1C,QAAQ;CACR,aAAa,CAAC,OAAO;CACrB,QAAQ,CAAC,YAAY,UAAU;CAC/B,SAAS,SAAkB;CAC3B,SAAS,UAAmB;CAC7B,CAAC;AAEF,MAAa,iBAAiB,WAAW;CACvC,QAAQ;CACR,aAAa,CAAC,OAAO;CACrB,QAAQ,CAAC,YAAY,QAAQ;CAC7B,SAAS,SAAe;CACxB,SAAS,UAAgB;CAC1B,CAAC;AAEF,MAAa,mBAAmB,WAAW;CACzC,QAAQ;CACR,aAAa,CAAC,SAAS;CACvB,QAAQ,CAAC,WAAW;CACpB,SAAS,SAA4B;CACrC,SAAS,UAA6B;CACtC,mBAAmB,eAAe;EAChC,MAAM,SAAS,WAAW;AAC1B,MAAI,WAAW,OAAW,QAAO;AACjC,MAAI,OAAO,WAAW,YAAY,CAAC,OAAO,SAAS,OAAO,IAAI,CAAC,OAAO,UAAU,OAAO,CACrF,OAAM,IAAI,MAAM,oEAAkE;AAEpF,SAAO,UAAU,OAAO;;CAE3B,CAAC"}
|
|
@@ -1,63 +0,0 @@
|
|
|
1
|
-
import type {
|
|
2
|
-
MongoContract,
|
|
3
|
-
MongoStorageCollection,
|
|
4
|
-
MongoStorageCollectionOptions,
|
|
5
|
-
MongoStorageIndex,
|
|
6
|
-
MongoStorageValidator,
|
|
7
|
-
} from '@prisma-next/mongo-contract';
|
|
8
|
-
import {
|
|
9
|
-
MongoSchemaCollection,
|
|
10
|
-
MongoSchemaCollectionOptions,
|
|
11
|
-
MongoSchemaIndex,
|
|
12
|
-
MongoSchemaIR,
|
|
13
|
-
MongoSchemaValidator,
|
|
14
|
-
} from '@prisma-next/mongo-schema-ir';
|
|
15
|
-
|
|
16
|
-
function convertIndex(index: MongoStorageIndex): MongoSchemaIndex {
|
|
17
|
-
return new MongoSchemaIndex({
|
|
18
|
-
keys: index.keys,
|
|
19
|
-
unique: index.unique,
|
|
20
|
-
sparse: index.sparse,
|
|
21
|
-
expireAfterSeconds: index.expireAfterSeconds,
|
|
22
|
-
partialFilterExpression: index.partialFilterExpression,
|
|
23
|
-
wildcardProjection: index.wildcardProjection,
|
|
24
|
-
collation: index.collation,
|
|
25
|
-
weights: index.weights,
|
|
26
|
-
default_language: index.default_language,
|
|
27
|
-
language_override: index.language_override,
|
|
28
|
-
});
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
function convertValidator(v: MongoStorageValidator): MongoSchemaValidator {
|
|
32
|
-
return new MongoSchemaValidator({
|
|
33
|
-
jsonSchema: v.jsonSchema,
|
|
34
|
-
validationLevel: v.validationLevel,
|
|
35
|
-
validationAction: v.validationAction,
|
|
36
|
-
});
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
function convertOptions(o: MongoStorageCollectionOptions): MongoSchemaCollectionOptions {
|
|
40
|
-
return new MongoSchemaCollectionOptions(o);
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
function convertCollection(name: string, def: MongoStorageCollection): MongoSchemaCollection {
|
|
44
|
-
const indexes = (def.indexes ?? []).map(convertIndex);
|
|
45
|
-
return new MongoSchemaCollection({
|
|
46
|
-
name,
|
|
47
|
-
indexes,
|
|
48
|
-
...(def.validator != null && { validator: convertValidator(def.validator) }),
|
|
49
|
-
...(def.options != null && { options: convertOptions(def.options) }),
|
|
50
|
-
});
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
export function contractToMongoSchemaIR(contract: MongoContract | null): MongoSchemaIR {
|
|
54
|
-
if (!contract) {
|
|
55
|
-
return new MongoSchemaIR([]);
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
const collections = Object.entries(contract.storage.collections).map(([name, def]) =>
|
|
59
|
-
convertCollection(name, def),
|
|
60
|
-
);
|
|
61
|
-
|
|
62
|
-
return new MongoSchemaIR(collections);
|
|
63
|
-
}
|
|
@@ -1,112 +0,0 @@
|
|
|
1
|
-
import type { MigrationPlanOperation } from '@prisma-next/framework-components/control';
|
|
2
|
-
import type {
|
|
3
|
-
CollModCommand,
|
|
4
|
-
CreateCollectionCommand,
|
|
5
|
-
CreateIndexCommand,
|
|
6
|
-
DropCollectionCommand,
|
|
7
|
-
DropIndexCommand,
|
|
8
|
-
MongoDdlCommandVisitor,
|
|
9
|
-
MongoIndexKey,
|
|
10
|
-
} from '@prisma-next/mongo-query-ast/control';
|
|
11
|
-
|
|
12
|
-
function formatKeySpec(keys: ReadonlyArray<MongoIndexKey>): string {
|
|
13
|
-
const entries = keys.map((k) => `${JSON.stringify(k.field)}: ${JSON.stringify(k.direction)}`);
|
|
14
|
-
return `{ ${entries.join(', ')} }`;
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
function formatOptions(cmd: CreateIndexCommand): string | undefined {
|
|
18
|
-
const parts: string[] = [];
|
|
19
|
-
if (cmd.unique) parts.push('unique: true');
|
|
20
|
-
if (cmd.sparse) parts.push('sparse: true');
|
|
21
|
-
if (cmd.expireAfterSeconds !== undefined)
|
|
22
|
-
parts.push(`expireAfterSeconds: ${cmd.expireAfterSeconds}`);
|
|
23
|
-
if (cmd.name) parts.push(`name: ${JSON.stringify(cmd.name)}`);
|
|
24
|
-
if (cmd.collation) parts.push(`collation: ${JSON.stringify(cmd.collation)}`);
|
|
25
|
-
if (cmd.weights) parts.push(`weights: ${JSON.stringify(cmd.weights)}`);
|
|
26
|
-
if (cmd.default_language) parts.push(`default_language: ${JSON.stringify(cmd.default_language)}`);
|
|
27
|
-
if (cmd.language_override)
|
|
28
|
-
parts.push(`language_override: ${JSON.stringify(cmd.language_override)}`);
|
|
29
|
-
if (cmd.wildcardProjection)
|
|
30
|
-
parts.push(`wildcardProjection: ${JSON.stringify(cmd.wildcardProjection)}`);
|
|
31
|
-
if (cmd.partialFilterExpression)
|
|
32
|
-
parts.push(`partialFilterExpression: ${JSON.stringify(cmd.partialFilterExpression)}`);
|
|
33
|
-
if (parts.length === 0) return undefined;
|
|
34
|
-
return `{ ${parts.join(', ')} }`;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
function formatCreateCollectionOptions(cmd: CreateCollectionCommand): string | undefined {
|
|
38
|
-
const parts: string[] = [];
|
|
39
|
-
if (cmd.capped) parts.push('capped: true');
|
|
40
|
-
if (cmd.size !== undefined) parts.push(`size: ${cmd.size}`);
|
|
41
|
-
if (cmd.max !== undefined) parts.push(`max: ${cmd.max}`);
|
|
42
|
-
if (cmd.timeseries) parts.push(`timeseries: ${JSON.stringify(cmd.timeseries)}`);
|
|
43
|
-
if (cmd.collation) parts.push(`collation: ${JSON.stringify(cmd.collation)}`);
|
|
44
|
-
if (cmd.clusteredIndex) parts.push(`clusteredIndex: ${JSON.stringify(cmd.clusteredIndex)}`);
|
|
45
|
-
if (cmd.validator) parts.push(`validator: ${JSON.stringify(cmd.validator)}`);
|
|
46
|
-
if (cmd.validationLevel) parts.push(`validationLevel: ${JSON.stringify(cmd.validationLevel)}`);
|
|
47
|
-
if (cmd.validationAction) parts.push(`validationAction: ${JSON.stringify(cmd.validationAction)}`);
|
|
48
|
-
if (cmd.changeStreamPreAndPostImages)
|
|
49
|
-
parts.push(`changeStreamPreAndPostImages: ${JSON.stringify(cmd.changeStreamPreAndPostImages)}`);
|
|
50
|
-
if (parts.length === 0) return undefined;
|
|
51
|
-
return `{ ${parts.join(', ')} }`;
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
class MongoDdlCommandFormatter implements MongoDdlCommandVisitor<string> {
|
|
55
|
-
createIndex(cmd: CreateIndexCommand): string {
|
|
56
|
-
const keySpec = formatKeySpec(cmd.keys);
|
|
57
|
-
const opts = formatOptions(cmd);
|
|
58
|
-
return opts
|
|
59
|
-
? `db.${cmd.collection}.createIndex(${keySpec}, ${opts})`
|
|
60
|
-
: `db.${cmd.collection}.createIndex(${keySpec})`;
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
dropIndex(cmd: DropIndexCommand): string {
|
|
64
|
-
return `db.${cmd.collection}.dropIndex(${JSON.stringify(cmd.name)})`;
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
createCollection(cmd: CreateCollectionCommand): string {
|
|
68
|
-
const opts = formatCreateCollectionOptions(cmd);
|
|
69
|
-
return opts
|
|
70
|
-
? `db.createCollection(${JSON.stringify(cmd.collection)}, ${opts})`
|
|
71
|
-
: `db.createCollection(${JSON.stringify(cmd.collection)})`;
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
dropCollection(cmd: DropCollectionCommand): string {
|
|
75
|
-
return `db.${cmd.collection}.drop()`;
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
collMod(cmd: CollModCommand): string {
|
|
79
|
-
const parts: string[] = [`collMod: ${JSON.stringify(cmd.collection)}`];
|
|
80
|
-
if (cmd.validator) parts.push(`validator: ${JSON.stringify(cmd.validator)}`);
|
|
81
|
-
if (cmd.validationLevel) parts.push(`validationLevel: ${JSON.stringify(cmd.validationLevel)}`);
|
|
82
|
-
if (cmd.validationAction)
|
|
83
|
-
parts.push(`validationAction: ${JSON.stringify(cmd.validationAction)}`);
|
|
84
|
-
if (cmd.changeStreamPreAndPostImages)
|
|
85
|
-
parts.push(
|
|
86
|
-
`changeStreamPreAndPostImages: ${JSON.stringify(cmd.changeStreamPreAndPostImages)}`,
|
|
87
|
-
);
|
|
88
|
-
return `db.runCommand({ ${parts.join(', ')} })`;
|
|
89
|
-
}
|
|
90
|
-
}
|
|
91
|
-
|
|
92
|
-
const formatter = new MongoDdlCommandFormatter();
|
|
93
|
-
|
|
94
|
-
interface MongoExecuteStep {
|
|
95
|
-
readonly command: { readonly accept: <R>(visitor: MongoDdlCommandVisitor<R>) => R };
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
export function formatMongoOperations(operations: readonly MigrationPlanOperation[]): string[] {
|
|
99
|
-
const statements: string[] = [];
|
|
100
|
-
for (const operation of operations) {
|
|
101
|
-
const candidate = operation as unknown as Record<string, unknown>;
|
|
102
|
-
if (!('execute' in candidate) || !Array.isArray(candidate['execute'])) {
|
|
103
|
-
continue;
|
|
104
|
-
}
|
|
105
|
-
for (const step of candidate['execute'] as MongoExecuteStep[]) {
|
|
106
|
-
if (step.command && typeof step.command.accept === 'function') {
|
|
107
|
-
statements.push(step.command.accept(formatter));
|
|
108
|
-
}
|
|
109
|
-
}
|
|
110
|
-
}
|
|
111
|
-
return statements;
|
|
112
|
-
}
|