Migrate User Guide Native chapter extras to test folder up to stored procedures

This commit is contained in:
Vlad Mihalcea 2016-02-10 18:07:48 +02:00
parent b5a86ea45c
commit 2167b442a4
29 changed files with 2127 additions and 499 deletions

View File

@ -30,6 +30,7 @@ include::chapters/portability/Portability.adoc[]
include::appendices/Legacy_Bootstrap.adoc[]
include::appendices/Legacy_DomainModel.adoc[]
include::appendices/Legacy_Criteria.adoc[]
include::appendices/Legacy_Native_Queries.adoc[]
include::Bibliography.adoc[]

View File

@ -0,0 +1,375 @@
[[appendix-legacy-native-queries]]
== Legacy Hibernate Native Queries
[[legacy-sql-named-queries]]
=== Legacy Named SQL queries
Named SQL queries can also be defined during mapping and called in exactly the same way as a named HQL query.
In this case, you do _not_ need to call `addEntity()` anymore.
.Named sql query using the `<sql-query>` mapping element
====
[source,xml]
----
<sql-query name = "persons">
<return alias="person" class="eg.Person"/>
SELECT person.NAME AS {person.name},
person.AGE AS {person.age},
person.SEX AS {person.sex}
FROM PERSON person
WHERE person.NAME LIKE :namePattern
</sql-query>
----
====
.Execution of a named query
====
[source, JAVA, indent=0]
----
List people = session
.getNamedQuery( "persons" )
.setString( "namePattern", namePattern )
.setMaxResults( 50 )
.list();
----
====
The `<return-join>` element is use to join associations and the `<load-collection>` element is used to define queries which initialize collections.
.Named sql query with association
====
[source,xml]
----
<sql-query name = "personsWith">
<return alias="person" class="eg.Person"/>
<return-join alias="address" property="person.mailingAddress"/>
SELECT person.NAME AS {person.name},
person.AGE AS {person.age},
person.SEX AS {person.sex},
address.STREET AS {address.street},
address.CITY AS {address.city},
address.STATE AS {address.state},
address.ZIP AS {address.zip}
FROM PERSON person
JOIN ADDRESS address
ON person.ID = address.PERSON_ID AND address.TYPE='MAILING'
WHERE person.NAME LIKE :namePattern
</sql-query>
----
====
A named SQL query may return a scalar value.
You must declare the column alias and Hibernate type using the `<return-scalar>` element:
.Named query returning a scalar
====
[source,xml]
----
<sql-query name = "mySqlQuery">
<return-scalar column = "name" type="string"/>
<return-scalar column = "age" type="long"/>
SELECT p.NAME AS name,
p.AGE AS age,
FROM PERSON p WHERE p.NAME LIKE 'Hiber%'
</sql-query>
----
====
You can externalize the resultset mapping information in a `<resultset>` element which will allow you to either reuse them across several named queries or through the `setResultSetMapping()` API.
.<resultset> mapping used to externalize mappinginformation
====
[source,xml]
----
<resultset name = "personAddress">
<return alias="person" class="eg.Person"/>
<return-join alias="address" property="person.mailingAddress"/>
</resultset>
<sql-query name = "personsWith" resultset-ref="personAddress">
SELECT person.NAME AS {person.name},
person.AGE AS {person.age},
person.SEX AS {person.sex},
address.STREET AS {address.street},
address.CITY AS {address.city},
address.STATE AS {address.state},
address.ZIP AS {address.zip}
FROM PERSON person
JOIN ADDRESS address
ON person.ID = address.PERSON_ID AND address.TYPE='MAILING'
WHERE person.NAME LIKE :namePattern
</sql-query>
----
====
You can, alternatively, use the resultset mapping information in your hbm files directly in java code.
.Programmatically specifying the result mapping information
====
[source, JAVA, indent=0]
----
List cats = session
.createSQLQuery( "select {cat.*}, {kitten.*} from cats cat, cats kitten where kitten.mother = cat.id" )
.setResultSetMapping("catAndKitten")
.list();
----
====
[[legacy-propertyresults]]
=== Legacy return-property to explicitly specify column/alias names
You can explicitly tell Hibernate what column aliases to use with `<return-property>`, instead of using the `{}` syntax to let Hibernate inject its own aliases.
For example:
[source,xml]
----
<sql-query name = "mySqlQuery">
<return alias = "person" class = "eg.Person">
<return-property name = "name" column = "myName"/>
<return-property name = "age" column = "myAge"/>
<return-property name = "sex" column = "mySex"/>
</return>
SELECT person.NAME AS myName,
person.AGE AS myAge,
person.SEX AS mySex,
FROM PERSON person WHERE person.NAME LIKE :name
</sql-query>
----
`<return-property>` also works with multiple columns.
This solves a limitation with the `{}` syntax which cannot allow fine grained control of multi-column properties.
[source,xml]
----
<sql-query name = "organizationCurrentEmployments">
<return alias = "emp" class = "Employment">
<return-property name = "salary">
<return-column name = "VALUE"/>
<return-column name = "CURRENCY"/>
</return-property>
<return-property name = "endDate" column = "myEndDate"/>
</return>
SELECT EMPLOYEE AS {emp.employee}, EMPLOYER AS {emp.employer},
STARTDATE AS {emp.startDate}, ENDDATE AS {emp.endDate},
REGIONCODE as {emp.regionCode}, EID AS {emp.id}, VALUE, CURRENCY
FROM EMPLOYMENT
WHERE EMPLOYER = :id AND ENDDATE IS NULL
ORDER BY STARTDATE ASC
</sql-query>
----
In this example `<return-property>` was used in combination with the `{}` syntax for injection.
This allows users to choose how they want to refer column and properties.
If your mapping has a discriminator you must use `<return-discriminator>` to specify the discriminator column.
[[legacy-sp_query]]
=== Legacy stored procedures for querying
Hibernate provides support for queries via stored procedures and functions.
Most of the following documentation is equivalent for both.
The stored procedure/function must return a resultset as the first out-parameter to be able to work with Hibernate.
An example of such a stored function in Oracle 9 and higher is as follows:
[source,xml]
----
CREATE OR REPLACE FUNCTION selectAllEmployments
RETURN SYS_REFCURSOR
AS
st_cursor SYS_REFCURSOR;
BEGIN
OPEN st_cursor FOR
SELECT EMPLOYEE, EMPLOYER,
STARTDATE, ENDDATE,
REGIONCODE, EID, VALUE, CURRENCY
FROM EMPLOYMENT;
RETURN st_cursor;
END;
----
To use this query in Hibernate you need to map it via a named query.
[source,xml]
----
<sql-query name = "selectAllEmployees_SP" callable = "true">
<return alias="emp" class="Employment">
<return-property name = "employee" column = "EMPLOYEE"/>
<return-property name = "employer" column = "EMPLOYER"/>
<return-property name = "startDate" column = "STARTDATE"/>
<return-property name = "endDate" column = "ENDDATE"/>
<return-property name = "regionCode" column = "REGIONCODE"/>
<return-property name = "id" column = "EID"/>
<return-property name = "salary">
<return-column name = "VALUE"/>
<return-column name = "CURRENCY"/>
</return-property>
</return>
{ ? = call selectAllEmployments() }
</sql-query>
----
Stored procedures currently only return scalars and entities.
`<return-join>` and `<load-collection>` are not supported.
[[legacy-sql-limits-storedprocedures]]
=== Legacy rules/limitations for using stored procedures
You cannot use stored procedures with Hibernate unless you follow some procedure/function rules.
If they do not follow those rules they are not usable with Hibernate.
If you still want to use these procedures you have to execute them via `session.doWork()`.
The rules are different for each database, since database vendors have different stored procedure semantics/syntax.
Stored procedure queries cannot be paged with `setFirstResult()/setMaxResults()`.
The recommended call form is standard SQL92: `{ ? = call functionName(<parameters>) }` or `{ ? = call procedureName(<parameters>}`.
Native call syntax is not supported.
For Oracle the following rules apply:
* A function must return a result set.
The first parameter of a procedure must be an `OUT` that returns a result set.
This is done by using a `SYS_REFCURSOR` type in Oracle 9 or 10.
In Oracle you need to define a `REF CURSOR` type.
See Oracle literature for further information.
For Sybase or MS SQL server the following rules apply:
* The procedure must return a result set.
Note that since these servers can return multiple result sets and update counts, Hibernate will iterate the results and take the first result that is a result set as its return value.
Everything else will be discarded.
* If you can enable `SET NOCOUNT ON` in your procedure it will probably be more efficient, but this is not a requirement.
[[legacy-sql-cud]]
=== Legacy custom SQL for create, update and delete
Hibernate can use custom SQL for create, update, and delete operations.
The SQL can be overridden at the statement level or individual column level.
This section describes statement overrides.
For columns, see <<chapters/domain/basic_types.adoc#mapping-column-read-and-write,Column transformers: read and write expressions>>.
The following example shows how to define custom SQL operations using annotations.
.Custom CRUD XML
====
[source,xml]
----
<class name = "Person">
<id name = "id">
<generator class = "increment"/>
</id>
<property name = "name" not-null = "true"/>
<sql-insert>INSERT INTO PERSON (NAME, ID) VALUES ( UPPER(?), ? )</sql-insert>
<sql-update>UPDATE PERSON SET NAME=UPPER(?) WHERE ID=?</sql-update>
<sql-delete>DELETE FROM PERSON WHERE ID=?</sql-delete>
</class>
----
====
[NOTE]
====
If you expect to call a store procedure, be sure to set the `callable` attribute to `true`, in annotations as well as in xml.
====
To check that the execution happens correctly, Hibernate allows you to define one of those three strategies:
* none: no check is performed: the store procedure is expected to fail upon issues
* count: use of rowcount to check that the update is successful
* param: like COUNT but using an output parameter rather that the standard mechanism
To define the result check style, use the `check` parameter which is again available in annotations as well as in xml.
Last but not least, stored procedures are in most cases required to return the number of rows inserted, updated and deleted.
Hibernate always registers the first statement parameter as a numeric output parameter for the CUD operations:
.Stored procedures and their return value
====
[source]
----
CREATE OR REPLACE FUNCTION updatePerson (uid IN NUMBER, uname IN VARCHAR2)
RETURN NUMBER IS
BEGIN
update PERSON
set
NAME = uname,
where
ID = uid;
return SQL%ROWCOUNT;
END updatePerson;
----
====
[[legacy-sql-load]]
=== Legacy custom SQL for loading
You can also declare your own SQL (or HQL) queries for entity loading.
As with inserts, updates, and deletes, this can be done at the individual column level as described in
For columns, see <<chapters/domain/basic_types.adoc#mapping-column-read-and-write,Column transformers: read and write expressions>> or at the statement level.
Here is an example of a statement level override:
[source,xml]
----
<sql-query name = "person">
<return alias = "pers" class = "Person" lock-mod e= "upgrade"/>
SELECT NAME AS {pers.name}, ID AS {pers.id}
FROM PERSON
WHERE ID=?
FOR UPDATE
</sql-query>
----
This is just a named query declaration, as discussed earlier. You can reference this named query in a class mapping:
[source,xml]
----
<class name = "Person">
<id name = "id">
<generator class = "increment"/>
</id>
<property name = "name" not-null = "true"/>
<loader query-ref = "person"/>
</class>
----
This even works with stored procedures.
You can even define a query for collection loading:
[source,xml]
----
<set name = "employments" inverse = "true">
<key/>
<one-to-many class = "Employment"/>
<loader query-ref = "employments"/>
</set>
----
[source,xml]
----
<sql-query name = "employments">
<load-collection alias = "emp" role = "Person.employments"/>
SELECT {emp.*}
FROM EMPLOYMENT emp
WHERE EMPLOYER = :id
ORDER BY STARTDATE ASC, EMPLOYEE ASC
</sql-query>
----
You can also define an entity loader that loads a collection by join fetching:
[source,xml]
----
<sql-query name = "person">
<return alias = "pers" class = "Person"/>
<return-join alias = "emp" property = "pers.employments"/>
SELECT NAME AS {pers.*}, {emp.*}
FROM PERSON pers
LEFT OUTER JOIN EMPLOYMENT emp
ON pers.ID = emp.PERSON_ID
WHERE ID=?
</sql-query>
----
The annotation equivalent `<loader>` is the `@Loader` annotation as seen in <<example-custom-crdu-via-annotations>>.

