0% encontró este documento útil (0 votos)
235 vistas75 páginas

Guía Completa de MongoDB: Comandos y CRUD

Derechos de autor
© © All Rights Reserved
Nos tomamos en serio los derechos de los contenidos. Si sospechas que se trata de tu contenido, reclámalo aquí.
Formatos disponibles
Descarga como PDF, TXT o lee en línea desde Scribd
0% encontró este documento útil (0 votos)
235 vistas75 páginas

Guía Completa de MongoDB: Comandos y CRUD

Derechos de autor
© © All Rights Reserved
Nos tomamos en serio los derechos de los contenidos. Si sospechas que se trata de tu contenido, reclámalo aquí.
Formatos disponibles
Descarga como PDF, TXT o lee en línea desde Scribd

MONGODB

1. Es una BD Open Source NoSQL (Not only SQL).

2. Esta enfocada a manejar enormes cantidades de datos (redes sociales,


videojuegos...) lo que conocemos como Big Data.

3. El nombre viene del termino Humongous (Gigante).

4. Esta orientado a documentos, usando JSON como formato de dato.

5. No esta basado en esquemas.

6. Es un tipo de BD multiplataforma, flexible, escalable y de propósito general.


- Multiplataforma: Escrito en C++, se puede utilizar en distintios sistemas
operativos.
- Escalable: Significa que podemos añadir más recursos a nuestra BD
simplemente añadiendo más servidores. A esta unión de computadores
para extender recursos se les conoce como clusters. Tiene escalado
horizontal

- Propósito general: Puede ser utilizada en cualquier tipo de aplicación.


Aunque esta enfocada a aquellos en los que se maneja un volumen de
información masivo.

7. Se distribuye en colecciones (grupos de objetos de JS o documentos).

INSTRUCCIONES DE INSTALACIÓN:

- Descargar el instalador desde la página oficial.

- Agregar la ruta de instalación a la variable de entorno "path"

- Ejecutar dos consolas cmd como administrador. La primera nos permite poner en
funcionamiento la BD con el comando "mongod". La segunda nos permite interactuar con
la BD a traves del Shell con el comando "mongo".

COMANDOS

db.help() : muestra los métodos de db

db.mycoll.help(): muestra los métodos de collection

sh.help(): sharding helpers

rs.help() : replica set helpers

help admin: administrative help

1
help connect: connecting to a db help

help keys: key shortcuts

help misc: misc things to know

help mr: mapreduce

show dbs: muestra los nombres de las BBDD

show collections: muestra las colecciones en la BD actual

show users: muestra los usuarios de la BD actual

show profile: show most recent system.profile entries with time >= 1ms

show logs: show the accessible logger names

show log [name] : prints out the last segment of log in memory, 'global' is default

use <db_name> : edita la BD actual

db.mycoll.find(): list objects in collection mycoll

db.mycoll.find( { a : 1 } ): list objects in mycoll where a == 1

it: result of the last line evaluated; use to further iterate

DBQuery.shellBatchSize = x: set default number of items to display on shell

exit: quit the mongo shell

COMANDOS CRUD

Create

db.<nombre_collection>.insert(<json_object>)

Ejemplo:

