Esta sección resume cómo distintas operaciones de inserción y actualización gestionan nombres de campos con el prefijo del signo de dólar ($). MongoDB desaconseja el uso de nombres de campos prefijados con el signo de dólar porque algunas funcionalidades no son compatibles con estos campos. Consulta restricciones generales para obtener más información.
Operaciones de inserción
Los campos con prefijo de dólar ($) están permitidos tanto como nombres de campos de nivel superior como de campos anidados para inserciones.
db.sales.insertOne( { "$price": 50.00, "quantity": 30 } )
Se permite el uso de campos prefijados con el símbolo de dólar ($) en inserciones que utilizan palabras reservadas. Nombres de operadores como $inc se pueden usar como nombres de campos, así como palabras como id, db y ref.
db.books.insertOne( { "$id": "h1961-01", "location": { "$db": "novels", "$ref": "2007042768", "$inc": true } } )
Una actualización que crea un nuevo documento durante una inserción o actualización se trata como un insert en lugar de un update para la validación del nombre del campo. Se pueden aceptar campos con prefijo de dólar ($) en upserts. Sin embargo, los upserts son un caso especial y operaciones de actualización similares pueden causar un error si la parte match de la actualización selecciona un documento existente.
Este código de muestra tiene upsert: true, por lo que insertará un nuevo documento si la colección aún no contiene un documento que coincida con el término de query, { "date": "2021-07-07" }. Si este código de muestra coincide con un documento existente, la operación de actualizar fallará dado que $hotel tiene un prefijo de signo de dólar ($).
db.expenses.updateOne( { "date": "2021-07-07" }, { $set: { "phone": 25.17, "$hotel": 320.10 } }, { upsert: true } )
Actualizaciones de reemplazo de documentos
Los operadores de actualización reemplazan los campos existentes con nuevos documentos o modifican esos campos. En los casos en que la actualización realiza un reemplazo, los nombres de campo de nivel superior con prefijo de dólar ($) no están permitidos.
Considere un documento como
{ "_id": "E123", "address": { "$number": 123, "$street": "Elm Road" }, "$rooms": { "br": 2, "bath": 1 } }
Podrías usar un operador de actualización que reemplace un documento existente para modificar el campo address.$street, pero no podrías actualizar el campo $rooms de esa manera.
db.housing.updateOne( { "_id": "E123" }, { $set: { "address.$street": "Elm Ave" } } )
Utiliza $setField como parte de una pipeline de agregación para actualizar de nivel superior campos con prefijo de dólar ($) como $rooms.
Actualizaciones que modifican documentos
Cuando una actualización modifica, en lugar de sustituir, los campos existentes del documento, los campos con prefijo de dólar ($) pueden ser nombres de campos de nivel superior. Los subcampos se pueden acceder directamente, pero se necesita un método asistente para acceder a los campos de nivel superior.
Considera una colección con documentos como este registro de inventario:
{ _id: ObjectId("610023ad7d58ecda39b8d161"), "part": "AB305", "$bin": 200, "quantity": 100, "pricing": { sale: true, "$discount": 60 } }
El subcampo pricing.$discount puede consultarse directamente.
db.inventory.findAndModify( { query: { "part": { $eq: "AB305" } }, update: { $inc: { "pricing.$discount": 10 } } } )
Utiliza $getField y $literal para acceder al valor del campo de nivel superior $bin.
db.inventory.findAndModify( { query: { $expr: { $eq: [ { $getField: { $literal: "$bin" } }, 200 ] } }, update: { $inc: { "quantity": 10 } } } )
Actualizaciones usando pipelines de agregación
Utiliza $setField, $getField y $literal en la etapa $replaceWith para modificar campos con prefijo de dólar ($) en una pipelinede agregación.
Considera una colección de registros escolares como:
db.school.insertOne ( { "_id": 100001, "$term": "fall", "registered": true, "grade": 4 } )
Cree una nueva colección para el semestre de primavera utilizando una pipeline para actualizar el campo $term con el prefijo dólar ($).
db.school.aggregate( [ { $match: { "registered": true } }, { $replaceWith: { $setField: { field: { $literal: "$term" }, input: "$$ROOT", value: "spring" } } }, { $out: "spring2022" } ] )