DefaultFilterDialect implements JoinFilterDialect, SubqueryFilterDialect { @Override public Map<String, FilterExpression> parseTypedExpression(String path, MultivaluedMap<String, String> filterParams) throws ParseException { Map<String, FilterExpression> expressionMap = new HashMap<>(); List<FilterPredicate> filterPredicates = extractPredicates(filterParams); for (FilterPredicate filterPredicate : filterPredicates) { validateFilterPredicate(filterPredicate); String entityType = dictionary.getJsonAliasFor(filterPredicate.getEntityType()); FilterExpression filterExpression = expressionMap.get(entityType); if (filterExpression != null) { expressionMap.put(entityType, new AndFilterExpression(filterExpression, filterPredicate)); } else { expressionMap.put(entityType, filterPredicate); } } return expressionMap; } DefaultFilterDialect(EntityDictionary dictionary); @Override FilterExpression parseGlobalExpression(String path, MultivaluedMap<String, String> filterParams); @Override Map<String, FilterExpression> parseTypedExpression(String path, MultivaluedMap<String, String> filterParams);  }
@Test public void testTypedExpressionParsing() throws Exception { MultivaluedMap<String, String> queryParams = new MultivaluedHashMap<>(); queryParams.add( "filter[book.title][in]", "foo,bar,baz" ); queryParams.add( "filter[book.genre]", "scifi" ); queryParams.add( "filter[author.name][infix]", "Hemingway" ); queryParams.add( "filter[author.books.title][in]", "foo,bar,baz" ); Map<String, FilterExpression> expressionMap = dialect.parseTypedExpression("/author", queryParams); assertEquals(2, expressionMap.size()); assertEquals("(book.title IN [foo, bar, baz] AND book.genre IN [scifi])", expressionMap.get("book").toString()); assertEquals("(author.books.title IN [foo, bar, baz] AND author.name INFIX [Hemingway])", expressionMap.get("author").toString()); }
@Test public void testInvalidType() throws ParseException { MultivaluedMap<String, String> queryParams = new MultivaluedHashMap<>(); queryParams.add( "filter[invalid.title][in]", "foo,bar,baz" ); assertThrows(ParseException.class, () -> dialect.parseTypedExpression("/invalid", queryParams)); }
@Test public void testInvalidAttribute() throws ParseException { MultivaluedMap<String, String> queryParams = new MultivaluedHashMap<>(); queryParams.add( "filter[book.invalid][in]", "foo,bar,baz" ); assertThrows(ParseException.class, () -> dialect.parseTypedExpression("/book", queryParams)); }
@Test public void testInvalidTypeQualifier() throws ParseException { MultivaluedMap<String, String> queryParams = new MultivaluedHashMap<>(); queryParams.add( "filter[author.books.title][in]", "foo,bar,baz" ); Map<String, FilterExpression> expressionMap = dialect.parseTypedExpression("/author", queryParams); assertEquals(1, expressionMap.size()); assertEquals("author.books.title IN [foo, bar, baz]", expressionMap.get("author").toString()); }
@Test public void testEmptyOperatorException() throws Exception { MultivaluedMap<String, String> queryParams = new MultivaluedHashMap<>(); queryParams.add( "filter[book.authors.name][isempty]", "" ); assertThrows(ParseException.class, () -> dialect.parseTypedExpression("/book", queryParams)); }
@Test public void testMemberOfOperator() throws Exception { MultivaluedMap<String, String> queryParams = new MultivaluedHashMap<>(); queryParams.add( "filter[book.awards][hasnomember]", "awards1" ); assertEquals( "{book=book.awards HASNOMEMBER [awards1]}", dialect.parseTypedExpression("/book", queryParams).toString() ); }
@Test public void testMemberOfOperatorException() throws Exception { MultivaluedMap<String, String> queryParams = new MultivaluedHashMap<>(); queryParams.add( "filter[book.authors.name][hasmember]", "name" ); assertThrows(ParseException.class, () -> dialect.parseTypedExpression("/book", queryParams)); queryParams.clear(); queryParams.add( "filter[book.title][hasmember]", "title" ); assertThrows(ParseException.class, () -> dialect.parseTypedExpression("/book", queryParams)); }