db.products.insert(

{"name":"monitor",

"precio":165,

"active":true,

"tags":["computers","gaming","techno"]

2
)

Create - Crear uno

Se utiliza insertOne() para insertar un documento en una colección. Dentro de los


paréntesis de insertOne(), incluya un objeto que contenga los datos del documento.

db.<nombre_collection>.insertOne(<json_object>)

Ejemplo:

db.grades.insertOne(

student_id: 654321,

products: [{ type: "exam", score: 90 }, { type: "homework", score: 59 } ],

class_id: 550,

Create - Crear muchos

Utilice insertMany() para insertar varios documentos a la vez. Dentro de insertMany(),


incluye los documentos dentro de una matriz. Cada documento debe estar separado por
una coma.

db.<nombre_collection>.insertMany(<json_object>,<json_object>)

Ejemplo:

db.grades.insertMany( [

student_id: 654321,

products: [{ type: "exam", score: 90 }, { type: "homework", score: 59 } ],

class_id: 550,

},

student_id: 224331,

3
products: [{ type: "homework", score: 80 }, { type: "quiz", score: 85 } ],

class_id: 551,

])

Read - Buscar todos

db.<nombre_collection>.find()

Ejemplo:

db.products.find()

Read - Buscar coincidencias

db.<nombre_collection>.find(<parametro/s a buscar>)

Ejemplo:

db.products.find({"name":"laptop","precio":442.5})

Read - Métodos adicionales

- sort({"clave":1}) : Ordena los resultados de forma creciente (1) o decreciente (-1)

- limit(<número_de_registros>) : Limita los resultados a la cantidad especificada

- pretty() : Da formato a la salida para una mejor visualización

- count() : Nos devuelve el número de registros encontrados

- forEach(<funcion_anonima>) : Recorre cada resultado de la consulta y aplica la


función ánonima para todos ellos.

Ejemplos:

db.products.find().limit(10).sort({"precio":1})

.forEach(product => print("Product Price:" + product.precio))

db.products.find({"name":"laptop"}).limit(3).sort({"precio":-1}).pretty()

Read - Operadores

$in - Selecciona documentos en los que el valor de un campo sea igual a cualquier
valor de la matriz especificada.

Ejemplo:

4
db.zips.find({ city: { $in: ["PHOENIX", "CHICAGO"] } })

$gt - Hace coincidir documentos con un campo mayor que el valor dado.

Ejemplo:

db.sales.find({ "items.price": { $gt: 50}})

$lt - Hace coincidir documentos con un campo menor que el valor dado.

Ejemplo:

db.sales.find({ "items.price": { $lt: 50}})

$gte - Hace coincidir documentos con un campo mayor o igual que el valor dado.

Ejemplo:

db.sales.find({ "customer.age": { $gte: 65}})

$lte - Hace coincidir documentos con un campo menor o igual que el valor dado.

Ejemplo:

db.sales.find({ "customer.age": { $lte: 65}})

$elemMatch - Para buscar todos los documentos que contengan el subdocumento


especificado.

Ejemplo:

db.sales.find({

items: {

$elemMatch: { name: "laptop", price: { $gt: 800 }, quantity: { $gte:


1 } },

},

})

$or - Para seleccionar documentos que coincidan con al menos una de las
expresiones incluidas.

Ejemplo:

db.routes.find({

$or: [{ dst_airport: "SEA" }, { src_airport: "SEA" }],

5
})

$and- Para seleccionar documentos que coincidan con varias expresiones con $and
implícito.

Ejemplo:

db.routes.find({ "airline.name": "Southwest Airlines", stops: { $gte: 1 } })

Use el $and operador para usar múltiples $or expresiones en su consulta.

Ejemplo:

db.routes.find({

$and: [

{ $or: [{ dst_airport: "SEA" }, { src_airport: "SEA" }] },

{ $or: [{ "airline.name": "American Airlines" }, { airplane: 320 }] },

})

Read con proyección

Las funciones find() nos permiten especificar como queremos que nos muestre los
resultados de la busqueda. Podemos pasarle como segundo argumento un documento con
los campos que queremos que se vean (asignandoles 1), de forma implicita nos muestra 2l
_id pero podemos especificar que no queremos verlo (asignandole 0).

db.<nombre_collection>.find(<parametro/s a buscar>,<parametro/s proyección>)

Ejemplo:

db.companies.find(

{ category_code:"music" }, Busqueda

{ name:1, number_of_employees:1, _id:0 } Proyección

Update - Registro entero

db.<nombre_collection>

.update(<parametro/s a buscar>,<json_object_sustituticion>)

Ejemplo:

6
db.products.update(

{"name":"keyboard"},

"name":"keyboard",

"precio":89.99,

"active":true,

"tags":["computers","gaming","techno"]

Update - Parametro

db.<nombre_collection>.

update(<parametros/s a buscar>,{$set: <parametro/s a modificar>})

Ejemplo:

db.products

.update(

{"name":"desktop"},

{$set:

{"description":"Gaming Desktop"}

db.products

.update(

{"name":"desktop"},

{$set:

{"description":"Gaming Desktop"}

7
},

{upsert:true}

Especificando el atributo "upsert" en true (por defecto en false) si la busqueda no


obtiene ningún resultado el registro se inserta

Update - Incremento númerico

db.<nombre_collection>

.update(<parametros/s a buscar>,{$inc: <campo:valor del incremento>})

Ejemplo:

db.products.update({"name":"keyboard"},{$inc:{"precio":0.01}})

Update - Renombrar clave

db.<nombre_collection>

.update(<parametro/s a buscar>,{$rename: <nombre_clave: nuevo_nombre>})

Ejemplo:

db.products.update({"name":"keyboard"},{$rename:{"precio":"prize"}})

* El parametro cambia de orden y se posiciona el último

Delete

db.<nombre_collection>.remove(<parametro/s a buscar>)

Ejemplo:

db.products.remove({"name":"monitor"})

* Si queremos borrar todos los registros dejamos los parametros vacios

db.products.remove({})

AGGREGATE

Agregación : recopilación y resumen de datos

Etapa : uno de los métodos integrados que se puede completar en los datos, pero
no los altera de forma permanente.

8
Tubería de agregación : una serie de etapas completadas en los datos

Estructura de una canalización de agregación :

db.collection.aggregate([

$stage1: {

{ expression1 },

{ expression2 }...

},

$stage2: {

{ expression1 }...

])

$match - La etapa filtra los documentos que coinciden con las condiciones especificadas.

Ejemplo:

$match: {

"field_name": "value"

$group - La etapa agrupa los documentos por una clave de grupo.

Ejemplo:

$group:

_id: <expression>, // Group key

9
<field>: { <accumulator> : <expression> }

Ejemplo $match y $group:

La siguiente canalización de agregación encuentra los documentos con un campo


llamado "estado" que coincide con un valor "CA" y luego agrupa esos documentos por
la clave de grupo "$ciudad" y muestra el número total de códigos postales en el
estado de California.

db.zips.aggregate([

$match: {

state: "CA"

},

$group: {

_id: "$city",

totalZips: { $count : { } }

])

$sort - Clasifica todos los documentos de entrada y los devuelve a la canalización en orden
ordenado. Usamos 1 para representar el orden ascendente y -1 para representar el
orden descendente.

Ejemplo:

$sort: {

"field_name": 1

10
}

$limit - Devuelve solo un número específico de registros.

Ejemplo:

$limit: 5

Ejemplo $sort y $limit:

La siguiente canalización de agregación ordena los documentos en orden


descendente, por lo que los documentos con el mayor valor "pop" aparecen primero
y limita la salida a solo los primeros cinco documentos después de la ordenación..

db.zips.aggregate([

$sort: {

pop: -1

},

$limit: 5

])

$project - Especifica los campos de los documentos de salida. 1 significa que el campo
debe incluirse y 0 significa que el campo debe suprimirse. Al campo también se le
puede asignar un nuevo valor.

Ejemplo:

$project: {

state:1,

11
zip:1,

population:"$pop",

_id:0

$count - Crea un nuevo documento, con la cantidad de documentos en esa etapa en la


canalización de agregación asignada al nombre de campo especificado.

Ejemplo:

$count: "total_zips"

$set - Crea nuevos campos o cambia el valor de los campos existentes y luego genera los
documentos con los nuevos campos.

Ejemplo:

$set: {

place: {

$concat:["$city",",","$state"]

},

pop:10000

$out - Graba los documentos devueltos por un conducto de agregación en una nueva
colección. Debe ser la última etapa.

Ejemplo:

db.zips.aggregate([

12
$group: {

_id:"$state"

total_pop: {$sum: "$pop"}

},

$match: { total_pop: { $lt:1000000 } }

},

$out: "small_states"

])

INDEXES

Los indices son estructuras de datos especiales que almacenan una pequeña parte de los
datos de colecciones en una forma ordenada que es fácil de recorrer y buscar de forma
eficiente. Apuntan a la identidad del documento y le permiten buscar, acceder y actualizar
datos más rapidamente. Se utilizan para mejorar el rendimiento de las consultas,
acelerandolas, reduciendo la entrada/salida en disco y reduciendo los recursos necesarios
para ello.

Crear un índice de campo

Use createIndex() para crear un nuevo índice en una colección. Dentro de los paréntesis de
createIndex(), incluya un objeto que contenga el campo y el orden de clasificación.

Ejemplo:

db.customers.createIndex({

birthdate: 1

})

Crear un índice de campo único

Agregue "{unique:true}" como un segundo parámetro opcional para forzar la exclusividad


en los valores del campo de índice. Una vez que se crea el índice único, cualquier inserción
o actualización que incluya valores duplicados en la colección para el/los campo/s del

13
índice fallará.

Ejemplo:

db.customers.createIndex(

email: 1

},

unique:true

MongoDB solo crea el índice único si no hay duplicación en los valores de campo para
el/los campo/s de índice.

Ver los índices utilizados en una colección

Use getIndexes() para ver todos los índices creados en una colección.

Ejemplo:

db.customers.getIndexes()

Comprobar si se está utilizando un índice en una consulta

Use explain() en una colección cuando ejecute una consulta para ver el plan de ejecución.
Este plan proporciona los detalles de las etapas de ejecución (IXSCAN, COLLSCAN, FETCH,
SORT, etc.).

⦁ La etapa IXSCAN indica que la consulta está utilizando un índice y qué índice se
está seleccionando.

⦁ La etapa COLLSCAN indica que se realiza un análisis de la colección, sin utilizar


ningún índice.

⦁ La etapa FETCH indica que se están leyendo documentos de la colección.

⦁ La etapa SORT indica que los documentos se están ordenando en la memoria.

Ejemplos:

db.customers.explain().find({

14
birthdate: {

$gt:ISODate("1995-08-01")

db.customers.explain().find({

birthdate: {

$gt:ISODate("1995-08-01")

}).sort({

email:1

Crear un índice multiclave de un solo campo

Si un solo campo o índice compuesto incluye un campo de matriz, entonces el índice es un


índice de clave múltiple.

Use createIndex() para crear un nuevo índice en una colección. Incluya un objeto como
parámetro que contenga el campo de matriz y el orden de clasificación. En este ejemplo
accounts es un campo de matriz.

Ejemplo:

db.customers.createIndex({

accounts: 1

})

Crear un índice compuesto

Úselo createIndex() para crear un nuevo índice en una colección. Dentro de los paréntesis
de createIndex(), incluya un objeto que contenga dos o más campos y su orden de
clasificación.

15
Ejemplo:

db.customers.createIndex({

active:1,

birthdate:-1,

name:1

Orden de los campos en un índice compuesto

El orden de los campos es importante al crear el índice y el orden de clasificación. Se


recomienda listar los campos en el siguiente orden: Igualdad, Ordenar y Rango.

⦁ Igualdad: campo/s que coincide con un solo valor de campo en una consulta

⦁ Ordenar: campo/s que ordena los resultados en una consulta

⦁ Rango: campo/s que la consulta filtra en un rango de valores válidos

La siguiente consulta incluye una coincidencia de igualdad en el campo activo, una


clasificación por cumpleaños (descendente) y nombre (ascendente), y también una
consulta de rango por cumpleaños.

Ejemplo de consulta:

db.customers.find({

birthdate: {

$gte:ISODate("1977-01-01")

},

active:true

}).sort({

birthdate:-1,

name:1

})

Ejemplo de un indice eficiente para la consulta anterior:

16
db.customers.createIndex({

active:1,

birthdate:-1,

name:1

})

Cubrir una consulta por el Índice

Un índice cubre una consulta cuando MongoDB no necesita obtener los datos de la
memoria, ya que el índice ya devuelve todos los datos necesarios.

En la mayoría de los casos, podemos usar proyecciones para devolver solo los campos
obligatorios y cubrir la consulta. Asegúrese de que esos campos en la proyección estén en
el índice.

Al agregar la proyección {name:1, birthdate:1, _id:0} en la consulta anterior, podemos


limitar los campos devueltos a solo name y birthdate. Estos campos son parte del índice y
cuando ejecutamos el comando explain(), el plan de ejecución muestra solo dos etapas:

⦁ IXSCAN: Escaneo de índice usando el índice compuesto.

⦁ PROJECTION_COVERED: El índice devuelve toda la información necesaria, no es


necesario recuperarla de la memoria.

Ejemplo:

db.customers.explain().find({

birthdate: {

$gte:ISODate("1977-01-01")

},

active:true

},

{name:1,

birthdate:1,

_id:0

}).sort({

17
birthdate:-1,

name:1

})

Eliminar un índice

Úselo dropIndex() para eliminar un índice existente de una colección. Dentro de los
paréntesis de dropIndex(), incluya un objeto que represente la clave del índice o
proporcione el nombre del índice como una cadena.

Eliminar índice por nombre:

db.customers.dropIndex(

'active_1_birthdate_-1_name_1'

Eliminar índice por clave:

db.customers.dropIndex({

active:1,

birthdate:-1,

name:1

})

Eliminar índices

Úselo dropIndexes()para eliminar todos los índices de una colección, con la excepción del
índice predeterminado en _id.

Ejemplo:

db.customers.dropIndexes()

El comando dropIndexes() también puede aceptar una matriz de nombres de índice como
parámetro para eliminar una lista específica de índices.

Ejemplo:

db.collection.dropIndexes([

'index1name', 'index2name', 'index3name'

])

18
MODELADO DE DATOS

TRANSACCIONES

ACID Compliant:

⦁ Atomicidad: Si cuando una operación consiste en una serie de pasos, de los que o
bien se ejecutan todos o ninguno, es decir, las transacciones son completas.

⦁ Consistencia: (Integridad). Es la propiedad que asegura que sólo se empieza aquello


que se puede acabar. Por lo tanto se ejecutan aquellas operaciones que no van a
romper las reglas y directrices de Integridad de la base de datos. La propiedad de
consistencia sostiene que cualquier transacción llevará a la base de datos desde un
estado válido a otro también válido. "La Integridad de la Base de Datos nos permite
asegurar que los datos son exactos y consistentes, es decir que estén siempre
intactos, sean siempre los esperados y que de ninguna manera cambian ni se
deformen. De esta manera podemos garantizar que la información que se presenta
al usuario será siempre la misma."

⦁ Aislamiento: Esta propiedad asegura que una operación no puede afectar a otras.
Esto asegura que la realización de dos transacciones sobre la misma información
sean independientes y no generen ningún tipo de error. Esta propiedad define cómo
y cuándo los cambios producidos por una operación se hacen visibles para las
demás operaciones concurrentes. El aislamiento puede alcanzarse en distintos
niveles, siendo el parámetro esencial a la hora de seleccionar SGBDs.

⦁ Durabilidad: (Persistencia). Esta propiedad asegura que una vez realizada la


operación, esta persistirá y no se podrá deshacer aunque falle el sistema y que de

19
esta forma los datos sobrevivan de alguna manera.

Transacciones de varios documentos

Las transacciones ACID en MongoDB generalmente se usan solo por aplicaciones donde los
valores se intercambian entre diferentes partes, como aplicaciones bancarias o comerciales.
Si se encuentra en un escenario donde se requiere una transacción de varios documentos,
es muy probable que complete una transacción con uno de los controladores de MongoDB.
Por ahora, concentrémonos en completar y cancelar transacciones de varios documentos en
el shell para familiarizarnos con los pasos.

Uso de una transacción:

Aquí hay un resumen del código que se usa para completar una transacción de varios
documentos:

Cancelación de una transacción

Si se encuentra en un escenario que requiere que revierta las operaciones de la base de


datos antes de que se complete una transacción, puede cancelar la transacción. Al hacerlo,
la base de datos volverá a su estado original, antes de que se iniciara la transacción.

Código: cancelación de una transacción

Aquí hay un resumen del código que se usa para cancelar una transacción antes de que se
complete:

Sintaxis transaccion ejecutada

const session = db.getMongo().startSession()

session.startTransaction()

const account = session.getDatabase('bank').getCollection('accounts')

20
account.insertOne({

account_id: "MDB454252264",

account_holder: "Florence Taylor",

account_type: "savings",

balance: 100.0,

transfers_complete: [],

last_updated: new Date()

})

account.updateOne( { account_id: "MDB963134500" }, {$inc: { balance: -100.00 }})

session.commitTransaction()

Sintaxis transaccion abortada

var session = db.getMongo().startSession()

session.startTransaction()

var account = session.getDatabase('bank').getCollection('accounts')

account.updateOne( { account_id: "MDB740836066" }, {$inc: { balance: 100 }})

account.updateOne( { account_id: "MDB963134500" }, {$inc: { balance: -5 }})

session.abortTransaction()

MONGOD

A continuación se muestran algunas de las opciones disponibles para mongod. Tenga en


cuenta que esta no es una lista completa de todas las configuraciones posibles de mongod.
Para ver todas las opciones disponibles, ejecute mongod con el indicador de ayuda.

mongod --help

Este comando generará las diversas opciones para mongod con una descripción de su
funcionalidad.

Nota: La opción --fork no está disponible en el sistema operativo Windows.

ruta de la base de datos

El dbpath es el directorio donde se almacenan todos los archivos de datos para su base de
datos. El dbpath también contiene registros de diario para brindar durabilidad en caso de un

21
bloqueo. Como vimos antes, el dbpath predeterminado es /data/db; sin embargo, puede
especificar cualquier directorio que exista en su máquina. El directorio debe tener permisos
de lectura/escritura ya que la base de datos y los archivos de diario se escribirán en el
directorio. Para usar la opción dbpath, incluya el indicador dbpath y especifique el nombre
de su directorio:

mongod --dbpath <directory path>

puerto

La opción de puerto nos permite especificar el puerto en el que mongod escuchará las
conexiones de los clientes. Si no especificamos un puerto, el valor predeterminado será
27017. Los clientes de la base de datos deben especificar el mismo puerto para conectarse a
mongod. Para especificar un puerto, ejecute:

mongod --port <port number>

autenticación

auth permite la autenticación para controlar qué usuarios pueden acceder a la base de
datos. Cuando se especifica la autenticación, todos los clientes de la base de datos que
deseen conectarse a mongod primero deben autenticarse.

Antes de que se haya configurado cualquier usuario de la base de datos, un shell de Mongo
que se ejecuta en localhost tendrá acceso a la base de datos. Luego podemos configurar
usuarios y sus niveles de permiso usando el shell. Una vez que se hayan configurado uno o
más usuarios, el shell ya no tendrá acceso predeterminado. Para habilitar la autenticación,
ejecute mongod con la opción auth:

mongod --auth

vincular_ip

La opción bind_ip nos permite especificar a qué direcciones IP debe vincularse mongod.
Cuando mongod se vincula a una dirección IP, los clientes de esa dirección pueden
conectarse a mongod. Por ejemplo, si quisiéramos permitir que los clientes con la dirección
IP 123.123.123.123 accedan a nuestra base de datos, usaríamos el siguiente comando:

mongod --bind_ip 123.123.123.123

Para enlazar a múltiples direcciones y/o hosts, puede especificarlos en una lista separada
por comas:

mongod --bind_ip localhost,123.123.123.123

Si usa la opción bind_ip con direcciones IP externas, se recomienda habilitar la autenticación


para asegurarse de que los clientes remotos que se conectan a mongod tengan las

22
credenciales adecuadas.

Para obtener documentación sobre todas las opciones de mongod, consulte la página de
referencia de mongod.
https://www.mongodb.com/docs/manual/reference/program/mongod/

Instrucciones de lectura

URL lineas de comando (opciones):


https://www.mongodb.com/docs/manual/reference/program/mongod/#options

URL opciones del archivo de configuración:

https://www.mongodb.com/docs/manual/reference/configuration-options/

Estas instrucciones de lectura no están destinadas a ser reproducidas en su entorno.


Reflejan lo que verá en el video de la conferencia. Sin embargo, pueden apuntar a recursos y
archivos no existentes.

Inicie mongod usando la configuración predeterminada:

mongod

Inicie mongod con --dbpath y --logpath especificados:

mongod --dbpath /data/db --logpath /data/log/mongod.log

Inicie mongod y bifurque el proceso:

mongod --dbpath /data/db --logpath /data/log/mongod.log --fork

Inicie mongod con muchas opciones de configuración:

Tenga en cuenta que todas las opciones de "ssl" se han editado para usar "tls" en su lugar. A
partir de MongoDB 4.2, las opciones que usan "ssl" han quedado obsoletas.

mongod --dbpath /data/db --logpath /data/log/mongod.log --fork --replSet


"M103" --keyFile /data/keyfile --bind_ip "127.0.0.1,192.168.103.100" --tlsMode
requireTLS --tlsCAFile "/etc/tls/TLSCA.pem" --tlsCertificateKeyFile
"/etc/tls/tls.pem"

Archivo de configuración de ejemplo, con las mismas opciones de configuración que el


anterior:

storage:

dbPath: "/data/db"

systemLog:

23
path: "/data/log/mongod.log"

destination: "file"

replication:

replSetName: M103

net:

bindIp : "127.0.0.1,192.168.103.100"

tls:

mode: "requireTLS"

certificateKeyFile: "/etc/tls/tls.pem"

CAFile: "/etc/tls/TLSCA.pem"

security:

keyFile: "/data/keyfile"

processManagement:

fork: true

Nota: En WiredTiger, el intervalo de confirmación de diario predeterminado es de 100


milisegundos. Para obtener más información.

Instrucciones de lectura

Liste el directorio --dbpath:

ls -l /data/db

Listar el directorio de datos de diagnóstico:

ls -l /data/db/diagnostic.data

Listar directorio de revistas:

ls -l /data/db/journal

Lista de archivos de socket:

ls /tmp/mongodb-27017.sock

24
Instrucciones de lectura

Comandos de gestión de usuarios:

db.createUser()

db.dropUser()

Comandos de gestión de colecciones:

db.<collection>.renameCollection()

db.<collection>.createIndex()

db.<collection>.drop()

Comandos de gestión de base de datos:

db.dropDatabase()

db.createCollection()

Comando de estado de la base de datos:

db.serverStatus()

Creación de índice con el comando de base de datos:

db.runCommand({

"createIndexes":"<collection_name>",

"indexes":[

"key":{ "product": 1 },

25
"name": "name_index"

Creando índice con Shell Helper:

db.<collection>.createIndex(

{ "product": 1 },

{ "name": "name_index" }

Introspeccione a un ayudante de Shell:

db.<collection>.createIndex

Instrucciones de lectura

Nota: La salida de registro ha cambiado en MongoDB 4.2. Si está interesado, puede


encontrar más información en las notas de la versión 4.2:
https://www.mongodb.com/docs/manual/release-notes/4.2/#logging-and-diagnostics

Obtenga los componentes de registro:

mongo admin --host 192.168.103.100:27000 -u m103-admin -p m103-pass --eval '

db.getLogComponents() '

Cambiar el nivel de registro:

mongo admin --host 192.168.103.100:27000 -u m103-admin -p m103-pass --eval '

db.setLogLevel(0, "index") '

Vea los registros a través del shell de Mongo:

db.adminCommand({ "getLog": "global" })

Ver los registros a través de la línea de comando:

tail -f /data/db/mongod.log

Actualizar un documento:

mongo admin --host 192.168.103.100:27000 -u m103-admin -p m103-pass --eval '

db.products.update( { "sku" : 6902667 }, { $set : { "salePrice" : 39.99} } ) '

26
Busque instrucciones en el archivo de registro con grep:

grep -i 'update' /data/db/mongod.log

Instrucciones de lectura

Nota: El comando ``mostrar colecciones`` ya no muestra las colecciones system.*. Cambió


después de la versión 4.0.

Para enumerar todos los nombres de las colecciones, puede ejecutar este comando:

db.runCommand({listCollections: 1})

Obtener nivel de perfil:

mongo newDB --host 192.168.103.100:27000 -u m103-admin -p m103-pass --


authenticationDatabase admin --eval ' db.getProfilingLevel() '

Establecer nivel de perfil:

mongo newDB --host 192.168.103.100:27000 -u m103-admin -p m103-pass --


authenticationDatabase admin --eval ' db.setProfilingLevel(1) '

Mostrar colecciones:

mongo newDB --host 192.168.103.100:27000 -u m103-admin -p m103-pass --


authenticationDatabase admin --eval ' db.getCollectionNames() '

Nota: Mostrar colecciones solo funciona desde dentro del shell

Establecer ralentizaciones a 0:

mongo newDB --host 192.168.103.100:27000 -u m103-admin -p m103-pass --


authenticationDatabase admin --eval ' db.setProfilingLevel( 1, { slowms: 0 } ) '

Inserte un documento en una nueva colección:

mongo newDB --host 192.168.103.100:27000 -u m103-admin -p m103-pass --


authenticationDatabase admin --eval ' db.new_collection.insert( { "a": 1 } ) '

Obtenga datos de perfiles de system.profile:

mongo newDB --host 192.168.103.100:27000 -u m103-admin -p m103-pass --


authenticationDatabase admin --eval ' db.system.profile.find().pretty() '

Instrucciones de lectura

Imprimir archivo de configuración:

cat /etc/mongod.conf

27
Lanzar mongod independiente:

mongod -f /etc/mongod.conf

Conéctese a mongod:

mongo --host 127.0.0.1:27017

Cree un nuevo usuario con el rol de root (también llamado root):

use admin

db.createUser({

user: "root",

pwd: "root123",

roles : [ "root" ]

})

Conéctese a mongod y autentíquese como root:

mongo --username root --password root123 --authenticationDatabase admin

Ejecutar estadísticas de base de datos:

db.stats()

Apague el servidor:

use admin

db.shutdownServer()

Instrucciones de lectura

Autenticarse como usuario root:

mongo admin -u root -p root123

Crear oficial de seguridad:

db.createUser(

{ user: "security_officer",

pwd: "h3ll0th3r3",

roles: [ { db: "admin", role: "userAdmin" } ]

28
}

Crear administrador de base de datos:

db.createUser(

{ user: "dba",

pwd: "c1lynd3rs",

roles: [ { db: "admin", role: "dbAdmin" } ]

Otorgar rol al usuario:

db.grantRolesToUser( "dba", [ { db: "playground", role: "dbOwner" } ] )

Mostrar privilegios de rol:

db.runCommand( { rolesInfo: { role: "dbOwner", db: "playground" },


showPrivileges: true} )

Instrucciones de lectura 0

Lista de binarios mongodb:

find /usr/bin/ -name "mongo*"

Cree un nuevo dbpath y ejecute mongod:

mkdir -p ~/first_mongod

mongod --port 30000 --dbpath ~/first_mongod --logpath


~/first_mongod/mongodb.log --fork

Use mongostat para obtener estadísticas sobre un proceso mongod en ejecución:

mongostat --help

mongostat --port 30000

Use mongodump para obtener un volcado BSON de una colección MongoDB:

mongodump --help

mongodump --port 30000 --db applicationData --collection products

29
ls dump/applicationData/

cat dump/applicationData/products.metadata.json

Use mongorestore para restaurar una colección MongoDB desde un volcado BSON:

mongorestore --drop --port 30000 dump/

Use mongoexport para exportar una colección MongoDB a JSON o CSV (¡o stdout!):

mongoexport --help

mongoexport --port 30000 --db applicationData --collection products

mongoexport --port 30000 --db applicationData --collection products -o


products.json

Siga el archivo JSON exportado:

tail products.json

Use mongoimport para crear una colección MongoDB a partir de un archivo JSON o CSV:

mongoimport --port 30000 products.json

REPLICACIÓN

Instrucciones de lectura 0

El archivo de configuración para el primer nodo (node1.conf):

storage:

dbPath: /var/mongodb/db/node1

net:

bindIp: 192.168.103.100,localhost

port: 27011

security:

authorization: enabled

keyFile: /var/mongodb/pki/m103-keyfile

systemLog:

destination: file

30
path: /var/mongodb/db/node1/mongod.log

logAppend: true

processManagement:

fork: true

replication:

replSetName: m103-example

Crear el archivo de claves y establecer permisos en él:

sudo mkdir -p /var/mongodb/pki/

sudo chown vagrant:vagrant /var/mongodb/pki/

openssl rand -base64 741 > /var/mongodb/pki/m103-keyfile

chmod 400 /var/mongodb/pki/m103-keyfile

Creando el dbpath para el nodo1 :

mkdir -p /var/mongodb/db/node1

Iniciando un mongod con node1.conf:

mongod -f node1.conf

Copiando node1.conf a node2.conf y node3.conf:

cp node1.conf node2.conf

cp node2.conf node3.conf

Editando node2.conf usando vi :

vi node2.conf

Guardando el archivo y saliendo de vi :

:wq

node2.conf, después de cambiar dbpath , port y logpath :

storage:

dbPath: /var/mongodb/db/node2

net:

31
bindIp: 192.168.103.100,localhost

port: 27012

security:

keyFile: /var/mongodb/pki/m103-keyfile

systemLog:

destination: file

path: /var/mongodb/db/node2/mongod.log

logAppend: true

processManagement:

fork: true

replication:

replSetName: m103-example

node3.conf, después de cambiar dbpath , port y logpath :

storage:

dbPath: /var/mongodb/db/node3

net:

bindIp: 192.168.103.100,localhost

port: 27013

security:

keyFile: /var/mongodb/pki/m103-keyfile

systemLog:

destination: file

path: /var/mongodb/db/node3/mongod.log

logAppend: true

processManagement:

fork: true

32
replication:

replSetName: m103-example

Creando los directorios de datos para el nodo2 y el nodo3 :

mkdir /var/mongodb/db/{node2,node3}

Iniciando procesos mongod con node2.conf y node3.conf:

mongod -f node2.conf

mongod -f node3.conf

Conectando al nodo1 :

mongo --port 27011

Iniciando el conjunto de réplicas:

rs.initiate()

Creando un usuario:

use admin

db.createUser({

user: "m103-admin",

pwd: "m103-pass",

roles: [

{role: "root", db: "admin"}

})

Saliendo del caparazón de Mongo y conectándose a todo el conjunto de réplicas:

exit

mongo --host "m103-example/192.168.103.100:27011" -u "m103-admin"

-p "m103-pass" --authenticationDatabase "admin"

Obtener el estado del conjunto de réplicas:

rs.status()

33
Adición de otros miembros al conjunto de réplicas:

rs.add("m103:27012")

rs.add("m103:27013")

Obtención de una descripción general de la topología del conjunto de réplicas:

rs.isMaster()

Reduciendo el primario actual:

rs.stepDown()

Comprobación de la descripción general del conjunto de réplicas después de la elección:

rs.isMaster()

Nos ofrece mucha información del Replica Set de Mongod:

rs.serverStatus()['repl']

Nos ofrece información del log de operaciones (oplog) del nodo en el que estamos
conectados:

rs.printReplicationInfo()

REPLICACIÓN: Práctica

Instrucciones de lectura 1

Cree un directorio de datos e inicie un proceso mongod para un nodo independiente:

mkdir allbymyselfdb

mongod --dbpath allbymyselfdb

Mostrar todas las bases de datos (por defecto, solo administrador y local ):

mongo

show dbs

Mostrar colecciones de la base de datos local (esto muestra más colecciones de un conjunto
de réplicas que de un nodo independiente):

use local

show collections

Consulta el registro de operaciones después de conectarte a un conjunto de réplicas:

34
use local

db.oplog.rs.find()

Obtenga información sobre el registro de operaciones (recuerde que el registro de


operaciones es una colección limitada).

Almacene las estadísticas de oplog como una variable llamada stats:

var stats = db.oplog.rs.stats()

Verifique que esta colección esté limitada (crecerá a un tamaño preconfigurado antes de
que comience a sobrescribir las entradas más antiguas con las más nuevas):

stats.capped

Obtenga el tamaño actual del registro de operaciones:

stats.size

Obtenga el límite de tamaño del registro de operaciones:

stats.maxSize

Obtenga datos de registro de operación actuales (incluidos los tiempos del primer y último
evento, y el tamaño de registro de operación configurado):

rs.printReplicationInfo()

Instrucciones de lectura 2

Cree un nuevo espacio de nombres m103.messages:

use m103

db.createCollection('messages')

Consulta el registro de operaciones, filtrando los latidos del corazón ("noop periódico") y
solo devolviendo la última entrada:

use local

db.oplog.rs.find( { "o.msg": { $ne: "periodic


noop" } } ).sort( { $natural: -1 } ).limit(1).pretty()

Inserta 100 documentos diferentes:

use m103

for ( i=0; i< 100; i++) { db.messages.insert( { 'msg': 'not yet', _id: i } ) }

35
db.messages.count()

Consulta el registro de operaciones para encontrar todas las operaciones relacionadas con
m103.messages:

use local

db.oplog.rs.find({"ns": "m103.messages"}).sort({$natural: -1})

Ilustre que una declaración de actualización puede generar muchas entradas en el registro
de operaciones:

use m103

db.messages.updateMany( {}, { $set: { author: 'norberto' } } )

use local

db.oplog.rs.find( { "ns": "m103.messages" } ).sort( { $natural: -1 } )

Recuerde, aunque puede escribir datos en la base de datos local, no debe hacerlo.

Instrucciones de lectura 3

nodo4.conf:

storage:

dbPath: /var/mongodb/db/node4

net:

bindIp: 192.168.103.100,localhost

port: 27014

systemLog:

destination: file

path: /var/mongodb/db/node4/mongod.log

logAppend: true

processManagement:

fork: true

replication:

replSetName: m103-example

36
árbitro.conf:

storage:

dbPath: /var/mongodb/db/arbiter

net:

bindIp: 192.168.103.100,localhost

port: 28000

systemLog:

destination: file

path: /var/mongodb/db/arbiter/mongod.log

logAppend: true

processManagement:

fork: true

replication:

replSetName: m103-example

Iniciando procesos mongod para nuestro cuarto nodo y árbitro:

mongod -f node4.conf

mongod -f arbiter.conf

Desde el caparazón de Mongo del conjunto de réplicas, agregando el nuevo secundario y el


nuevo árbitro:

rs.add("m103:27014")

rs.addArb("m103:28000")

Comprobación de la configuración del conjunto de réplicas después de agregar dos nuevos


nodos.

rs.isMaster()

Eliminando el árbitro de nuestro conjunto de réplicas:

rs.remove("m103:28000")

Asignando la configuración actual a una variable de shell que podemos editar, para

37
reconfigurar el conjunto de réplicas:

cfg = rs.conf()

Editando nuestra nueva variable cfg para cambiar la topología, específicamente,


modificando cfg.members:

cfg.members[3].votes = 0

cfg.members[3].hidden = true

cfg.members[3].priority = 0

Actualizar nuestro conjunto de réplicas para usar la nueva configuración cfg:

rs.reconfig(cfg)

Instrucciones de lectura 4

Conexión al conjunto de réplicas:

mongo --host "m103-example/m103:27011" -u "m103-admin" -p

"m103-pass" --authenticationDatabase "admin"

Comprobación de la topología del conjunto de réplicas:

rs.isMaster()

Insertar un documento en una nueva colección:

use newDB

db.new_collection.insert( { "student": "Matt Javaly", "grade": "A+" } )

Conexión directa a un nodo secundario (¡este nodo puede no ser un secundario en su


conjunto de réplicas!):

mongo --host "m103:27012" -u "m103-admin" -p "m103-pass"

--authenticationDatabase "admin"

Intentando ejecutar un comando de lectura en un nodo secundario (esto debería fallar):

show dbs

Habilitación de comandos de lectura en un nodo secundario:

rs.slaveOk()

Lectura desde un nodo secundario:

38
use newDB

db.new_collection.find()

Intentar escribir datos directamente en un nodo secundario (esto debería fallar, porque no
podemos escribir datos directamente en un nodo secundario):

db.new_collection.insert( { "student": "Norberto Leite", "grade": "B+" } )

Apagar el servidor (en ambos nodos secundarios)

use admin

db.shutdownServer()

Conectando directamente al último nodo saludable en nuestro conjunto:

mongo --host "m103:27011" -u "m103-admin" -p "m103-pass"

--authenticationDatabase "admin"

Verificación de que el último nodo se redujo para convertirse en secundario cuando la


mayoría de los nodos del conjunto no estaban disponibles:

rs.isMaster()

Instrucciones de lectura 5

Almacenamiento de la configuración del conjunto de réplicas como una variable cfg:

cfg = rs.conf()

Establecer la prioridad de un nodo en 0, por lo que no puede convertirse en principal


(haciendo que el nodo sea "pasivo"):

cfg.members[2].priority = 0

Actualizar nuestro conjunto de réplicas para usar la nueva configuración cfg:

rs.reconfig(cfg)

Comprobando la nueva topología de nuestro conjunto:

rs.isMaster()

Forzar una elección en este conjunto de réplicas (aunque en este caso, manipulamos la
elección para que solo un nodo pudiera convertirse en primario):

rs.stepDown()

Comprobando la topología de nuestro conjunto después de la elección:

39
rs.isMaster()

FRAGMENTACIÓN

Instrucciones de lectura

Si desea implementar un clúster fragmentado en su máquina, puede encontrar los


comandos de la lección aquí:

Archivo de configuración para el primer servidor de configuración csrs_1.conf:

sharding:

clusterRole: configsvr

replication:

replSetName: m103-csrs

security:

keyFile: /var/mongodb/pki/m103-keyfile

net:

bindIp: localhost,192.168.103.100

port: 26001

systemLog:

destination: file

path: /var/mongodb/db/csrs1.log

logAppend: true

processManagement:

fork: true

storage:

dbPath: /var/mongodb/db/csrs1

csrs_2.conf:

sharding:

clusterRole: configsvr

40
replication:

replSetName: m103-csrs

security:

keyFile: /var/mongodb/pki/m103-keyfile

net:

bindIp: localhost,192.168.103.100

port: 26002

systemLog:

destination: file

path: /var/mongodb/db/csrs2.log

logAppend: true

processManagement:

fork: true

storage:

dbPath: /var/mongodb/db/csrs2

csrs_3.conf:

sharding:

clusterRole: configsvr

replication:

replSetName: m103-csrs

security:

keyFile: /var/mongodb/pki/m103-keyfile

net:

bindIp: localhost,192.168.103.100

port: 26003

systemLog:

41
destination: file

path: /var/mongodb/db/csrs3.log

logAppend: true

processManagement:

fork: true

storage:

dbPath: /var/mongodb/db/csrs3

Iniciando los tres servidores de configuración:

mongod -f csrs_1.conf

mongod -f csrs_2.conf

mongod -f csrs_3.conf

Conéctese a uno de los servidores de configuración:

mongo --port 26001

Iniciando el CSRS:

rs.initiate()

Creando superusuario en CSRS:

use admin

db.createUser({

user: "m103-admin",

pwd: "m103-pass",

roles: [

{role: "root", db: "admin"}

})

Autenticación como superusuario:

db.auth("m103-admin", "m103-pass")

42
Agregue el segundo y tercer nodo al CSRS:

rs.add("192.168.103.100:26002")

rs.add("192.168.103.100:26003")

Configuración de Mongos (mongos.conf):

sharding:

configDB: m103-
csrs/192.168.103.100:26001,192.168.103.100:26002,192.168.103.100:26003

security:

keyFile: /var/mongodb/pki/m103-keyfile

net:

bindIp: localhost,192.168.103.100

port: 26000

systemLog:

destination: file

path: /var/mongodb/db/mongos.log

logAppend: true

processManagement:

fork: true

Inicie el servidor mongos:

mongos -f mongos.conf

Conéctate a mongos:

vagrant@m103:~$ mongo --port 26000 --username m103-admin --password


m103-pass --authenticationDatabase admin

Comprobar el estado de fragmentación:

MongoDB Enterprise mongos> sh.status()

Configuración actualizada para node1.conf:

sharding:

43
clusterRole: shardsvr

storage:

dbPath: /var/mongodb/db/node1

wiredTiger:

engineConfig:

cacheSizeGB: .1

net:

bindIp: 192.168.103.100,localhost

port: 27011

security:

keyFile: /var/mongodb/pki/m103-keyfile

systemLog:

destination: file

path: /var/mongodb/db/node1/mongod.log

logAppend: true

processManagement:

fork: true

replication:

replSetName: m103-repl

Configuración actualizada para node2.conf:

sharding:

clusterRole: shardsvr

storage:

dbPath: /var/mongodb/db/node2

wiredTiger:

engineConfig:

44
cacheSizeGB: .1

net:

bindIp: 192.168.103.100,localhost

port: 27012

security:

keyFile: /var/mongodb/pki/m103-keyfile

systemLog:

destination: file

path: /var/mongodb/db/node2/mongod.log

logAppend: true

processManagement:

fork: true

replication:

replSetName: m103-repl

Configuración actualizada para node3.conf:

sharding:

clusterRole: shardsvr

storage:

dbPath: /var/mongodb/db/node3

wiredTiger:

engineConfig:

cacheSizeGB: .1

net:

bindIp: 192.168.103.100,localhost

port: 27013

security:

45
keyFile: /var/mongodb/pki/m103-keyfile

systemLog:

destination: file

path: /var/mongodb/db/node3/mongod.log

logAppend: true

processManagement:

fork: true

replication:

replSetName: m103-repl

Conexión directa al nodo secundario (tenga en cuenta que si se ha realizado una elección en
su conjunto de réplicas, el nodo especificado puede haberse convertido en principal):

mongo --port 27012 -u "m103-admin" -p "m103-pass" --authenticationDatabase


"admin"

Apagando el nodo:

use admin

db.shutdownServer()

Reinicio del nodo con nueva configuración:

mongod -f node2.conf

Bajando la primaria actual:

rs.stepDown()

Agregando un nuevo fragmento al clúster desde mongos:

sh.addShard("m103-repl/192.168.103.100:27012")

Instrucciones de lectura 2

Si desea explorar las colecciones en la base de datos de configuración, puede encontrar las
instrucciones aquí:

Cambie a la base de datos de configuración:

use config

46
Consulta config.bases de datos:

db.databases.find().pretty()

Consulta config.colecciones:

db.collections.find().pretty()

Consulta config.shards:

db.shards.find().pretty()

Consultar config.chunks:

db.chunks.find().pretty()

Consulta config.mongos:

db.mongos.find().pretty()

Instrucciones de lectura 3

Nota: A partir de MongoDB 4.2, los valores de la clave de fragmento son mutables, aunque
la clave de fragmento en sí misma es inmutable. Si está interesado, puede obtener más
información en la documentación de valores de clave de fragmento .

A partir de MongoDB 4.4, puede usar refineCollectionShardKey para actualizar el valor de la


clave de fragmento de un documento, a menos que el campo de clave de fragmento sea el
campo _id inmutable. Si está interesado, puede leer más en la documentación de
refineCollectionShardKey .

Si desea fragmentar una colección, puede encontrar instrucciones para crear una clave
fragmentada aquí:

Mostrar colecciones en la base de datos m103:

use m103

show collections

Habilite la fragmentación en la base de datos m103:

sh.enableSharding("m103")

Encuentre un documento de la colección de productos, para ayudarnos a elegir una clave de


fragmento:

db.products.findOne()

Crear un índice en sku:

47
db.products.createIndex( { "sku": 1 } )

Fragmenta la colección de productos en sku:

sh.shardCollection( "m103.products", { "sku": 1 } )

Comprobación del estado del clúster fragmentado:

sh.status()

Selección de una buena clave fragmentada

CARDINALIDAD - Para una buena fragmentación se recomienda que la clave de


fragmentación tenga un alto rango de valores posibles.

FRECUENCIA - Se recomienda que los valores únicos tengan una baja frecuencia.

CAMBIOS MONOTONOS - Se recomienda evitar aquellos datos como fechas o marcas de


tiempo, que sufren cambios crecientes o decrecientes en progresión númerica. En caso
contrario puede provocar que los registros acaben en uno solo de los fragmentos.

Claves fragmentadas hash

La función hash asigna un valor númerico a la clave de fragmentación. Esto permite que
datos no demasiado recomendable como fechas o marcas de tiempo (comentadas en el
apartado anterior) puedan usarse al disponer de un valor estable y único en el que
establecer su ubicación en un fragmento.

Inconveniente: Las consultas realizadas en fragmentos basados en claves hash deberan


analizar varios fragmentos, haciendo que sean menos eficientes. La razón es que la
distribución se realiza de manera aleatoria, evitando aislar y agrupar los datos en un
fragmento concreto.

48
Nota: Las claves hash solo pueden basarse en datos únicos. Dicho de otra manera, no se
admiten arrays.

FRAGMENTACIÓN - TROZOS (CHUNKS)

Los trozos es el número de datos admitido por un fragmento. Para establecer una buena
configuración de fragmentación es relevante que se tenga en cuenta la cardinalidad de la
clave de fragmento, que nos permitira una mejor división de los trozos. También hay otros
aspectos limitantes para los trozos:

TAMAÑO DEL TROZO (ChunkSize) - Por defecto MongoDB toma 64MB como fragmento
predeterminado, pero nosotros podemos modificarlo y establecerlo entre 1MB y 1024MB
(1GB).

Instrucciones de lectura

Mostrar colecciones en la base de datos de configuración:

use config

show collections

Encuentre un documento de la colección de fragmentos:

db.chunks.findOne()

Cambiar el tamaño del fragmento:

use config

db.settings.save({_id: "chunksize", value: 2})

Compruebe el estado del clúster fragmentado:

sh.status()

Importe el nuevo conjunto de datos products.part2 a MongoDB:

mongoimport /dataset/products.part2.json --port 26000 -u "m103-admin" -p


"m103-pass" --authentication

EQUILIBRIO

A medida que se insertan datos los fragmentos aumentan, el equilibrador MongoDB


identifica cuál de los fragmentos tiene demasiados trozos y automáticamente se encarga de
mover trozos a través de fragmentos en el clúster fragmentado, en un intento de mantener
el equilibrio y lograr una mejor distribución de los datos.

Si el balanceador detecta un desequilibrio, comienza una ronda de balanceo. Puede migrar


fragmentos en paralelo. Un fragmento dado no puede participar en más de una migración a

49
la vez, asi que toma el número de fragmentos y el número de trozos que se puede migrar en
una ronda de equilibrio (balancer round) y los divide entre dos.

Inicie el equilibrador:

sh.startBalancer(timeout, interval)

Detener el equilibrador:

sh.stopBalancer(timeout, interval)

Habilitar/deshabilitar el balanceador:

sh.setBalancerState(boolean)

Consultas en un clúster fragmentado

Cuando realizamos una consulta en un clúster fragmentado, primero se crea una lista de
fragmentos objetivos para orientar la consulta, las consultas se realizan en cada fragmento y
posteriormente se fusionan para ofrecernos un único conjunto de resultados.

Compartamiento de métodos:

sort() - mongos aplica el criterio de ordenación a cada uno de los fragmentos antes
de la fusión.

limit() - mongos pasa el limite a cada uno de los fragmentos objetivos y reaplica el
limite una vez fusionado el conjunto de resultados.

skip() - mongos aplica el skip, una vez realizada la fusión.

Nota: Cuando se usa junto con limit(), los mongos pasarán el límite más el valor de skip() a
los fragmentos para garantizar que se devuelva una cantidad suficiente de documentos a los
mongos para aplicar el limit() y skip() exitosamente.

50
Consultas dirigidas VS Recopilación dispersa

Consulta dirigida - Cuando usamos la clave de fragmentación para realizar una consulta,
mongos se fija en una tabla donde figuran los datos de fragmentación, es decir, los rangos
en los que hemos dividido los datos en los distintos fragmentos. De esta forma se dirige al
fragmento correspondiente, haciendo que la consulta sea más rapida y eficiente.

Recopilación dispersa - Si no se usa la clave de fragmentación en la consulta, mongos no


puede derivar exactamente que fragmentos satisfacen la consulta. En este caso, mongos,
realiza un ping a cada clúster y esperar para la respuesta de cada fragmento en el clúster, sin
importar si ellos tienen algo para contribuir a la ejecución de la consulta. Dependiendo del
número de fragmentos en tu grupo, la cantidad de latencia de la red entre fragmentos -
mongos y una serie de otros factrores, estas consultas pueden ser lentas. Por eso se
aconseja que a la hora de elegir la clave de fragmentación, esta satisfaga el mayor número
de consultas habituales posibles.

Cuando utilizamos un indice compuesto como clave de fragmentación, se puede usar parte
o la totalidad de los datos como prefijo de la consulta y está se realizará de forma dirigida.
Siempre y cuando la realicemos teniendo en cuenta el orden de prioridad establecido.

Instrucciones de lectura

Una consulta find() en la que el predicado coincide con la clave de fragmento y la consulta
puede orientarse :

db.products.find( { "sku": 20009151 } )

Una consulta find() donde el predicado no coincide con la clave de fragmento y la consulta
es una recopilación dispersa :

db.products.find( { "type": "movie" } )

Ejemplo de una clave de fragmento compuesta:

51
{ "sku": 1, "type": 1, "name": 1 }

Ejemplos de consultas a las que se dirigiría la clave de fragmento compuesto:

db.products.find( { "sku": ... } )

db.products.find( { "sku": ... , "type": ... } )

db.products.find( { "sku": ... , "type": ... , "name": ... } )

Ejemplos de consultas que se dispersarían con la clave de fragmento compuesto:

db.products.find( { "type": ... } )

db.products.find( { "name": ... } )

Instrucciones de lectura 2

Mostrar colecciones en la base de datos m103:

use m103

show collections

Consulta dirigida con salida de explicación ():

db.products.find({"sku" : 1000000749 }).explain()

Consulta de recopilación dispersa con salida de explicación ():

db.products.find( {

"name" : "Gods And Heroes: Rome Rising - Windows [Digital Download]" }

).explain()

DATA MODELING (Modelado de datos)

Glosario:

Conceptos y vocabulario de MongoDB

1. Base de datos y colección en MongoDB

2. Realizar uniones con $lookup

Conceptos y vocabulario de bases de datos relacionales

1. Tabla

2. Tabla

3. Modelo de relación de entidad

52
4. El modelo de datos de relación de entidad

5. Crow´s Foot Notation y ERD

Conceptos y definiciones generales de bases de datos

1. Base de datos

2. Esquema

3. Definición breve del esquema

4. Transacciones de base de datos

5. Transacciones de base de datos Descripción breve

6. Rendimiento frente a latencia

7. Bases de datos NoSQL

Diagrama de metodología de modelado de datos

Diagrama para modelado de simplicidad

53
Diagrama para modelado de rendimiento

Diagrama para modelado con combinado de simplicidad y rendimiento

54
Resumen de enfoque de modelado

Patrones

55
Patrón de atributo (Attribute Pattern)

- Problemas: Muchos campos similares, necesidad de buscar en muchos campos a la


vez, campos presentes solo en un subconjunto de documentos.

- Solución: Dividir la clave/valor en un subdocumento; {fieldA:field,fieldB:value}

ejemplo:

{"color":"blue","size":"large"}

{ specs: [

{"k":"color","v":"blue"},

{"k":"size","v":"large"}

]}

- Beneficios:

1 - Facil de indexar -> db.collection.createIndex("specs.k":1,"specs.v":1)

56
Nota: Esto también se puede hacer con Wildcard Index

db.collection.createIndex( { "specs.$**" : 1 } )

2 - Permite usar nombres en los campos no deterministas.

3 - Habilita la clasificación de la relación orginal en el campo y valor.

- Casos de uso: Características de productos, conjuntos de campo con el mismo tipo


de valor, ejemplo: fechaDeEstreno (fechaDeEstreno_USA, fechaDeEstreno_EU,
fechaDeEstreno_ASIA...)

Patrón de referencia ampliado (Extended Reference Pattern)

- Problemas: Uniones (joins) muy repetitivas y frecuentes.

- Solución: Identificar valores en el lado de búsqueda, incrustar (embeber) esos


campos al documento principal.

- Beneficios: Lectura más rápida, reducir el número de uniones.

- Perjuicios: Puede introducir muchos duplicados si la referencia extendida contiene


campos que cambián con frecuencia.

- Casos de uso: Cátalogos, Aplicaciones de móvil, Análisis en tiempo real.

Patrón de subconjunto (Subset Pattern)

- Problemas: El conjunto de trabajo (working set) es muy grande, muchos


documentos son desalojados por falta de memoria, gran parte de la información de
los documentosse utilizan en raras ocasiones.

- Solución: Dividir la colección en dos colecciones (datos más usados y datos menos
usados), la división se usa con más frecuencia para las relaciones 1-M y M-M.

- Beneficios: Conjuntos de trabajo y documentos más pequeños, accesos a disco


más cortos paraa recuperar información.

- Perjuicios: Más documentos para recuperar (más viajes de ida y vuelta), requiere
más espacio en el disco.

- Casos de uso: Listas de reseñas de productos, listas de comentarios de un


artículo/post, lista de actores en una película (información adicional del actor).

Patrón calculado (Computed Pattern)

- Problemas: Alto coste de cálculo y manipulación de los datos, ejecuciones


frecuentes de calculos en los datos que producen el mismo resultado.

- Solución: Mejorar el rendimiento de las operaciones y almacenar el resultado en el


documento y colección apropiado. Rehacer las operaciones manteniendo la fuente.

- Beneficios: Consultas de lectura más rapidas, ahorro en recursos como CPU y


disco.

57
- Perjuicios: Puede ser dificil identificar la necesidad, evite aplicarlo o usarlo en
exceso a menos que sea necesario.

- Casos de uso: Internet de las cosas (IOT), abastecimiento de eventos, datos de


series de tiempo, consultas frecuentes del marco de agregación.

Patrón de depósito (Bucket Pattern)

- Problemas: Evitando demasiados documentos o documentos demasiado grandes,


relaciones 1-M que no pueden ser incrustadas.

- Solución: Definir la cantidad óptima de información para agrupar, crear matrices


para almacenar la información en el objeto principal, es básicamente una relación
incrustada de 1-M, donde obtiene N documentos, cada uno con un promedio de
muchos/n subdocumentos.

- Beneficios: Buen equilibrio entre el número de accesos a los datos y el tamaño de


los datos devueltos, hace que los datos sean más manejables y fáciles de eliminar.

- Perjuicios: Puede dar lugar a resultados de consulta deficientes si no se diseñan


correctamente y son menos amigables con las herramientas de BI.

- Casos de uso: Internet de las cosas (IOT), almacén de datos, mucha información
asociada a un objeto.

Patrón de control de versiones del esquema (Schema versioning Pattern)

- Problemas: Evite el tiempo de inactividad mientras realiza actualizaciones de


esquemas, la actualización de todos los documentos puede llevar horas, días o
incluso semanas cuando se trata de grandes datos, no desea actualizar todos los
documentos.

- Solución: Asignar a cada documento un campo "schema_version", la aplicación


puede manejar todas las versiones, elija su estrategia para migrar los documentos.

- Beneficios: No se necesita tiempo de inactividad, control de la migración, menos


deuda técnica futura.

- Perjuicios: Puede necesitar 2 índices para el mismo campo durante el período de


migración.

- Casos de uso: Cada documento que utiliza una base de datos, desplegado en
producción y muy utilizado, sistema con una gran cantidad de datos heredados.

Patrón de arboles (Tree Pattern)

- Problemas: Necesidad de representar datos estructurados jerárquicos, patrón de


acceso diferente para navegar por el árbol, proporcionar un modelo optimizado
para operaciones comunes.

- Solución: Diferentes patrones:

- Referencia a hijos (Child reference)

58
Beneficios: Navegación facil hacia los "nodos hijos" o patrones de
acceso de árbol descendente.

- Referencia principal (Parent reference)

Beneficios: Detección inmediata de nodos principales y


actualizaciones de árboles "Array of Ancestors".

- Matriz de antepasados (Array of ancestors)

Beneficios: Navegar hacia arriba en el camino de los antepasados


"Materialized Paths".

- Rutas materializadas (Materialized Paths)

Beneficios: Permite usar expresiones regulares para encontrar


nodos en el arbol, separando los nodos con carácteres (. $ % / -).

- Casos de uso: Org charts, productos categorizados.

Patrón polimórfico (Polymorphic Pattern)

- Problemas: Documentos similares con diferencias, necesidad de almacenar


documentos en la misma colección.

- Solución: Rastrear el tipo de documento o subdocumento, la aplicación tiene


diferentes rutas de código por tipo de documento o tiene subclases.

- Beneficios: Fácil de implementar, permite consultas en una sola colección.

- Casos de uso: Vistas sencillas, catálogos de productos, gestión de contenido.

Otros patrones:

Patrón de aproximación (Approximation Pattern):

- Problemas: Los datos son costosos de calcular, no importa si los números


no son precisos.

- Solución: Hacer menos escrituras pero con más carga útil.

- Beneficios: Menos escrituras, menos contenido de los documentos,


números estadísticamente validos.

- Perjuicios: Poca precisión numérica, debe implementarse en la aplicación.

- Casos de uso: Contadores en páginas web, cualquier contador sin


necesidad de precisión, estadíticas métricas.

Patrón átipico (Outlier Pattern):

- Problemas: Pocos documentos necesitan la solución, el impacto es


negativo en la mayoría de consultas.

- Solución: No tener miedo de implementar para la mayoría de casos de

59
uso, identificar los campos atípicos como una excepción, ubicar las
excepciones en otro lugar dentro de la aplicación.

- Beneficios: Solución optimizada para la mayoría de casos de uso.

- Perjuicios: Diferentes lugares de almacenamiento en la aplicación,


dificultad para manejar la aplicación de manera uniforme.

- Casos de uso: Redes sociales, popularidad.

MONGODB ADMINISTRADO EN JAVA

60
61
62
Conéctese a su clúster Atlas

1. Cree un nuevo archivo llamado Connection.java con el siguiente código. Este archivo
utiliza su cadena de conexión MongoDB y MongoClient para establecer una conexión con su
clúster Atlas:

package com.mongodb.quickstart;

import com.mongodb.client.MongoClient;

import com.mongodb.client.MongoClients;

import org.bson.Document;

import java.util.ArrayList;

import java.util.List;

public class Connection {

public static void main(String[] args) {

String connectionString = System.getProperty("mongodb.uri");

try (MongoClient mongoClient = MongoClients.create(connectionString)) {

List<Document> databases = mongoClient.listDatabases().into(new


ArrayList<>());

63
databases.forEach(db -> System.out.println(db.toJson()));

2. En la carpeta raíz del proyecto, ejecute el siguiente comando para compilar su proyecto
Maven y conectarse a su clúster Atlas:

mvn compile exec:java -Dexec.mainClass="com.mongodb.quickstart.Connection" -


Dmongodb.uri="<connectionString>"mvn compile exec:java -
Dexec.mainClass="com.mongodb.quickstart.Connection" -
Dmongodb.uri="<connectionString>"

Conéctese a su clúster Atlas editando la configuración (diseño singleton)

private static MongoClient mongoClient;

private static synchronized MongoClient getMongoClient(String uri) {

if (mongoClient == null) {

ConnectionString connectionString = new ConnectionString(uri);

MongoClientSettings settings = MongoClientSettings.builder()

.applyConnectionString(connectionString)

.serverApi(ServerApi.builder()

.version(ServerApiVersion.V1)

.build()

).build();

MongoClient mongoClient = MongoClients.create(settings);

return mongoClient;

Solución a problemas de una conexión MongoDB en aplicaciones Java

64
65
usando $match y $group

Revise el siguiente código, que demuestra cómo crear las etapas y de una canalización de
agregación en MongoDB con Java. $match $group

$match y $group

En los dos ejemplos siguientes, usamos la clase Aggregates de constructor para crear las
etapas y de una canalización de agregattion. $match $group

Primero, usamos para encontrar una cuenta que pertenece a un cliente. Comenzamos
creando un nuevo método llamado que llamamos en el método principal. En, usamos la
clase de constructor para especificar qué cuenta estamos buscando. El método crea una
etapa de canalización que compara los documentos entrantes con el filtro de consulta
especificado y filtra los documentos que no coinciden.

66
$matchmatchStagematchStageFiltersmatch()$match

public static void main(String[] args) {

String connectionString = System.getProperty("mongodb.uri");

try (MongoClient mongoClient = MongoClients.create(connectionString)) {

MongoDatabase db = mongoClient.getDatabase("bank");

MongoCollection<Document> accounts = db.getCollection("accounts");

matchStage(accounts);

private static void matchStage(MongoCollection<Document> accounts){

Bson matchStage = Aggregates.match(Filters.eq("account_id",


"MDB310054629"));

System.out.println("Display aggregation results");

accounts.aggregate(Arrays.asList(matchStage)).forEach(document->
System.out.print(document.toJson()));

En el siguiente ejemplo, usamos y para encontrar los saldos promedio y total de las cuentas
del cliente. Comenzamos creando un nuevo método llamado que llamamos en el método
principal. El método crea una etapa de canalización que compara los documentos entrantes
con el filtro de consulta especificado y filtra los documentos que no coinciden. Luego, el
método crea una etapa de canalización para agrupar documentos por una expresión
específica y generar un documento para cada agrupación distinta.$match
$groupmatchAndGroupStagesmatch()$matchgroup()$group

public static void main(String[] args) {

String connectionString = System.getProperty("mongodb.uri");

try (MongoClient mongoClient = MongoClients.create(connectionString)) {

MongoDatabase db = mongoClient.getDatabase("bank");

MongoCollection<Document> accounts = db.getCollection("accounts");

matchAndGroupStages(accounts);

private static void matchAndGroupStages(MongoCollection<Document> accounts)

67
{

Bson matchStage = Aggregates.match(Filters.eq("account_id",


"MDB310054629"));

Bson groupStage = Aggregates.group("$account_type", sum("total_balance",


"$balance"), avg("average_balance", "$balance"));

System.out.println("Display aggregation results");

accounts.aggregate(Arrays.asList(matchStage,
groupStage)).forEach(document->System.out.print(document.toJson()));

usando $sort y $project

Revise el siguiente código, que demuestra cómo crear las etapas $sorty $projectde una
canalización de agregación en MongoDB con Java.

$sort y $project

En el siguiente ejemplo, usamos la Aggregatesclase de constructor para construir las etapas


$sort y $project de una canalización de agregación. Esta canalización busca todas las
cuentas corrientes con un saldo superior a 1500 y ordena los resultados en orden
descendente. La consulta devolverá solo cuatro campos, incluido un saldo en euros recién
calculado.

El método match() crea una etapa de canalización que compara los documentos entrantes
con el filtro de consulta especificado y filtra los documentos que no coinciden. Luego, el
método crea una etapa de canalización para ordenar según los criterios especificados.
Finalmente, el método crea una etapa de canalización que proyecta campos de documentos
específicos. La proyección de campo en la agregación sigue las mismas reglas que la
proyección de campo en las consultas.$matchsort()$sortproject()$project

public static void main(String[] args) {

String connectionString = System.getProperty("mongodb.uri");

try (MongoClient mongoClient = MongoClients.create(connectionString)) {

MongoDatabase db = mongoClient.getDatabase("bank");

MongoCollection<Document> accounts = db.getCollection("accounts");

matchSortAndProjectStages(accounts);

private static void matchSortAndProjectStages(MongoCollection<Document>


accounts){

Bson matchStage = Aggregates.match(Filters.and(Filters.gt("balance", 1500),

68
Filters.eq("account_type", "checking")));

Bson sortStage = Aggregates.sort(Sorts.orderBy(descending("balance")));

Bson projectStage =
Aggregates.project(Projections.fields(Projections.include("account_id",
"account_type", "balance"), Projections.computed("euro_balance", new
Document("$divide", asList("$balance", 1.20F))), Projections.excludeId()));

System.out.println("Display aggregation results");

accounts.aggregate(asList(matchStage,sortStage,
projectStage)).forEach(document -> System.out.print(document.toJson()));

Insertar un documento en aplicaciones Java

Revise el código siguiente, que muestra cómo insertar un solo documento y varios
documentos en una colección.

Insertar un documento

Para insertar un solo documento en una colección:

Utilice el método getCollection() para acceder al objeto MongoCollection, que se utiliza


para representar la colección especificada.

Agregue el método insertOne() al collectionobjeto.

Dentro de los paréntesis de insertOne(), incluya un objeto que contenga los datos del
documento.

Imprima la identificación del documento insertado.

Aquí hay un ejemplo:

MongoDatabase database = mongoClient.getDatabase("sample_training");

MongoCollection<Document> collection = database.getCollection("inspections");

Document inspection = new Document("_id", new ObjectId())

.append("id", "10021-2015-ENFO")

.append("certificate_number", 9278806)

.append("business_name", "ATLIXCO DELI GROCERY INC.")

.append("date", Date.from(LocalDate.of(2015, 2,
20).atStartOfDay(ZoneId.systemDefault()).toInstant()))

.append("result", "No Violation Issued")

.append("sector", "Cigarette Retail Dealer - 127")

69
.append("address", new Document().append("city",
"RIDGEWOOD").append("zip", 11385).append("street", "MENAHAN
ST").append("number", 1712));

InsertOneResult result = collection.insertOne(inspection);

BsonValue id = result.getInsertedId();

System.out.println(id);

Insertar varios documentos

Para insertar varios documentos en una colección:

Agregue el método insertMany() al collectionobjeto.

Dentro de los paréntesis de insertMany(), incluya un objeto que contenga los datos del
documento.

Imprima las identificaciones de los documentos insertados.

Aquí hay un ejemplo:

MongoDatabase database = mongoClient.getDatabase("bank");

MongoCollection<Document> collection = database.getCollection("accounts");

Document doc1 = new Document()

.append("account_holder","john doe")

.append("account_id","MDB99115881")

.append("balance",1785)

.append("account_type","checking");

Document doc2 = new Document()

.append("account_holder","jane doe")

.append("account_id","MDB79101843")

.append("balance",1468)

.append("account_type","checking");

List<Document> accounts = Arrays.asList(doc1, doc2);

InsertManyResult result = collection.insertMany(accounts);

result.getInsertedIds().forEach((x,y)-> System.out.println(y.asObjectId()));

Consulta de una colección MongoDB en aplicaciones Java

Revise el siguiente código, que demuestra cómo consultar documentos en MongoDB con

70
Java.

Usando find()

En el siguiente ejemplo encontramos todas las cuentas que tienen un saldo mayor o igual a
1000 y son cuentas corrientes. Procesamos cada documento que devuelve el método find()
iterando MongoCursor. El método find() acepta un filtro de consulta y devuelve documentos
que coinciden con el filtro en la colección.

MongoDatabase database = mongoClient.getDatabase("bank");

MongoCollection<Document> collection = database.getCollection("accounts");

try(MongoCursor<Document> cursor = collection.find(and(gte("balance",


1000),eq("account_type","checking")))

.iterator())

while(cursor.hasNext()) {

System.out.println(cursor.next().toJson());

Usando find().first()

Al encadenar los métodos find() y first() se encuentra el primer documento coincidente para
el filtro de consulta que se pasa al método find(). En el siguiente ejemplo, devolvemos un
solo documento de la misma consulta:

MongoDatabase database = mongoClient.getDatabase("bank");

MongoCollection<Document> collection = database.getCollection("accounts");

Document doc = collection.find(Filters.and(gte("balance", 1000),


Filters.eq("account_type", "checking"))).first();

System.out.println(doc.toJson());

Actualización de documentos en aplicaciones Java

Revise el siguiente código, que demuestra cómo actualizar documentos en MongoDB con
Java.

Usando updateOne()

Para actualizar un solo documento, usamos el método updateOne() en un objeto


MongoCollection. El método acepta un filtro que coincide con el documento que queremos
actualizar y una declaración de actualización que indica al controlador cómo cambiar el
documento coincidente. El método updateOne() actualiza solo el primer documento que

71
coincide con el filtro.

En el siguiente ejemplo, actualizamos un documento aumentando el saldo de una cuenta


específica en 100 y configurando el estado de la cuenta como activo:

MongoDatabase database = mongoClient.getDatabase("bank");

MongoCollection<Document> collection = database.getCollection("accounts");

Bson query = Filters.eq("account_id","MDB12234728");

Bson updates =
Updates.combine(Updates.set("account_status","active"),Updates.inc("balance",
100));

UpdateResult upResult = collection.updateOne(query, updates);

Usando updateMany()

Para actualizar varios documentos, usamos el método updateMany() en un objeto


MongoCollection. El método acepta un filtro que coincide con el documento que queremos
actualizar y una declaración de actualización que indica al controlador cómo cambiar el
documento coincidente. El método updateMany() actualiza todos los documentos de la
colección que coinciden con el filtro.

En el siguiente ejemplo, actualizamos muchos documentos agregando un saldo mínimo de


100 a todas las cuentas de ahorro:

MongoDatabase database = mongoClient.getDatabase("bank");

MongoCollection<Document> collection = database.getCollection("accounts");

Bson query = Filters.eq("account_type","savings");

Bson updates = Updates.combine(Updates.set("minimum_balance",100));

UpdateResult upResult = collection.updateMany(query, updates);

Eliminación de documentos en aplicaciones Java

Revise el siguiente código, que demuestra cómo eliminar documentos en MongoDB con
Java.

Usando deleteOne()

Para eliminar un solo documento de una colección, usamos el método deleteOne() en un


objeto MongoCollection. El método acepta un filtro de consulta que coincide con el
documento que queremos eliminar. Si no especificamos un filtro, MongoDB coincide con el
primer documento de la colección. El método deleteOne() elimina solo el primer
documento que coincide.

En el siguiente ejemplo, eliminamos un solo documento que pertenece a la cuenta de John

72
Doe:

MongoDatabase database = mongoClient.getDatabase("bank");

MongoCollection<Document> collection = database.getCollection("accounts");

Bson query = Filters.eq("account_holder", "john doe");

DeleteResult delResult = collection.deleteOne(query);

System.out.println("Deleted a document:");

System.out.println("\t" + delResult.getDeletedCount());

Uso deleteMany() con un objeto de consulta

Para eliminar varios documentos de una colección en una sola operación, llamamos al
método deleteMany() en un objeto MongoCollection. Para especificar qué documentos
eliminar, pasamos un filtro de consulta que coincide con los documentos que queremos
eliminar. Si proporcionamos un documento vacío, MongoDB hace coincidir todos los
documentos de la colección y los elimina.

En el siguiente ejemplo, eliminamos todas las cuentas inactivas mediante un objeto de


consulta. Luego, imprimimos el número total de documentos eliminados.

MongoDatabase database = mongoClient.getDatabase("bank");

MongoCollection<Document> collection = database.getCollection("accounts");

Bson query = eq("account_status", "dormant");

DeleteResult delResult = collection.deleteMany(query);

System.out.println(delResult.getDeletedCount());

Uso deleteMany() con un filtro de consulta

Para eliminar varios documentos de una colección en una sola operación, llamamos al
método deleteMany() en un objeto MongoCollection. Para especificar qué documentos
eliminar, pasamos un filtro de consulta que coincide con los documentos que queremos
eliminar. Si proporcionamos un documento vacío, MongoDB hace coincidir todos los
documentos de la colección y los elimina.

En el siguiente ejemplo, eliminamos todas las cuentas inactivas mediante un filtro de


consulta. Luego, imprimimos el número total de documentos eliminados.

MongoDatabase database = mongoClient.getDatabase("bank");

MongoCollection<Document> collection = database.getCollection("accounts");

DeleteResult delResult = collection.deleteMany(Filters.eq("account_status",


"dormant"));

System.out.println(delResult.getDeletedCount());

73
Creación de transacciones MongoDB en aplicaciones Java

Revise el siguiente código, que demuestra cómo crear transacciones de varios documentos
en MongoDB con Java.

Creación de una transacción

Para iniciar la transacción, usamos el método WithTransaction() de la sesión. Luego


definimos la secuencia de operaciones a realizar dentro de la transacción. Estos son los
pasos para completar una transacción de varios documentos, seguidos del código:

1. Iniciar una nueva sesión.

2. Comience una transacción con el método WithTransaction() en la sesión.

3. Cree variables que se utilizarán en la transacción.

4. Obtenga la información de las cuentas de usuario que se utilizará en la transacción.

5. Cree el documento tranfers.

6. Actualizar las cuentas de usuario.

7. Inserte el documento transfer.

8. Confirmar la transacción.

El código siguiente muestra estos pasos:

final MongoClient client = MongoClients.create(connectionString);

final ClientSession clientSession = client.startSession();

TransactionBody txnBody = new TransactionBody<String>(){

public String execute() {

MongoCollection<Document> bankingCollection =
client.getDatabase("bank").getCollection("accounts");

Bson fromAccount = eq("account_id", "MDB310054629");

Bson withdrawal = Updates.inc("balance", -200);

Bson toAccount = eq("account_id", "MDB643731035");

Bson deposit = Updates.inc("balance", 200);

System.out.println("This is from Account " +


74
fromAccount.toBsonDocument().toJson() + " withdrawn " +
withdrawal.toBsonDocument().toJson());

System.out.println("This is to Account " +


toAccount.toBsonDocument().toJson() + " deposited " +
deposit.toBsonDocument().toJson());

bankingCollection.updateOne(clientSession, fromAccount, withdrawal);

bankingCollection.updateOne(clientSession, toAccount, deposit);

return "Transferred funds from John Doe to Mary Doe";

};

try {

clientSession.withTransaction(txnBody);

} catch (RuntimeException e){

System.out.println(e);

}finally{

clientSession.close();

75

También podría gustarte