-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 14 posts ] 
Author Message
 Post subject: how to create Criteria using composite-element property
PostPosted: Wed Jun 15, 2005 12:35 am 
Beginner
Beginner

Joined: Mon Sep 27, 2004 3:48 am
Posts: 23
Invoice.java
Code:
...
  /**
    *
    * @hibernate.list lazy="true" table="STATUS_CHANGE"
    * @hibernate.collection-key column="STATEFUL_ID"
    * @hibernate.collection-index column="POSITION"
    * @hibernate.collection-composite-element class="StatusChange"
    *
    * @return Returns the payment categories.
    */
  public List getHistory() {
    return history;
  }
....


StatusChange .java
Code:
   private String id;
   private Date statusChangeDate;
   private String note;
   private boolean isCurrent;
   private String status; // new / pending / approved / rejected
   ....

  /**
   * @hibernate.property name="isCurrent"
   *   column="IS_CURRENT"
   *   not-null="true"
   */
  public boolean isCurrent()
  {
    return isCurrent;
  }

  /**
   * @hibernate.property name="status"
   *    column="STATUS"
   * @return
   */
  public String getStatus() {
    return status;
  }



if I want to get the list of invoice objects whose history include a record its isCurrent=true and status='new', and I do not want to use HQL but would rather the Criteria like this:

Criteria criteria =session.createCriteria(Invoice.class)
.add(...

How to do it?


[/code]


Top
 Profile  
 
 Post subject:
PostPosted: Tue Nov 22, 2005 12:25 pm 
Newbie

Joined: Fri Nov 04, 2005 12:32 pm
Posts: 14
Location: Detroit, MI, USA
I think this is what you are looking for:

Code:
Criteria criteria = session.createCriteria(Invoice.class)
                                     .createCriteria(StatusChange.class)
                                     .add(Restrictions.eq("status", "new"))
                                     .add(Restrictions.eq("isCurrent", true));


Top
 Profile  
 
 Post subject:
PostPosted: Tue Nov 22, 2005 12:26 pm 
Newbie

Joined: Fri Nov 04, 2005 12:32 pm
Posts: 14
Location: Detroit, MI, USA
Sorry, I didn't notice that the history objects was a List.


Top
 Profile  
 
 Post subject:
PostPosted: Wed Nov 23, 2005 1:42 am 
Expert
Expert

Joined: Thu May 26, 2005 9:19 am
Posts: 262
Location: Oak Creek, WI
Hi

You can use Expression for this
e.g crt.add(Expression.eq("status", "new"));

so you will see a where clause in the Hibernate generated Query with status.

_________________
RamnathN
Senior Software Engineer
http://www.linkedin.com/in/ramnathn
Don't forget to rate.


Top
 Profile  
 
 Post subject:
PostPosted: Wed Nov 23, 2005 3:17 am 
Beginner
Beginner

Joined: Tue Nov 22, 2005 4:53 pm
Posts: 41
Location: Netherlands
cheeser wrote:
I think this is what you are looking for:

Code:
Criteria criteria = session.createCriteria(Invoice.class)
                                     .createCriteria(StatusChange.class)
                                     .add(Restrictions.eq("status", "new"))
                                     .add(Restrictions.eq("isCurrent", true));


Almost correct ;)

Code:
Criteria criteria = session.createCriteria(Invoice.class)
                                     .createCriteria("history")
                                     .add(Restrictions.eq("status", "new"))
                                     .add(Restrictions.eq("current", true));


The base Criteria you specify by Class.. each relation you specify by creating a criteria for that relation by attribute name.

So this works as well:
Code:
Criteria invoiceCriteria = session.createCriteria(Invoice.class);
Criteria historyCriteria = invoiceCriteria.createCriteria("history");
historyCriteria.add(Restrictions.eq("status", "new")).add(Restrictions.eq("current", true));

Criteria otherCriteria = invoiceCriteria.createCriteria("otherAttribute");
otherCriteria.add(Restrictions.gt("value", value);

// etc..


N.B.

You property isCurrent should be called only current.
The methods for this property than will be isCurrent() and setCurrent();
That is the normal standard for boolean attributes.

And I thought that the reflection, used by Hibernate will search for a 'get' or 'is' method to get the attributes value.

So if you specify 'isCurrent' in you Criteria, Hibernate will probably seach for getIsCurrent() or isIsCurrent ;)[/b]


Top
 Profile  
 
 Post subject:
PostPosted: Wed Nov 23, 2005 11:45 am 
Newbie

Joined: Wed Nov 02, 2005 2:48 pm
Posts: 2
Location: Indianapolis
momania wrote:

Code:
Criteria criteria = session.createCriteria(Invoice.class)
                                     .createCriteria("history")
                                     .add(Restrictions.eq("status", "new"))
                                     .add(Restrictions.eq("current", true));


Hibernate will return a "collection was not an association" error if the history object is mapped with composite-element.

