JPA标准API - 如何添加JOIN子句(一般句子越好) [英] JPA Criteria API - How to add JOIN clause (as general sentence as possible)

查看:2409
本文介绍了JPA标准API - 如何添加JOIN子句(一般句子越好)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图动态构造查询,我的下一个目标是增加JOIN子句(我不知道我怎么可以使用API​​)。

到现在为止,例如,对我来说这code的工作:

  ...
类基类;
...
CriteriaBuilder CB = JpaHandle.get()getCriteriaBuilder()。
CriteriaQuery中CQ = cb.createQuery(this.baseClass);
根entity_ = cq.from(this.baseClass);
predicate限制= NULL;
...
限制= cb.conjunction();
限制= cb.and(限制entity_.get(ID)中(this.listId));
...
cq.where(限制);
...
查询QRY = JpaHandle.get()的createQuery(CQ)。

(注:JpaHandle是从检票JPA实现)

我的愿望是加入JOIN子句(如generical越好)!

我在班级的特殊注解(this.baseClass)

例如:

  @ManyToOne(取= FetchType.LAZY)
@JoinColumn(NAME =assay_id,可为空= FALSE)

那么,有没有办法在标准JPA这样的事情? (注:这不编译)

这里的实用失败aproaches:

  ...
加入<实验,测定> experimentAssays = entity_.join(entity_.get(assay_id));

之类的:

  ...
CriteriaQuery中<客户> Q = cb.createQuery(Customer.class);
根<客户> C = q.from(Customer.class);
SetJoin<客户,PurchaseOrder的> O = c.join(Customer_.orders);

对于我来说,如果能尽可能多generical这将是伟大的...

  ...
加入joinClause = entity_join(entity_.get(assay_id),entity2_.get(ID));

当然,我在班级的特殊注解(this.baseClass)

感谢您的时间。我将AP preciate都挺评论!


解决方案

也许从的第23章 - 使用标准的API创建中的Java EE 6教程的查询会抛出一些轻(实际上,我建议在阅读整个第23章):


  

查询关系使用连接


  
  

对于定位到相关查询
  实体类,查询必须定义
  一个由加入到相关的实体
  调用的 From.join 方法之一
  查询根对象,或其他上
  加入对象。联接方法
  类似于JPQL的加入关键字。


  
  

联接的目标使用
  元模型类类型
  的EntityType< T> 来指定
  持久字段或财产
  加盟实体。


  
  

join方法返回的对象
  键入加入< X,Y> ,其中 X
  源实体和是目标
  加入。


  
  

示例23-10加入一个查询

  CriteriaQuery中<宠物及GT; CQ = cb.createQuery(Pet.class);
元模型M = em.getMetamodel();
的EntityType<宠物及GT; Pet_ = m.entity(Pet.class);根<宠物及GT;宠物= cq.from(Pet.class);
加入<宠物,所有者>所有者= pet.join(Pet_.owners);


  
  

联接可以一起拴
  导航到相关实体
  目标实体,而无需创建
  一个加入< X,Y方式> 实例为每个加盟


  
  

例23-11链连接在一起
  在查询

  CriteriaQuery中<宠物及GT; CQ = cb.createQuery(Pet.class);
元模型M = em.getMetamodel();
的EntityType<宠物及GT; Pet_ = m.entity(Pet.class);
的EntityType<拥有者GT; Owner_ = m.entity(Owner.class);根<宠物及GT;宠物= cq.from(Pet.class);
加入<所有者,地址>地址= cq.join(Pet_.owners)。加入(Owner_.addresses);


话虽这么说,我有一些补充说明:

首先,在code以下行:

 根entity_ = cq.from(this.baseClass);

让我觉得你莫名其妙错过了静态元模型类的一部分。元模型类,如宠物_ 中引用的例子是用来描述的元信息一个持久化类。他们是典型的生成使用注释处理器(规范元模型类的),也可以由开发人员编写(的非规范元模型的)。但是你的语法看起来怪异,我想你想模仿的东西,你错过了。

二,我真的觉得你应该忘记这个 assay_id 外键,你走错了路就在这里。你真的需要开始考虑对象的关联,而不是表和列。

第三,我真的不知道要明白你的意思究竟是什么通过添加的 JOIN子句generical尽可能的和你的对象模型的样子,因为你没有提供它(见previous点)。这从而也就不可能回答你的问题更precisely。

