Obtenga el último registro de la colección mongodb


99

Quiero saber el registro más reciente de una colección. ¿Como hacer eso?

Nota: sé que las siguientes consultas de línea de comando funcionan:

1. db.test.find().sort({"idate":-1}).limit(1).forEach(printjson);
2. db.test.find().skip(db.test.count()-1).forEach(printjson)

donde idate tiene la marca de tiempo agregada.

El problema es que más tiempo de recopilación es el momento de recuperar los datos y mi recopilación de "prueba" es realmente enorme. Necesito una consulta con respuesta en tiempo constante.

Si hay alguna consulta mejor en la línea de comandos de mongodb, hágamelo saber.

Respuestas:


138

Esta es una repetición de la respuesta anterior, pero es más probable que funcione en diferentes versiones de mongodb.

db.collection.find().limit(1).sort({$natural:-1})

10
db.collection.find().limit(1).sort({$natural:-1}).pretty()si quieres que se vea bien
— Anthony

Entonces, ¿cuál es la diferencia con este orden:db.collection.find().sort({$natural:-1}).limit(1).pretty()
— Leo

@Digits qué impacto en el rendimiento tendrá si colocamos un límite al final y también cómo se obtiene el último registro cuando se limita la salida a un solo documento y debe ser el documento superior de la colección.
— kailash yogeshwar

Buena respuesta. Intenté así: db.collection ("nombre de la colección"). Find ({}, {limit: 1}). Sort ({$ natural: -1})
— Abdul Alim Shakir

Para cualquier persona que utilice AWS DocDB: Query failed with error code 303 and error message 'option $natural is not supported' on server docdb. Ojalá esa característica llegue pronto.
— Marc

34

Esto le dará un último documento para una collection

db.collectionName.findOne({}, {sort:{$natural:-1}})

$natural:-1 significa orden opuesto al que se insertan los registros.

Editar : Para todos los votantes negativos, arriba hay una sintaxis de Mongoose, la sintaxis de CLI de mongo es:db.collectionName.find({}).sort({$natural:-1}).limit(1)


7
Tu sintaxis parece estar mal. No puedo hacer que funcione como lo tiene. Lo que sí funciona es: 'db.punchdeck.findOne ({$ query: {}, $ orderby: {$ natural: -1}})'
— Dave Lowerre

no estoy seguro, por qué todos los votos negativos: este código funciona perfectamente para mí y es rápido
— dark_ruby

2
@dark_ruby Tu consulta devuelve el error "$ err": "No se puede canonicalizar la consulta: BadValue Opción de proyección no admitida: ordenar: {$ natural: -1.0}",
— Roman Podlinov

20

Necesito una consulta con respuesta en tiempo constante.

Por defecto, los índices en MongoDB son B-Trees. La búsqueda de un árbol B es una operación O (logN), por lo que incluso find({_id:...})no proporcionará respuestas O (1) de tiempo constante.

Dicho esto, también puede ordenar por _idsi está utilizando ObjectIdpara sus ID. Consulte aquí para obtener más detalles . Por supuesto, incluso eso solo es bueno hasta el último segundo.

Puede recurrir a "escribir dos veces". Escriba una vez en la colección principal y vuelva a escribir en una colección "actualizada por última vez". Sin transacciones esto no será perfecto, pero con un solo artículo en la colección "última actualización" siempre será rápido.


2
Veo muchas soluciones noSQL y MongoDB que abogan por "escribir dos veces", principalmente para los titulares de conteos cuando el tamaño de los datos se vuelve muy grande. ¿Supongo que esto es una práctica común?
— Vinny

MongoDB no se descarga en el disco con mucha frecuencia y no tiene transacciones, por lo que las escrituras se vuelven significativamente más rápidas. La compensación aquí es que se le anima a desnormalizar los datos, lo que a menudo conduce a múltiples escrituras. Por supuesto, si obtiene un rendimiento de escritura de 10x o 100x (que he visto), entonces 2x o 3x las escrituras siguen siendo una gran mejora.
— Vicepresidente de Gates

13

Otra forma más de obtener el último elemento de una colección MongoDB (no te preocupes por los ejemplos):

> db.collection.find().sort({'_id':-1}).limit(1)

Proyección normal

> db.Sports.find()
{ "_id" : ObjectId("5bfb5f82dea65504b456ab12"), "Type" : "NFL", "Head" : "Patriots Won SuperBowl 2017", "Body" : "Again, the Pats won the Super Bowl." }
{ "_id" : ObjectId("5bfb6011dea65504b456ab13"), "Type" : "World Cup 2018", "Head" : "Brazil Qualified for Round of 16", "Body" : "The Brazilians are happy today, due to the qualification of the Brazilian Team for the Round of 16 for the World Cup 2018." }
{ "_id" : ObjectId("5bfb60b1dea65504b456ab14"), "Type" : "F1", "Head" : "Ferrari Lost Championship", "Body" : "By two positions, Ferrari loses the F1 Championship, leaving the Italians in tears." }

Proyección ordenada (_id: orden inverso)

> db.Sports.find().sort({'_id':-1})
{ "_id" : ObjectId("5bfb60b1dea65504b456ab14"), "Type" : "F1", "Head" : "Ferrari Lost Championship", "Body" : "By two positions, Ferrari loses the F1 Championship, leaving the Italians in tears." }
{ "_id" : ObjectId("5bfb6011dea65504b456ab13"), "Type" : "World Cup 2018", "Head" : "Brazil Qualified for Round of 16", "Body" : "The Brazilians are happy today, due to the qualification of the Brazilian Team for the Round of 16 for the World Cup 2018." }
{ "_id" : ObjectId("5bfb5f82dea65504b456ab12"), "Type" : "NFL", "Head" : "Patriots Won SuperBowl 2018", "Body" : "Again, the Pats won the Super Bowl" }

sort({'_id':-1}), define una proyección en orden descendente de todos los documentos, en función de su _ids.

Proyección ordenada (_id: orden inverso): obtener el último (último) documento de una colección.

> db.Sports.find().sort({'_id':-1}).limit(1)
{ "_id" : ObjectId("5bfb60b1dea65504b456ab14"), "Type" : "F1", "Head" : "Ferrari Lost Championship", "Body" : "By two positions, Ferrari loses the F1 Championship, leaving the Italians in tears." }

2

php7.1 mongoDB:
$data = $collection->findOne([],['sort' => ['_id' => -1],'projection' => ['_id' => 1]]);


1

Mi solución :

db.collection("name of collection").find({}, {limit: 1}).sort({$natural: -1})


0

Si está utilizando identificadores de objeto Mongo generados automáticamente en su documento, contiene una marca de tiempo en los primeros 4 bytes con el último documento insertado en la colección. Entiendo que esta es una pregunta antigua, pero si alguien aún termina aquí buscando una alternativa más.

db.collectionName.aggregate(
[{$group: {_id: null, latestDocId: { $max: "$_id"}}}, {$project: {_id: 0, latestDocId: 1}}])

La consulta anterior daría el _id para el último documento insertado en la colección


0

Así es como se obtiene el último registro de todos los documentos MongoDB de la colección "foo" (cambie foo, x, y, etc.)

db.foo.aggregate([{$sort:{ x : 1, date : 1 } },{$group: { _id: "$x" ,y: {$last:"$y"},yz: {$last:"$yz"},date: { $last : "$date" }}} ],{   allowDiskUse:true  })

puedes agregar o quitar del grupo

artículos de ayuda: https://docs.mongodb.com/manual/reference/operator/aggregation/group/#pipe._S_group

https://docs.mongodb.com/manual/reference/operator/aggregation/last/

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.