2014-05-25 120 views
4

我使用JPA與Hibernate作爲JPA提供程序。我無法弄清楚如何配置我的實體以將一個休眠過濾器應用於一對多關聯。我有一個Master收集Details。這裏是我的實體定義:Hibernate @Filter在JPA中不起作用?

@Entity 
public class Master extends Base { 
    private List<Detail> details; 

    @OneToMany 
    @OrderColumn 
    @JoinTable(name = "master_details") 
    @Filter(name = "notDeleted") 
// @Where(clause = "deleted = 'false'") 
    public List<Detail> getDetails() { 
     return details; 
    } 

    public void setDetails(List<Detail> details) { 
     this.details = details; 
    } 
} 

@Entity 
@FilterDef(name = "notDeleted", defaultCondition = "deleted = false") 
public class Detail extends Base { 
    private Boolean deleted = false; 

    public Boolean getDeleted() { 
     return deleted; 
    } 

    public void setDeleted(Boolean deleted) { 
     this.deleted = deleted; 
    } 
} 

Base沒什麼特別的,但一個簡單的MappedSuperClass

@MappedSuperclass 
public class Base { 
    private Long id; 

    @Id 
    @GeneratedValue(strategy = GenerationType.IDENTITY) 
    public Long getId() { 
     return id; 
    } 

    public void setId(Long id) { 
     this.id = id; 
    } 
} 

當加載MasterentityManager.find(Master.class, mid),過濾器應prvent所有Details加載,但我查了SQL由hibernate生成的查詢(按show_sql=true),並且在加載主節點時不添加where子句!由Hibernate生成的查詢示例是:

select 
    details0_.Master_id as Master1_6_1_, 
    details0_.details_id as details2_1_, 
    details0_.details_ORDER as details3_1_, 
    detail1_.id as id7_0_, 
    detail1_.deleted as deleted7_0_, 
from 
    master_details details0_ 
inner join 
    Detail detail1_ 
     on details0_.details_id=detail1_.id 
where 
    details0_.Master_id=? 

一些搜索後有一些跡象表明「加載由ID不使用過濾器,使用查詢」,所以我嘗試以下,但沒有收穫:(

entityManager.createQuery("from Master where id=" + mid).getSingleResult(); 

但是,僅僅如果上述@Where getDetails未被註釋(而不是@Filter),它的條款被添加到由休眠生成查詢(但我不能使用@Where

+0

我有同樣的問題,我可以確認通過ID加載不會使用過濾器,使用queries_。如果你有更多的信息,爲什麼會這樣,那會很好。同樣通過id_的_loading,我們的意思是'session.get(Entity.class,id)',對吧? –

回答

6

過濾器需要被激活的手動:

session.enableFilter("myFilter").setParameter("myFilterParam", "some-value"); 

但過濾器需要一個參數,你似乎不需要一個。

所以,如果你加

@org.hibernate.annotations.Where(clause="deleted=false")   
public List<Detail> getDetails() { 
    return details; 
} 

你應該得到的不刪Details列表。

我不明白你爲什麼要使用1<>0條件。

+0

'1 <> 0'只是用來表示一個微不足道的條件。你是對的,不好主意:) – rabolfazl

+0

你有沒有試過@Where子句? –