Overview
Mediante esta guía, puedes aprender a usar PyMongo para agregar documentos a una colección de MongoDB mediante la realización de operaciones de inserción.
Una operación de inserción inserta uno o más documentos en una colección de MongoDB. Puede realizar una operación de inserción utilizando insert_one() o método insert_many().
Nota
El campo _id debe ser único
En una colección de MongoDB, cada documento debe contener un campo _id con un valor único.
Si se especifica un valor para el campo _id, debe asegurarse de que el valor sea único en la colección. De lo contrario, el controlador genera automáticamente un valor ObjectId único para el campo.
Recomendamos dejar que el controlador genere valores de _id automáticamente para garantizar la unicidad. Los valores duplicados de _id violan restricciones de índice único, lo que provoca que el controlador devuelva un error.
Datos de muestra
Los ejemplos de esta guía utilizan la colección sample_restaurants.restaurants de Conjuntos de datos de muestra de Atlas. Para aprender a crear un clúster gratuito de MongoDB Atlas y cargar los conjuntos de datos de muestra, consulte
Tutorial paraempezar a usar PyMongo.
Inserta un documento
Para añadir un único documento a una colección de MongoDB, llama al método insert_one() y pasa el documento que quieras añadir.
El siguiente ejemplo inserta un documento en la colección restaurants. Seleccione el
Synchronous o pestaña Asynchronous para ver el código correspondiente:
sample_restaurants.restaurants.insert_one({"name" : "Mongo's Burgers"})
await sample_restaurants.restaurants.insert_one({"name" : "Mongo's Burgers"})
También puedes pasar una instancia de una clase personalizada al método insert_one(). Esto proporciona seguridad de tipos adicional si estás utilizando una herramienta de comprobación de tipos. La instancia que apruebes debe heredar de la clase TypedDict .
Nota
TypedDict en Python 3.7 y versiones anteriores
La clase TypedDict se encuentra en el módulo typing, el cual está disponible solo en Python 3.8 y versiones posteriores. Para usar la clase TypedDict en versiones anteriores de Python, instala el paquete typing_extensions.
El siguiente ejemplo pasa una instancia de la clase Restaurant al método insert_one() para aumentar la seguridad de tipos. Selecciona la pestaña Synchronous o Asynchronous para ver el código correspondiente:
class Restaurant(TypedDict): name: str sample_restaurants.restaurants.insert_one(Restaurant(name="Mongo's Burgers"))
class Restaurant(TypedDict): name: str await sample_restaurants.restaurants.insert_one(Restaurant(name="Mongo's Burgers"))
Tip
Herramientas de verificación de tipos
Para aprender más sobre las herramientas de verificación de tipos disponibles para Python, échale un vistazo a Verificadores de tipos en la página de herramientas.
Inserta varios documentos
Para añadir varios documentos a una colección de MongoDB, llama al método insert_many() y pasa una lista de documentos que quieres añadir.
El siguiente ejemplo inserta una lista de documentos en la colección restaurants. Se debe seleccionar la pestaña Synchronous o Asynchronous para ver el código correspondiente:
document_list = [ { "name" : "Mongo's Burgers" }, { "name" : "Mongo's Pizza" } ] sample_restaurants.restaurants.insert_many(document_list)
document_list = [ { "name" : "Mongo's Burgers" }, { "name" : "Mongo's Pizza" } ] await sample_restaurants.restaurants.insert_many(document_list)
También puedes pasar una lista de instancias de una clase personalizada al método insert_many(). Esto proporciona seguridad de tipos adicional si estás utilizando una herramienta de comprobación de tipos. Las instancias que superes deben heredar de la clase TypedDict .
Nota
TypedDict en Python 3.7 y versiones anteriores
La clase TypedDict se encuentra en el módulo typing, el cual está disponible solo en Python 3.8 y versiones posteriores. Para usar la clase TypedDict en versiones anteriores de Python, instala el paquete typing_extensions.
El siguiente ejemplo llama al método insert_many() y pasa una lista que contiene instancias de la clase Restaurant. Esto añade seguridad de tipo a la operación de inserción. Selecciona la pestaña Synchronous o Asynchronous para ver el código correspondiente:
class Restaurant(TypedDict): name: str document_list = [ Restaurant(name="Mongo's Burgers"), Restaurant(name="Mongo's Pizza") ] sample_restaurants.restaurants.insert_many(document_list)
class Restaurant(TypedDict): name: str document_list = [ Restaurant(name="Mongo's Burgers"), Restaurant(name="Mongo's Pizza") ] await sample_restaurants.restaurants.insert_many(document_list)
Tip
Herramientas de verificación de tipos
Para aprender más sobre las herramientas de verificación de tipos disponibles para Python, échale un vistazo a Verificadores de tipos en la página de herramientas.
Modificar el comportamiento de inserción
El método insert_one() opcionalmente acepta parámetros adicionales que representan opciones que puedes usar para configurar la operación de inserción. Si no especificas ningún parámetro adicional, el driver no personaliza la inserción.
Propiedad | Descripción |
|---|---|
| If set to True, allows the write to opt out of
document-level validation.Defaults to False. |
| An instance of ClientSession. |
| A comment to attach to the operation. For more information, see the insert command
fields guide in the
MongoDB Server manual for more information. |
El método insert_many() acepta los parámetros opcionales anteriores, así como la propiedad ordered opcional:
Propiedad | Descripción |
|---|---|
| If set to True, the driver sends documents to the
server in the order provided. If an error occurs, the driver
and server cancel all remaining insert operations.Defaults to True. |
Ejemplo
El siguiente código utiliza el método insert_many() para insertar tres nuevos documentos en una colección. Como el segundo argumento del método es bypass_document_validation = True, esta operación de inserción omite la validación a nivel de documento. Selecciona la pestaña Synchronous o Asynchronous para ver el código correspondiente:
document_list = [ { "name" : "Mongo's Burgers" }, { "name" : "Mongo's Pizza" }, { "name" : "Mongo's Tacos" } ] sample_restaurants.restaurants.insert_many(document_list, bypass_document_validation = True)
document_list = [ { "name" : "Mongo's Burgers" }, { "name" : "Mongo's Pizza" }, { "name" : "Mongo's Tacos" } ] await sample_restaurants.restaurants.insert_many(document_list, bypass_document_validation = True)
Solución de problemas
Anotaciones de tipo de cliente
Si no se agrega una anotación de tipo para el objeto MongoClient, el verificador de tipos podría mostrar un error similar al siguiente:
from pymongo import MongoClient client = MongoClient() # error: Need type annotation for "client"
La solución es anotar el objeto MongoClient como client: MongoClient o client: MongoClient[Dict[str, Any]].
Tipo incompatible
Si especifica MongoClient como una sugerencia de tipo, pero no incluye los tipos de datos para el documento, las claves y los valores, su verificador de tipos podría mostrar un error similar al siguiente:
error: Dict entry 0 has incompatible type "str": "int"; expected "Mapping[str, Any]": "int"
La solución es agregar la siguiente sugerencia de tipo al objeto MongoClient:
client: MongoClient[Dict[str, Any]]
Es posible que veas un error similar si pasas una lista al método insert_one():
error: Argument 1 to "insert_one" of "Collection" has incompatible type "List[Dict[<nothing>, <nothing>]]"; expected "Mapping[str, Any]"
Este error se produce porque el método insert_one() acepta un documento, no una lista. Puedes resolver este error pasando un documento al método insert_one() o llamando al método insert_many() en su lugar.
TypedDict Missing _id Key
Si no especificas el campo _id, PyMongo lo inserta automáticamente en el documento. Puedes recuperar el valor del campo _id en tiempo de ejecución, pero si utilizas MyPy u otra herramienta para realizar la comprobación de tipos estáticos, no encontrará el campo _id de tu clase y mostrará un error similar al siguiente:
TypedDict has no key "_id"
Esto se debe a un código similar al siguiente:
from typing import TypedDict from pymongo import MongoClient from pymongo.collection import Collection class Movie(TypedDict): name: str year: int client: MongoClient = MongoClient() collection: Collection[Movie] = client.test.test inserted = collection.insert_one(Movie(name="Jurassic Park", year=1993)) result = collection.find_one({"name": "Jurassic Park"}) # _id is present but was added by PyMongo; this will raise a type-checking error assert result["_id"]
Una solución es añadir un comentario # type:ignore al final de la línea que utiliza el campo _id. Este comentario indica a la herramienta de verificación de tipos que ignore cualquier error que provoque la línea. El siguiente ejemplo muestra cómo implementar esta solución:
from typing import TypedDict from pymongo import MongoClient from pymongo.collection import Collection class Movie(TypedDict): name: str year: int collection: Collection[Movie] = client.test.test inserted = collection.insert_one( Movie(name="Jurassic Park", year=1993) ) result = collection.find_one({"name": "Jurassic Park"}) assert result is not None assert result["_id"] # type:ignore[typeddict-item]
En vez de ignorar el error de tipo, puedes evitarlo incluyendo el campo _id en tu clase modelo y especificando explícitamente un valor para este campo cuando creas la instancia de clase. El siguiente código muestra cómo implementar esta solución:
from typing import TypedDict from pymongo import MongoClient from pymongo.collection import Collection from bson import ObjectId class Movie(TypedDict): _id: ObjectId name: str year: int collection: Collection[ExplicitMovie] = client.test.test inserted = collection.insert_one( ExplicitMovie(_id=ObjectId(), name="Jurassic Park", year=1993) ) result = collection.find_one({"name": "Jurassic Park"}) assert result is not None assert result["_id"]
Una desventaja de agregar el campo _id a tu clase personalizada es que debes incluir un valor para el campo en cada instancia de la clase que crees. Para evitar esto, puedes instalar el paquete typing.NotRequired, que incluye la sugerencia de tipo NotRequired. Si usas esta sugerencia de tipo para el campo _id, puedes acceder al valor del campo _id en tiempo de ejecución sin ver ningún error de tipo en tiempo de compilación.
El siguiente ejemplo de código muestra cómo implementar esta solución:
from typing import TypedDict, NotRequired from pymongo import MongoClient from pymongo.collection import Collection from bson import ObjectId class Movie(TypedDict): _id: NotRequired[ObjectId] name: str year: int client: MongoClient = MongoClient() collection: Collection[Movie] = client.test.test inserted = collection.insert_one(Movie(name="Jurassic Park", year=1993)) result = collection.find_one({"name": "Jurassic Park"}) assert result is not None assert result["_id"]
Importante
NotRequired Requiere Python 3.11+
La clase NoRequerido está disponible solo en Python 3,11 y posteriores. Para usar NotRequired en versiones anteriores de Python, instala el paquete typing_extensions en su lugar.
Información Adicional
Para obtener ejemplos de código ejecutable de insertar documentos con PyMongo, mira Operaciones CRUD.
Documentación de la API
Para obtener más información sobre cualquiera de los métodos o tipos discutidos en esta guía, consultar la siguiente documentación de la API: