Pregunta

Tengo una colección que contiene un campo de fecha.Quiero agruparlo por DIGNOFMONTH, pero en el momento de la proyección, quiero proyectar la fecha completa y la cuenta asociada.

Tengo una colección cruda en Mongodb que contiene una marca de tiempo (campo de fecha) Esta es mi consulta de agregación:

db.raw.aggregate(
{
    "$match" : { "Timestamp":{$gte:new Date("2012-05-30T00:00:00.000Z"),$lt:new Date("2014-05-31T00:00:00.000Z")}}
},
{ 
    $group: 
    { 
        _id: { ApplicationId: "$ApplicationId", date: {$dayOfMonth: '$Timestamp'}   }, 
        count: { $sum: 1 } 
    }
}
)

En la consulta anterior, estoy agrupando con Dayof Month, pero ¿cómo puedo proyectar la fecha con el conteo?

¿Fue útil?

Solución

Los valores de su "timestamp" son claramente puntos reales a tiempo, por lo que realmente no hay una "fecha completa" para volver. Usted podría generalmente "hacer las matemáticas" según el intervalo de fechas que está solicitando y los valores "Día de Mes" devueltos a medida que procesa los resultados devueltos.

Pero alternativamente, podría "aplicar las matemáticas" a los valores de la fecha en orden al redondear los valores de "Timestamp" al día. Los valores devueltos ya no son objetos de fecha, pero son el milisegundo desde los valores de Epoch, por lo que es relativamente fácil "sembrar" las funciones de fecha:

db.raw.aggregate([
    { "$match" : { 
        "Timestamp":{
            "$gte": new Date("2012-05-30"), 
            "$lt": new Date("2014-05-31")
        }
    }},
    { "$group": {
        "_id": {
            "$subtract": [
                { "$subtract": [ "$Timestamp", new Date("1970-01-01") ] },
                { "$mod": [
                    { "$subtract": [ "$Timestamp", new Date("1970-01-01") ] },
                    1000 * 60 * 60 * 24
                ])
            ]
        },
        "count": { "$sum": 1 }
    }}
])

Entonces, cuando reste un objeto de fecha de otra, la diferencia es que los milisegundos se devuelven como un número. Así que esto se normaliza a los segundos de Epoch restando la fecha de la época. El resto es la fecha básica de matemáticas para redondear el resultado al día actual.

Alternativamente, simplemente podría usar otros operadores de agregación de fecha y concatenar a una cadena, pero generalmente habría un poco más de trabajo involucrado a menos que esos valores fuera para uso directo:

db.raw.aggregate([
    { "$match" : { 
        "Timestamp":{
            "$gte": new Date("2012-05-30"), 
            "$lt": new Date("2014-05-31")
        }
    }},
    { "$group": {
        "_id": {
            "$concat": [
                 { "$substr": [{ "$year": "$Timestamp" },0,4] },
                 "-",
                 { "$substr": [{ "$month": "$Timestamp" },0,2] },
                 "-",
                 { "$substr": [{ "$dayOfMonth": "$Timestamp" },0,2] }
            ]
        },
        "count": { "$sum": 1 }
    }}
])

Otros consejos

Neil Lunn ha proporcionado una gran respuesta. Su enfoque más que puedes usar:

db.raw.aggregate([
    {
        "$match" : 
            {   
                "Timestamp":{"$gte": new Date("2012-05-30"), "$lt": new Date("2014-07-31")}
            }
    },
    { 
        "$group" :
            {   
                "_id":{"$dayOfMonth": "$Timestamp"},
                "Date":{"$first":"$Timestamp"},
                "count": { "$sum": 1 }
            }
    }
])

le devolverá la fecha. Espero que esto te ayude.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top