View File

@ -0,0 +1,3 @@
SELECT *
FROM phone ph
JOIN call c ON c.phone_id = ph.id

View File

@ -0,0 +1,5 @@
SELECT id ,
number ,
type ,
person_id
FROM phone

View File

@ -0,0 +1,3 @@
SELECT *
FROM phone ph
JOIN call c ON c.phone_id = ph.id

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
/**

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
import java.util.Date;
@ -10,7 +16,7 @@ import javax.persistence.ManyToOne;
* @author Vlad Mihalcea
*/
//tag::hql-examples-domain-model-example[]
@Entity(name = "Call")
@Entity
public class Call {
@Id

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
import javax.persistence.Entity;

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
import javax.persistence.Entity;
@ -16,11 +22,11 @@ public class Partner {
@GeneratedValue
private Long id;
private String name;
@Version
private int version;
private String name;
//Getters and setters are omitted for brevity
//end::hql-examples-domain-model-example[]

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
import java.math.BigDecimal;
@ -5,6 +11,7 @@ import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Inheritance;
import javax.persistence.InheritanceType;
import javax.persistence.ManyToOne;
/**
@ -12,7 +19,7 @@ import javax.persistence.ManyToOne;
*/
//tag::hql-examples-domain-model-example[]
@Entity
@Inheritance
@Inheritance(strategy = InheritanceType.JOINED)
public class Payment {
@Id

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
import java.util.ArrayList;
@ -6,16 +12,24 @@ import java.util.HashMap;
import java.util.List;
import java.util.Map;
import javax.persistence.CascadeType;
import javax.persistence.ColumnResult;
import javax.persistence.ConstructorResult;
import javax.persistence.ElementCollection;
import javax.persistence.Entity;
import javax.persistence.EntityResult;
import javax.persistence.EnumType;
import javax.persistence.FieldResult;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.MapKeyEnumerated;
import javax.persistence.NamedNativeQueries;
import javax.persistence.NamedNativeQuery;
import javax.persistence.NamedQueries;
import javax.persistence.NamedQuery;
import javax.persistence.OneToMany;
import javax.persistence.OrderColumn;
import javax.persistence.SqlResultSetMapping;
import javax.persistence.SqlResultSetMappings;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import javax.persistence.Version;
@ -23,6 +37,115 @@ import javax.persistence.Version;
/**
* @author Vlad Mihalcea
*/
@NamedNativeQueries({
//tag::sql-scalar-NamedNativeQuery-example[]
@NamedNativeQuery(
name = "find_person_name",
query =
"SELECT name " +
"FROM person "
),
//end::sql-scalar-NamedNativeQuery-example[]
//tag::sql-multiple-scalar-values-NamedNativeQuery-example[]
@NamedNativeQuery(
name = "find_person_name_and_nickName",
query =
"SELECT " +
" name, " +
" nickName " +
"FROM person "
),
//end::sql-multiple-scalar-values-NamedNativeQuery-example[]
// tag::sql-multiple-scalar-values-dto-NamedNativeQuery-example[]
@NamedNativeQuery(
name = "find_person_name_and_nickName_dto",
query =
"SELECT " +
" name, " +
" nickName " +
"FROM person ",
resultSetMapping = "name_and_nickName_dto"
),
//end::sql-multiple-scalar-values-dto-NamedNativeQuery-example[]
//tag::sql-entity-NamedNativeQuery-example[]
@NamedNativeQuery(
name = "find_person_by_name",
query =
"SELECT " +
" p.id AS \"id\", " +
" p.name AS \"name\", " +
" p.nickName AS \"nickName\", " +
" p.address AS \"address\", " +
" p.createdOn AS \"createdOn\", " +
" p.version AS \"version\" " +
"FROM person p " +
"WHERE p.name LIKE :name",
resultClass = Person.class
),
//end::sql-entity-NamedNativeQuery-example[]
//tag::sql-entity-associations-NamedNativeQuery-example[]
@NamedNativeQuery(
name = "find_person_with_phones_by_name",
query =
"SELECT " +
" pr.id AS \"pr.id\", " +
" pr.name AS \"pr.name\", " +
" pr.nickName AS \"pr.nickName\", " +
" pr.address AS \"pr.address\", " +
" pr.createdOn AS \"pr.createdOn\", " +
" pr.version AS \"pr.version\", " +
" ph.id AS \"ph.id\", " +
" ph.person_id AS \"ph.person_id\", " +
" ph.number AS \"ph.number\", " +
" ph.type AS \"ph.type\" " +
"FROM person pr " +
"JOIN phone ph ON pr.id = ph.person_id " +
"WHERE pr.name LIKE :name",
resultSetMapping = "person_with_phones"
)
//end::sql-entity-associations-NamedNativeQuery-example[]
})
@SqlResultSetMappings({
//tag::sql-entity-associations-NamedNativeQuery-example[]
@SqlResultSetMapping(
name = "person_with_phones",
entities = {
@EntityResult(
entityClass = Person.class,
fields = {
@FieldResult( name = "id", column = "pr.id" ),
@FieldResult( name = "name", column = "pr.name" ),
@FieldResult( name = "nickName", column = "pr.nickName" ),
@FieldResult( name = "address", column = "pr.address" ),
@FieldResult( name = "createdOn", column = "pr.createdOn" ),
@FieldResult( name = "version", column = "pr.version" ),
}
),
@EntityResult(
entityClass = Phone.class,
fields = {
@FieldResult( name = "id", column = "ph.id" ),
@FieldResult( name = "person", column = "ph.person_id" ),
@FieldResult( name = "number", column = "ph.number" ),
@FieldResult( name = "type", column = "ph.type" ),
}
)
}
),
//end::sql-entity-associations-NamedNativeQuery-example[]
//tag::sql-multiple-scalar-values-dto-NamedNativeQuery-example[]
@SqlResultSetMapping(
name = "name_and_nickName_dto",
classes = @ConstructorResult(
targetClass = PersonNames.class,
columns = {
@ColumnResult(name = "name"),
@ColumnResult(name = "nickName")
}
)
)
//end::sql-multiple-scalar-values-dto-NamedNativeQuery-example[]
})
//tag::hql-examples-domain-model-example[]
//tag::jpql-api-named-query-example[]
@NamedQueries(

View File

@ -0,0 +1,32 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
/**
* @author Vlad Mihalcea
*/
//tag::sql-ConstructorResult-dto-example[]
public class PersonNames {
private final String name;
private final String nickName;
public PersonNames(String name, String nickName) {
this.name = name;
this.nickName = nickName;
}
public String getName() {
return name;
}
public String getNickName() {
return nickName;
}
}
//end::sql-ConstructorResult-dto-example[]

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
import java.util.ArrayList;
@ -10,6 +16,7 @@ import javax.persistence.ElementCollection;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.FetchType;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
import javax.persistence.MapKey;
@ -27,7 +34,7 @@ public class Phone {
@Id
private Long id;
@ManyToOne
@ManyToOne(fetch = FetchType.LAZY)
private Person person;
private String number;

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
/**

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.model;
import javax.persistence.Entity;

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.criteria;
/**

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.hql;
/**

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.locking;
import java.util.ArrayList;

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.locking;
import java.util.Date;

View File

@ -0,0 +1,32 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
//$Id$
package org.hibernate.userguide.sql;
import javax.persistence.EmbeddedId;
import javax.persistence.Entity;
/**
* @author Emmanuel Bernard
* @author Vlad MIhalcea
*/
//tag::sql-composite-key-entity-associations_named-query-example[]
@Entity
public class Captain {
@EmbeddedId
private Identity id;
public Identity getId() {
return id;
}
public void setId(Identity id) {
this.id = id;
}
}
//end::sql-composite-key-entity-associations_named-query-example[]

View File

@ -0,0 +1,40 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
//$Id$
package org.hibernate.userguide.sql;
import javax.persistence.Embeddable;
/**
* @author Emmanuel Bernard
* @author Vlad MIhalcea
*/
//tag::sql-composite-key-entity-associations_named-query-example[]
@Embeddable
public class Dimensions {
private int length;
private int width;
public int getLength() {
return length;
}
public void setLength(int length) {
this.length = length;
}
public int getWidth() {
return width;
}
public void setWidth(int width) {
this.width = width;
}
}
//end::sql-composite-key-entity-associations_named-query-example[]

View File

@ -0,0 +1,60 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
//$Id$
package org.hibernate.userguide.sql;
import java.io.Serializable;
import javax.persistence.Embeddable;
/**
* @author Emmanuel Bernard
* @author Vlad MIhalcea
*/
//tag::sql-composite-key-entity-associations_named-query-example[]
@Embeddable
public class Identity implements Serializable {
private String firstname;
private String lastname;
public String getFirstname() {
return firstname;
}
public void setFirstname(String firstname) {
this.firstname = firstname;
}
public String getLastname() {
return lastname;
}
public void setLastname(String lastname) {
this.lastname = lastname;
}
public boolean equals(Object o) {
if ( this == o ) return true;
if ( o == null || getClass() != o.getClass() ) return false;
final Identity identity = (Identity) o;
if ( !firstname.equals( identity.firstname ) ) return false;
if ( !lastname.equals( identity.lastname ) ) return false;
return true;
}
public int hashCode() {
int result;
result = firstname.hashCode();
result = 29 * result + lastname.hashCode();
return result;
}
}
//end::sql-composite-key-entity-associations_named-query-example[]

View File

@ -0,0 +1,37 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.sql;
import java.math.BigInteger;
/**
* @author Vlad Mihalcea
*/
//tag::sql-hibernate-dto-query-example[]
public class PersonSummaryDTO {
private BigInteger id;
private String name;
public BigInteger getId() {
return id;
}
public void setId(BigInteger id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
//end::sql-hibernate-dto-query-example[]

View File

@ -0,0 +1,761 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.sql;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.sql.Timestamp;
import java.time.LocalDateTime;
import java.time.ZoneOffset;
import java.util.List;
import javax.persistence.PersistenceException;
import org.hibernate.Criteria;
import org.hibernate.Session;
import org.hibernate.jpa.test.BaseEntityManagerFunctionalTestCase;
import org.hibernate.loader.custom.NonUniqueDiscoveredSqlAliasException;
import org.hibernate.transform.Transformers;
import org.hibernate.type.LongType;
import org.hibernate.type.StringType;
import org.hibernate.userguide.model.AddressType;
import org.hibernate.userguide.model.Call;
import org.hibernate.userguide.model.CreditCardPayment;
import org.hibernate.userguide.model.Partner;
import org.hibernate.userguide.model.Person;
import org.hibernate.userguide.model.PersonNames;
import org.hibernate.userguide.model.Phone;
import org.hibernate.userguide.model.PhoneType;
import org.hibernate.userguide.model.WireTransferPayment;
import org.junit.Before;
import org.junit.Test;
import org.jboss.logging.Logger;
import static org.hibernate.userguide.util.TransactionUtil.doInJPA;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.fail;
/**
* @author Vlad Mihalcea
*/
public class SQLTest extends BaseEntityManagerFunctionalTestCase {
private static final Logger log = Logger.getLogger( SQLTest.class );
@Override
protected Class<?>[] getAnnotatedClasses() {
return new Class<?>[] {
Person.class,
Partner.class,
Phone.class,
Call.class,
CreditCardPayment.class,
WireTransferPayment.class,
SpaceShip.class,
Captain.class,
};
}
@Before
public void init() {
doInJPA( this::entityManagerFactory, entityManager -> {
Person person1 = new Person("John Doe" );
person1.setNickName( "JD" );
person1.setAddress( "Earth" );
person1.setCreatedOn( Timestamp.from( LocalDateTime.of( 2000, 1, 1, 0, 0, 0 ).toInstant( ZoneOffset.UTC ) )) ;
person1.getAddresses().put( AddressType.HOME, "Home address" );
person1.getAddresses().put( AddressType.OFFICE, "Office address" );
entityManager.persist(person1);
Person person2 = new Person("Mrs. John Doe" );
person2.setAddress( "Earth" );
person2.setCreatedOn( Timestamp.from( LocalDateTime.of( 2000, 1, 2, 12, 0, 0 ).toInstant( ZoneOffset.UTC ) )) ;
entityManager.persist(person2);
Person person3 = new Person("Dr_ John Doe" );
entityManager.persist(person3);
Phone phone1 = new Phone( "123-456-7890" );
phone1.setId( 1L );
phone1.setType( PhoneType.MOBILE );
person1.addPhone( phone1 );
phone1.getRepairTimestamps().add( Timestamp.from( LocalDateTime.of( 2005, 1, 1, 12, 0, 0 ).toInstant( ZoneOffset.UTC ) ) );
phone1.getRepairTimestamps().add( Timestamp.from( LocalDateTime.of( 2006, 1, 1, 12, 0, 0 ).toInstant( ZoneOffset.UTC ) ) );
Call call11 = new Call();
call11.setDuration( 12 );
call11.setTimestamp( Timestamp.from( LocalDateTime.of( 2000, 1, 1, 0, 0, 0 ).toInstant( ZoneOffset.UTC ) ) );
Call call12 = new Call();
call12.setDuration( 33 );
call12.setTimestamp( Timestamp.from( LocalDateTime.of( 2000, 1, 1, 1, 0, 0 ).toInstant( ZoneOffset.UTC ) ) );
phone1.addCall(call11);
phone1.addCall(call12);
Phone phone2 = new Phone( "098_765-4321" );
phone2.setId( 2L );
phone2.setType( PhoneType.LAND_LINE );
Phone phone3 = new Phone( "098-765-4320" );
phone3.setId( 3L );
phone3.setType( PhoneType.LAND_LINE );
person2.addPhone( phone2 );
person2.addPhone( phone3 );
CreditCardPayment creditCardPayment = new CreditCardPayment();
creditCardPayment.setCompleted( true );
creditCardPayment.setAmount( BigDecimal.ZERO );
creditCardPayment.setPerson( person1 );
WireTransferPayment wireTransferPayment = new WireTransferPayment();
wireTransferPayment.setCompleted( true );
wireTransferPayment.setAmount( BigDecimal.valueOf( 100 ) );
wireTransferPayment.setPerson( person2 );
entityManager.persist( creditCardPayment );
entityManager.persist( wireTransferPayment );
Partner partner = new Partner( "John Doe" );
entityManager.persist( partner );
Captain captain = new Captain();
captain.setId( new Identity() );
captain.getId().setFirstname( "Jean-Luc" );
captain.getId().setLastname( "Picard" );
entityManager.persist( captain );
SpaceShip spaceShip = new SpaceShip();
spaceShip.setName( "Enterprise" );
spaceShip.setDimensions( new Dimensions() );
spaceShip.getDimensions().setLength( 100 );
spaceShip.getDimensions().setWidth( 20 );
spaceShip.setModel( "E-1" );
spaceShip.setSpeed( 150 );
spaceShip.setCaptain( captain );
entityManager.persist( spaceShip );
});
}
@Test
public void test_sql_jpa_all_columns_scalar_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-all-columns-scalar-query-example[]
List<Object[]> persons = entityManager.createNativeQuery(
"SELECT * FROM person" )
.getResultList();
//end::sql-jpa-all-columns-scalar-query-example[]
assertEquals( 3, persons.size() );
} );
}
@Test
public void test_sql_jpa_custom_column_selection_scalar_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-custom-column-selection-scalar-query-example[]
List<Object[]> persons = entityManager.createNativeQuery(
"SELECT id, name FROM person" )
.getResultList();
for(Object[] person : persons) {
BigInteger id = (BigInteger) person[0];
String name = (String) person[1];
}
//end::sql-jpa-custom-column-selection-scalar-query-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_hibernate_query_scalar_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-all-columns-scalar-query-example[]
List<Object[]> persons = session.createSQLQuery(
"SELECT * FROM person" )
.list();
//end::sql-hibernate-all-columns-scalar-query-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_hibernate_custom_column_selection_scalar_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-custom-column-selection-scalar-query-example[]
List<Object[]> persons = session.createSQLQuery(
"SELECT id, name FROM person" )
.list();
for(Object[] person : persons) {
BigInteger id = (BigInteger) person[0];
String name = (String) person[1];
}
//end::sql-hibernate-custom-column-selection-scalar-query-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_hibernate_query_scalar_explicit_result_set_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-scalar-query-explicit-result-set-example[]
List<Object[]> persons = session.createSQLQuery(
"SELECT * FROM person" )
.addScalar( "id", LongType.INSTANCE )
.addScalar( "name", StringType.INSTANCE )
.list();
for(Object[] person : persons) {
Long id = (Long) person[0];
String name = (String) person[1];
}
//end::sql-hibernate-scalar-query-explicit-result-set-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_hibernate_query_scalar_partial_explicit_result_set_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-scalar-query-partial-explicit-result-set-example[]
List<Object[]> persons = session.createSQLQuery(
"SELECT * FROM person" )
.addScalar( "id", LongType.INSTANCE )
.addScalar( "name" )
.list();
for(Object[] person : persons) {
Long id = (Long) person[0];
String name = (String) person[1];
}
//end::sql-hibernate-scalar-query-partial-explicit-result-set-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_jpa_entity_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-entity-query-example[]
List<Person> persons = entityManager.createNativeQuery(
"SELECT * FROM person", Person.class )
.getResultList();
//end::sql-jpa-entity-query-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_hibernate_entity_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-entity-query-example[]
List<Person> persons = session.createSQLQuery(
"SELECT * FROM person" )
.addEntity( Person.class )
.list();
//end::sql-hibernate-entity-query-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_jpa_entity_query_explicit_result_set_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-entity-query-explicit-result-set-example[]
List<Person> persons = entityManager.createNativeQuery(
"SELECT id, name, nickName, address, createdOn, version " +
"FROM person", Person.class )
.getResultList();
//end::sql-jpa-entity-query-explicit-result-set-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_hibernate_entity_query_explicit_result_set_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-entity-query-explicit-result-set-example[]
List<Person> persons = session.createSQLQuery(
"SELECT id, name, nickName, address, createdOn, version " +
"FROM person" )
.addEntity( Person.class )
.list();
//end::sql-hibernate-entity-query-explicit-result-set-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_jpa_entity_associations_query_many_to_one_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-entity-associations-query-many-to-one-example[]
List<Phone> phones = entityManager.createNativeQuery(
"SELECT id, number, type, person_id " +
"FROM phone", Phone.class )
.getResultList();
//end::sql-jpa-entity-associations-query-many-to-one-example[]
assertEquals(3, phones.size());
});
}
@Test
public void test_sql_hibernate_entity_associations_query_many_to_one_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-entity-associations-query-many-to-one-example[]
List<Phone> phones = session.createSQLQuery(
"SELECT id, number, type, person_id " +
"FROM phone" )
.addEntity( Phone.class )
.list();
//end::sql-hibernate-entity-associations-query-many-to-one-example[]
assertEquals(3, phones.size());
});
}
@Test
public void test_sql_jpa_entity_associations_query_many_to_one_join_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-entity-associations-query-many-to-one-join-example[]
List<Phone> phones = entityManager.createNativeQuery(
"SELECT * " +
"FROM phone ph " +
"JOIN person pr ON ph.person_id = pr.id", Phone.class )
.getResultList();
for(Phone phone : phones) {
Person person = phone.getPerson();
}
//end::sql-jpa-entity-associations-query-many-to-one-join-example[]
assertEquals(3, phones.size());
});
}
@Test
public void test_sql_hibernate_entity_associations_query_many_to_one_join_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-entity-associations-query-many-to-one-join-example[]
List<Object[]> tuples = session.createSQLQuery(
"SELECT * " +
"FROM phone ph " +
"JOIN person pr ON ph.person_id = pr.id" )
.addEntity("phone", Phone.class )
.addJoin( "pr", "phone.person")
.list();
for(Object[] tuple : tuples) {
Phone phone = (Phone) tuple[0];
Person person = (Person) tuple[1];
}
//end::sql-hibernate-entity-associations-query-many-to-one-join-example[]
assertEquals(3, tuples.size());
});
}
@Test
public void test_sql_hibernate_entity_associations_query_many_to_one_join_result_transformer_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-entity-associations-query-many-to-one-join-result-transformer-example[]
List<Person> persons = session.createSQLQuery(
"SELECT * " +
"FROM phone ph " +
"JOIN person pr ON ph.person_id = pr.id" )
.addEntity("phone", Phone.class )
.addJoin( "pr", "phone.person")
.setResultTransformer( Criteria.ROOT_ENTITY )
.list();
for(Person person : persons) {
person.getPhones();
}
//end::sql-hibernate-entity-associations-query-many-to-one-join-result-transformer-example[]
assertEquals(3, persons.size());
});
}
@Test
public void test_sql_jpa_entity_associations_query_one_to_many_join_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-entity-associations-query-one-to-many-join-example[]
List<Phone> phones = entityManager.createNativeQuery(
"SELECT * " +
"FROM phone ph " +
"JOIN call c ON c.phone_id = ph.id", Phone.class )
.getResultList();
for(Phone phone : phones) {
List<Call> calls = phone.getCalls();
}
//end::sql-jpa-entity-associations-query-one-to-many-join-example[]
assertEquals(2, phones.size());
});
}
@Test
public void test_sql_hibernate_entity_associations_query_one_to_many_join_example_1() {
try {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
List<Phone> phones = session.createSQLQuery(
"SELECT * " +
"FROM phone ph " +
"JOIN call c ON c.phone_id = ph.id" )
.addEntity("phone", Phone.class )
.addJoin( "c", "phone.calls")
.setResultTransformer( Criteria.DISTINCT_ROOT_ENTITY )
.list();
for(Phone phone : phones) {
List<Call> calls = phone.getCalls();
}
assertEquals(2, phones.size());
});
}
catch (Exception e) {
log.error( "HHH-10504", e );
//See issue https://hibernate.atlassian.net/browse/HHH-10504
}
}
@Test
public void test_sql_hibernate_entity_associations_query_one_to_many_join_example_2() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-entity-associations-query-one-to-many-join-example[]
List<Object[]> tuples = session.createSQLQuery(
"SELECT * " +
"FROM phone ph " +
"JOIN call c ON c.phone_id = ph.id" )
.addEntity("phone", Phone.class )
.addJoin( "c", "phone.calls")
.list();
for(Object[] tuple : tuples) {
Phone phone = (Phone) tuple[0];
Call call = (Call) tuple[1];
}
//end::sql-hibernate-entity-associations-query-one-to-many-join-example[]
assertEquals(2, tuples.size());
});
}
@Test
public void test_sql_jpa_multi_entity_query_example() {
try {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-multi-entity-query-example[]
List<Object> entities = entityManager.createNativeQuery(
"SELECT * " +
"FROM person pr, partner pt " +
"WHERE pr.name = pt.name" )
.getResultList();
//end::sql-jpa-multi-entity-query-example[]
assertEquals(2, entities.size());
});
fail("Should throw NonUniqueDiscoveredSqlAliasException!");
}
catch (PersistenceException expected) {
assertEquals( NonUniqueDiscoveredSqlAliasException.class, expected.getCause().getClass() );
}
}
@Test(expected = NonUniqueDiscoveredSqlAliasException.class)
public void test_sql_hibernate_multi_entity_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-multi-entity-query-example[]
List<Object> entities = session.createSQLQuery(
"SELECT * " +
"FROM person pr, partner pt " +
"WHERE pr.name = pt.name" )
.list();
//end::sql-hibernate-multi-entity-query-example[]
assertEquals(2, entities.size());
});
fail("Should throw NonUniqueDiscoveredSqlAliasException!");
}
@Test
public void test_sql_hibernate_multi_entity_query_alias_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-multi-entity-query-alias-example[]
List<Object> entities = session.createSQLQuery(
"SELECT {pr.*}, {pt.*} " +
"FROM person pr, partner pt " +
"WHERE pr.name = pt.name" )
.addEntity( "pr", Person.class)
.addEntity( "pt", Partner.class)
.list();
//end::sql-hibernate-multi-entity-query-alias-example[]
assertEquals(1, entities.size());
});
}
@Test
public void test_sql_hibernate_dto_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-dto-query-example[]
List<PersonSummaryDTO> dtos = session.createSQLQuery(
"SELECT p.id as \"id\", p.name as \"name\" " +
"FROM person p")
.setResultTransformer( Transformers.aliasToBean( PersonSummaryDTO.class ) )
.list();
//end::sql-hibernate-dto-query-example[]
assertEquals(3, dtos.size());
});
}
@Test
public void test_sql_hibernate_inheritance_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-inheritance-query-example[]
List<CreditCardPayment> payments = session.createSQLQuery(
"SELECT * " +
"FROM Payment p " +
"JOIN CreditCardPayment cp on cp.id = p.id" )
.addEntity( CreditCardPayment.class )
.list();
//end::sql-hibernate-inheritance-query-example[]
assertEquals(1, payments.size());
});
}
@Test
public void test_sql_jpa_query_parameters_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-query-parameters-example[]
List<Person> persons = entityManager.createNativeQuery(
"SELECT * " +
"FROM person " +
"WHERE name like :name", Person.class )
.setParameter("name", "J%")
.getResultList();
//end::sql-jpa-query-parameters-example[]
assertEquals(1, persons.size());
});
}
@Test
public void test_sql_hibernate_query_parameters_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-query-parameters-example[]
List<Person> persons = session.createSQLQuery(
"SELECT * " +
"FROM person " +
"WHERE name like :name" )
.addEntity( Person.class )
.setParameter("name", "J%")
.list();
//end::sql-hibernate-query-parameters-example[]
assertEquals(1, persons.size());
});
}
@Test
public void test_sql_jpa_scalar_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-scalar-named-query-example[]
List<String> names = entityManager.createNamedQuery(
"find_person_name" )
.getResultList();
//end::sql-jpa-scalar-named-query-example[]
assertEquals(3, names.size());
});
}
@Test
public void test_sql_hibernate_scalar_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-scalar-named-query-example[]
List<String> names = session.getNamedQuery(
"find_person_name" )
.list();
//end::sql-hibernate-scalar-named-query-example[]
assertEquals(3, names.size());
});
}
@Test
public void test_sql_jpa_multiple_scalar_values_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-multiple-scalar-values-named-query-example[]
List<Object[]> tuples = entityManager.createNamedQuery(
"find_person_name_and_nickName" )
.getResultList();
for(Object[] tuple : tuples) {
String name = (String) tuple[0];
String nickName = (String) tuple[1];
}
//end::sql-jpa-multiple-scalar-values-named-query-example[]
assertEquals(3, tuples.size());
});
}
@Test
public void test_sql_hibernate_multiple_scalar_values_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-multiple-scalar-values-named-query-example[]
List<Object[]> tuples = session.getNamedQuery(
"find_person_name_and_nickName" )
.list();
for(Object[] tuple : tuples) {
String name = (String) tuple[0];
String nickName = (String) tuple[1];
}
//end::sql-hibernate-multiple-scalar-values-named-query-example[]
assertEquals(3, tuples.size());
});
}
@Test
public void test_sql_jpa_multiple_scalar_values_dto_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-multiple-scalar-values-dto-named-query-example[]
List<PersonNames> personNames = entityManager.createNamedQuery(
"find_person_name_and_nickName_dto" )
.getResultList();
//end::sql-jpa-multiple-scalar-values-dto-named-query-example[]
assertEquals(3, personNames.size());
});
}
@Test
public void test_sql_hibernate_multiple_scalar_values_dto_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-multiple-scalar-values-dto-named-query-example[]
List<PersonNames> personNames = session.getNamedQuery(
"find_person_name_and_nickName_dto" )
.list();
//end::sql-hibernate-multiple-scalar-values-dto-named-query-example[]
assertEquals(3, personNames.size());
});
}
@Test
public void test_sql_jpa_entity_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-entity-named-query-example[]
List<Person> persons = entityManager.createNamedQuery(
"find_person_by_name" )
.setParameter("name", "J%")
.getResultList();
//end::sql-jpa-entity-named-query-example[]
assertEquals(1, persons.size());
});
}
@Test
public void test_sql_hibernate_entity_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-entity-named-query-example[]
List<Person> persons = session.getNamedQuery(
"find_person_by_name" )
.setParameter("name", "J%")
.list();
//end::sql-hibernate-entity-named-query-example[]
assertEquals(1, persons.size());
});
}
@Test
public void test_sql_jpa_entity_associations_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-entity-associations_named-query-example[]
List<Object[]> tuples = entityManager.createNamedQuery(
"find_person_with_phones_by_name" )
.setParameter("name", "J%")
.getResultList();
for(Object[] tuple : tuples) {
Person person = (Person) tuple[0];
Phone phone = (Phone) tuple[1];
}
//end::sql-jpa-entity-associations_named-query-example[]
assertEquals(1, tuples.size());
});
}
@Test
public void test_sql_hibernate_entity_associations_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-entity-associations_named-query-example[]
List<Object[]> tuples = session.getNamedQuery(
"find_person_with_phones_by_name" )
.setParameter("name", "J%")
.list();
for(Object[] tuple : tuples) {
Person person = (Person) tuple[0];
Phone phone = (Phone) tuple[1];
}
//end::sql-hibernate-entity-associations_named-query-example[]
assertEquals(1, tuples.size());
});
}
@Test
public void test_sql_jpa_composite_key_entity_associations_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
//tag::sql-jpa-composite-key-entity-associations_named-query-example[]
List<Object[]> tuples = entityManager.createNamedQuery(
"find_all_spaceships" )
.getResultList();
for(Object[] tuple : tuples) {
SpaceShip spaceShip = (SpaceShip) tuple[0];
Integer surface = (Integer) tuple[1];
Integer volume = (Integer) tuple[2];
}
//end::sql-jpa-composite-key-entity-associations_named-query-example[]
assertEquals(1, tuples.size());
});
}
@Test
public void test_sql_hibernate_composite_key_entity_associations_named_query_example() {
doInJPA( this::entityManagerFactory, entityManager -> {
Session session = entityManager.unwrap( Session.class );
//tag::sql-hibernate-composite-key-entity-associations_named-query-example[]
List<Object[]> tuples = session.getNamedQuery(
"find_all_spaceships" )
.list();
for(Object[] tuple : tuples) {
SpaceShip spaceShip = (SpaceShip) tuple[0];
Integer surface = (Integer) tuple[1];
Integer volume = (Integer) tuple[2];
}
//end::sql-hibernate-composite-key-entity-associations_named-query-example[]
assertEquals(1, tuples.size());
});
}
}

