Actualización múltiple en MongoDB

Actualización múltiple en MongoDBSeguimos con un nuevo artículo sobre las operaciones CRUD en MongoDB (Create, Read, Update, Delete). En el anterior artículo sobre cómo actualizar documentos en MongoDB se forzó intencionadamente que sólo hubiese un documento a actualizar. Sin embargo, la realidad es que la mayoría de las veces se va a querer o va a ser necesario actualizar múltipes documentos que cumplan un mismo criterio de búsqueda.

Para realizar esto se debe pasar como último parámetro la cláusula “multi: true” al método update. Por defecto, el valor para indicar una actualización múltiple es false, como medida de seguridad ante posibles descuidos y evitar actualizaciones masivas no deseadas. Al igual que con el update normal, el primer parámetro es el criterio de búsqueda y el segundo las modificaciones o actualizaciones que se desean realizar.

Actualizar documentos de una colección

Para actualizar todos los documentos de una colección sólo se tiene que indicar un documento vacío en el primer parámetro correspondiente al criterio de búsqueda, es decir, no se usa ningún criterio de búsqueda para que absolutamente todos los documentos sean tenidos en cuenta. Esto es muy útil, por ejemplo, para añadir un nuevo campo a todos los documentos de una colección.

Como ya se ha mencionado anteriormente, para indicar que la actualización es múltiple y, por tanto, debe ser realizada en todos y cada uno de los documentos resultantes del filtro de búsqueda se añade un tercer parámetro con el valor “multi: true”. Sino se añade este parámetro se actualizaría solamente el primer documento que encuentre (de forma arbitraria).

Para ver un ejemplo, se va a añadir un campo “title” a todos los documentos de la colección “people” con el valor por defecto “Dr”:

> db.people.update( {}, { $set: { title: "Dr" }}, {multi: true} )
> db.people.find()
{ "_id" : ObjectId("513900c13929ab2874366e50"), "name" : "Julliet", "salary" : 4000, "title" : "Dr" }
{ "_id" : ObjectId("5138ecaa3929ab2874366295"), "age" : 28, "name" : "Jose David", "title" : "Dr" }

Para ver un ejemplo más completo, se va añadir a todos los documentos un nuevo campo “age” con valor por defecto 25, y posteriormente, a todas las personas que tengan 25 años o menos (en este caso todas) se les va a incrementar la edad en 5 años:

> db.people.update( {}, { $set: { age: 25} }, {multi: true} )
> db.people.find()
{ "_id" : ObjectId("5138ecaa3929ab2874366295"), "age" : 25, "name" : "Jose David", "title" : "Dr" }
{ "_id" : ObjectId("513900c13929ab2874366e50"), "age" : 25, "name" : "Julliet", "salary" : 4000, "title" : "Dr" }
> db.people.update( { age: { $lte: 25}}, { $inc: { age: 5 }}, {multi: true} )
> db.people.find()
{ "_id" : ObjectId("5138ecaa3929ab2874366295"), "age" : 30, "name" : "Jose David", "title" : "Dr" }
{ "_id" : ObjectId("513900c13929ab2874366e50"), "age" : 30, "name" : "Julliet", "salary" : 4000, "title" : "Dr" }

Seguridad

Este tipo de actualización en MongoDB difiere totalmente de las actualizaciones en SQL, ya que en este caso, por defecto, se actualizan todos los registros que coincidan con el criterio de busqueda (where) y, por el contrario, en MongoDB se actualiza sólo un documento por defecto. Recalco en este punto la importancia de que el valor por defecto sea false para evitar actualizaciones masivas erróneas derivadas de un descuido.

En los drivers para lenguajes de programación (Java, Python…), la actualización múltiple es separada de la normal, teniendo dos métodos distintos, update y multiUpdate, pero en el shell de MongoDB hay que indicar el tercer parámetro “multi” como se ha visto en el ejemplo.

Concurrencia y rendimiento

Para tolerar actualizaciones en gran cantidad de documentos sin interferir con otras consultas u operaciones concurrentes y no mermar el rendimiento de la base de datos la actualización múltiple se hace de forma secuencial y de forma atómica por documento, separados en hilos distintos de modo que, puede actualizar un determinado número de documentos, dejar paso a otra operación contra la base de datos y continuar actualizando otro grupo de documentos. Básicamente se usa un “mutex lock“.

Esto es muy importante de cara a la concurrencia por lo que hay que controlar en nuestra aplicación que estos cambios sean totalmente visibles antes de querer usarlos con otras operaciones de lectura o escritura. En resumen, la actualización de un documento es atómica y segura pero no lo es la operación en sí de actualizar todos los documentos.

 Conclusión

La actualización múltiple es una herramienta de gran valor en cualquier base de datos, ya sea NoSQL o SQL, y será usada con frecuencia por cualquier aplicación. Por esto, es primordial tener cuidado al realizar este tipo de actualizaciones e intentar evitar la ocurrencia de cualquier tipo de error para no alterar de forma errónea el contenido de los documentos almacenados.

Espero les haya quedado claro el uso de la actualización múltiple en MongoDB con este artículo del tutorial de MongoDB con Java.

Happy Minds!!!

Share on FacebookTweet about this on TwitterShare on LinkedInShare on RedditShare on Google+Digg thisShare on TumblrPin on PinterestBuffer this pagePrint this pageEmail this to someone