2015-06-15 131 views
5

我正在使用spring-data-mongodb。spring-data-mongodb可選查詢參數

我想通過在查詢中傳遞一些可選參數來查詢數據庫。

我有一個域類。

public class Doc { 
    @Id 
    private String id; 

    private String type; 

    private String name; 

    private int index; 

    private String data; 

    private String description; 

    private String key; 

    private String username; 
    // getter & setter 
} 

我的控制器:

@RequestMapping(value = "/getByCategory", method = RequestMethod.GET, consumes = MediaType.APPLICATION_JSON, produces = MediaType.APPLICATION_JSON) 
    public Iterable<Doc> getByCategory(
      @RequestParam(value = "key", required = false) String key, 
      @RequestParam(value = "username", required = false) String username, 
      @RequestParam(value = "page", required = false, defaultValue = "0") int page, 
      @RequestParam(value = "size", required = false, defaultValue = "0") int size, 
      @RequestParam(value = "categories") List<String> categories) 
      throws EntityNotFoundException { 
     Iterable<Doc> nodes = docService.getByCategory(key, username , categories, page, size); 
     return nodes; 
    } 

這裏重點用戶名是可選的查詢參數。

如果我傳遞了其中的任何一個,它應該返回給定密鑰或用戶名的匹配文檔。

我的服務的方法是:

public Iterable<Doc> getByCategory(String key, String username, List<String> categories, int page, int size) { 

     return repository.findByCategories(key, username, categories, new PageRequest(page, size)); 
    } 

庫:

@Query("{ $or : [ {'key':?0},{'username':?1},{categories:{$in: ?2}}] }")  
List<Doc> findByCategories(String key, String username,List<String> categories, Pageable pageable); 

但是,通過使用上面的查詢不返回文檔與任一給定的密鑰或用戶名。 我的查詢出了什麼問題?

這是我想提出的請求 http://localhost:8080/document/getByCategory?key=key_one&username=ppotdar&categories=category1&categories=category2

+0

您可以開始設置MongoDB事件探查器,使用命令db.setProfilingLevel(2)記錄所有操作(以及查詢),然後準確查看您正在執行的查詢。請記住,完成後將其設置爲0。 – araknoid

回答

0

就個人而言,我想在這一點上溝接口驅動庫模式,創建一個DAO是@Autowire SA MongoTemplate對象,然後通過查詢數據庫改爲Criteria。那樣的話,你有明確的代碼不能擴展@Query註釋的功能。

所以,像這樣(未經測試的僞代碼):

@Repository 
public class DocDAOImpl implements DocDAO { 
    @Autowired private MongoTemplate mongoTemplate; 

    public Page<Doc> findByCategories(UserRequest request, Pageable pageable){ 
     //Go through user request and make a criteria here 
     Criteria c = Criteria.where("foo").is(bar).and("x").is(y); 
     Query q = new Query(c); 
     Long count = mongoTemplate.count(q); 

     // Following can be refactored into another method, given the Query and the Pageable. 
     q.with(sort); //Build the sort from the pageable. 
     q.limit(limit); //Build this from the pageable too 
     List<Doc> results = mongoTemplate.find(q, Doc.class); 
     return makePage(results, pageable, count); 
    } 

    ... 
} 

我知道這蒼蠅對運行時產生的DB代碼潮流的臉,但在我看來,它仍然是最好的方法來處理更具挑戰性的數據庫操作,因爲它更易於查看實際正在進行的操作。