Hibernate filter Entity where oneToMany relation contains an object

hibernate, hibernate-filters, java

Solution

If you are comfortable with Criteria you could create criteria like this

Session hbSession= sessionFactory.openSession();
Criteria criteria = hbSession.createCriteria(Message.class);
criteria.createCriteria("msgUserList","userListAlias");// msgUserList is variable name of users list in Message
criteria.add(Restrictions.eq("userListAlias.user",myUser));//user is variable for User type in msgUserList's class.
List<Message> userMessages = criteria.list();

Have a look at this for reference while creating criteria!

If you only want to use filter then I hope you have configured filter on your `User` `List` some thing like bellow

By *.hbm.xml

<hibernate-mapping package="com....">
    <class name="Message" table="message_table">
        ....
        <list name="msgUserList" inverse="true" cascade="all">
            <key column="user_id" />
            <one-to-many class="MessageUsers" />
            <filter name="userRecipient" condition="user_id =:userParam" />
        </list>
    </class>
    <filter-def name="userRecipient">
        <filter-param name="userParam" type="User" />//User is class
    </filter-def>
</hibernate-mapping>

Or By annotation

@Entity
@FilterDef(name="userRecipient", 
parameters=@ParamDef(name="userParam", type="PAKAGE.User" ))
@Table(name = "message_table", catalog = "your_db")
public class Message{

...
@OneToMany(fetch = FetchType.LAZY, mappedBy = "stock")
@Filter(name = "userRecipient",condition="user = :userParam")
public List<MessageUser> msgUserList;

after this you will be able get your filter working

Filter filter = session.enableFilter("userRecipient");
filter.setParameter("userParam", myUser);

Update

Purpose of `Filter` is different than the `Criteria`, from my understanding you can say that `Filter` is just like a Criteria that is already applied on your class or collection which has `on` and `off` switch. If your hibernate session has certain filter enabled with it's parameters set than that filter is `on` and all queries relating to the class or collection which has this filter specified will always return filtered result as per the condition. This means you don't have to explicitly define it every time and by using `getEnabledFilter("filterName")` you can just change that filter's parameters any time.

Example usage of filter can be if you have `Movies` table and `Actor` table with many-to-many relationship, like `Leonardo Dicaprio` can have many movies at the same times A `titanic` can have many actors, here when you get `Actor` obviously you would want only those movies which this `Actor` has performed in, so you can use filter here which is applied on collection of `Movies` that is mapped in `Actor` class. This way when you get `Actor` object say by simple criteria of name and nothing else and access it's `Movie` collection by `.` operator on `Actor` object it will return you only movies which that actor has performed. This also means no matter how you got `Actor` object from database when you access `Movie` collection of `Actor` it will provide you movies that this actor has performed in

Criteria on the other hand you can use when you require result from database with certain conditions which does not need to be replicated rather you don't want it to be replicated later in the hibernate session. Like `Actor` lets say `Leonardo Dicaprio` containing collection of `Movies` that got nominated him in Oscar. This collection will only be populated in `Actor` object when gone through certain criteria and will not be available on other `Actor` objects which have not being retrieved by this criteria.

I hope you understood basic concept of filter and criteria, and from my understanding of your problem it will be better if you use criteria!

Problem

I want to use the hibernate filter but I don't know if what I want to do is possible I have 2 entities : Message and MessageUser. A Message has a list of MessageUser. I want to create a filter so I can do something like : ``` final Session filteredSession = sessionFactory.openSession(); final Filter filter = filteredSession.enableFilter("userRecipient"); filter.setParameter("userRecipient", myUser); filter.validate(); final List<Message> userMessages = filteredSession.createQuery("from Message").list(); ``` it returns me only the message where myUser is the recipient ? is it possible to to and how? Thanks a lot !

Original source