mongodbviewspring-data-mongodb

Use MongoDB views in Spring-Data


To improve our query performances and hence the API response times, we created views on MongoDB by aggregating the data.

However, when we try to use the view with Spring-Data's MongoTemplate, we run into several issues like "View not supported":

Caused by: com.mongodb.MongoCommandException: Command failed with error 166 (CommandNotSupportedOnView): 'Namespace aiops.hostView is a view, not a collection' on server 192.168.20.166:30011. The full response is {​​​​​​​"ok": 0.0, "errmsg": "Namespace aiops.hostView is a view, not a collection", "code": 166, "codeName": "CommandNotSupportedOnView"}​​​​​​​
at com.mongodb.internal.connection.ProtocolHelper.getCommandFailureException(ProtocolHelper.java:175)
at com.mongodb.internal.connection.InternalStreamConnection.receiveCommandMessageResponse(InternalStreamConnection.java:303)
at com.mongodb.internal.connection.InternalStreamConnection.sendAndReceive(InternalStreamConnection.java:259)

Does Spring support MongoDB views out of the box (any example will help)?


Solution

  • This is somewhat old, but I will leave my solution in case someone stumbles on this, like I did.

    As far as I know, you can't use the usual Spring Data approach: you can't annotate an Entity with the @Document(value="YOUR_VIEW_NAME") annotation and create a related repository extending the MongoRepository class.

    But you can query the view directly from the MongoTemplate, passing along the name of your view.

    Let's say you have a User entity defined like this:

    public class User {
        @Id
        String id;
    
        String name;
    }
    

    Then you can map it to the documents of a view named "userview", and query it like this:

    
    Query query = new Query();
    query.addCriteria(Criteria.where("name").is("Bob"));
    
    // template is an object of class MongoTemplate that you can inject or autowire
    List<User> users = template.find(query, User.class, "userview");