Pregunta

Estoy buscando agregar los siguientes datos

{
   "user": "user1",
   "error": true 
}
{
   "user": "user2",
   "error": false
}
{
   "user": "user1",
   "error": false
}

En

{
     "_id": "user1",
     "errorCount": 1,
     "totalCount": 2
},
{
     "_id": "user2",
     "errorCount": 0,
     "totalCount": 1
}

Con el operador con cond, esto se puede lograr usando:

$group: {
    _id: "$user",
    errorCount : { "$sum" : {"$cond" : ["$error", 1, 0]}},
    totalCount : { "$sum" : 1 }
}

Sin embargo, dado que estoy usando Spring-data-mongodb que aún no admite con cond (a partir de la VERSIÓN 1.3.4), no pude hacer esto.

¿Hay alguna manera de hacer la misma agregación sin con cond?

¿Fue útil?

Solución

No está obligado a esto, incluso si aún no hay una "interfaz funcional" en Spring data.(Por cierto, levanta una JIRA)

Simplemente obtenga el formulario nativo y use los tipos BasicDBObject en la canalización.Entonces, en principio:

    DBCollection myCollection = mongoOperation.getCollection("collection");

    <result cast> = myCollection.aggregate(<pipeline here>);

Spring data te da abstracciones, pero no lo hace prohibir el uso de la nativo funciones del conductor.En realidad te da accesores para usarlos, como demostré anteriormente.

Otros consejos

Gracias a la sugerencia de Neil Lunn, he logrado obtener con cond para usar el soporte de agregación de spring-data.Para hacer esto, debe implementar la interfaz AggregationOperation para incorporar un DBObject.

public class DBObjectAggregationOperation implements AggregationOperation {
  private DBObject operation;

  public DBObjectAggregationOperation (DBObject operation) {
    this.operation = operation;
  }

  @Override
  public DBObject toDBObject(AggregationOperationContext context) {
    return context.getMappedObject(operation);
  }
}

Entonces podrá usarlo en la agregación de tipos normalmente:

DBObject operation = (DBObject)JSON.parse ("your pipleline here...");
TypedAggregation<UserStats> aggregation = newAggregation(User.class,
    new DBObjectAggregationOperation(operation)
    );
AggregationResults<UserStats> result = mongoTemplate.aggregate(aggregation, UserStats.class); 

Este enfoque le permitirá utilizar cualquier operador de agregación que aún no esté definido en el marco.Sin embargo, también omitió la validación implementada por spring-data y debe usarse con precaución.
Vote si desea que el operador con cond sea compatible correctamente a través del marco: https://jira.springsource.org/browse/DATAMONGO-861

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