JPA标准API-JPQL查询的另一种方式

2019-04-22 23:42|来源: 网路

标准是用来定义查询实体的预定义API。它是定义JPQL查询的另一种方式。这些查询是类型安全的,可移植的,并且容易被改变的语法进行修改。类似于JPQL,它遵循的抽象模式(容易编辑模式)和嵌入的对象。元数据API是夹杂着标准的API模型持久性实体的标准查询。

标准的API的主要优点是,错误可以较早在编译时被检测到。基于字符串JPQL查询和基于查询JPA的范围是在性能和效率相同。

标准API历史

该标准被纳入因此标准的每一步中JPA的规范通知所有版本JPA。

  • 在JPA2.0中,标准查询API,查询的标准化开发。

  • 在JPA2.1,标准更新和删除(批量更新和删除)都包括在内。

标准查询结构

该标准与JPQL是密切相关的,并允许使用类似的操作符在他们的查询设计。它遵循javax.persistence.criteria包设计一个查询。查询结构指的语法条件查询。

下面简单的条件查询返回数据源中的实体类的所有实例。

EntityManager em = ...;
CriteriaBuilder cb = em.getCriteriaBuilder();
CriteriaQuery<Entity class> cq = cb.createQuery(Entity.class);
Root<Entity> from = cq.from(Entity.class);
cq.select(Entity);
TypedQuery<Entity> q = em.createQuery(cq);
List<Entity> allitems = q.getResultList();


查询演示了基本的步骤来创建一个标准。

  • EntityManager实例被用来创建一个CriteriaBuilder对象。

  • CriteriaQuery实例是用来创建一个查询对象。这个查询对象的属性将与该查询的细节进行修改。

  • CriteriaQuery.form方法被调用来设置查询根。

  • CriteriaQuery.select被调用来设置结果列表类型。

  • TypedQuery<T>实例是用来准备一个查询执行和指定的查询结果的类型。

  • 在TypedQuery<T>对象getResultList方法来执行查询。该查询返回实体的集合,结果存储在一个列表中。

标准API示例

让我们考虑 employee 数据库的例子。让我们假定该 jpadb.employee表包含以下记录:

Eid    Ename          Salary	Deg
401    Gopal	        40000	Technical Manager
402    Manisha	    40000	Proof reader
403    Masthanvali    35000	Technical Writer
404  Satish           30000	Technical writer
405    Krishna	    30000	Technical Writer
406    Kiran	        35000	Proof reader


在名为JPA_Eclipselink_Criteria Eclipse IDE中创建JPA项目。这个项目的所有模块下面讨论:

创建实体

在'src'中创建包名为com656463.eclipselink.entity

创建一个名为Employee.java类。Employee实体如下图所示:

package com656463.eclipselink.entity;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;

@Entity
public class Employee 
{
   @Id
   @GeneratedValue(strategy= GenerationType.AUTO) 	
   private int eid;
   private String ename;
   private double salary;
   private String deg;
   public Employee(int eid, String ename, double salary, String deg) 
   {
   	super( );
   	this.eid = eid;
   	this.ename = ename;
   	this.salary = salary;
   	this.deg = deg;
   }
   
   public Employee( ) 
   {
   	super();
   }
   
   public int getEid( ) 
   {
   	return eid;
   }
   public void setEid(int eid)  
   {
   	this.eid = eid;
   }
   
   public String getEname( ) 
   {
   	return ename;
   }
   public void setEname(String ename) 
   {
   	this.ename = ename;
   }
   
   public double getSalary( ) 
   {
   	return salary;
   }
   public void setSalary(double salary) 
   {
   	this.salary = salary;
   }
   
   public String getDeg( ) 
   {
   	return deg;
   }
   public void setDeg(String deg) 
   {
   	this.deg = deg;
   }
   @Override
   public String toString() {
   	return "Employee [eid=" + eid + ", ename=" + ename + ", salary="
   			+ salary + ", deg=" + deg + "]";
   }
}


Persistence.xml

Persistence.xml 文件的内容如下:

<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.0" xmlns="http://java.sun.com/xml/ns/persistence" 
             xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
             xsi:schemaLocation="http://java.sun.com/xml/ns/persistence 
             http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd">
   <persistence-unit name="Eclipselink_JPA" 
                        transaction-type="RESOURCE_LOCAL">
   <class>cn.sxt.eclipselink.entity.Employee</class>
   	<properties>
   		<property name="javax.persistence.jdbc.url" 
   		          value="jdbc:mysql://localhost:3306/jpadb"/>
   		<property name="javax.persistence.jdbc.user" value="root"/>
   		<property name="javax.persistence.jdbc.password" 
   		          value="root"/>
   		<property name="javax.persistence.jdbc.driver" 
   		          value="com.mysql.jdbc.Driver"/>
   		<property name="eclipselink.logging.level" value="FINE"/>
   		<property name="eclipselink.ddl-generation" 
   		          value="create-tables"/>
   	</properties>
   </persistence-unit>