综上所述,我认为你需要阅读更多的关于JPA 2.0标准和元模型API和我热烈推荐下面为起点的资源。

另请参见

相关问题

I am trying to construct queries dynamically, and my next target is add JOIN clauses (I don't know how can I use the API).

By now, for example, this code work for me :

...
Class baseClass;   
...
CriteriaBuilder cb = JpaHandle.get().getCriteriaBuilder();
CriteriaQuery cq = cb.createQuery(this.baseClass);
Root entity_ = cq.from(this.baseClass); 
Predicate restrictions = null;
...
restrictions = cb.conjunction();
restrictions = cb.and(restrictions, entity_.get("id").in(this.listId));
...
cq.where(restrictions);
...
Query qry = JpaHandle.get().createQuery(cq);

(Note : JpaHandle is from wicket-JPA implementation)

My desire is add JOIN clause (as generical as possible)!

I have the particular annotations in the classes (this.baseClass)

For example :

@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "assay_id", nullable = false)

So,Is there a way to something like this in standard JPA ? (Note : this don't compile)

Here a practical fail aproaches :

...
Join<Experiment,Assay> experimentAssays = entity_.join( entity_.get("assay_id") );

Or like that :

...
CriteriaQuery<Customer> q = cb.createQuery(Customer.class);
Root<Customer> c = q.from(Customer.class);
SetJoin<Customer, PurchaseOrder> o = c.join(Customer_.orders);

For me, if it could be more generical as possible it will be great... :

...
Join joinClause = entity_join(entity_.get("assay_id"), entity2_.get("id"));

Of course, I have the particular annotations in the classes (this.baseClass)

Thank you for your time. I'll appreciate all kind of comments!

解决方案

Maybe the following extract from the Chapter 23 - Using the Criteria API to Create Queries of the Java EE 6 tutorial will throw some light (actually, I suggest reading the whole Chapter 23):

Querying Relationships Using Joins

For queries that navigate to related entity classes, the query must define a join to the related entity by calling one of the From.join methods on the query root object, or another join object. The join methods are similar to the JOIN keyword in JPQL.

The target of the join uses the Metamodel class of type EntityType<T> to specify the persistent field or property of the joined entity.

The join methods return an object of type Join<X, Y>, where X is the source entity and Y is the target of the join.

Example 23-10 Joining a Query

CriteriaQuery<Pet> cq = cb.createQuery(Pet.class);
Metamodel m = em.getMetamodel();
EntityType<Pet> Pet_ = m.entity(Pet.class);

Root<Pet> pet = cq.from(Pet.class);
Join<Pet, Owner> owner = pet.join(Pet_.owners);

Joins can be chained together to navigate to related entities of the target entity without having to create a Join<X, Y> instance for each join.

Example 23-11 Chaining Joins Together in a Query

CriteriaQuery<Pet> cq = cb.createQuery(Pet.class);
Metamodel m = em.getMetamodel();
EntityType<Pet> Pet_ = m.entity(Pet.class);
EntityType<Owner> Owner_ = m.entity(Owner.class);

Root<Pet> pet = cq.from(Pet.class);
Join<Owner, Address> address = cq.join(Pet_.owners).join(Owner_.addresses);

That being said, I have some additional remarks:

First, the following line in your code:

Root entity_ = cq.from(this.baseClass);

Makes me think that you somehow missed the Static Metamodel Classes part. Metamodel classes such as Pet_ in the quoted example are used to describe the meta information of a persistent class. They are typically generated using an annotation processor (canonical metamodel classes) or can be written by the developer (non-canonical metamodel). But your syntax looks weird, I think you are trying to mimic something that you missed.

Second, I really think you should forget this assay_id foreign key, you're on the wrong path here. You really need to start to think object and association, not tables and columns.

Third, I'm not really sure to understand what you mean exactly by adding a JOIN clause as generical as possible and what your object model looks like, since you didn't provide it (see previous point). It's thus just impossible to answer your question more precisely.

To sum up, I think you need to read a bit more about JPA 2.0 Criteria and Metamodel API and I warmly recommend the resources below as a starting point.

See also

Related question

这篇关于JPA标准API - 如何添加JOIN子句(一般句子越好)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