Fix ToOne @Fetch(FetchMode.SELECT)
This commit is contained in:
parent
8971843626
commit
2f98e4bfe8
|
@ -34,6 +34,7 @@ import org.hibernate.mapping.Component;
|
|||
import org.hibernate.mapping.IndexedCollection;
|
||||
import org.hibernate.mapping.KeyValue;
|
||||
import org.hibernate.mapping.OneToMany;
|
||||
import org.hibernate.mapping.OneToOne;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.Property;
|
||||
import org.hibernate.mapping.Selectable;
|
||||
|
@ -1041,59 +1042,72 @@ public class MappingModelCreationHelper {
|
|||
PropertyAccess propertyAccess,
|
||||
CascadeStyle cascadeStyle,
|
||||
MappingModelCreationProcess creationProcess) {
|
||||
ToOne value = (ToOne) bootProperty.getValue();
|
||||
final EntityPersister entityPersister = creationProcess.getEntityPersister( value.getReferencedEntityName() );
|
||||
if ( bootProperty.getValue() instanceof ToOne ) {
|
||||
final ToOne value = (ToOne) bootProperty.getValue();
|
||||
final EntityPersister entityPersister = creationProcess.getEntityPersister( value.getReferencedEntityName() );
|
||||
final StateArrayContributorMetadataAccess stateArrayContributorMetadataAccess = getStateArrayContributorMetadataAccess(
|
||||
bootProperty,
|
||||
attrType,
|
||||
propertyAccess,
|
||||
cascadeStyle,
|
||||
creationProcess
|
||||
);
|
||||
SessionFactoryImplementor sessionFactory = creationProcess.getCreationContext().getSessionFactory();
|
||||
|
||||
final StateArrayContributorMetadataAccess stateArrayContributorMetadataAccess = getStateArrayContributorMetadataAccess(
|
||||
bootProperty,
|
||||
attrType,
|
||||
propertyAccess,
|
||||
cascadeStyle,
|
||||
creationProcess
|
||||
);
|
||||
SessionFactoryImplementor sessionFactory = creationProcess.getCreationContext().getSessionFactory();
|
||||
|
||||
final AssociationType type = (AssociationType) bootProperty.getType();
|
||||
final FetchStyle fetchStyle = FetchStrategyHelper
|
||||
.determineFetchStyleByMetadata(
|
||||
bootProperty.getValue().getFetchMode(),
|
||||
type,
|
||||
sessionFactory
|
||||
);
|
||||
|
||||
final FetchTiming fetchTiming = FetchStrategyHelper.determineFetchTiming( fetchStyle, type, sessionFactory );
|
||||
|
||||
final FetchStrategy fetchStrategy = new FetchStrategy( fetchTiming, fetchStyle );
|
||||
|
||||
final SingularAssociationAttributeMapping attributeMapping = new SingularAssociationAttributeMapping(
|
||||
attrName,
|
||||
stateArrayPosition,
|
||||
(ToOne) bootProperty.getValue(),
|
||||
stateArrayContributorMetadataAccess,
|
||||
fetchStrategy,
|
||||
entityPersister,
|
||||
declaringType,
|
||||
propertyAccess
|
||||
);
|
||||
creationProcess.registerInitializationCallback(
|
||||
() -> {
|
||||
final Dialect dialect = creationProcess.getCreationContext()
|
||||
.getSessionFactory()
|
||||
.getJdbcServices()
|
||||
.getDialect();
|
||||
|
||||
MappingModelCreationHelper.interpretKeyDescriptor(
|
||||
attributeMapping,
|
||||
bootProperty,
|
||||
(ToOne) bootProperty.getValue(),
|
||||
declaringType.findContainingEntityMapping(),
|
||||
dialect,
|
||||
creationProcess
|
||||
final AssociationType type = (AssociationType) bootProperty.getType();
|
||||
final FetchStyle fetchStyle = FetchStrategyHelper
|
||||
.determineFetchStyleByMetadata(
|
||||
bootProperty.getValue().getFetchMode(),
|
||||
type,
|
||||
sessionFactory
|
||||
);
|
||||
return true;
|
||||
}
|
||||
);
|
||||
return attributeMapping;
|
||||
}
|
||||
|
||||
final FetchTiming fetchTiming;
|
||||
|
||||
if ( fetchStyle == fetchStyle.JOIN
|
||||
|| ( value instanceof OneToOne && value.isNullable() )
|
||||
|| !( value ).isLazy() ) {
|
||||
fetchTiming = FetchTiming.IMMEDIATE;
|
||||
}
|
||||
else {
|
||||
fetchTiming = FetchStrategyHelper.determineFetchTiming( fetchStyle, type, sessionFactory );
|
||||
}
|
||||
|
||||
final FetchStrategy fetchStrategy = new FetchStrategy( fetchTiming, fetchStyle );
|
||||
|
||||
final SingularAssociationAttributeMapping attributeMapping = new SingularAssociationAttributeMapping(
|
||||
attrName,
|
||||
stateArrayPosition,
|
||||
(ToOne) bootProperty.getValue(),
|
||||
stateArrayContributorMetadataAccess,
|
||||
fetchStrategy,
|
||||
entityPersister,
|
||||
declaringType,
|
||||
propertyAccess
|
||||
);
|
||||
|
||||
creationProcess.registerInitializationCallback(
|
||||
() -> {
|
||||
final Dialect dialect = creationProcess.getCreationContext()
|
||||
.getSessionFactory()
|
||||
.getJdbcServices()
|
||||
.getDialect();
|
||||
|
||||
MappingModelCreationHelper.interpretKeyDescriptor(
|
||||
attributeMapping,
|
||||
bootProperty,
|
||||
(ToOne) bootProperty.getValue(),
|
||||
declaringType.findContainingEntityMapping(),
|
||||
dialect,
|
||||
creationProcess
|
||||
);
|
||||
return true;
|
||||
}
|
||||
);
|
||||
return attributeMapping;
|
||||
}
|
||||
else {
|
||||
throw new NotYetImplementedFor6Exception( "AnyType support has not yet been implemented" );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -15,7 +15,6 @@ import org.hibernate.engine.profile.FetchProfile;
|
|||
import org.hibernate.engine.spi.LoadQueryInfluencers;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.loader.PropertyPath;
|
||||
import org.hibernate.mapping.ToOne;
|
||||
import org.hibernate.persister.collection.AbstractCollectionPersister;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.persister.entity.EntityPersister;
|
||||
|
@ -120,14 +119,6 @@ public final class FetchStrategyHelper {
|
|||
FetchStyle style,
|
||||
AssociationType type,
|
||||
SessionFactoryImplementor sessionFactory) {
|
||||
if ( type instanceof ToOne ) {
|
||||
if ( ( (ToOne) type ).isLazy() ) {
|
||||
return FetchTiming.DELAYED;
|
||||
}
|
||||
else {
|
||||
return FetchTiming.IMMEDIATE;
|
||||
}
|
||||
}
|
||||
switch ( style ) {
|
||||
case JOIN: {
|
||||
return FetchTiming.IMMEDIATE;
|
||||
|
|
|
@ -0,0 +1,364 @@
|
|||
/*
|
||||
* 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>.
|
||||
*/
|
||||
|
||||
/*
|
||||
* 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.orm.test.fetchmode.toone;
|
||||
|
||||
import java.util.List;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.ManyToOne;
|
||||
import javax.persistence.OneToOne;
|
||||
import javax.persistence.Table;
|
||||
|
||||
import org.hibernate.Hibernate;
|
||||
import org.hibernate.annotations.Fetch;
|
||||
import org.hibernate.annotations.FetchMode;
|
||||
import org.hibernate.boot.SessionFactoryBuilder;
|
||||
import org.hibernate.boot.spi.MetadataImplementor;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
|
||||
import org.hibernate.testing.jdbc.SQLStatementInterceptor;
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.ServiceRegistry;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryProducer;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.containsString;
|
||||
import static org.hamcrest.CoreMatchers.is;
|
||||
import static org.hamcrest.CoreMatchers.not;
|
||||
import static org.hamcrest.MatcherAssert.assertThat;
|
||||
|
||||
@DomainModel(
|
||||
annotatedClasses = {
|
||||
EagerToOneWithJoinFetchModeTests.RootEntity.class,
|
||||
EagerToOneWithJoinFetchModeTests.SimpleEntity.class
|
||||
}
|
||||
)
|
||||
@SessionFactory
|
||||
@ServiceRegistry(
|
||||
settings = {
|
||||
@ServiceRegistry.Setting(name = AvailableSettings.HBM2DDL_DATABASE_ACTION, value = "create-drop")
|
||||
}
|
||||
)
|
||||
public class EagerToOneWithJoinFetchModeTests implements SessionFactoryProducer {
|
||||
|
||||
private SQLStatementInterceptor sqlStatementInterceptor;
|
||||
|
||||
@Override
|
||||
public SessionFactoryImplementor produceSessionFactory(MetadataImplementor model) {
|
||||
final SessionFactoryBuilder sessionFactoryBuilder = model.getSessionFactoryBuilder();
|
||||
sqlStatementInterceptor = new SQLStatementInterceptor( sessionFactoryBuilder );
|
||||
return (SessionFactoryImplementor) sessionFactoryBuilder.build();
|
||||
}
|
||||
|
||||
@BeforeEach
|
||||
public void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
SimpleEntity manyToOneSimpleEntity = new SimpleEntity( 1, "manyToOne" );
|
||||
SimpleEntity oneToOneSimpleEntity = new SimpleEntity( 2, "oneToOne" );
|
||||
session.save( manyToOneSimpleEntity );
|
||||
session.save( oneToOneSimpleEntity );
|
||||
|
||||
RootEntity rootEntity = new RootEntity( 1, "root" );
|
||||
rootEntity.manyToOneSimpleEntity = manyToOneSimpleEntity;
|
||||
rootEntity.oneToOneSimpleEntity = oneToOneSimpleEntity;
|
||||
session.save( rootEntity );
|
||||
} );
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
public void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
session.createQuery( "delete from RootEntity" ).executeUpdate();
|
||||
session.createQuery( "delete from SimpleEntity" ).executeUpdate();
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testFind(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.find( RootEntity.class, 1 );
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String executedStatement = sqls.get( 0 );
|
||||
assertThat( executedStatement, containsString( " root_entity " ) );
|
||||
assertThat( executedStatement, containsString( " left outer join simple_entity " ) );
|
||||
assertThat(
|
||||
executedStatement.replaceFirst( "left outer join", "" ),
|
||||
containsString( " left outer join " )
|
||||
);
|
||||
assertThat(
|
||||
executedStatement.replaceFirst( " left outer join", "" )
|
||||
.replaceFirst( "left outer join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHql(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
assertThat( sqls.get( 0 ), not( containsString( " join " ) ) );
|
||||
assertThat( sqls.get( 0 ), containsString( " root_entity " ) );
|
||||
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 1 ), not( containsString( " join " ) ) );
|
||||
|
||||
assertThat( sqls.get( 2 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 2 ), not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinManyToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.manyToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 1 ), not( containsString( " join " ) ) );
|
||||
|
||||
assertThat( sqls.get( 2 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 2 ), not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 1 ), not( containsString( " join " ) ) );
|
||||
|
||||
assertThat( sqls.get( 2 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 2 ), not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchManyToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.manyToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 2 ) );
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 2 ) );
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinManyToOneAndOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.manyToOneSimpleEntity join r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
containsString( " inner join " )
|
||||
);
|
||||
assertThat(
|
||||
firstStatement
|
||||
.replaceFirst( "inner join", "" )
|
||||
.replaceFirst( "inner join", "" )
|
||||
,
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 1 ), not( containsString( " join " ) ) );
|
||||
|
||||
assertThat( sqls.get( 2 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 2 ), not( containsString( " join " ) ) );
|
||||
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Entity(name = "RootEntity")
|
||||
@Table(name = "root_entity")
|
||||
public static class RootEntity {
|
||||
@Id
|
||||
private Integer id;
|
||||
private String name;
|
||||
|
||||
@ManyToOne
|
||||
@Fetch(FetchMode.JOIN)
|
||||
private SimpleEntity manyToOneSimpleEntity;
|
||||
|
||||
@OneToOne
|
||||
@Fetch(FetchMode.JOIN)
|
||||
private SimpleEntity oneToOneSimpleEntity;
|
||||
|
||||
public RootEntity() {
|
||||
}
|
||||
|
||||
public RootEntity(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Entity(name = "SimpleEntity")
|
||||
@Table(name = "simple_entity")
|
||||
public static class SimpleEntity {
|
||||
|
||||
@Id
|
||||
private Integer id;
|
||||
|
||||
private String name;
|
||||
|
||||
public SimpleEntity() {
|
||||
}
|
||||
|
||||
public SimpleEntity(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,389 @@
|
|||
/*
|
||||
* 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.orm.test.fetchmode.toone;
|
||||
|
||||
import java.util.List;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.ManyToOne;
|
||||
import javax.persistence.OneToOne;
|
||||
import javax.persistence.Table;
|
||||
|
||||
import org.hibernate.Hibernate;
|
||||
import org.hibernate.annotations.Fetch;
|
||||
import org.hibernate.annotations.FetchMode;
|
||||
import org.hibernate.boot.SessionFactoryBuilder;
|
||||
import org.hibernate.boot.spi.MetadataImplementor;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
|
||||
import org.hibernate.testing.jdbc.SQLStatementInterceptor;
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.ServiceRegistry;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryProducer;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.containsString;
|
||||
import static org.hamcrest.CoreMatchers.is;
|
||||
import static org.hamcrest.CoreMatchers.not;
|
||||
import static org.hamcrest.MatcherAssert.assertThat;
|
||||
import static org.hibernate.testing.hamcrest.CollectionMatchers.hasSize;
|
||||
|
||||
/**
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
@DomainModel(
|
||||
annotatedClasses = {
|
||||
EagerToOneWithSelectFetchModeTests.RootEntity.class,
|
||||
EagerToOneWithSelectFetchModeTests.SimpleEntity.class
|
||||
}
|
||||
)
|
||||
@SessionFactory
|
||||
@ServiceRegistry(
|
||||
settings = {
|
||||
@ServiceRegistry.Setting(name = AvailableSettings.HBM2DDL_DATABASE_ACTION, value = "create-drop")
|
||||
}
|
||||
)
|
||||
public class EagerToOneWithSelectFetchModeTests implements SessionFactoryProducer {
|
||||
|
||||
private SQLStatementInterceptor sqlStatementInterceptor;
|
||||
|
||||
@Override
|
||||
public SessionFactoryImplementor produceSessionFactory(MetadataImplementor model) {
|
||||
final SessionFactoryBuilder sessionFactoryBuilder = model.getSessionFactoryBuilder();
|
||||
sqlStatementInterceptor = new SQLStatementInterceptor( sessionFactoryBuilder );
|
||||
return (SessionFactoryImplementor) sessionFactoryBuilder.build();
|
||||
}
|
||||
|
||||
@BeforeEach
|
||||
public void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
SimpleEntity manyToOneSimpleEntity = new SimpleEntity( 1, "manyToOne" );
|
||||
SimpleEntity oneToOneSimpleEntity = new SimpleEntity( 2, "oneToOne" );
|
||||
session.save( manyToOneSimpleEntity );
|
||||
session.save( oneToOneSimpleEntity );
|
||||
|
||||
RootEntity rootEntity = new RootEntity( 1, "root" );
|
||||
rootEntity.manyToOneSimpleEntity = manyToOneSimpleEntity;
|
||||
rootEntity.oneToOneSimpleEntity = oneToOneSimpleEntity;
|
||||
session.save( rootEntity );
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testFind(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.find( RootEntity.class, 1 );
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
assertThat( sqls.get( 0 ), not( containsString( " join " ) ) );
|
||||
assertThat( sqls.get( 0 ), containsString( " root_entity " ) );
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 2 ), containsString( " simple_entity " ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHql(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, not( containsString( " join " ) ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
|
||||
String thirthStatement = sqls.get( 2 );
|
||||
assertThat( thirthStatement, containsString( " simple_entity " ) );
|
||||
assertThat( thirthStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinManyToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.manyToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
|
||||
String thirthStatement = sqls.get( 2 );
|
||||
assertThat( thirthStatement, containsString( " simple_entity " ) );
|
||||
assertThat( thirthStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
|
||||
String thirthStatement = sqls.get( 2 );
|
||||
assertThat( thirthStatement, containsString( " simple_entity " ) );
|
||||
assertThat( thirthStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchManyToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.manyToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 2 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( " join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinManyToOneAndOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join r.manyToOneSimpleEntity join r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
containsString( " inner join " )
|
||||
);
|
||||
assertThat(
|
||||
firstStatement
|
||||
.replaceFirst( "inner join", "" )
|
||||
.replaceFirst( "inner join", "" )
|
||||
,
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 1 ), not( containsString( " join " ) ) );
|
||||
|
||||
assertThat( sqls.get( 2 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 2 ), not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 2 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( " join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchManyToOneAndOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.manyToOneSimpleEntity join fetch r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
containsString( " inner join " )
|
||||
);
|
||||
|
||||
assertThat(
|
||||
firstStatement
|
||||
.replaceFirst( " inner join ", "" )
|
||||
.replaceFirst( " inner join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
public void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
session.createQuery( "delete from RootEntity" ).executeUpdate();
|
||||
session.createQuery( "delete from SimpleEntity" ).executeUpdate();
|
||||
} );
|
||||
}
|
||||
|
||||
@Entity(name = "RootEntity")
|
||||
@Table(name = "root_entity")
|
||||
public static class RootEntity {
|
||||
@Id
|
||||
private Integer id;
|
||||
private String name;
|
||||
|
||||
@ManyToOne
|
||||
@Fetch(FetchMode.SELECT)
|
||||
private SimpleEntity manyToOneSimpleEntity;
|
||||
|
||||
@OneToOne
|
||||
@Fetch(FetchMode.SELECT)
|
||||
private SimpleEntity oneToOneSimpleEntity;
|
||||
|
||||
public RootEntity() {
|
||||
}
|
||||
|
||||
public RootEntity(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Entity(name = "SimpleEntity")
|
||||
@Table(name = "simple_entity")
|
||||
public static class SimpleEntity {
|
||||
|
||||
@Id
|
||||
private Integer id;
|
||||
|
||||
private String name;
|
||||
|
||||
public SimpleEntity() {
|
||||
}
|
||||
|
||||
public SimpleEntity(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,400 @@
|
|||
/*
|
||||
* 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.orm.test.fetchmode.toone;
|
||||
|
||||
import java.util.List;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.FetchType;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.ManyToOne;
|
||||
import javax.persistence.OneToOne;
|
||||
import javax.persistence.Table;
|
||||
|
||||
import org.hibernate.Hibernate;
|
||||
import org.hibernate.annotations.Fetch;
|
||||
import org.hibernate.annotations.FetchMode;
|
||||
import org.hibernate.boot.SessionFactoryBuilder;
|
||||
import org.hibernate.boot.spi.MetadataImplementor;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
|
||||
import org.hibernate.testing.jdbc.SQLStatementInterceptor;
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.ServiceRegistry;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryProducer;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.containsString;
|
||||
import static org.hamcrest.CoreMatchers.is;
|
||||
import static org.hamcrest.CoreMatchers.not;
|
||||
import static org.hamcrest.MatcherAssert.assertThat;
|
||||
import static org.hibernate.testing.hamcrest.CollectionMatchers.hasSize;
|
||||
|
||||
/**
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
@DomainModel(
|
||||
annotatedClasses = {
|
||||
LazyToOneWithJoinFetchModeTests.RootEntity.class,
|
||||
LazyToOneWithJoinFetchModeTests.SimpleEntity.class
|
||||
}
|
||||
)
|
||||
@SessionFactory
|
||||
@ServiceRegistry(
|
||||
settings = {
|
||||
@ServiceRegistry.Setting(name = AvailableSettings.HBM2DDL_DATABASE_ACTION, value = "create-drop")
|
||||
}
|
||||
)
|
||||
public class LazyToOneWithJoinFetchModeTests implements SessionFactoryProducer {
|
||||
|
||||
private SQLStatementInterceptor sqlStatementInterceptor;
|
||||
|
||||
@Override
|
||||
public SessionFactoryImplementor produceSessionFactory(MetadataImplementor model) {
|
||||
final SessionFactoryBuilder sessionFactoryBuilder = model.getSessionFactoryBuilder();
|
||||
sqlStatementInterceptor = new SQLStatementInterceptor( sessionFactoryBuilder );
|
||||
return (SessionFactoryImplementor) sessionFactoryBuilder.build();
|
||||
}
|
||||
|
||||
@BeforeEach
|
||||
public void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
SimpleEntity manyToOneSimpleEntity = new SimpleEntity( 1, "manyToOne" );
|
||||
SimpleEntity oneToOneSimpleEntity = new SimpleEntity( 2, "oneToOne" );
|
||||
session.save( manyToOneSimpleEntity );
|
||||
session.save( oneToOneSimpleEntity );
|
||||
|
||||
RootEntity rootEntity = new RootEntity( 1, "root" );
|
||||
rootEntity.manyToOneSimpleEntity = manyToOneSimpleEntity;
|
||||
rootEntity.oneToOneSimpleEntity = oneToOneSimpleEntity;
|
||||
session.save( rootEntity );
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testFind(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.find( RootEntity.class, 1 );
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String executedStatement = sqls.get( 0 );
|
||||
assertThat( executedStatement, containsString( " root_entity " ) );
|
||||
assertThat( executedStatement, containsString( " left outer join simple_entity " ) );
|
||||
assertThat(
|
||||
executedStatement.replaceFirst( "left outer join", "" ),
|
||||
containsString( " left outer join " )
|
||||
);
|
||||
assertThat(
|
||||
executedStatement.replaceFirst( " left outer join", "" )
|
||||
.replaceFirst( "left outer join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHql(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, not( containsString( " join " ) ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
|
||||
String thirthStatement = sqls.get( 2 );
|
||||
assertThat( thirthStatement, containsString( " simple_entity " ) );
|
||||
assertThat( thirthStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinManyToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.manyToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
|
||||
String thirthStatement = sqls.get( 2 );
|
||||
assertThat( thirthStatement, containsString( " simple_entity " ) );
|
||||
assertThat( thirthStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
|
||||
String thirthStatement = sqls.get( 2 );
|
||||
assertThat( thirthStatement, containsString( " simple_entity " ) );
|
||||
assertThat( thirthStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchManyToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.manyToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 2 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( " join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinManyToOneAndOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join r.manyToOneSimpleEntity join r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 3 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
containsString( " inner join " )
|
||||
);
|
||||
assertThat(
|
||||
firstStatement
|
||||
.replaceFirst( "inner join", "" )
|
||||
.replaceFirst( "inner join", "" )
|
||||
,
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( sqls.get( 1 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 1 ), not( containsString( " join " ) ) );
|
||||
|
||||
assertThat( sqls.get( 2 ), containsString( " simple_entity " ) );
|
||||
assertThat( sqls.get( 2 ), not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 2 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( " join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
String secondStatement = sqls.get( 1 );
|
||||
assertThat( secondStatement, containsString( " simple_entity " ) );
|
||||
assertThat( secondStatement, not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchManyToOneAndOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.manyToOneSimpleEntity join fetch r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
containsString( " inner join " )
|
||||
);
|
||||
|
||||
assertThat(
|
||||
firstStatement
|
||||
.replaceFirst( " inner join ", "" )
|
||||
.replaceFirst( " inner join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
public void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
session.createQuery( "delete from RootEntity" ).executeUpdate();
|
||||
session.createQuery( "delete from SimpleEntity" ).executeUpdate();
|
||||
} );
|
||||
}
|
||||
|
||||
@Entity(name = "RootEntity")
|
||||
@Table(name = "root_entity")
|
||||
public static class RootEntity {
|
||||
@Id
|
||||
private Integer id;
|
||||
private String name;
|
||||
|
||||
@ManyToOne(fetch = FetchType.LAZY)
|
||||
@Fetch(FetchMode.JOIN)
|
||||
private SimpleEntity manyToOneSimpleEntity;
|
||||
|
||||
@OneToOne(fetch = FetchType.LAZY)
|
||||
@Fetch(FetchMode.JOIN)
|
||||
private SimpleEntity oneToOneSimpleEntity;
|
||||
|
||||
public RootEntity() {
|
||||
}
|
||||
|
||||
public RootEntity(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Entity(name = "SimpleEntity")
|
||||
@Table(name = "simple_entity")
|
||||
public static class SimpleEntity {
|
||||
|
||||
@Id
|
||||
private Integer id;
|
||||
|
||||
private String name;
|
||||
|
||||
public SimpleEntity() {
|
||||
}
|
||||
|
||||
public SimpleEntity(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,352 @@
|
|||
/*
|
||||
* 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.orm.test.fetchmode.toone;
|
||||
|
||||
import java.util.List;
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.FetchType;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.ManyToOne;
|
||||
import javax.persistence.OneToOne;
|
||||
import javax.persistence.Table;
|
||||
|
||||
import org.hibernate.Hibernate;
|
||||
import org.hibernate.annotations.Fetch;
|
||||
import org.hibernate.annotations.FetchMode;
|
||||
import org.hibernate.boot.SessionFactoryBuilder;
|
||||
import org.hibernate.boot.spi.MetadataImplementor;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
|
||||
import org.hibernate.testing.jdbc.SQLStatementInterceptor;
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.ServiceRegistry;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryProducer;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.containsString;
|
||||
import static org.hamcrest.CoreMatchers.is;
|
||||
import static org.hamcrest.CoreMatchers.not;
|
||||
import static org.hamcrest.MatcherAssert.assertThat;
|
||||
import static org.hibernate.testing.hamcrest.CollectionMatchers.hasSize;
|
||||
|
||||
/**
|
||||
* @author Nathan Xu
|
||||
*/
|
||||
@DomainModel(
|
||||
annotatedClasses = {
|
||||
LazyToOneWithSelectFetchModeTests.RootEntity.class,
|
||||
LazyToOneWithSelectFetchModeTests.SimpleEntity.class
|
||||
}
|
||||
)
|
||||
@SessionFactory
|
||||
@ServiceRegistry(
|
||||
settings = {
|
||||
@ServiceRegistry.Setting(name = AvailableSettings.HBM2DDL_DATABASE_ACTION, value = "create-drop")
|
||||
}
|
||||
)
|
||||
public class LazyToOneWithSelectFetchModeTests implements SessionFactoryProducer {
|
||||
|
||||
private SQLStatementInterceptor sqlStatementInterceptor;
|
||||
|
||||
@Override
|
||||
public SessionFactoryImplementor produceSessionFactory(MetadataImplementor model) {
|
||||
final SessionFactoryBuilder sessionFactoryBuilder = model.getSessionFactoryBuilder();
|
||||
sqlStatementInterceptor = new SQLStatementInterceptor( sessionFactoryBuilder );
|
||||
return (SessionFactoryImplementor) sessionFactoryBuilder.build();
|
||||
}
|
||||
|
||||
@BeforeEach
|
||||
public void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
SimpleEntity manyToOneSimpleEntity = new SimpleEntity( 1, "manyToOne" );
|
||||
SimpleEntity oneToOneSimpleEntity = new SimpleEntity( 2, "oneToOne" );
|
||||
session.save( manyToOneSimpleEntity );
|
||||
session.save( oneToOneSimpleEntity );
|
||||
|
||||
RootEntity rootEntity = new RootEntity( 1, "root" );
|
||||
rootEntity.manyToOneSimpleEntity = manyToOneSimpleEntity;
|
||||
rootEntity.oneToOneSimpleEntity = oneToOneSimpleEntity;
|
||||
session.save( rootEntity );
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testFind(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.find( RootEntity.class, 1 );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( false ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( false ) );
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls, hasSize( 1 ) );
|
||||
assertThat( sqls.get( 0 ), not( containsString( " join " ) ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHql(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( sqls.get( 0 ), not( containsString( " join " ) ) );
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( false ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( false ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinManyToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.manyToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( false ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( false ) );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"select r from RootEntity r join r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( false ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( false ) );
|
||||
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchManyToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.manyToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( false ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( " join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinManyToOneAndOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join r.manyToOneSimpleEntity join r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( false ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( false ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( " join ", "" ),
|
||||
containsString( " join " )
|
||||
);
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( " join ", "" ).replaceFirst( " join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( false ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat( firstStatement, containsString( " join simple_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( " join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testHqlJoinFetchManyToOneAndOneToOne(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
sqlStatementInterceptor.clear();
|
||||
|
||||
RootEntity rootEntity = session.createQuery(
|
||||
"from RootEntity r join fetch r.manyToOneSimpleEntity join fetch r.oneToOneSimpleEntity where r.id = :id",
|
||||
RootEntity.class
|
||||
).setParameter( "id", 1 ).getSingleResult();
|
||||
|
||||
List<String> sqls = sqlStatementInterceptor.getSqlQueries();
|
||||
assertThat( sqls.size(), is( 1 ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.manyToOneSimpleEntity ), is( true ) );
|
||||
assertThat( Hibernate.isInitialized( rootEntity.oneToOneSimpleEntity ), is( true ) );
|
||||
|
||||
String firstStatement = sqls.get( 0 );
|
||||
assertThat( firstStatement, containsString( " inner join " ) );
|
||||
assertThat( firstStatement, containsString( " root_entity " ) );
|
||||
assertThat(
|
||||
firstStatement.replaceFirst( "inner join", "" ),
|
||||
containsString( " inner join " )
|
||||
);
|
||||
|
||||
assertThat(
|
||||
firstStatement
|
||||
.replaceFirst( " inner join ", "" )
|
||||
.replaceFirst( " inner join ", "" ),
|
||||
not( containsString( " join " ) )
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
public void tearDown(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> {
|
||||
session.createQuery( "delete from RootEntity" ).executeUpdate();
|
||||
session.createQuery( "delete from SimpleEntity" ).executeUpdate();
|
||||
} );
|
||||
}
|
||||
|
||||
@Entity(name = "RootEntity")
|
||||
@Table(name = "root_entity")
|
||||
public static class RootEntity {
|
||||
@Id
|
||||
private Integer id;
|
||||
private String name;
|
||||
|
||||
@ManyToOne(fetch = FetchType.LAZY)
|
||||
@Fetch(FetchMode.SELECT)
|
||||
private SimpleEntity manyToOneSimpleEntity;
|
||||
|
||||
@OneToOne(fetch = FetchType.LAZY)
|
||||
@Fetch(FetchMode.SELECT)
|
||||
private SimpleEntity oneToOneSimpleEntity;
|
||||
|
||||
public RootEntity() {
|
||||
}
|
||||
|
||||
public RootEntity(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Entity(name = "SimpleEntity")
|
||||
@Table(name = "simple_entity")
|
||||
public static class SimpleEntity {
|
||||
|
||||
@Id
|
||||
private Integer id;
|
||||
|
||||
private String name;
|
||||
|
||||
public SimpleEntity() {
|
||||
}
|
||||
|
||||
public SimpleEntity(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,138 @@
|
|||
/*
|
||||
* 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>.
|
||||
*/
|
||||
|
||||
/*
|
||||
* 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.orm.test.onetoone;
|
||||
|
||||
import javax.persistence.Entity;
|
||||
import javax.persistence.FetchType;
|
||||
import javax.persistence.Id;
|
||||
import javax.persistence.OneToOne;
|
||||
|
||||
import org.hibernate.Hibernate;
|
||||
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.SessionFactory;
|
||||
import org.hibernate.testing.orm.junit.SessionFactoryScope;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.is;
|
||||
import static org.hamcrest.MatcherAssert.assertThat;
|
||||
|
||||
/**
|
||||
* @author Andrea Boriero
|
||||
*/
|
||||
@DomainModel(
|
||||
annotatedClasses = {
|
||||
OneToOneLazy.Title.class,
|
||||
OneToOneLazy.Book.class
|
||||
}
|
||||
)
|
||||
@SessionFactory
|
||||
public class OneToOneLazy {
|
||||
|
||||
@BeforeEach
|
||||
public void setUp(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
sesison -> {
|
||||
Title title = new Title( 1L );
|
||||
Book book = new Book( 2L, title );
|
||||
|
||||
sesison.save( title );
|
||||
sesison.save( book );
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testLazyLoading(SessionFactoryScope scope) {
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
Book book = session.find( Book.class, 2L );
|
||||
assertThat( Hibernate.isInitialized( book.getTitle() ), is( false ) );
|
||||
}
|
||||
);
|
||||
|
||||
scope.inTransaction(
|
||||
session -> {
|
||||
Title title = session.find( Title.class, 1L );
|
||||
assertThat( Hibernate.isInitialized( title.getBook() ), is( true ) );
|
||||
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
@Entity
|
||||
public static class Book {
|
||||
|
||||
@Id
|
||||
private Long id;
|
||||
|
||||
@OneToOne(fetch = FetchType.LAZY)
|
||||
private Title title;
|
||||
|
||||
public Book() {
|
||||
}
|
||||
|
||||
public Book(Long id, Title title) {
|
||||
this.id = id;
|
||||
this.title = title;
|
||||
title.setBook( this );
|
||||
}
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Long id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public Title getTitle() {
|
||||
return title;
|
||||
}
|
||||
}
|
||||
|
||||
@Entity
|
||||
public static class Title {
|
||||
|
||||
@Id
|
||||
private Long id;
|
||||
|
||||
@OneToOne(fetch = FetchType.LAZY, mappedBy = "title")
|
||||
private Book book;
|
||||
|
||||
public Title() {
|
||||
}
|
||||
|
||||
public Title(Long id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Long id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public Book getBook() {
|
||||
return book;
|
||||
}
|
||||
|
||||
public void setBook(Book book) {
|
||||
this.book = book;
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue