Main entity is Article having list of PriceInfo which holds amount, currency and Provider entity.
Each Provider has a parent and list of children, but only one of those is filled giving me exactly two levels of parent-child relation.
Parent Provider is used for generic prices, for example large brands having many stores around the country. Child Provider is used for specific store in case when article is, for example, on discount in that particular store and not in all stores.
In order to display all Article entries under parent Provider including also those under child Provider I generated a bridge that creates parentId field inside Provider.
During creation of SearchPredicate childProvidersByParentId (line 9, code snippet is below) exception is thrown:
HSEARCH600050: Unable to convert DSL argument: Cannot cast java.lang.Integer to
com.thevegcat.app.entities.provider.Provider
Is it possible to create Integer value and only Integer value instead of whole parent Provider because all other content from parent Provider is not relevant for search? What am I doing wrong?
Java Version: 18.0.2.1
Spring Boot version: 3.0.4
Hibernate version: 6.2.0.CR3
Hibernate Search version: 6.1.8.Final (afraid to put 6.2.0.Alpha2 into production)
Article.java
class Article {
@IndexedEmbedded
private Set<PriceInfo> priceInfos;
}
PriceInfo.java:
class PriceInfo {
private BigDecimal amount;
private CustomCurrency currency;
@IndexedEmbedded
private Provider provider;
}
Provider.java
class Provider {
@GenericField(
projectable = Projectable.NO,
searchable = Searchable.YES,
sortable = Sortable.NO
)
private Integer id;
@GenericField(
name = "parentId",
projectable = Projectable.NO,
searchable = Searchable.YES,
sortable = Sortable.NO,
valueBridge = @ValueBridgeRef(type = ProviderIdBridge.class)
)
private Provider parent;
}
ProviderIdBridge.java
class ProviderIdBridge implements ValueBridge<Provider, Integer> {
@Override
public Integer toIndexedValue(
Provider provider,
ValueBridgeToIndexedValueContext context
) {
if (provider == null) {
return null;
}
return provider.getId();
}
}
Code snippet to generate SearchPredicate:
01 SearchPredicateFactory pf = searchSession.scope(Article.class).predicate();
02
03 SearchPredicate mainProviderById =
04 pf.match()
05 .field("priceInfos.provider.id")
06 .matching(providerId)
07 .toPredicate();
08
09 SearchPredicate childProvidersByParentId =
10 pf.match()
11 .field("priceInfos.provider.parentId")
12 .matching(providerId)
13 .toPredicate();
14
15 SearchPredicate all =
16 pf.bool()
17 .should(mainProviderById)
18 .should(childProvidersByParentId)
19 .minimumShouldMatchNumber(1)
20 .toPredicate();