</persistence>


服务类

该模块包含服务类,它实现了使用元数据API的初始化条件查询的一部分。创建一个名为“com656463.eclipselink.service'包。在这个包下创建一个类CriteriaAPI.java。在DAO类如下所示:

package com656463.eclipselink.service;

import java.util.List;
import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.Persistence;
import javax.persistence.TypedQuery;
import javax.persistence.criteria.CriteriaBuilder;
import javax.persistence.criteria.CriteriaQuery;
import javax.persistence.criteria.Root;
import com656463.eclipselink.entity.Employee;

public class CriteriaApi 
{
   public static void main(String[] args) 
   {
   	EntityManagerFactory emfactory = Persistence.
   			createEntityManagerFactory( "Eclipselink_JPA" );
   	EntityManager entitymanager = emfactory.
   			createEntityManager( );
   	CriteriaBuilder criteriaBuilder = entitymanager
   			.getCriteriaBuilder();
   	CriteriaQuery<Object> criteriaQuery = criteriaBuilder
   			.createQuery();
   	Root<Employee> from = criteriaQuery.from(Employee.class);
   	
   	//select all records
        System.out.println(“Select all records”);
   	CriteriaQuery<Object> select =criteriaQuery.select(from);
   	TypedQuery<Object> typedQuery = entitymanager
   			.createQuery(select);
   	List<Object> resultlist= typedQuery.getResultList();
   	
   	for(Object o:resultlist)
   	{
   		Employee e=(Employee)o;
   		System.out.println("EID : "+e.getEid()
   				+" Ename : "+e.getEname());
   	}
   	
   	//Ordering the records 
        System.out.println(“Select all records by follow ordering”);
   	CriteriaQuery<Object> select1 = criteriaQuery.select(from);
        select1.orderBy(criteriaBuilder.asc(from.get("ename")));
        TypedQuery<Object> typedQuery1 = entitymanager
           	.createQuery(select);
        List<Object> resultlist1= typedQuery1.getResultList();
   	
   	for(Object o:resultlist1)
   	{
   		Employee e=(Employee)o;
   		System.out.println("EID : "+e.getEid()
   				+" Ename : "+e.getEname());
   	}
   	
   	entitymanager.close( );
   	emfactory.close( );
   }
}


编译和执行上述程序后,将在Eclipse IDE的控制台面板输出下面的内容。

Select All records
EID : 401 Ename : Gopal
EID : 402 Ename : Manisha
EID : 403 Ename : Masthanvali
EID : 404 Ename : Satish
EID : 405 Ename : Krishna
EID : 406 Ename : Kiran
Select All records by follow Ordering
EID : 401 Ename : Gopal
EID : 406 Ename : Kiran
EID : 405 Ename : Krishna
EID : 402 Ename : Manisha
EID : 403 Ename : Masthanvali
EID : 404 Ename : Satish



相关问答

更多

jpa表达式大于 小于怎么表示

JPA是Java persistence api即java的持久化api,JPQL是Java persistence query language即java持久化查询语言,JPQL是JPA里头定义的一种查询语句规范,JPA将这种JPQL语句转换成相应的持久化操作(增删改查),进而达到使用者的目的。

spring依赖除了(set注入,构造方法注入)还有哪种注入方式?

除了属性注入(set),和构造注入(constractor),还有工厂注入。工厂注入具体有分为动态工厂注入和静态工厂注入,具体操作时在bean标签上有factory-method属性写你的工厂方法,静态工厂与动态工厂的差别就不说了,还有一种就是也是属性注入的情况,spring或者是其他和spring配合的框架提供了一系列Aware接口让你直接使用的

JPA 多对多JPQL查询语句怎么写?

有中间表了为什么还要做成多对多的.这样的话就不能使用jpql,因为你的中间表没有对应的实体。可以将Order和order_product做成1对多,Product和order_product做成多对1。这样就可以了

linux上用 apt-get install命令安装的包是放在哪个文件夹的?可以提取出来放到另一

/var/cache/apt/archives文件夹中的文件是使用sudo apt-get install appname时下载的安装文件 不能放到另一种发行版的linux

如何正确地将JPQL“join fetch”与“where”子句一起表示为JPA 2 CriteriaQuery?(How to properly express JPQL “join fetch” with “where” clause as JPA 2 CriteriaQuery?)

在JPQL中,规范中也是如此。 JPA规范不允许将别名赋予获取联接。 问题在于,通过限制联合抓取的上下文,您可以轻松地将自己拍摄在脚下。 加入两次更安全。 ToMany通常比ToOnes更像一个问题。 例如, Select e from Employee e join fetch e.phones p where p.areaCode = '613' 这将错误地返回所有包含'613'区号中号码的员工,但会在返回列表中排除其他地区的电话号码。 这意味着在613和416区号中有电话的员工将丢失4 ...