To clarify: this only applies to an entity which is using a ClassBridge right? For fields of an entity which is not using such a bridge, I would expect the indexing engine to be able to figure out that a specific entity property is not going to be read, without even needing an annotation. Wondering if we can avoid the additional annotation and still do the right thing.
In our case, it's more about transient (computed) fields than about ClassBridge s. But yes, for {{ClassBridge} s the problem would be the same. To clarify, the use case is the following:
@Indexed
@Entity
public class MyClass {
@Id
private Long id;
@Basic
private String field1UsedInTransientIndex;
@Basic
private String field2UsedInTransientIndex;
@Basic
private String field3NOTUsedInTransientIndex;
@Transient
@Field
public int getComputedValue() {
return doSomeComplexCalculation(field1UsedInTransientIndex, field2UsedInTransientIndex);
}
}
In this case, Hibernate Search cannot know (without additional metadata) what entity property the method getComputedValue depend on. Which is, as you said, quite different from knowing which index fields are affected by this method. Currently, it means that whenever Hibernate Search detects an @Transient @Field, it disables dirty-checking completely. One solution, proposed in https://hibernate.atlassian.net/browse/HSEARCH-1093, would be to add an annotation to declare which entity properties this method rely on:
@Basic
private String field1UsedInTransientIndex;
@Basic
private String field2UsedInTransientIndex;
@Basic
private String field3NOTUsedInTransientIndex;
@AssociateDirty(fields={"field1UsedInTransientIndex", "field2UsedInTransientIndex"}) @Transient
@Field
public int getComputedValue() {
return doSomeComplexCalculation(field1UsedInTransientIndex, field2UsedInTransientIndex);
}
That way, Hibernate Search would consider that whenever "field1UsedInTransientIndex" or "field2UsedInTransientIndex" are dirty, then the "computedValue" field needs reindexing. This seems like a valid solution, but: 1. Nobody seems to have time to implement it right now (judging by the last update on the JIRA ticket) 2. This would not solve the issue for ClassBridge s (unless we allow adding this annotation on a ClassBridge 's class?) The other solution, proposed in this ticket, would be to add an annotation to declare which entity properties no field (i.e. no @Transient @Field method, no ClassBridge) depend on:
@Basic
private String field1UsedInTransientIndex;
@Basic
private String field2UsedInTransientIndex;
@Basic
@IndexTransient private String field3NOTUsedInTransientIndex;
@Transient
@Field
public int getComputedValue() {
return doSomeComplexCalculation(field1UsedInTransientIndex, field2UsedInTransientIndex);
}
That way, we could implement a preliminary check in the FullTextIndexEventListener whenever a Hibernate update occurs: if all of the dirty properties are annotated @IndexTransient, then skip re-indexing. This second solution would provide a way to positively identify entity properties that are not used when indexing. Currently either we are sure they are used (annotated @Field) or we don't know (no annotation). With this annotation, we'd have a third category, where we know the property is not used when indexing. I think this second solution really is relevant even if the first is ultimately implemented: if I've got 3 properties and 10 @Transient @Field methods, I'd rather just annotate one property with @IndexTransient than annotate my 10 methods with @AssociateDirty... |