Hi folks, i encountered a problem while trying to query a Lucene Index using Hibernate Search. (This is a stock JBOSS-4.2.2.GA build with integrated Hibernate/Lucene)
Use case:
Entities:
Code:
@Entity
@Name("job")
@Table(name = "job", schema = "public")
@Indexed
public class Stelle implements java.io.Serializable {
Long id;
@IndexedEmbedded(depth=3)
private Firm firm;
@Field(index=Index.UN_TOKENIZED)
@FieldBridge(impl = BooleanBridge.class)
private Boolean aktuell;
@ContainedIn
private Person person;
@Id
@GeneratedValue(strategy = SEQUENCE, generator = "generator")
@Column(name = "id", unique = true, nullable = false)
@DocumentId
public Long getId() {
return this.id;
}
public void setId(Long id) {
this.id = id;
}
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "firm_id")
public Firma getFirm() {
return this.firm;
}
public void setFirm(Firm firm) {
this.firm = firm;
}
@Column(name = "current", length = 1)
public Boolean getCurrent() {
return current;
}
public void setAktuell(Boolean current) {
this.current = current;
}
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "person_id")
public Person getPerson() {
return this.person;
}
public void setPerson(Person person) {
this.person = person;
}
}
@Entity
@Table(name = "firm", schema = "public")
@Embeddable
@Name("firm")
public class Firm implements java.io.Serializable {
private Long id;
@Fields( { @Field(index = Index.TOKENIZED),
@Field(name = "ufirmname", index = Index.UN_TOKENIZED) })
private String firmname;
@ContainedIn
private Collection<Job> jobs = new ArrayList<Job>();
@Id
@GeneratedValue(strategy = SEQUENCE, generator = "generator")
@Column(name = "id", unique = true, nullable = false)
@DocumentId
public Long getId() {
return this.id;
}
public void setId(Long id) {
this.id = id;
}
@Column(name = "firmname", length = 50)
public String getFirmname() {
return firmname;
}
public void setFirmname(String firmname) {
this.firmname = firmname;
}
@OneToMany(cascade = { CascadeType.PERSIST, CascadeType.MERGE,
CascadeType.REFRESH }, fetch = FetchType.LAZY, mappedBy = "firm")
public Collection<Job> getJobs() {
return this.jobs;
}
public void setStelles(Collection<Job> jobs) {
this.jobs = jobs;
}
}
@Entity
@Name("person")
@Table(name = "person", schema = "public")
@Indexed
public class Person implements java.io.Serializable {
private Long id;
@IndexedEmbedded(depth = 4)
private Collection<Job> jobs = new ArrayList<Job>();
@Id
@GeneratedValue(strategy = SEQUENCE, generator = "generator")
@Column(name = "id", unique = true, nullable = false)
@DocumentId
public Long getId() {
return this.id;
}
public void setId(Long id) {
this.id = id;
}
@OneToMany(cascade = { CascadeType.PERSIST, CascadeType.MERGE,
CascadeType.REFRESH, CascadeType.REMOVE }, fetch = FetchType.LAZY, mappedBy = "person")
@OrderBy("current")
public Collection<Job> getJobs() {
return this.Jobs;
}
public void setJobs(Collection<Job> jobs) {
this.stelles = stelles;
}
}
Query trying to find person objects:
Code:
+jobs.firm.firmname:siemens* +jobs.current:true
This returns all person objects belonging to siemens* (intended), but also everbody who had a affiliation with siemens* in the past (job.aktuell == false, not intended). I reconstructed the index using Luke and this is what it stores for jobs.aktuell (example with one person having three jobs in the collection):
false false true
To me it seems like Hibernate concatenates all collection values and Lucene assumes a successful match if at least one match (job.aktuell == true) is found in the entire collection.
Is this intended behaviour and why? How do i search the collection in the way i outlined above, i.e. "get all persons who have job.aktuell == true and for this job firm.firmname == siemens*"?