When using the composite element mapping, you must use hql:
Code:
Query query = session.createQuery("select invoice from Invoice invoice where invoice.names.name like '%' || ? || '%'");
query.setString(0, "Bob Smith");
List<Invoice> invoices = query.list();



I realize this is a slightly different case, however Truecolor simply needs to use invoice.history.status = ? in the hql instead.


Top
 Profile  
 
 Post subject:
PostPosted: Wed Nov 23, 2005 11:53 am 
Newbie

Joined: Fri Nov 04, 2005 12:32 pm
Posts: 14
Location: Detroit, MI, USA
So it looks like you cannot do this without using HQL. The problem lies in that the history is a List instead of a direct association.


Top
 Profile  
 
 Post subject:
PostPosted: Tue Dec 06, 2005 7:56 pm 
Regular
Regular

Joined: Tue Sep 28, 2004 6:34 pm
Posts: 50
cheeser wrote:
So it looks like you cannot do this without using HQL. The problem lies in that the history is a List instead of a direct association.


Did anyone managed to create Criteria query (not HQL) that sets constraints on collection elements that are composite-elements?

If no one did, should this be reported as a bug?

Basically it fails on CollectionType.getAssociatedEntityName check:

Code:
if ( !collectionPersister.getElementType().isEntityType() ) {
            throw new MappingException( "collection was not an association: "
               + collectionPersister.getRole() );
         }


Simply component in not entity.


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 06, 2006 6:14 pm 
Newbie

Joined: Wed Jan 04, 2006 10:50 pm
Posts: 3
Location: Brazil
PLEASE... Can I make Criterias with <composite-element... /> ONE-TO-MANY or MANY-TO-MANY?

Leonardo.

_________________
Leonardo Pereira
Rio de Janeiro, Brazil


Top
 Profile  
 
 Post subject:
PostPosted: Mon Mar 06, 2006 6:33 am 
Newbie

Joined: Mon Dec 05, 2005 8:00 am
Posts: 5
Location: Rome
I'm waiting for an answer to this question too. Anyone can help with this?

Lukasz (Qr) wrote:
Did anyone managed to create Criteria query (not HQL) that sets constraints on collection elements that are composite-elements?

If no one did, should this be reported as a bug?
Simply component in not entity.


Top
 Profile  
 
 Post subject:
PostPosted: Fri May 05, 2006 5:47 am 
Newbie

Joined: Fri May 05, 2006 5:38 am
Posts: 2
Found a way to restrict components of classes:

public class MyClass
{
MyComponent myComponent;

setter
getter
}

public class MyComponent
{
String myVariable

setter
getter
}



Criteria c = session.createCriteria(clazz);
c.add(Restrictions.eq("myComponent.myVariable","restriction"));
c.list();

Hope this is what your after


Top
 Profile  
 
 Post subject:
PostPosted: Tue Jul 04, 2006 5:28 am 
Beginner
Beginner

Joined: Mon Sep 27, 2004 3:48 am
Posts: 23
I used HQL instead of Criteria query at last:

Code:
String hqlString = "select distinct invoice from Invoice invoice ";
String whereString = "";

if (invoiceStatuses != null && invoiceStatuses.size() > 0) {
    hqlString += "join invoice.history as history ";
    whereString = "where history.current = true and history.status in :invoiceStatusList) ";
}


Query q = session.createQuery(hqlString + whereString );
if (invoiceStatuses != null && invoiceStatuses.size() > 0) {
    q.setParameterList("invoiceStatusList", invoiceStatuses);
}

List invoiceList = q.list();


Top
 Profile  
 
 Post subject:
PostPosted: Fri Aug 11, 2006 7:13 pm 
Newbie

Joined: Thu Jan 12, 2006 5:34 pm
Posts: 4
This was a helpful post. For hours I struggled why I couldn't query the elements of my collection in a composite element:
<class name="lbControl.Pool" table="pools">

...

<set name="members" table="poolmembers" cascade="all">
<key column="pool_id"/>
<composite-element class="lbControl.PoolMember">
<many-to-one name="service" class="lbControl.Service" cascade="all">
<column name="service_id"/>
</many-to-one>
<property name="ratio" type="long"/>

</composite-element>
</set>

now this HQL wasn't working

select pool from Pool pool where pool.members.service.name = "foo"

I got complaints net.sf.hibernate.QueryException: expecting 'elements' or 'indices' after: name.

for some reason this works though

select pool from Pool pool join pool.members as members where members.service.name = "foo"

Does anyone understand why? And why this is so dreadfully documented? Neither the Hibernate online docs, "Hibernate Programmers Notebook," nor "Hibernate in Action" made clear the need for this syntax. It seems like a rather arbitrary requirement.


Top
 Profile  
 
 Post subject:
PostPosted: Fri Jun 01, 2007 12:28 pm 
Newbie

Joined: Tue Nov 14, 2006 3:20 am
Posts: 3
I have exactly the same problem. Have you find the reason?

Andrew


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 14 posts ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.