View File

@ -0,0 +1,124 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
//$Id$
package org.hibernate.userguide.sql;
import javax.persistence.ColumnResult;
import javax.persistence.Entity;
import javax.persistence.EntityResult;
import javax.persistence.FetchType;
import javax.persistence.FieldResult;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.JoinColumns;
import javax.persistence.ManyToOne;
import javax.persistence.NamedNativeQueries;
import javax.persistence.NamedNativeQuery;
import javax.persistence.SqlResultSetMapping;
/**
* @author Emmanuel Bernard
* @author Vlad MIhalcea
*/
//tag::sql-composite-key-entity-associations_named-query-example[]
@Entity
@NamedNativeQueries({
@NamedNativeQuery(name = "find_all_spaceships",
query =
"SELECT " +
" name as \"name\", " +
" model, " +
" speed, " +
" lname as lastn, " +
" fname as firstn, " +
" length, " +
" width, " +
" length * width as surface, " +
" length * width * 10 as volume " +
"FROM SpaceShip",
resultSetMapping = "spaceship"
)
})
@SqlResultSetMapping(
name = "spaceship",
entities = @EntityResult(
entityClass = SpaceShip.class,
fields = {
@FieldResult(name = "name", column = "name"),
@FieldResult(name = "model", column = "model"),
@FieldResult(name = "speed", column = "speed"),
@FieldResult(name = "captain.lastname", column = "lastn"),
@FieldResult(name = "captain.firstname", column = "firstn"),
@FieldResult(name = "dimensions.length", column = "length"),
@FieldResult(name = "dimensions.width", column = "width"),
}
),
columns = {
@ColumnResult(name = "surface"),
@ColumnResult(name = "volume")
}
)
public class SpaceShip {
@Id
private String name;
private String model;
private double speed;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumns({
@JoinColumn(name = "fname", referencedColumnName = "firstname"),
@JoinColumn(name = "lname", referencedColumnName = "lastname")
})
private Captain captain;
private Dimensions dimensions;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getModel() {
return model;
}
public void setModel(String model) {
this.model = model;
}
public double getSpeed() {
return speed;
}
public void setSpeed(double speed) {
this.speed = speed;
}
public Captain getCaptain() {
return captain;
}
public void setCaptain(Captain captain) {
this.captain = captain;
}
public Dimensions getDimensions() {
return dimensions;
}
public void setDimensions(Dimensions dimensions) {
this.dimensions = dimensions;
}
}
//end::sql-composite-key-entity-associations_named-query-example[]

View File

@ -1,3 +1,9 @@
/*
* Hibernate, Relational Persistence for Idiomatic Java
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.userguide.transactions;
import javax.persistence.Entity;

View File

@ -25,8 +25,7 @@ log4j.logger.org.hibernate.reflection=info
log4j.logger.org.hibernate.SQL=debug
### log JDBC bind parameters ###
#log4j.logger.org.hibernate.type=info
log4j.logger.org.hibernate.type=trace
log4j.logger.org.hibernate.type=info
### log schema export/update ###
log4j.logger.org.hibernate.tool.hbm2ddl=info