Update H2 to 1.4.200. Replace LockMode in Fetch and DomainResult with the source alias to resolve lock mode during initializer creation. Introduce notion of aggregate function with an optional filter clause. Implement support for rendering locks into SQL. Move locking tests to orm package

This commit is contained in:
Christian Beikov 2021-05-25 15:29:55 +02:00
parent 6ced2f0aca
commit 5e0864729b
259 changed files with 3597 additions and 1138 deletions

View File

@ -13,7 +13,7 @@ ext {
junitVintageVersion = '5.7.1'
junit5Version = '5.7.1'
h2Version = '1.4.199'
h2Version = '1.4.200'
bytemanVersion = '4.0.13' //Compatible with JDK16
jnpVersion = '5.0.6.CR1'

View File

@ -124,7 +124,12 @@ public class LockOptions implements Serializable {
if ( aliasSpecificLockModes == null ) {
aliasSpecificLockModes = new LinkedHashMap<>();
}
if ( lockMode == null ) {
aliasSpecificLockModes.remove( alias );
}
else {
aliasSpecificLockModes.put( alias, lockMode );
}
return this;
}
@ -338,13 +343,16 @@ public class LockOptions implements Serializable {
return destination;
}
public boolean isCompatible(LockOptions that) {
if ( that == null ) {
return isEmpty();
}
else if ( this == that ) {
@Override
public boolean equals(Object o) {
if ( this == o ) {
return true;
}
if ( o == null || getClass() != o.getClass() ) {
return false;
}
LockOptions that = (LockOptions) o;
if ( timeout != that.timeout ) {
return false;
@ -363,4 +371,14 @@ public class LockOptions implements Serializable {
return followOnLocking != null ? followOnLocking.equals( that.followOnLocking ) : that.followOnLocking == null;
}
@Override
public int hashCode() {
int result = lockMode != null ? lockMode.hashCode() : 0;
result = 31 * result + timeout;
result = 31 * result + ( aliasSpecificLockModes != null ? aliasSpecificLockModes.hashCode() : 0 );
result = 31 * result + ( followOnLocking != null ? followOnLocking.hashCode() : 0 );
result = 31 * result + ( scope ? 1 : 0 );
return result;
}
}

View File

@ -11,7 +11,6 @@ import java.util.Collection;
import java.util.Iterator;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.collection.spi.BagSemantics;
import org.hibernate.collection.spi.CollectionInitializerProducer;
import org.hibernate.engine.FetchTiming;
@ -68,7 +67,6 @@ public abstract class AbstractBagSemantics<E> implements BagSemantics<Collection
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
DomainResultCreationState creationState) {
return new BagInitializerProducer(
attributeMapping,
@ -77,7 +75,6 @@ public abstract class AbstractBagSemantics<E> implements BagSemantics<Collection
navigablePath.append( CollectionPart.Nature.ID.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
),
@ -86,7 +83,6 @@ public abstract class AbstractBagSemantics<E> implements BagSemantics<Collection
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
)
@ -100,7 +96,6 @@ public abstract class AbstractBagSemantics<E> implements BagSemantics<Collection
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
Fetch indexFetch,
Fetch elementFetch,
DomainResultCreationState creationState){
@ -110,7 +105,6 @@ public abstract class AbstractBagSemantics<E> implements BagSemantics<Collection
navigablePath.append( CollectionPart.Nature.ID.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
);
@ -121,7 +115,6 @@ public abstract class AbstractBagSemantics<E> implements BagSemantics<Collection
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
);

View File

@ -12,7 +12,6 @@ import java.util.Map;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.collection.spi.CollectionInitializerProducer;
import org.hibernate.collection.spi.MapSemantics;
import org.hibernate.engine.FetchTiming;
@ -80,7 +79,6 @@ public abstract class AbstractMapSemantics<MKV extends Map<K,V>, K, V> implement
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
DomainResultCreationState creationState) {
return new MapInitializerProducer(
attributeMapping,
@ -89,7 +87,6 @@ public abstract class AbstractMapSemantics<MKV extends Map<K,V>, K, V> implement
navigablePath.append( CollectionPart.Nature.INDEX.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
),
@ -98,7 +95,6 @@ public abstract class AbstractMapSemantics<MKV extends Map<K,V>, K, V> implement
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
)
@ -112,7 +108,6 @@ public abstract class AbstractMapSemantics<MKV extends Map<K,V>, K, V> implement
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
Fetch indexFetch,
Fetch elementFetch,
DomainResultCreationState creationState){
@ -122,7 +117,6 @@ public abstract class AbstractMapSemantics<MKV extends Map<K,V>, K, V> implement
navigablePath.append( CollectionPart.Nature.INDEX.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
);
@ -133,7 +127,6 @@ public abstract class AbstractMapSemantics<MKV extends Map<K,V>, K, V> implement
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
);

View File

@ -10,7 +10,6 @@ import java.util.Iterator;
import java.util.Set;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.collection.spi.CollectionInitializerProducer;
import org.hibernate.collection.spi.CollectionSemantics;
import org.hibernate.engine.FetchTiming;
@ -53,7 +52,6 @@ public abstract class AbstractSetSemantics<SE extends Set<E>,E> implements Colle
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
DomainResultCreationState creationState) {
return new SetInitializerProducer(
attributeMapping,
@ -62,7 +60,6 @@ public abstract class AbstractSetSemantics<SE extends Set<E>,E> implements Colle
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
)
@ -76,7 +73,6 @@ public abstract class AbstractSetSemantics<SE extends Set<E>,E> implements Colle
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
Fetch indexFetch,
Fetch elementFetch,
DomainResultCreationState creationState){
@ -87,7 +83,6 @@ public abstract class AbstractSetSemantics<SE extends Set<E>,E> implements Colle
fetchParent,
selected,
resultVariable,
lockMode,
creationState
);
}

View File

@ -10,7 +10,6 @@ import java.util.Arrays;
import java.util.Iterator;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.collection.spi.CollectionInitializerProducer;
import org.hibernate.collection.spi.CollectionSemantics;
import org.hibernate.collection.spi.PersistentCollection;
@ -101,7 +100,6 @@ public class StandardArraySemantics<E> implements CollectionSemantics<E[], E> {
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
DomainResultCreationState creationState) {
return new ArrayInitializerProducer(
attributeMapping,
@ -110,7 +108,6 @@ public class StandardArraySemantics<E> implements CollectionSemantics<E[], E> {
navigablePath.append( CollectionPart.Nature.INDEX.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
),
@ -119,7 +116,6 @@ public class StandardArraySemantics<E> implements CollectionSemantics<E[], E> {
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
)
@ -133,7 +129,6 @@ public class StandardArraySemantics<E> implements CollectionSemantics<E[], E> {
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
Fetch indexFetch,
Fetch elementFetch,
DomainResultCreationState creationState){
@ -143,7 +138,6 @@ public class StandardArraySemantics<E> implements CollectionSemantics<E[], E> {
navigablePath.append( CollectionPart.Nature.INDEX.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
);
@ -154,7 +148,6 @@ public class StandardArraySemantics<E> implements CollectionSemantics<E[], E> {
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
);

View File

@ -10,7 +10,6 @@ import java.util.Iterator;
import java.util.List;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.collection.spi.CollectionInitializerProducer;
import org.hibernate.collection.spi.CollectionSemantics;
import org.hibernate.collection.spi.PersistentCollection;
@ -75,7 +74,6 @@ public class StandardListSemantics<E> implements CollectionSemantics<List<E>, E>
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
DomainResultCreationState creationState) {
return new ListInitializerProducer(
attributeMapping,
@ -84,7 +82,6 @@ public class StandardListSemantics<E> implements CollectionSemantics<List<E>, E>
navigablePath.append( CollectionPart.Nature.INDEX.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
),
@ -93,7 +90,6 @@ public class StandardListSemantics<E> implements CollectionSemantics<List<E>, E>
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
)
@ -107,7 +103,6 @@ public class StandardListSemantics<E> implements CollectionSemantics<List<E>, E>
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
Fetch indexFetch,
Fetch elementFetch,
DomainResultCreationState creationState) {
@ -117,7 +112,6 @@ public class StandardListSemantics<E> implements CollectionSemantics<List<E>, E>
navigablePath.append( CollectionPart.Nature.INDEX.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
);
@ -128,7 +122,6 @@ public class StandardListSemantics<E> implements CollectionSemantics<List<E>, E>
navigablePath.append( CollectionPart.Nature.ELEMENT.getName() ),
FetchTiming.IMMEDIATE,
selected,
lockMode,
null,
creationState
);

View File

@ -65,7 +65,6 @@ public interface CollectionSemantics<CE, E> {
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
DomainResultCreationState creationState);
CollectionInitializerProducer createInitializerProducer(
@ -74,7 +73,6 @@ public interface CollectionSemantics<CE, E> {
FetchParent fetchParent,
boolean selected,
String resultVariable,
LockMode lockMode,
Fetch indexFetch,
Fetch elementFetch,
DomainResultCreationState creationState);

View File

@ -923,6 +923,11 @@ public abstract class AbstractHANADialect extends Dialect {
return true;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return RowLockStrategy.COLUMN;
}
@Override
public String getAddColumnString() {
return "add (";

View File

@ -158,6 +158,11 @@ abstract class AbstractTransactSQLDialect extends Dialect {
return "";
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return RowLockStrategy.TABLE;
}
@Override
public String appendLockHint(LockOptions lockOptions, String tableName) {
return lockOptions.getLockMode().greaterThan( LockMode.READ ) ? tableName + " holdlock" : tableName;

View File

@ -34,6 +34,19 @@ public class CacheSqlAstTranslator<T extends JdbcOperation> extends AbstractSqlA
super( sessionFactory, statement );
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
return LockStrategy.NONE;
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
// Cache does not support the FOR UPDATE clause
}
@Override
protected boolean needsRowsToSkip() {
return true;

View File

@ -6,6 +6,8 @@
*/
package org.hibernate.dialect;
import org.hibernate.LockMode;
import org.hibernate.LockOptions;
import org.hibernate.dialect.function.CommonFunctionFactory;
import org.hibernate.dialect.pagination.LimitHandler;
import org.hibernate.dialect.pagination.OffsetFetchLimitHandler;
@ -24,6 +26,8 @@ import org.hibernate.sql.exec.spi.JdbcOperation;
import org.hibernate.type.StandardBasicTypes;
import java.sql.Types;
import java.util.Iterator;
import java.util.Map;
import javax.persistence.TemporalType;
@ -43,10 +47,10 @@ public class CockroachDialect extends Dialect {
// * no support for java.sql.Clob
private int version;
private final int version;
public CockroachDialect() {
this(192);
this( 1920 );
}
public CockroachDialect(DialectResolutionInfo info) {
@ -354,4 +358,151 @@ public class CockroachDialect extends Dialect {
return OffsetFetchLimitHandler.INSTANCE;
}
@Override
public String getForUpdateString(String aliases) {
return getForUpdateString() + " of " + aliases;
}
@Override
public String getForUpdateString(LockOptions lockOptions) {
// Support was added in 20.1: https://www.cockroachlabs.com/docs/v20.1/select-for-update.html
if ( getVersion() < 2010 ) {
return "";
}
return super.getForUpdateString( lockOptions );
}
@Override
public String getForUpdateString(String aliases, LockOptions lockOptions) {
// Support was added in 20.1: https://www.cockroachlabs.com/docs/v20.1/select-for-update.html
if ( getVersion() < 2010 ) {
return "";
}
/*
* Parent's implementation for (aliases, lockOptions) ignores aliases.
*/
if ( aliases.isEmpty() ) {
LockMode lockMode = lockOptions.getLockMode();
final Iterator<Map.Entry<String, LockMode>> itr = lockOptions.getAliasLockIterator();
while ( itr.hasNext() ) {
// seek the highest lock mode
final Map.Entry<String, LockMode> entry = itr.next();
final LockMode lm = entry.getValue();
if ( lm.greaterThan( lockMode ) ) {
aliases = entry.getKey();
}
}
}
LockMode lockMode = lockOptions.getAliasSpecificLockMode( aliases );
if (lockMode == null ) {
lockMode = lockOptions.getLockMode();
}
switch ( lockMode ) {
//noinspection deprecation
case UPGRADE:
return getForUpdateString(aliases);
case PESSIMISTIC_READ:
return getReadLockString( aliases, lockOptions.getTimeOut() );
case PESSIMISTIC_WRITE:
return getWriteLockString( aliases, lockOptions.getTimeOut() );
case UPGRADE_NOWAIT:
//noinspection deprecation
case FORCE:
case PESSIMISTIC_FORCE_INCREMENT:
return getForUpdateNowaitString(aliases);
case UPGRADE_SKIPLOCKED:
return getForUpdateSkipLockedString(aliases);
default:
return "";
}
}
private String withTimeout(String lockString, int timeout) {
switch (timeout) {
case LockOptions.NO_WAIT:
return supportsNoWait() ? lockString + " nowait" : lockString;
case LockOptions.SKIP_LOCKED:
return supportsSkipLocked() ? lockString + " skip locked" : lockString;
default:
return lockString;
}
}
@Override
public String getWriteLockString(int timeout) {
return withTimeout( getForUpdateString(), timeout );
}
@Override
public String getWriteLockString(String aliases, int timeout) {
return withTimeout( getForUpdateString( aliases ), timeout );
}
@Override
public String getReadLockString(int timeout) {
return withTimeout(" for share", timeout );
}
@Override
public String getReadLockString(String aliases, int timeout) {
return withTimeout(" for share of " + aliases, timeout );
}
@Override
public String getForUpdateNowaitString() {
return supportsNoWait()
? " for update nowait"
: getForUpdateString();
}
@Override
public String getForUpdateNowaitString(String aliases) {
return supportsNoWait()
? " for update of " + aliases + " nowait"
: getForUpdateString(aliases);
}
@Override
public String getForUpdateSkipLockedString() {
return supportsSkipLocked()
? " for update skip locked"
: getForUpdateString();
}
@Override
public String getForUpdateSkipLockedString(String aliases) {
return supportsSkipLocked()
? " for update of " + aliases + " skip locked"
: getForUpdateString( aliases );
}
@Override
public boolean supportsOuterJoinForUpdate() {
return false;
}
@Override
public boolean supportsNoWait() {
return getVersion() >= 2010;
}
@Override
public boolean supportsWait() {
return false;
}
@Override
public boolean supportsSkipLocked() {
return getVersion() >= 2010;
}
@Override
public boolean forUpdateOfColumns() {
return getVersion() >= 2010;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return getVersion() >= 2010 ? RowLockStrategy.TABLE : RowLockStrategy.NONE;
}
}

View File

@ -29,6 +29,32 @@ public class CockroachSqlAstTranslator<T extends JdbcOperation> extends Abstract
super( sessionFactory, statement );
}
@Override
protected String getForShare() {
return " for share";
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
// Support was added in 20.1: https://www.cockroachlabs.com/docs/v20.1/select-for-update.html
if ( getDialect().getVersion() < 2010 ) {
return LockStrategy.NONE;
}
return super.determineLockingStrategy( querySpec, forUpdateClause, followOnLocking );
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
// Support was added in 20.1: https://www.cockroachlabs.com/docs/v20.1/select-for-update.html
if ( getDialect().getVersion() < 2010 ) {
return;
}
super.renderForUpdateClause( querySpec, forUpdateClause );
}
protected boolean shouldEmulateFetchClause(QueryPart queryPart) {
// Check if current query part is already row numbering to avoid infinite recursion
return useOffsetFetchClause( queryPart ) && getQueryPartForRowNumbering() != queryPart

View File

@ -57,11 +57,6 @@ import javax.persistence.TemporalType;
*/
public class DB2Dialect extends Dialect {
// KNOWN LIMITATIONS:
// * can't select a parameter unless wrapped
// in a cast or function call
private static final String FOR_READ_ONLY_SQL = " for read only with rs";
private static final String FOR_SHARE_SQL = FOR_READ_ONLY_SQL + " use and keep share locks";
private static final String FOR_UPDATE_SQL = FOR_READ_ONLY_SQL + " use and keep update locks";
@ -71,8 +66,7 @@ public class DB2Dialect extends Dialect {
private final int version;
private LimitHandler limitHandler;
private final LimitHandler limitHandler;
private final UniqueDelegate uniqueDelegate;
public DB2Dialect(DialectResolutionInfo info) {
@ -80,7 +74,7 @@ public class DB2Dialect extends Dialect {
}
public DB2Dialect() {
this(900);
this( 900 );
}
public DB2Dialect(int version) {
@ -292,6 +286,10 @@ public class DB2Dialect extends Dialect {
pattern.append("+(");
// DB2 supports temporal arithmetic. See https://www.ibm.com/support/knowledgecenter/en/SSEPGG_9.7.0/com.ibm.db2.luw.sql.ref.doc/doc/r0023457.html
switch (unit) {
case NATIVE:
// AFAICT the native format is seconds with fractional parts after the decimal point
pattern.append("?2) seconds");
break;
case NANOSECOND:
pattern.append("(?2)/1e9) seconds");
break;
@ -339,20 +337,6 @@ public class DB2Dialect extends Dialect {
}
}
@Override
public String getReadLockString(int timeout) {
return timeout==LockOptions.SKIP_LOCKED
? FOR_SHARE_SKIP_LOCKED_SQL
: FOR_SHARE_SQL;
}
@Override
public String getWriteLockString(int timeout) {
return timeout==LockOptions.SKIP_LOCKED
? FOR_UPDATE_SKIP_LOCKED_SQL
: FOR_UPDATE_SQL;
}
@Override
public String getForUpdateString() {
return FOR_UPDATE_SQL;
@ -360,13 +344,36 @@ public class DB2Dialect extends Dialect {
@Override
public boolean supportsSkipLocked() {
return true;
// Introduced in 11.5: https://www.ibm.com/docs/en/db2/11.5?topic=statement-concurrent-access-resolution-clause
return getVersion() >= 1150;
}
@Override
public String getForUpdateSkipLockedString() {
return FOR_UPDATE_SKIP_LOCKED_SQL;
return supportsSkipLocked()
? FOR_UPDATE_SKIP_LOCKED_SQL
: FOR_UPDATE_SQL;
}
@Override
public String getForUpdateSkipLockedString(String aliases) {
return getForUpdateSkipLockedString();
}
@Override
public String getWriteLockString(int timeout) {
return timeout == LockOptions.SKIP_LOCKED && supportsSkipLocked()
? FOR_UPDATE_SKIP_LOCKED_SQL
: FOR_UPDATE_SQL;
}
@Override
public String getReadLockString(int timeout) {
return timeout == LockOptions.SKIP_LOCKED && supportsSkipLocked()
? FOR_SHARE_SKIP_LOCKED_SQL
: FOR_SHARE_SQL;
}
@Override
public boolean supportsOuterJoinForUpdate() {
return false;

View File

@ -42,6 +42,21 @@ public class DB2SqlAstTranslator<T extends JdbcOperation> extends AbstractSqlAst
super( sessionFactory, statement );
}
@Override
protected String getForUpdate() {
return " for read only with rs use and keep update locks";
}
@Override
protected String getForShare() {
return " for read only with rs use and keep share locks";
}
@Override
protected String getSkipLocked() {
return " skip locked data";
}
protected boolean shouldEmulateFetchClause(QueryPart queryPart) {
// Percent fetches or ties fetches aren't supported in DB2
// According to LegacyDB2LimitHandler, variable limit also isn't supported before 11.1
@ -59,7 +74,7 @@ public class DB2SqlAstTranslator<T extends JdbcOperation> extends AbstractSqlAst
@Override
public void visitQueryGroup(QueryGroup queryGroup) {
final boolean emulateFetchClause = shouldEmulateFetchClause( queryGroup );
if ( emulateFetchClause || hasOffset( queryGroup ) && !supportsOffsetClause() ) {
if ( emulateFetchClause || !supportsOffsetClause() && hasOffset( queryGroup ) ) {
emulateFetchOffsetWithWindowFunctions( queryGroup, emulateFetchClause );
}
else {
@ -70,7 +85,7 @@ public class DB2SqlAstTranslator<T extends JdbcOperation> extends AbstractSqlAst
@Override
public void visitQuerySpec(QuerySpec querySpec) {
final boolean emulateFetchClause = shouldEmulateFetchClause( querySpec );
if ( emulateFetchClause || hasOffset( querySpec ) && !supportsOffsetClause() ) {
if ( emulateFetchClause || !supportsOffsetClause() && hasOffset( querySpec ) ) {
emulateFetchOffsetWithWindowFunctions( querySpec, emulateFetchClause );
}
else {
@ -81,7 +96,7 @@ public class DB2SqlAstTranslator<T extends JdbcOperation> extends AbstractSqlAst
@Override
public void visitOffsetFetchClause(QueryPart queryPart) {
if ( !isRowNumberingCurrentQueryPart() ) {
if ( !hasOffset( queryPart ) || supportsOffsetClause() ) {
if ( supportsOffsetClause() || !hasOffset( queryPart ) ) {
renderOffsetFetchClause( queryPart, true );
}
else if ( queryPart.isRoot() && hasLimit() ) {

View File

@ -6,6 +6,7 @@
*/
package org.hibernate.dialect;
import org.hibernate.LockOptions;
import org.hibernate.dialect.identity.DB2390IdentityColumnSupport;
import org.hibernate.dialect.identity.DB2IdentityColumnSupport;
import org.hibernate.dialect.identity.IdentityColumnSupport;
@ -87,11 +88,6 @@ public class DB2iDialect extends DB2Dialect {
}
}
@Override
public String getForUpdateString() {
return " for update with rs";
}
@Override
public LimitHandler getLimitHandler() {
if ( getIVersion() >= 730) {
@ -112,6 +108,11 @@ public class DB2iDialect extends DB2Dialect {
}
}
@Override
public boolean supportsSkipLocked() {
return true;
}
@Override
public SqlAstTranslatorFactory getSqlAstTranslatorFactory() {
return new StandardSqlAstTranslatorFactory() {

View File

@ -10,6 +10,7 @@ import java.sql.Types;
import javax.persistence.TemporalType;
import org.hibernate.LockOptions;
import org.hibernate.dialect.identity.DB2390IdentityColumnSupport;
import org.hibernate.dialect.identity.IdentityColumnSupport;
import org.hibernate.dialect.pagination.FetchLimitHandler;
@ -36,11 +37,11 @@ public class DB2zDialect extends DB2Dialect {
private final int version;
public DB2zDialect(DialectResolutionInfo info) {
this( info.getDatabaseMajorVersion() );
this( info.getDatabaseMajorVersion() * 100 + info.getDatabaseMinorVersion() * 10 );
}
public DB2zDialect() {
this(7);
this( 700 );
}
public DB2zDialect(int version) {
@ -55,7 +56,7 @@ public class DB2zDialect extends DB2Dialect {
@Override
public boolean supportsTimezoneTypes() {
return getVersion() > 1000;
return getZVersion() > 1000;
}
int getZVersion() {
@ -64,14 +65,14 @@ public class DB2zDialect extends DB2Dialect {
@Override
public SequenceSupport getSequenceSupport() {
return getZVersion() < 8
return getZVersion() < 800
? NoSequenceSupport.INSTANCE
: DB2390SequenceSupport.INSTANCE;
}
@Override
public String getQuerySequencesString() {
return getZVersion() < 8 ? null : "select * from sysibm.syssequences";
return getZVersion() < 800 ? null : "select * from sysibm.syssequences";
}
@Override
@ -84,6 +85,11 @@ public class DB2zDialect extends DB2Dialect {
return new DB2390IdentityColumnSupport();
}
@Override
public boolean supportsSkipLocked() {
return true;
}
@Override
public String timestampaddPattern(TemporalUnit unit, TemporalType temporalType) {
StringBuilder pattern = new StringBuilder();

View File

@ -401,6 +401,16 @@ public class DerbyDialect extends Dialect {
return false;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return RowLockStrategy.NONE;
}
@Override
public RowLockStrategy getReadRowLockStrategy() {
return RowLockStrategy.NONE;
}
@Override
public String getForUpdateString() {
return " for update with rs";
@ -416,11 +426,6 @@ public class DerbyDialect extends Dialect {
return " for read only with rs";
}
@Override
public String getWriteLockString(String aliases, int timeout) {
return " for update of " + aliases + " with rs";
}
@Override
public boolean supportsOuterJoinForUpdate() {
//TODO: check this!

View File

@ -39,6 +39,21 @@ public class DerbySqlAstTranslator<T extends JdbcOperation> extends AbstractSqlA
super( sessionFactory, statement );
}
@Override
protected String getForUpdate() {
return " for update";
}
@Override
protected String getForShare() {
return " for read only";
}
@Override
protected String getForUpdateWithClause() {
return " with rs";
}
@Override
public void visitCteContainer(CteContainer cteContainer) {
if ( cteContainer.isWithRecursive() ) {

View File

@ -1725,12 +1725,29 @@ public abstract class Dialect implements ConversionContext {
*
* @return True if the database supports <tt>FOR UPDATE OF</tt> syntax;
* false otherwise.
* @deprecated Use {@link #getWriteRowLockStrategy()} instead
*/
@Deprecated
public boolean forUpdateOfColumns() {
// by default we report no support
return false;
}
/**
* The row lock strategy to use for write locks.
*/
public RowLockStrategy getWriteRowLockStrategy() {
// by default we report no support
return RowLockStrategy.NONE;
}
/**
* The row lock strategy to use for read locks.
*/
public RowLockStrategy getReadRowLockStrategy() {
return getWriteRowLockStrategy();
}
/**
* Does this dialect support <tt>FOR UPDATE</tt> in conjunction with
* outer joined rows?
@ -1843,7 +1860,9 @@ public abstract class Dialect implements ConversionContext {
* @param lockOptions The lock options to apply
* @param tableName The name of the table to which to apply the lock hint.
* @return The table with any required lock hints.
* @deprecated This was moved to {@link AbstractSqlAstTranslator}
*/
@Deprecated
public String appendLockHint(LockOptions lockOptions, String tableName){
return tableName;
}
@ -3515,6 +3534,15 @@ public abstract class Dialect implements ConversionContext {
return false;
}
/**
* Does this dialect/database support WAIT timeout.
*
* @return {@code true} if WAIT is supported
*/
public boolean supportsWait() {
return supportsNoWait();
}
/**
* Inline String literal.
*
@ -3732,6 +3760,23 @@ public abstract class Dialect implements ConversionContext {
return "X'" + StandardBasicTypes.BINARY.toString( bytes ) + "'";
}
public RowLockStrategy getLockRowIdentifier(LockMode lockMode) {
switch ( lockMode ) {
case PESSIMISTIC_READ:
return getReadRowLockStrategy();
case WRITE:
case FORCE:
case PESSIMISTIC_FORCE_INCREMENT:
case PESSIMISTIC_WRITE:
case UPGRADE:
case UPGRADE_SKIPLOCKED:
case UPGRADE_NOWAIT:
return getWriteRowLockStrategy();
default:
return RowLockStrategy.NONE;
}
}
/**
* Pluggable strategy for determining the Size to use for columns of
* a given SQL type.

View File

@ -13,7 +13,6 @@ import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.internal.util.collections.Stack;
import org.hibernate.metamodel.mapping.JdbcMapping;
import org.hibernate.query.ComparisonOperator;
import org.hibernate.query.sqm.sql.internal.SqmParameterInterpretation;
import org.hibernate.sql.ast.Clause;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
import org.hibernate.sql.ast.spi.SqlAppender;
@ -27,7 +26,6 @@ import org.hibernate.sql.ast.tree.expression.FunctionExpression;
import org.hibernate.sql.ast.tree.expression.JdbcLiteral;
import org.hibernate.sql.ast.tree.expression.JdbcParameter;
import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.NullnessLiteral;
import org.hibernate.sql.ast.tree.expression.QueryLiteral;
import org.hibernate.sql.ast.tree.expression.SelfRenderingExpression;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
@ -52,6 +50,11 @@ public class FirebirdSqlAstTranslator<T extends JdbcOperation> extends AbstractS
super( sessionFactory, statement );
}
@Override
protected String getForUpdate() {
return " with lock";
}
protected boolean shouldEmulateFetchClause(QueryPart queryPart) {
// Percent fetches or ties fetches aren't supported in Firebird
// Before 3.0 there was also no support for window functions

View File

@ -101,7 +101,7 @@ public class H2Dialect extends Dialect {
// Prior to 1.4.200 the 'cascade' in 'drop table' was implicit
cascadeConstraints = version >= 104200;
// 1.4.200 introduced changes in current_time and current_timestamp
useLocalTime = version >= 140199;
useLocalTime = version >= 104199;
getDefaultProperties().setProperty( AvailableSettings.STATEMENT_BATCH_SIZE, DEFAULT_BATCH_SIZE );
// http://code.google.com/p/h2database/issues/detail?id=235
@ -193,7 +193,13 @@ public class H2Dialect extends Dialect {
CommonFunctionFactory.median( queryEngine );
CommonFunctionFactory.stddevPopSamp( queryEngine );
CommonFunctionFactory.varPopSamp( queryEngine );
if ( version == 104200 ) {
// See https://github.com/h2database/h2database/issues/2518
CommonFunctionFactory.format_toChar( queryEngine );
}
else {
CommonFunctionFactory.format_formatdatetime( queryEngine );
}
CommonFunctionFactory.rownum( queryEngine );
}
@ -432,6 +438,10 @@ public class H2Dialect extends Dialect {
@Override
public String translateDatetimeFormat(String format) {
if ( version == 104200 ) {
// See https://github.com/h2database/h2database/issues/2518
return OracleDialect.datetimeFormat( format, true, true ).result();
}
return new Replacer( format, "'", "''" )
.replace("e", "u")
.replace( "xxx", "XXX" )

View File

@ -10,18 +10,16 @@ import java.util.List;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.query.ComparisonOperator;
import org.hibernate.query.sqm.sql.internal.SqmParameterInterpretation;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
import org.hibernate.sql.ast.spi.SqlSelection;
import org.hibernate.sql.ast.tree.Statement;
import org.hibernate.sql.ast.tree.cte.CteStatement;
import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.JdbcParameter;
import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.NullnessLiteral;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
import org.hibernate.sql.exec.spi.JdbcOperation;
/**
@ -35,6 +33,30 @@ public class HSQLSqlAstTranslator<T extends JdbcOperation> extends AbstractSqlAs
super( sessionFactory, statement );
}
@Override
public boolean supportsFilterClause() {
return true;
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
if ( getDialect().getVersion() < 200 ) {
return LockStrategy.NONE;
}
return super.determineLockingStrategy( querySpec, forUpdateClause, followOnLocking );
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
if ( getDialect().getVersion() < 200 ) {
return;
}
super.renderForUpdateClause( querySpec, forUpdateClause );
}
@Override
public void visitOffsetFetchClause(QueryPart queryPart) {
if ( supportsOffsetFetchClause() ) {

View File

@ -34,6 +34,19 @@ public class IngresSqlAstTranslator<T extends JdbcOperation> extends AbstractSql
super( sessionFactory, statement );
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
return LockStrategy.NONE;
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
// Ingres does not support the FOR UPDATE clause
}
@Override
protected void renderFetchPlusOffsetExpression(
Expression fetchClauseExpression,

View File

@ -30,6 +30,11 @@ public class MariaDBSqlAstTranslator<T extends JdbcOperation> extends AbstractSq
super( sessionFactory, statement );
}
@Override
protected String getForShare() {
return " lock in share mode";
}
protected boolean shouldEmulateFetchClause(QueryPart queryPart) {
// Check if current query part is already row numbering to avoid infinite recursion
return useOffsetFetchClause( queryPart ) && getQueryPartForRowNumbering() != queryPart && supportsWindowFunctions() && !isRowsOnlyFetchClauseType( queryPart );

View File

@ -956,11 +956,17 @@ public class MySQLDialect extends Dialect {
return getMySQLVersion() >= 800;
}
@Override
public boolean supportsWait() {
//only supported on MariaDB
return false;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return supportsAliasLocks() ? RowLockStrategy.TABLE : RowLockStrategy.NONE;
}
boolean supportsForShare() {
return getMySQLVersion() >= 800;
}

View File

@ -30,6 +30,11 @@ public class MySQLSqlAstTranslator<T extends JdbcOperation> extends AbstractSqlA
super( sessionFactory, statement );
}
@Override
protected String getForShare() {
return getDialect().getVersion() >= 800 ? " for share" : " lock in share mode";
}
protected boolean shouldEmulateFetchClause(QueryPart queryPart) {
// Check if current query part is already row numbering to avoid infinite recursion
return useOffsetFetchClause( queryPart ) && getQueryPartForRowNumbering() != queryPart

View File

@ -1058,6 +1058,11 @@ public class OracleDialect extends Dialect {
return true;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return RowLockStrategy.COLUMN;
}
@Override
public String getForUpdateNowaitString() {
return " for update nowait";
@ -1092,7 +1097,7 @@ public class OracleDialect extends Dialect {
case LockOptions.WAIT_FOREVER:
return lockString;
default:
return supportsNoWait() ? lockString + " wait " + Math.round(timeout / 1e3f) : lockString;
return supportsWait() ? lockString + " wait " + Math.round(timeout / 1e3f) : lockString;
}
}

View File

@ -6,11 +6,14 @@
*/
package org.hibernate.dialect;
import java.util.Collections;
import java.util.List;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.internal.util.collections.Stack;
import org.hibernate.query.ComparisonOperator;
import org.hibernate.query.FetchClauseType;
import org.hibernate.query.IllegalQueryOperationException;
import org.hibernate.sql.ast.Clause;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
import org.hibernate.sql.ast.spi.SqlSelection;
@ -20,11 +23,13 @@ import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.from.UnionTableGroup;
import org.hibernate.sql.ast.tree.insert.Values;
import org.hibernate.sql.ast.tree.select.QueryGroup;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
import org.hibernate.sql.ast.tree.select.SelectClause;
import org.hibernate.sql.ast.tree.select.SortSpecification;
import org.hibernate.sql.exec.spi.JdbcOperation;
/**
@ -38,12 +43,127 @@ public class OracleSqlAstTranslator<T extends JdbcOperation> extends AbstractSql
super( sessionFactory, statement );
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
LockStrategy strategy = super.determineLockingStrategy( querySpec, forUpdateClause, followOnLocking );
final boolean followOnLockingDisabled = Boolean.FALSE.equals( followOnLocking );
if ( strategy != LockStrategy.FOLLOW_ON && querySpec.hasSortSpecifications() ) {
if ( followOnLockingDisabled ) {
throw new IllegalQueryOperationException( "Locking with ORDER BY is not supported!" );
}
strategy = LockStrategy.FOLLOW_ON;
}
// Oracle also doesn't support locks with set operators
// See https://docs.oracle.com/cd/B19306_01/server.102/b14200/statements_10002.htm#i2066346
if ( strategy != LockStrategy.FOLLOW_ON && isPartOfQueryGroup() ) {
if ( followOnLockingDisabled ) {
throw new IllegalQueryOperationException( "Locking with set operators is not supported!" );
}
strategy = LockStrategy.FOLLOW_ON;
}
if ( strategy != LockStrategy.FOLLOW_ON && hasSetOperations( querySpec ) ) {
if ( followOnLockingDisabled ) {
throw new IllegalQueryOperationException( "Locking with set operators is not supported!" );
}
strategy = LockStrategy.FOLLOW_ON;
}
if ( strategy != LockStrategy.FOLLOW_ON && useOffsetFetchClause( querySpec ) && !isRowsOnlyFetchClauseType( querySpec ) ) {
if ( followOnLockingDisabled ) {
throw new IllegalQueryOperationException( "Locking with FETCH is not supported!" );
}
strategy = LockStrategy.FOLLOW_ON;
}
if ( strategy != LockStrategy.FOLLOW_ON ) {
final boolean hasOffset;
if ( querySpec.isRoot() && hasLimit() && getLimit().getFirstRowJpa() != 0 ) {
hasOffset = true;
// We must record that the generated SQL depends on the fact that there is an offset
addAppliedParameterBinding( getOffsetParameter(), null );
}
else {
hasOffset = querySpec.getOffsetClauseExpression() != null;
}
if ( hasOffset ) {
if ( followOnLockingDisabled ) {
throw new IllegalQueryOperationException( "Locking with OFFSET is not supported!" );
}
strategy = LockStrategy.FOLLOW_ON;
}
}
return strategy;
}
private boolean hasSetOperations(QuerySpec querySpec) {
return querySpec.getFromClause().queryTableGroups( group -> group instanceof UnionTableGroup ? group : null ) != null;
}
private boolean isPartOfQueryGroup() {
return getQueryPartStack().findCurrentFirst( part -> part instanceof QueryGroup ? part : null ) != null;
}
protected boolean shouldEmulateFetchClause(QueryPart queryPart) {
// Check if current query part is already row numbering to avoid infinite recursion
return getQueryPartForRowNumbering() != queryPart && !supportsOffsetFetchClause() && (
queryPart.isRoot() && hasLimit() || queryPart.getFetchClauseExpression() != null || queryPart.getOffsetClauseExpression() != null
if (getQueryPartForRowNumbering() == queryPart) {
return false;
}
final boolean hasLimit = queryPart.isRoot() && hasLimit() || queryPart.getFetchClauseExpression() != null
|| queryPart.getOffsetClauseExpression() != null;
if ( !hasLimit ) {
return false;
}
// Even if Oracle supports the OFFSET/FETCH clause, there are conditions where we still want to use the ROWNUM pagination
if ( supportsOffsetFetchClause() ) {
// When the query has no sort specifications and offset, we want to use the ROWNUM pagination as that is a special locking case
return !queryPart.hasSortSpecifications() && !hasOffset( queryPart );
}
return true;
}
@Override
protected void emulateFetchOffsetWithWindowFunctions(
QueryPart queryPart,
Expression offsetExpression,
Expression fetchExpression,
FetchClauseType fetchClauseType,
boolean emulateFetchClause) {
if ( queryPart instanceof QuerySpec && !queryPart.hasSortSpecifications() && offsetExpression == null && fetchClauseType == FetchClauseType.ROWS_ONLY ) {
// Special case for Oracle to support locking along with simple max results paging
final QuerySpec querySpec = (QuerySpec) queryPart;
withRowNumbering(
querySpec,
() -> {
appendSql( "select * from (" );
super.visitQuerySpec( querySpec );
appendSql( ") where rownum <= " );
final Stack<Clause> clauseStack = getClauseStack();
clauseStack.push( Clause.WHERE );
try {
fetchExpression.accept( this );
// We render the FOR UPDATE clause in the outer query
clauseStack.pop();
clauseStack.push( Clause.FOR_UPDATE );
visitForUpdateClause( querySpec );
}
finally {
clauseStack.pop();
}
}
);
}
else {
super.emulateFetchOffsetWithWindowFunctions(
queryPart,
offsetExpression,
fetchExpression,
fetchClauseType,
emulateFetchClause
);
}
}
@Override
protected void visitValuesList(List<Values> valuesList) {
@ -104,7 +224,18 @@ public class OracleSqlAstTranslator<T extends JdbcOperation> extends AbstractSql
@Override
protected void renderRowNumber(SelectClause selectClause, QueryPart queryPart) {
if ( supportsOffsetFetchClause() || selectClause.isDistinct() ) {
super.renderRowNumber( selectClause, queryPart );
final List<SortSpecification> sortSpecifications = getSortSpecificationsRowNumbering( selectClause, queryPart );
if ( selectClause.isDistinct() ) {
appendSql( "dense_rank()" );
}
else {
if ( sortSpecifications.isEmpty() ) {
appendSql( "rownum" );
return;
}
appendSql( "row_number()" );
}
visitOverClause( Collections.emptyList(), sortSpecifications );
}
else {
appendSql( "rownum" );

View File

@ -784,11 +784,21 @@ public class PostgreSQLDialect extends Dialect {
return getVersion() >= 810;
}
@Override
public boolean supportsWait() {
return false;
}
@Override
public boolean supportsSkipLocked() {
return getVersion() >= 950;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return RowLockStrategy.TABLE;
}
@Override
public GroupBySummarizationRenderingStrategy getGroupBySummarizationRenderingStrategy() {
return getVersion() >= 950 ? GroupBySummarizationRenderingStrategy.FUNCTION : GroupBySummarizationRenderingStrategy.NONE;

View File

@ -10,6 +10,7 @@ import org.hibernate.query.FetchClauseType;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
import org.hibernate.sql.ast.tree.Statement;
import org.hibernate.sql.ast.tree.cte.CteMaterialization;
import org.hibernate.sql.ast.tree.cte.CteStatement;
import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.Literal;
@ -30,6 +31,26 @@ public class PostgreSQLSqlAstTranslator<T extends JdbcOperation> extends Abstrac
super( sessionFactory, statement );
}
@Override
protected void renderMaterializationHint(CteMaterialization materialization) {
if ( getDialect().getVersion() >= 1200 ) {
if ( materialization == CteMaterialization.NOT_MATERIALIZED ) {
appendSql( "not " );
}
appendSql( "materialized " );
}
}
@Override
public boolean supportsFilterClause() {
return getDialect().getVersion() >= 940;
}
@Override
protected String getForShare() {
return " for share";
}
protected boolean shouldEmulateFetchClause(QueryPart queryPart) {
// Check if current query part is already row numbering to avoid infinite recursion
if ( getQueryPartForRowNumbering() == queryPart || isRowsOnlyFetchClauseType( queryPart ) ) {

View File

@ -176,7 +176,7 @@ public class RDMSOS2200Dialect extends Dialect {
@Override
protected <T extends JdbcOperation> SqlAstTranslator<T> buildTranslator(
SessionFactoryImplementor sessionFactory, Statement statement) {
return new RDBMSOS2200SqlAstTranslator<>( sessionFactory, statement );
return new RDMSOS2200SqlAstTranslator<>( sessionFactory, statement );
}
};
}

View File

@ -11,7 +11,6 @@ import java.util.List;
import org.hibernate.query.FetchClauseType;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.query.ComparisonOperator;
import org.hibernate.query.Limit;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
import org.hibernate.sql.ast.spi.SqlSelection;
import org.hibernate.sql.ast.tree.Statement;
@ -22,6 +21,7 @@ import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
import org.hibernate.sql.exec.spi.JdbcOperation;
/**
@ -29,12 +29,25 @@ import org.hibernate.sql.exec.spi.JdbcOperation;
*
* @author Christian Beikov
*/
public class RDBMSOS2200SqlAstTranslator<T extends JdbcOperation> extends AbstractSqlAstTranslator<T> {
public class RDMSOS2200SqlAstTranslator<T extends JdbcOperation> extends AbstractSqlAstTranslator<T> {
public RDBMSOS2200SqlAstTranslator(SessionFactoryImplementor sessionFactory, Statement statement) {
public RDMSOS2200SqlAstTranslator(SessionFactoryImplementor sessionFactory, Statement statement) {
super( sessionFactory, statement );
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
return LockStrategy.NONE;
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
// Unisys 2200 does not support the FOR UPDATE clause
}
@Override
public void visitOffsetFetchClause(QueryPart queryPart) {
if ( queryPart.isRoot() ) {

View File

@ -0,0 +1,27 @@
/*
* 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.dialect;
/**
* The strategy for rendering which row to lock with the FOR UPDATE OF clause.
*
* @author Christian Beikov
*/
public enum RowLockStrategy {
/**
* Use a column name.
*/
COLUMN,
/**
* Use a table alias.
*/
TABLE,
/**
* No support for specifying rows to lock.
*/
NONE;
}

View File

@ -394,6 +394,11 @@ public class SQLServerDialect extends AbstractTransactSQLDialect {
return getVersion() >= 9;
}
@Override
public boolean supportsWait() {
return false;
}
@Override
public GroupBySummarizationRenderingStrategy getGroupBySummarizationRenderingStrategy() {
return GroupBySummarizationRenderingStrategy.CLAUSE;

View File

@ -8,6 +8,8 @@ package org.hibernate.dialect;
import java.util.List;
import org.hibernate.LockMode;
import org.hibernate.LockOptions;
import org.hibernate.query.FetchClauseType;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.query.ComparisonOperator;
@ -20,6 +22,8 @@ import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.from.TableReference;
import org.hibernate.sql.ast.tree.from.UnionTableReference;
import org.hibernate.sql.ast.tree.select.QueryGroup;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
@ -34,10 +38,98 @@ import org.hibernate.sql.exec.spi.JdbcOperation;
*/
public class SQLServerSqlAstTranslator<T extends JdbcOperation> extends AbstractSqlAstTranslator<T> {
private static final String UNION_ALL = " union all ";
public SQLServerSqlAstTranslator(SessionFactoryImplementor sessionFactory, Statement statement) {
super( sessionFactory, statement );
}
@Override
protected boolean renderTableReference(TableReference tableReference, LockMode lockMode) {
final String tableExpression = tableReference.getTableExpression();
if ( tableReference instanceof UnionTableReference && lockMode != LockMode.NONE && tableExpression.charAt( 0 ) == '(' ) {
// SQL Server requires to push down the lock hint to the actual table names
int searchIndex = 0;
int unionIndex;
while ( ( unionIndex = tableExpression.indexOf( UNION_ALL, searchIndex ) ) != -1 ) {
appendSql( tableExpression.substring( searchIndex, unionIndex ) );
renderLockHint( lockMode );
appendSql( UNION_ALL );
searchIndex = unionIndex + UNION_ALL.length();
}
appendSql( tableExpression.substring( searchIndex, tableExpression.length() - 2 ) );
renderLockHint( lockMode );
appendSql( " )" );
registerAffectedTable( tableReference );
final Clause currentClause = getClauseStack().getCurrent();
if ( rendersTableReferenceAlias( currentClause ) ) {
final String identificationVariable = tableReference.getIdentificationVariable();
if ( identificationVariable != null ) {
appendSql( getDialect().getTableAliasSeparator() );
appendSql( identificationVariable );
}
}
}
else {
super.renderTableReference( tableReference, lockMode );
renderLockHint( lockMode );
}
// Just always return true because SQL Server doesn't support the FOR UPDATE clause
return true;
}
private void renderLockHint(LockMode lockMode) {
if ( getDialect().getVersion() >= 9 ) {
final int effectiveLockTimeout = getEffectiveLockTimeout( lockMode );
final String writeLockStr = effectiveLockTimeout == LockOptions.SKIP_LOCKED ? "updlock" : "updlock, holdlock";
final String readLockStr = effectiveLockTimeout == LockOptions.SKIP_LOCKED ? "updlock" : "holdlock";
final String noWaitStr = effectiveLockTimeout == LockOptions.NO_WAIT ? ", nowait" : "";
final String skipLockStr = effectiveLockTimeout == LockOptions.SKIP_LOCKED ? ", readpast" : "";
switch ( lockMode ) {
//noinspection deprecation
case UPGRADE:
case PESSIMISTIC_WRITE:
case WRITE:
appendSql( " with (" + writeLockStr + ", rowlock" + noWaitStr + skipLockStr + ")" );
break;
case PESSIMISTIC_READ:
appendSql( " with (" + readLockStr + ", rowlock" + noWaitStr + skipLockStr + ")" );
break;
case UPGRADE_SKIPLOCKED:
appendSql( " with (updlock, rowlock, readpast" + noWaitStr + ")" );
break;
case UPGRADE_NOWAIT:
appendSql( " with (updlock, holdlock, rowlock, nowait)" );
break;
}
}
else {
switch ( lockMode ) {
//noinspection deprecation
case UPGRADE:
case UPGRADE_NOWAIT:
case PESSIMISTIC_WRITE:
case WRITE:
appendSql( " with (updlock, rowlock)" );
break;
case PESSIMISTIC_READ:
appendSql(" with (holdlock, rowlock)" );
break;
case UPGRADE_SKIPLOCKED:
appendSql( " with (updlock, rowlock, readpast)" );
break;
}
}
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
// SQL Server does not support the FOR UPDATE clause
}
protected OffsetFetchClauseMode getOffsetFetchClauseMode(QueryPart queryPart) {
final int version = getDialect().getVersion();
final boolean hasLimit;

View File

@ -109,25 +109,25 @@ public class SpannerDialect extends Dialect {
super.initializeFunctionRegistry( queryEngine );
// Aggregate Functions
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "any_value" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "any_value" )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "array_agg" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "array_agg" )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "countif" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "countif" )
.setInvariantType( StandardBasicTypes.LONG )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "logical_and" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "logical_and" )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "logical_or" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "logical_or" )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "string_agg" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "string_agg" )
.setInvariantType( StandardBasicTypes.STRING )
.setArgumentCountBetween( 1, 2 )
.register();

View File

@ -19,6 +19,7 @@ import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
import org.hibernate.sql.exec.spi.JdbcOperation;
/**
@ -32,6 +33,19 @@ public class SpannerSqlAstTranslator<T extends JdbcOperation> extends AbstractSq
super( sessionFactory, statement );
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
return LockStrategy.NONE;
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
// Spanner does not support the FOR UPDATE clause
}
@Override
public void visitOffsetFetchClause(QueryPart queryPart) {
renderLimitOffsetClause( queryPart );

View File

@ -47,7 +47,7 @@ public class SybaseASEDialect extends SybaseDialect {
}
public SybaseASEDialect(int version) {
super(version);
super( version );
//On Sybase ASE, the 'bit' type cannot be null,
//and cannot have indexes (while we don't use
@ -421,15 +421,20 @@ public class SybaseASEDialect extends SybaseDialect {
return getVersion() >= 1570;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return getVersion() >= 1570 ? RowLockStrategy.COLUMN : RowLockStrategy.TABLE;
}
@Override
public String getForUpdateString() {
return getVersion() < 1570 ? super.getForUpdateString() : " for update";
return getVersion() < 1570 ? "" : " for update";
}
@Override
public String getForUpdateString(String aliases) {
return getVersion() < 1570
? super.getForUpdateString( aliases )
? ""
: getForUpdateString() + " of " + aliases;
}

View File

@ -8,6 +8,7 @@ package org.hibernate.dialect;
import java.util.List;
import org.hibernate.LockMode;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.query.ComparisonOperator;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
@ -18,6 +19,7 @@ import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.from.TableReference;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
import org.hibernate.sql.ast.tree.select.SelectClause;
@ -34,6 +36,26 @@ public class SybaseASESqlAstTranslator<T extends JdbcOperation> extends Abstract
super( sessionFactory, statement );
}
@Override
protected boolean renderTableReference(TableReference tableReference, LockMode lockMode) {
super.renderTableReference( tableReference, lockMode );
if ( getDialect().getVersion() < 1570 ) {
if ( LockMode.READ.lessThan( lockMode ) ) {
appendSql( " holdlock" );
}
return true;
}
return false;
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
if ( getDialect().getVersion() < 1570 ) {
return;
}
super.renderForUpdateClause( querySpec, forUpdateClause );
}
@Override
protected void renderSearchClause(CteStatement cte) {
// Sybase ASE does not support this, but it's just a hint anyway

View File

@ -7,12 +7,14 @@
package org.hibernate.dialect;
import org.hibernate.LockOptions;
import org.hibernate.dialect.identity.IdentityColumnSupport;
import org.hibernate.dialect.identity.SybaseAnywhereIdentityColumnSupport;
import org.hibernate.dialect.pagination.LimitHandler;
import org.hibernate.dialect.pagination.TopLimitHandler;
import org.hibernate.engine.jdbc.dialect.spi.DialectResolutionInfo;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.sql.ForUpdateFragment;
import org.hibernate.sql.ast.SqlAstTranslator;
import org.hibernate.sql.ast.SqlAstTranslatorFactory;
import org.hibernate.sql.ast.spi.StandardSqlAstTranslatorFactory;
@ -20,6 +22,7 @@ import org.hibernate.sql.ast.tree.Statement;
import org.hibernate.sql.exec.spi.JdbcOperation;
import java.sql.Types;
import java.util.Map;
/**
* SQL Dialect for Sybase Anywhere
@ -28,7 +31,7 @@ import java.sql.Types;
public class SybaseAnywhereDialect extends SybaseDialect {
public SybaseAnywhereDialect() {
this(8);
this( 800 );
}
public SybaseAnywhereDialect(DialectResolutionInfo info){
@ -130,6 +133,41 @@ public class SybaseAnywhereDialect extends SybaseDialect {
return new SybaseAnywhereIdentityColumnSupport();
}
@Override
public boolean forUpdateOfColumns() {
return getVersion() >= 1000;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return getVersion() >= 1000 ? RowLockStrategy.COLUMN : RowLockStrategy.TABLE;
}
@Override
public String getForUpdateString() {
return getVersion() < 1000 ? "" : " for update";
}
@Override
public String getForUpdateString(String aliases) {
return getVersion() < 1000
? ""
: getForUpdateString() + " of " + aliases;
}
@Override
public String appendLockHint(LockOptions mode, String tableName) {
return getVersion() < 1000 ? super.appendLockHint( mode, tableName ) : tableName;
}
@Override
@SuppressWarnings("deprecation")
public String applyLocksToSql(String sql, LockOptions aliasedLockOptions, Map<String, String[]> keyColumnNames) {
return getVersion() < 1000
? super.applyLocksToSql( sql, aliasedLockOptions, keyColumnNames )
: sql + new ForUpdateFragment( this, aliasedLockOptions, keyColumnNames ).toFragmentString();
}
@Override
public LimitHandler getLimitHandler() {
//TODO: support 'TOP ? START AT ?'

View File

@ -8,6 +8,7 @@ package org.hibernate.dialect;
import java.util.List;
import org.hibernate.LockMode;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.query.ComparisonOperator;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
@ -18,6 +19,7 @@ import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.from.TableReference;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
import org.hibernate.sql.ast.tree.select.SelectClause;
@ -34,6 +36,26 @@ public class SybaseAnywhereSqlAstTranslator<T extends JdbcOperation> extends Abs
super( sessionFactory, statement );
}
@Override
protected boolean renderTableReference(TableReference tableReference, LockMode lockMode) {
super.renderTableReference( tableReference, lockMode );
if ( getDialect().getVersion() < 1000 ) {
if ( LockMode.READ.lessThan( lockMode ) ) {
appendSql( " holdlock" );
}
return true;
}
return false;
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
if ( getDialect().getVersion() < 1000 ) {
return;
}
super.renderForUpdateClause( querySpec, forUpdateClause );
}
@Override
protected boolean needsRowsToSkip() {
return getDialect().getVersion() < 900;

View File

@ -38,7 +38,7 @@ public class SybaseDialect extends AbstractTransactSQLDialect {
private static final int PARAM_LIST_SIZE_LIMIT = 250000;
public SybaseDialect(){
this(1100);
this( 1100 );
}
public SybaseDialect(DialectResolutionInfo info){

View File

@ -8,6 +8,7 @@ package org.hibernate.dialect;
import java.util.List;
import org.hibernate.LockMode;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.query.ComparisonOperator;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
@ -18,7 +19,9 @@ import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.from.TableReference;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
import org.hibernate.sql.exec.spi.JdbcOperation;
/**
@ -32,6 +35,20 @@ public class SybaseSqlAstTranslator<T extends JdbcOperation> extends AbstractSql
super( sessionFactory, statement );
}
@Override
protected boolean renderTableReference(TableReference tableReference, LockMode lockMode) {
super.renderTableReference( tableReference, lockMode );
if ( LockMode.READ.lessThan( lockMode ) ) {
appendSql( " holdlock" );
}
return true;
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
// Sybase does not support the FOR UPDATE clause
}
@Override
protected void renderSearchClause(CteStatement cte) {
// Sybase does not support this, but it's just a hint anyway

View File

@ -482,6 +482,16 @@ public class TeradataDialect extends Dialect {
return false;
}
@Override
public boolean supportsNoWait() {
return true;
}
@Override
public boolean supportsWait() {
return false;
}
@Override
public boolean useFollowOnLocking(String sql, QueryOptions queryOptions) {
return getVersion() >= 14;
@ -581,7 +591,6 @@ public class TeradataDialect extends Dialect {
@Override
public LimitHandler getLimitHandler() {
//TODO: is this right?!
return TopLimitHandler.INSTANCE;
}

View File

@ -34,6 +34,46 @@ public class TeradataSqlAstTranslator<T extends JdbcOperation> extends AbstractS
super( sessionFactory, statement );
}
@Override
public void visitQuerySpec(QuerySpec querySpec) {
if ( querySpec.isRoot() && getDialect().getVersion() >= 14 ) {
final ForUpdateClause forUpdateClause = new ForUpdateClause();
forUpdateClause.merge( getLockOptions() );
super.renderForUpdateClause( querySpec, forUpdateClause );
}
else {
super.visitQuerySpec( querySpec );
}
}
@Override
protected String getForUpdate() {
return "locking row for write ";
}
@Override
protected String getForShare() {
return "locking row for read ";
}
@Override
protected String getNoWait() {
return "nowait ";
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
return LockStrategy.NONE;
}
@Override
protected void renderForUpdateClause(QuerySpec querySpec, ForUpdateClause forUpdateClause) {
// Teradata does not support the FOR UPDATE clause but has a proprietary LOCKING clause
}
@Override
protected boolean needsRowsToSkip() {
return true;

View File

@ -7,6 +7,7 @@
package org.hibernate.dialect;
import org.hibernate.LockMode;
import org.hibernate.LockOptions;
import org.hibernate.cfg.Environment;
import org.hibernate.dialect.function.CommonFunctionFactory;
import org.hibernate.dialect.lock.*;
@ -215,11 +216,59 @@ public class TimesTenDialect extends Dialect {
return true;
}
@Override
public boolean forUpdateOfColumns() {
return true;
}
@Override
public RowLockStrategy getWriteRowLockStrategy() {
return RowLockStrategy.COLUMN;
}
@Override
public String getForUpdateString(String aliases) {
return " for update of " + aliases;
}
@Override
public String getForUpdateNowaitString() {
return " for update nowait";
}
@Override
public String getWriteLockString(int timeout) {
return withTimeout( getForUpdateString(), timeout );
}
@Override
public String getWriteLockString(String aliases, int timeout) {
return withTimeout( getForUpdateString(aliases), timeout );
}
@Override
public String getReadLockString(int timeout) {
return getWriteLockString( timeout );
}
@Override
public String getReadLockString(String aliases, int timeout) {
return getWriteLockString( aliases, timeout );
}
private String withTimeout(String lockString, int timeout) {
switch (timeout) {
case LockOptions.NO_WAIT:
return supportsNoWait() ? lockString + " nowait" : lockString;
case LockOptions.SKIP_LOCKED:
case LockOptions.WAIT_FOREVER:
return lockString;
default:
return supportsWait() ? lockString + " wait " + Math.round( timeout / 1e3f ) : lockString;
}
}
@Override
public boolean supportsColumnCheck() {
return false;

View File

@ -10,6 +10,8 @@ import java.util.List;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.query.ComparisonOperator;
import org.hibernate.query.IllegalQueryOperationException;
import org.hibernate.query.SemanticException;
import org.hibernate.sql.ast.spi.AbstractSqlAstTranslator;
import org.hibernate.sql.ast.spi.SqlSelection;
import org.hibernate.sql.ast.tree.Statement;
@ -18,6 +20,7 @@ import org.hibernate.sql.ast.tree.expression.Expression;
import org.hibernate.sql.ast.tree.expression.Literal;
import org.hibernate.sql.ast.tree.expression.SqlTuple;
import org.hibernate.sql.ast.tree.expression.Summarization;
import org.hibernate.sql.ast.tree.select.QueryGroup;
import org.hibernate.sql.ast.tree.select.QueryPart;
import org.hibernate.sql.ast.tree.select.QuerySpec;
import org.hibernate.sql.ast.tree.select.SelectClause;
@ -34,6 +37,23 @@ public class TimesTenSqlAstTranslator<T extends JdbcOperation> extends AbstractS
super( sessionFactory, statement );
}
@Override
protected LockStrategy determineLockingStrategy(
QuerySpec querySpec,
ForUpdateClause forUpdateClause,
Boolean followOnLocking) {
// TimesTen supports locks with aggregates but not with set operators
// See https://docs.oracle.com/cd/E11882_01/timesten.112/e21642/state.htm#TTSQL329
LockStrategy strategy = LockStrategy.CLAUSE;
if ( getQueryPartStack().findCurrentFirst( part -> part instanceof QueryGroup ? part : null ) != null ) {
if ( Boolean.FALSE.equals( followOnLocking ) ) {
throw new IllegalQueryOperationException( "Locking with set operators is not supported!" );
}
strategy = LockStrategy.FOLLOW_ON;
}
return strategy;
}
@Override
protected void renderSearchClause(CteStatement cte) {
// TimesTen does not support this, but it's just a hint anyway

View File

@ -167,7 +167,7 @@ public class CommonFunctionFactory {
}
public static void median(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "median" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "median" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
@ -189,7 +189,7 @@ public class CommonFunctionFactory {
* - On Oracle, DB2, MySQL it means stdev_pop()
*/
public static void stddev(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "stddev" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "stddev" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
@ -202,47 +202,47 @@ public class CommonFunctionFactory {
* - On Oracle, DB2, MySQL it means var_pop()
*/
public static void variance(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "variance" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "variance" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
}
public static void stddevPopSamp(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "stddev_pop" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "stddev_pop" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "stddev_samp" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "stddev_samp" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
}
public static void varPopSamp(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "var_pop" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "var_pop" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "var_samp" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "var_samp" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
}
public static void covarPopSamp(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "covar_pop" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "covar_pop" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 2 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "covar_samp" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "covar_samp" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 2 )
.register();
}
public static void corr(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "corr" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "corr" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 2 )
.register();
@ -254,7 +254,7 @@ public class CommonFunctionFactory {
"regr_slope", "regr_sxx", "regr_sxy", "regr_syy"
)
.forEach( fnName ->
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( fnName )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( fnName )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 2 )
.register()
@ -265,11 +265,11 @@ public class CommonFunctionFactory {
* DB2
*/
public static void stdevVarianceSamp(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "stddev_samp" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "stddev_samp" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "variance_samp" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "variance_samp" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
@ -279,11 +279,11 @@ public class CommonFunctionFactory {
* SQL Server-style
*/
public static void stddevPopSamp_stdevp(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "stdev" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "stdev" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "stdevp" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "stdevp" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
@ -295,11 +295,11 @@ public class CommonFunctionFactory {
* SQL Server-style
*/
public static void varPopSamp_varp(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "var" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "var" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "varp" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "varp" )
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount( 1 )
.register();
@ -638,11 +638,11 @@ public class CommonFunctionFactory {
* These are aggregate functions taking one argument!
*/
public static void bitAndOr(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "bit_and" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "bit_and" )
.setExactArgumentCount( 1 )
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "bit_or" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "bit_or" )
.setExactArgumentCount( 1 )
.register();
@ -656,13 +656,13 @@ public class CommonFunctionFactory {
* These are aggregate functions taking one argument!
*/
public static void everyAny(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "every" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "every" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setArgumentListSignature("(predicate)")
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "any" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "any" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setArgumentListSignature("(predicate)")
@ -675,14 +675,14 @@ public class CommonFunctionFactory {
* and predicates!
*/
public static void everyAny_boolAndOr(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "bool_and" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "bool_and" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setArgumentListSignature("(predicate)")
.register();
queryEngine.getSqmFunctionRegistry().registerAlternateKey( "every", "bool_and" );
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder( "bool_or" )
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder( "bool_or" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setArgumentListSignature("(predicate)")
@ -696,14 +696,14 @@ public class CommonFunctionFactory {
* aggregation functions using sum() and case.
*/
public static void everyAny_sumCase(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().patternDescriptorBuilder( "every",
queryEngine.getSqmFunctionRegistry().patternAggregateDescriptorBuilder( "every",
"(sum(case when ?1 then 0 else 1 end)=0)" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setArgumentListSignature("(predicate)")
.register();
queryEngine.getSqmFunctionRegistry().patternDescriptorBuilder( "any",
queryEngine.getSqmFunctionRegistry().patternAggregateDescriptorBuilder( "any",
"(sum(case when ?1 then 1 else 0 end)>0)" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
@ -716,14 +716,14 @@ public class CommonFunctionFactory {
* for SQL Server.
*/
public static void everyAny_sumIif(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().patternDescriptorBuilder( "every",
queryEngine.getSqmFunctionRegistry().patternAggregateDescriptorBuilder( "every",
"min(iif(?1,1,0))" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setArgumentListSignature("(predicate)")
.register();
queryEngine.getSqmFunctionRegistry().patternDescriptorBuilder( "any",
queryEngine.getSqmFunctionRegistry().patternAggregateDescriptorBuilder( "any",
"max(iif(?1,1,0))" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
@ -736,14 +736,14 @@ public class CommonFunctionFactory {
* for Oracle.
*/
public static void everyAny_sumCaseCase(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().patternDescriptorBuilder( "every",
queryEngine.getSqmFunctionRegistry().patternAggregateDescriptorBuilder( "every",
"min(case when ?1 then 1 else 0 end)" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
.setArgumentListSignature("(predicate)")
.register();
queryEngine.getSqmFunctionRegistry().patternDescriptorBuilder( "any",
queryEngine.getSqmFunctionRegistry().patternAggregateDescriptorBuilder( "any",
"max(case when ?1 then 1 else 0 end)" )
.setExactArgumentCount( 1 )
.setInvariantType( StandardBasicTypes.BOOLEAN )
@ -1482,11 +1482,11 @@ public class CommonFunctionFactory {
}
public static void aggregates(QueryEngine queryEngine) {
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder("max")
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder("max")
.setExactArgumentCount(1)
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder("min")
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder("min")
.setExactArgumentCount(1)
.register();
@ -1500,7 +1500,7 @@ public class CommonFunctionFactory {
// Double when applied to state fields of floating point types;
// BigInteger when applied to state fields of type BigInteger;
// and BigDecimal when applied to state fields of type BigDecimal.
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder("sum")
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder("sum")
.setReturnTypeResolver( new FunctionReturnTypeResolver() {
@Override
public AllowableFunctionReturnType<?> resolveFunctionReturnType(AllowableFunctionReturnType<?> impliedType, List<SqmTypedNode<?>> arguments, TypeConfiguration typeConfiguration) {
@ -1574,12 +1574,12 @@ public class CommonFunctionFactory {
.setExactArgumentCount(1)
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder("avg")
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder("avg")
.setInvariantType( StandardBasicTypes.DOUBLE )
.setExactArgumentCount(1)
.register();
queryEngine.getSqmFunctionRegistry().namedDescriptorBuilder("count")
queryEngine.getSqmFunctionRegistry().namedAggregateDescriptorBuilder("count")
.setInvariantType( StandardBasicTypes.LONG )
.setExactArgumentCount(1)
.setArgumentListSignature("([distinct ]{arg|*})")

View File

@ -801,6 +801,9 @@ public abstract class AbstractSharedSessionContract implements SharedSessionCont
HqlQueryImplementor<T> query = namedHqlDescriptor.toQuery( this, resultType );
query.setComment( "dynamic HQL query" );
applyQuerySettingsAndHints( query );
if ( namedHqlDescriptor.getLockOptions() != null ) {
query.setLockOptions( namedHqlDescriptor.getLockOptions() );
}
return query;
}

View File

@ -107,7 +107,6 @@ public abstract class AbstractNaturalIdLoader<T> implements NaturalIdLoader<T> {
navigablePath,
fetchable.getMappedFetchOptions().getTiming(),
true,
options.getLockOptions() != null ? options.getLockOptions().getLockMode() : LockMode.READ,
null,
creationState
);
@ -158,7 +157,6 @@ public abstract class AbstractNaturalIdLoader<T> implements NaturalIdLoader<T> {
else {
lockOptions = LockOptions.READ;
}
final LockMode lockMode = lockOptions.getLockMode();
final NavigablePath entityPath = new NavigablePath( entityDescriptor.getRootPathName() );
final QuerySpec rootQuerySpec = new QuerySpec( true );
@ -176,7 +174,6 @@ public abstract class AbstractNaturalIdLoader<T> implements NaturalIdLoader<T> {
final TableGroup rootTableGroup = entityDescriptor.createRootTableGroup(
entityPath,
null,
lockMode,
() -> rootQuerySpec::applyPredicate,
sqlAstCreationState,
sessionFactory
@ -232,7 +229,7 @@ public abstract class AbstractNaturalIdLoader<T> implements NaturalIdLoader<T> {
@Override
public Callback getCallback() {
return afterLoadAction -> {};
throw new UnsupportedOperationException( "Follow-on locking not supported yet" );
}
},
row -> (L) row[0],
@ -327,7 +324,6 @@ public abstract class AbstractNaturalIdLoader<T> implements NaturalIdLoader<T> {
navigablePath,
fetchable.getMappedFetchOptions().getTiming(),
true,
LockMode.READ,
null,
creationState
);
@ -410,8 +406,7 @@ public abstract class AbstractNaturalIdLoader<T> implements NaturalIdLoader<T> {
@Override
public Callback getCallback() {
return afterLoadAction -> {
};
throw new UnsupportedOperationException( "Follow-on locking not supported yet" );
}
},
(row) -> {

View File

@ -10,7 +10,6 @@ import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import org.hibernate.LockMode;
import org.hibernate.LockOptions;
import org.hibernate.engine.jdbc.env.spi.JdbcEnvironment;
import org.hibernate.engine.jdbc.spi.JdbcServices;
@ -91,7 +90,6 @@ class DatabaseSnapshotExecutor {
final TableGroup rootTableGroup = entityDescriptor.createRootTableGroup(
rootPath,
null,
LockMode.NONE,
() -> rootQuerySpec::applyPredicate,
state,
sessionFactory

View File

@ -380,7 +380,6 @@ public class LoaderSelectBuilder {
final TableGroup rootTableGroup = loadable.createRootTableGroup(
rootNavigablePath,
null,
lockOptions.getLockMode(),
() -> rootQuerySpec::applyPredicate,
sqlAstCreationState,
creationContext
@ -705,7 +704,6 @@ public class LoaderSelectBuilder {
}
}
final LockMode lockMode = LockMode.READ;
FetchTiming fetchTiming = fetchable.getMappedFetchOptions().getTiming();
boolean joined = fetchable.getMappedFetchOptions().getStyle() == FetchStyle.JOIN;
@ -779,7 +777,6 @@ public class LoaderSelectBuilder {
fetchablePath,
fetchTiming,
joined,
lockMode,
null,
creationState
);
@ -865,7 +862,6 @@ public class LoaderSelectBuilder {
final TableGroup rootTableGroup = loadable.createRootTableGroup(
rootNavigablePath,
null,
lockOptions.getLockMode(),
() -> rootQuerySpec::applyPredicate,
sqlAstCreationState,
creationContext

View File

@ -108,8 +108,8 @@ public class LoaderSqlAstCreationState
}
@Override
public LockMode determineLockMode(String identificationVariable) {
return lockOptions.getEffectiveLockMode( identificationVariable );
public void registerLockMode(String identificationVariable, LockMode explicitLockMode) {
throw new UnsupportedOperationException( "Registering lock modes should only be done for result set mappings!" );
}
@Override

View File

@ -177,8 +177,7 @@ public class SimpleNaturalIdLoader<T> extends AbstractNaturalIdLoader<T> {
@Override
public Callback getCallback() {
return afterLoadAction -> {
};
throw new UnsupportedOperationException( "Follow-on locking not supported yet" );
}
},
row -> row[0],

View File

@ -84,7 +84,16 @@ public class SingleIdEntityLoaderStandardImpl<T> extends SingleIdEntityLoaderSup
session.getFactory()
);
return loadPlan.load( key, lockOptions, entityInstance, readOnly, session );
// It seems lock options were ignored in Hibernate 5.x
final LockOptions lockOptionsToUse;
if ( session.getLoadQueryInfluencers().getEnabledCascadingFetchProfile() != null
&& LockMode.UPGRADE.greaterThan( lockOptions.getLockMode() ) ) {
lockOptionsToUse = lockOptions.makeCopy().setLockMode( LockMode.NONE );
}
else {
lockOptionsToUse = lockOptions;
}
return loadPlan.load( key, lockOptionsToUse, entityInstance, readOnly, session );
}
@Internal

View File

@ -15,6 +15,7 @@ import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.loader.ast.spi.Loadable;
import org.hibernate.metamodel.mapping.ModelPart;
import org.hibernate.query.internal.SimpleQueryOptions;
import org.hibernate.query.spi.QueryOptions;
import org.hibernate.query.spi.QueryOptionsAdapter;
import org.hibernate.query.spi.QueryParameterBindings;
@ -22,6 +23,7 @@ import org.hibernate.sql.ast.Clause;
import org.hibernate.sql.ast.SqlAstTranslatorFactory;
import org.hibernate.sql.ast.tree.expression.JdbcParameter;
import org.hibernate.sql.ast.tree.select.SelectStatement;
import org.hibernate.sql.exec.internal.CallbackImpl;
import org.hibernate.sql.exec.internal.JdbcParameterBindingsImpl;
import org.hibernate.sql.exec.internal.JdbcSelectExecutorStandardImpl;
import org.hibernate.sql.exec.spi.Callback;
@ -111,10 +113,12 @@ public class SingleIdLoadPlan<T> implements SingleEntityLoadPlan {
);
}
assert offset == jdbcParameters.size();
final QueryOptions queryOptions = new SimpleQueryOptions( lockOptions, readOnly );
final Callback callback = new CallbackImpl();
final JdbcSelect jdbcSelect = sqlAstTranslatorFactory.buildSelectTranslator( sessionFactory, sqlAst )
.translate( jdbcParameterBindings, QueryOptions.NONE );
.translate( jdbcParameterBindings, queryOptions );
final List list = JdbcSelectExecutorStandardImpl.INSTANCE.list(
final List<T> list = JdbcSelectExecutorStandardImpl.INSTANCE.list(
jdbcSelect,
jdbcParameterBindings,
new ExecutionContext() {
@ -135,12 +139,7 @@ public class SingleIdLoadPlan<T> implements SingleEntityLoadPlan {
@Override
public QueryOptions getQueryOptions() {
return new QueryOptionsAdapter() {
@Override
public Boolean isReadOnly() {
return readOnly;
}
};
return queryOptions;
}
@Override
@ -150,8 +149,7 @@ public class SingleIdLoadPlan<T> implements SingleEntityLoadPlan {
@Override
public Callback getCallback() {
return afterLoadAction -> {
};
return callback;
}
},
RowTransformerPassThruImpl.instance(),
@ -162,7 +160,6 @@ public class SingleIdLoadPlan<T> implements SingleEntityLoadPlan {
return null;
}
//noinspection unchecked
return (T) list.get( 0 );
return list.get( 0 );
}
}

View File

@ -123,8 +123,7 @@ public class SingleUniqueKeyEntityLoaderStandard<T> implements SingleUniqueKeyEn
@Override
public Callback getCallback() {
return afterLoadAction -> {
};
throw new UnsupportedOperationException( "Follow-on locking not supported yet" );
}
},
row -> row[0],
@ -201,8 +200,7 @@ public class SingleUniqueKeyEntityLoaderStandard<T> implements SingleUniqueKeyEn
@Override
public Callback getCallback() {
return afterLoadAction -> {
};
throw new UnsupportedOperationException( "Follow-on locking not supported yet" );
}
},
row -> row[0],

View File

@ -9,7 +9,6 @@ package org.hibernate.loader.ast.spi;
import java.util.function.Consumer;
import java.util.function.Supplier;
import org.hibernate.LockMode;
import org.hibernate.NotYetImplementedFor6Exception;
import org.hibernate.engine.spi.LoadQueryInfluencers;
import org.hibernate.metamodel.mapping.ModelPart;
@ -40,7 +39,6 @@ public interface Loadable extends ModelPart, RootTableGroupProducer {
default TableGroup createRootTableGroup(
NavigablePath navigablePath,
String explicitSourceAlias,
LockMode lockMode,
Supplier<Consumer<Predicate>> additionalPredicateCollectorAccess,
SqlAstCreationState creationState, SqlAstCreationContext creationContext) {
throw new NotYetImplementedFor6Exception( getClass() );

View File

@ -9,7 +9,6 @@ package org.hibernate.metamodel.internal;
import java.util.List;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SessionFactoryImplementor;
@ -151,7 +150,6 @@ public abstract class AbstractCompositeIdentifierMapping
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
return new EmbeddableFetchImpl(
@ -172,7 +170,6 @@ public abstract class AbstractCompositeIdentifierMapping
String explicitSourceAlias,
SqlAstJoinType sqlAstJoinType,
boolean fetched,
LockMode lockMode,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {

View File

@ -12,7 +12,6 @@ import java.util.Map;
import java.util.function.Consumer;
import java.util.function.Supplier;
import org.hibernate.LockMode;
import org.hibernate.NotYetImplementedFor6Exception;
import org.hibernate.engine.spi.LoadQueryInfluencers;
import org.hibernate.loader.ast.spi.Loadable;
@ -273,14 +272,12 @@ public interface EntityMappingType extends ManagedMappingType, EntityValuedModel
default TableGroup createRootTableGroup(
NavigablePath navigablePath,
String explicitSourceAlias,
LockMode lockMode,
Supplier<Consumer<Predicate>> additionalPredicateCollectorAccess,
SqlAstCreationState creationState,
SqlAstCreationContext creationContext) {
return getEntityPersister().createRootTableGroup(
navigablePath,
explicitSourceAlias,
lockMode,
additionalPredicateCollectorAccess,
creationState,
creationContext

View File

@ -6,12 +6,10 @@
*/
package org.hibernate.metamodel.mapping.internal;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.metamodel.mapping.EntityDiscriminatorMapping;
import org.hibernate.metamodel.mapping.JdbcMapping;
import org.hibernate.metamodel.mapping.MappingType;
import org.hibernate.persister.entity.DiscriminatorType;
import org.hibernate.persister.entity.EntityPersister;
import org.hibernate.query.NavigablePath;
@ -138,7 +136,6 @@ public abstract class AbstractEntityDiscriminatorMapping implements EntityDiscri
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
final SqlAstCreationState sqlAstCreationState = creationState.getSqlAstCreationState();

View File

@ -8,7 +8,6 @@ package org.hibernate.metamodel.mapping.internal;
import java.io.Serializable;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SessionFactoryImplementor;
@ -181,7 +180,6 @@ public class AnyDiscriminatorPart implements BasicValuedModelPart, FetchOptions,
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
final SqlAstCreationState sqlAstCreationState = creationState.getSqlAstCreationState();

View File

@ -9,7 +9,6 @@ package org.hibernate.metamodel.mapping.internal;
import java.util.Collections;
import java.util.List;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SessionFactoryImplementor;
@ -138,7 +137,6 @@ public class AnyKeyPart implements BasicValuedModelPart, FetchOptions {
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
final FromClauseAccess fromClauseAccess = creationState

View File

@ -8,7 +8,6 @@ package org.hibernate.metamodel.mapping.internal;
import java.util.function.BiConsumer;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
@ -270,7 +269,6 @@ public class BasicAttributeMapping
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
final SqlAstCreationState sqlAstCreationState = creationState.getSqlAstCreationState();

View File

@ -8,7 +8,6 @@ package org.hibernate.metamodel.mapping.internal;
import java.util.Locale;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SessionFactoryImplementor;
@ -292,7 +291,6 @@ public class BasicEntityIdentifierMappingImpl implements BasicEntityIdentifierMa
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
return new BasicFetch<>(

View File

@ -10,7 +10,6 @@ import java.util.Collections;
import java.util.List;
import java.util.function.BiConsumer;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
@ -208,7 +207,6 @@ public class BasicValuedCollectionPart
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
ResultsLogger.LOGGER.debugf(

View File

@ -6,7 +6,6 @@
*/
package org.hibernate.metamodel.mapping.internal;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SessionFactoryImplementor;
@ -145,7 +144,6 @@ public class CollectionIdentifierDescriptorImpl implements CollectionIdentifierD
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
// get the collection TableGroup

View File

@ -10,7 +10,6 @@ import java.io.Serializable;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.NotYetImplementedFor6Exception;
import org.hibernate.SharedSessionContract;
import org.hibernate.engine.FetchStyle;
@ -120,7 +119,6 @@ public class DiscriminatedAssociationAttributeMapping
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
return discriminatorMapping.generateFetch(
@ -128,7 +126,6 @@ public class DiscriminatedAssociationAttributeMapping
fetchablePath,
fetchTiming,
selected,
lockMode,
resultVariable,
creationState
);

View File

@ -315,7 +315,6 @@ public class DiscriminatedAssociationMapping implements MappingType, FetchOption
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
return new AnyValuedFetch(

View File

@ -8,7 +8,6 @@ package org.hibernate.metamodel.mapping.internal;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.mapping.Any;
@ -106,7 +105,6 @@ public class DiscriminatedCollectionPart implements DiscriminatedAssociationMode
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
return discriminatorMapping.generateFetch(
@ -114,7 +112,6 @@ public class DiscriminatedCollectionPart implements DiscriminatedAssociationMode
fetchablePath,
fetchTiming,
selected,
lockMode,
resultVariable,
creationState
);

View File

@ -10,7 +10,6 @@ import java.util.List;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
@ -209,7 +208,6 @@ public class EmbeddedAttributeMapping
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
return new EmbeddableFetchImpl(
@ -277,7 +275,6 @@ public class EmbeddedAttributeMapping
String explicitSourceAlias,
SqlAstJoinType sqlAstJoinType,
boolean fetched,
LockMode lockMode,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {

View File

@ -11,7 +11,6 @@ import java.util.List;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
@ -151,7 +150,6 @@ public class EmbeddedCollectionPart implements CollectionPart, EmbeddableValuedF
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
return new EmbeddableFetchImpl(
@ -203,7 +201,6 @@ public class EmbeddedCollectionPart implements CollectionPart, EmbeddableValuedF
String explicitSourceAlias,
SqlAstJoinType sqlAstJoinType,
boolean fetched,
LockMode lockMode,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {

View File

@ -10,7 +10,6 @@ import java.util.ArrayList;
import java.util.List;
import java.util.function.IntFunction;
import org.hibernate.LockMode;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
import org.hibernate.mapping.IndexedConsumer;
import org.hibernate.metamodel.mapping.AssociationKey;
@ -303,7 +302,6 @@ public class EmbeddedForeignKeyDescriptor implements ForeignKeyDescriptor {
null,
SqlAstJoinType.INNER,
true,
LockMode.NONE,
creationState.getSqlAstCreationState()
);
return tableGroupJoin.getJoinedGroup();

View File

@ -8,7 +8,6 @@ package org.hibernate.metamodel.mapping.internal;
import java.util.function.BiConsumer;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
@ -144,7 +143,6 @@ public class EntityCollectionPart
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
// find or create the TableGroup associated with this `fetchablePath`
@ -166,7 +164,7 @@ public class EntityCollectionPart
}
);
return new EntityFetchJoinedImpl( fetchParent, this, tableGroup, lockMode, selected, fetchablePath, creationState );
return new EntityFetchJoinedImpl( fetchParent, this, tableGroup, selected, fetchablePath, creationState );
}
@Override
@ -353,7 +351,6 @@ public class EntityCollectionPart
String explicitSourceAlias,
SqlAstJoinType sqlAstJoinType,
boolean fetched,
LockMode lockMode,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {
@ -363,7 +360,6 @@ public class EntityCollectionPart
explicitSourceAlias,
sqlAstJoinType,
fetched,
lockMode,
aliasBaseGenerator,
sqlExpressionResolver,
creationContext

View File

@ -8,7 +8,6 @@ package org.hibernate.metamodel.mapping.internal;
import java.util.function.BiConsumer;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
@ -142,7 +141,6 @@ public class EntityVersionMappingImpl implements EntityVersionMapping, FetchOpti
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
final SqlAstCreationState sqlAstCreationState = creationState.getSqlAstCreationState();

View File

@ -12,7 +12,6 @@ import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;
import org.hibernate.LockMode;
import org.hibernate.NotYetImplementedFor6Exception;
import org.hibernate.dialect.Dialect;
import org.hibernate.engine.FetchStyle;
@ -478,7 +477,6 @@ public class PluralAttributeMappingImpl
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
final SqlAstCreationState sqlAstCreationState = creationState.getSqlAstCreationState();
@ -499,7 +497,6 @@ public class PluralAttributeMappingImpl
null,
SqlAstJoinType.LEFT,
true,
lockMode,
creationState.getSqlAstCreationState()
);
return tableGroupJoin.getJoinedGroup();
@ -556,7 +553,6 @@ public class PluralAttributeMappingImpl
String explicitSourceAlias,
SqlAstJoinType sqlAstJoinType,
boolean fetched,
LockMode lockMode,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {
@ -568,7 +564,6 @@ public class PluralAttributeMappingImpl
explicitSourceAlias,
sqlAstJoinType,
fetched,
lockMode,
aliasBaseGenerator,
sqlExpressionResolver,
creationContext
@ -581,7 +576,6 @@ public class PluralAttributeMappingImpl
explicitSourceAlias,
sqlAstJoinType,
fetched,
lockMode,
aliasBaseGenerator,
sqlExpressionResolver,
creationContext
@ -600,14 +594,13 @@ public class PluralAttributeMappingImpl
String explicitSourceAlias,
SqlAstJoinType sqlAstJoinType,
boolean fetched,
LockMode lockMode,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {
final TableGroup tableGroup = createOneToManyTableGroup(
navigablePath,
fetched,
lockMode,
explicitSourceAlias,
aliasBaseGenerator,
sqlExpressionResolver,
creationContext
@ -634,7 +627,7 @@ public class PluralAttributeMappingImpl
private TableGroup createOneToManyTableGroup(
NavigablePath navigablePath,
boolean fetched,
LockMode lockMode,
String sourceAlias,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {
@ -661,7 +654,7 @@ public class PluralAttributeMappingImpl
navigablePath,
this,
fetched,
lockMode,
sourceAlias,
primaryTableReference,
true,
sqlAliasBase,
@ -684,14 +677,13 @@ public class PluralAttributeMappingImpl
String explicitSourceAlias,
SqlAstJoinType sqlAstJoinType,
boolean fetched,
LockMode lockMode,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {
final TableGroup tableGroup = createCollectionTableGroup(
navigablePath,
fetched,
lockMode,
explicitSourceAlias,
aliasBaseGenerator,
sqlExpressionResolver,
creationContext
@ -718,7 +710,7 @@ public class PluralAttributeMappingImpl
private TableGroup createCollectionTableGroup(
NavigablePath navigablePath,
boolean fetched,
LockMode lockMode,
String sourceAlias,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {
@ -847,7 +839,7 @@ public class PluralAttributeMappingImpl
navigablePath,
this,
fetched,
lockMode,
sourceAlias,
collectionTableReference,
true,
sqlAliasBase,
@ -931,7 +923,6 @@ public class PluralAttributeMappingImpl
public TableGroup createRootTableGroup(
NavigablePath navigablePath,
String explicitSourceAlias,
LockMode lockMode,
Supplier<Consumer<Predicate>> additionalPredicateCollectorAccess,
SqlAstCreationState creationState,
SqlAstCreationContext creationContext) {
@ -939,7 +930,7 @@ public class PluralAttributeMappingImpl
return createOneToManyTableGroup(
navigablePath,
false,
lockMode,
explicitSourceAlias,
creationState.getSqlAliasBaseGenerator(),
creationState.getSqlExpressionResolver(),
creationContext
@ -949,7 +940,7 @@ public class PluralAttributeMappingImpl
return createCollectionTableGroup(
navigablePath,
false,
lockMode,
explicitSourceAlias,
creationState.getSqlAliasBaseGenerator(),
creationState.getSqlExpressionResolver(),
creationContext

View File

@ -11,7 +11,6 @@ import java.util.List;
import java.util.function.Function;
import java.util.function.IntFunction;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchStyle;
import org.hibernate.engine.FetchTiming;
import org.hibernate.engine.spi.SharedSessionContractImplementor;
@ -491,7 +490,6 @@ public class SimpleForeignKeyDescriptor implements ForeignKeyDescriptor, BasicVa
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
return null;

View File

@ -600,7 +600,6 @@ public class ToOneAttributeMapping
NavigablePath fetchablePath,
FetchTiming fetchTiming,
boolean selected,
LockMode lockMode,
String resultVariable,
DomainResultCreationState creationState) {
@ -622,7 +621,7 @@ public class ToOneAttributeMapping
fetchablePath,
true,
getJoinType( fetchablePath, parentTableGroup ),
lockMode,
resultVariable,
creationState,
parentTableGroup
);
@ -632,7 +631,7 @@ public class ToOneAttributeMapping
tableGroup = fromClauseAccess.resolveTableGroup(
fetchablePath,
np ->
createTableGroupJoin( fetchablePath, true, lockMode, creationState, parentTableGroup )
createTableGroupJoin( fetchablePath, true, resultVariable, creationState, parentTableGroup )
);
}
@ -641,7 +640,6 @@ public class ToOneAttributeMapping
fetchParent,
this,
tableGroup,
lockMode,
true,
fetchablePath,
creationState
@ -733,7 +731,6 @@ public class ToOneAttributeMapping
null,
tableGroup.isInnerJoinPossible() ? SqlAstJoinType.INNER : SqlAstJoinType.LEFT,
true,
null,
creationState.getSqlAstCreationState()
);
@ -764,14 +761,14 @@ public class ToOneAttributeMapping
private TableGroup createTableGroupJoin(
NavigablePath fetchablePath,
boolean fetched,
LockMode lockMode,
String sourceAlias,
DomainResultCreationState creationState,
TableGroup parentTableGroup) {
return createTableGroupJoin(
fetchablePath,
fetched,
getDefaultSqlAstJoinType( parentTableGroup ),
lockMode,
sourceAlias,
creationState,
parentTableGroup
);
@ -793,16 +790,15 @@ public class ToOneAttributeMapping
NavigablePath fetchablePath,
boolean fetched,
SqlAstJoinType sqlAstJoinType,
LockMode lockMode,
String sourceAlias,
DomainResultCreationState creationState,
TableGroup parentTableGroup) {
final TableGroupJoin tableGroupJoin = createTableGroupJoin(
fetchablePath,
parentTableGroup,
null,
sourceAlias,
sqlAstJoinType,
fetched,
lockMode,
creationState.getSqlAstCreationState()
);
@ -821,7 +817,6 @@ public class ToOneAttributeMapping
String explicitSourceAlias,
SqlAstJoinType sqlAstJoinType,
boolean fetched,
LockMode lockMode,
SqlAliasBaseGenerator aliasBaseGenerator,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {
@ -862,7 +857,7 @@ public class ToOneAttributeMapping
);
},
this,
null,
explicitSourceAlias,
sqlAliasBase,
creationContext.getSessionFactory(),
lhs
@ -910,7 +905,7 @@ public class ToOneAttributeMapping
public TableGroup createTableGroupJoinInternal(
NavigablePath navigablePath,
boolean fetched,
LockMode lockMode,
String sourceAlias,
final SqlAliasBase sqlAliasBase,
SqlExpressionResolver sqlExpressionResolver,
SqlAstCreationContext creationContext) {
@ -924,7 +919,7 @@ public class ToOneAttributeMapping
navigablePath,
this,
fetched,
lockMode,
sourceAlias,
primaryTableReference,
false,
sqlAliasBase,

View File

@ -1362,7 +1362,6 @@ public abstract class AbstractEntityPersister
public TableGroup createRootTableGroup(
NavigablePath navigablePath,
String explicitSourceAlias,
LockMode lockMode,
Supplier<Consumer<Predicate>> additionalPredicateCollectorAccess,
SqlAstCreationState creationState,
SqlAstCreationContext creationContext) {
@ -1379,7 +1378,7 @@ public abstract class AbstractEntityPersister
return new StandardTableGroup(
navigablePath,
this,
lockMode,
explicitSourceAlias,
primaryTableReference,
true,
sqlAliasBase,
@ -2245,7 +2244,7 @@ public abstract class AbstractEntityPersister
if ( !isVersioned() ) {
return this;
}
return getVersionType().nullSafeGet( rs, VERSION_COLUMN_ALIAS, session, null );
return getVersionMapping().getJdbcMapping().getJdbcValueExtractor().extract( rs, 1, session );
}
finally {
session.getJdbcCoordinator().getLogicalConnection().getResourceRegistry().release( rs, st );

View File

@ -18,7 +18,6 @@ import java.util.function.Consumer;
import java.util.function.Supplier;
import org.hibernate.HibernateException;
import org.hibernate.LockMode;
import org.hibernate.MappingException;
import org.hibernate.boot.model.relational.Database;
import org.hibernate.cache.spi.access.EntityDataAccess;
@ -924,16 +923,15 @@ public class SingleTableEntityPersister extends AbstractEntityPersister {
public TableGroup createRootTableGroup(
NavigablePath navigablePath,
String explicitSourceAlias,
LockMode lockMode,
Supplier<Consumer<Predicate>> additionalPredicateCollectorAccess,
SqlAstCreationState creationState,
SqlAstCreationContext creationContext) {
final TableGroup tableGroup = super.createRootTableGroup(
navigablePath,
explicitSourceAlias,
lockMode,
additionalPredicateCollectorAccess,
creationState, creationContext
creationState,
creationContext
);
if ( needsDiscriminator() ) {

View File

@ -21,7 +21,6 @@ import java.util.function.Supplier;
import org.hibernate.AssertionFailure;
import org.hibernate.HibernateException;
import org.hibernate.LockMode;
import org.hibernate.MappingException;
import org.hibernate.boot.model.relational.Database;
import org.hibernate.cache.spi.access.EntityDataAccess;
@ -54,7 +53,6 @@ import org.hibernate.sql.ast.tree.from.TableReference;
import org.hibernate.sql.ast.tree.from.UnionTableGroup;
import org.hibernate.sql.ast.tree.from.UnionTableReference;
import org.hibernate.sql.ast.tree.predicate.Predicate;
import org.hibernate.tuple.entity.EntityMetamodel;
import org.hibernate.type.StandardBasicTypes;
import org.hibernate.type.Type;
@ -245,7 +243,6 @@ public class UnionSubclassEntityPersister extends AbstractEntityPersister {
public TableGroup createRootTableGroup(
NavigablePath navigablePath,
String explicitSourceAlias,
LockMode lockMode,
Supplier<Consumer<Predicate>> additionalPredicateCollectorAccess,
SqlAstCreationState creationState,
SqlAstCreationContext creationContext) {
@ -253,7 +250,7 @@ public class UnionSubclassEntityPersister extends AbstractEntityPersister {
final TableReference tableReference = resolvePrimaryTableReference(sqlAliasBase);
return new UnionTableGroup( navigablePath, tableReference, this );
return new UnionTableGroup( navigablePath, tableReference, this, explicitSourceAlias );
}
@Override

View File

@ -87,7 +87,7 @@ public class QueryInterpretationCacheStandardImpl implements QueryInterpretation
}
final SelectQueryPlan plan = creator.get();
queryPlanCache.put( key, plan );
queryPlanCache.put( key.prepareForStore(), plan );
return plan;
}

View File

@ -0,0 +1,34 @@
/*
* 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.query.internal;
import org.hibernate.LockOptions;
import org.hibernate.query.spi.QueryOptionsAdapter;
/**
* @author Christian Beikov
*/
public class SimpleQueryOptions extends QueryOptionsAdapter {
private final LockOptions lockOptions;
private final Boolean readOnlyEnabled;
public SimpleQueryOptions(LockOptions lockOptions, Boolean readOnlyEnabled) {
this.lockOptions = lockOptions;
this.readOnlyEnabled = readOnlyEnabled;
}
@Override
public LockOptions getLockOptions() {
return lockOptions;
}
@Override
public Boolean isReadOnly() {
return readOnlyEnabled;
}
}

View File

@ -43,11 +43,9 @@ import org.hibernate.query.results.implicit.ImplicitModelPartResultBuilderEntity
import org.hibernate.sql.ast.spi.FromClauseAccess;
import org.hibernate.sql.ast.tree.from.TableGroup;
import org.hibernate.sql.results.graph.DomainResultCreationState;
import org.hibernate.sql.results.graph.FetchParent;
import org.hibernate.sql.results.graph.Fetchable;
import org.hibernate.sql.results.graph.collection.internal.EntityCollectionPartTableGroup;
import org.hibernate.sql.results.graph.embeddable.EmbeddableValuedFetchable;
import org.hibernate.sql.results.graph.entity.EntityValuedFetchable;
import org.hibernate.type.BasicType;
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
@ -292,7 +290,6 @@ public class Builders {
fetchablePath,
FetchTiming.IMMEDIATE,
true,
LockMode.NONE,
null,
domainResultCreationState
);

View File

@ -75,6 +75,7 @@ public class DomainResultCreationStateImpl
private final Stack<Function<String, FetchBuilder>> fetchBuilderResolverStack = new StandardStack<>( fetchableName -> null );
private final Stack<NavigablePath> relativePathStack = new StandardStack<>();
private Map<String, LockMode> registeredLockModes;
private boolean processingKeyFetches = false;
private boolean resolvingCircularFetch;
private ForeignKeyDescriptor.Nature currentlyResolvingForeignKeySide;
@ -209,8 +210,15 @@ public class DomainResultCreationStateImpl
}
@Override
public LockMode determineLockMode(String identificationVariable) {
return LockMode.READ;
public void registerLockMode(String identificationVariable, LockMode explicitLockMode) {
if (registeredLockModes == null ) {
registeredLockModes = new HashMap<>();
}
registeredLockModes.put( identificationVariable, explicitLockMode );
}
public Map<String, LockMode> getRegisteredLockModes() {
return registeredLockModes;
}
@Override

View File

@ -8,7 +8,6 @@ package org.hibernate.query.results;
import java.util.function.BiFunction;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchTiming;
import org.hibernate.metamodel.mapping.AttributeMapping;
import org.hibernate.query.NavigablePath;
@ -47,7 +46,6 @@ public class ImplicitAttributeFetchBuilder implements FetchBuilder, ImplicitFetc
fetchPath,
FetchTiming.IMMEDIATE,
true,
LockMode.READ,
null,
domainResultCreationState
);

View File

@ -7,9 +7,18 @@
package org.hibernate.query.results;
import java.util.List;
import java.util.Map;
import java.util.function.Supplier;
import org.hibernate.LockMode;
import org.hibernate.metamodel.mapping.ModelPart;
import org.hibernate.query.NavigablePath;
import org.hibernate.sql.ast.spi.SqlAstCreationContext;
import org.hibernate.sql.ast.spi.SqlSelection;
import org.hibernate.sql.results.graph.AssemblerCreationState;
import org.hibernate.sql.results.graph.DomainResult;
import org.hibernate.sql.results.graph.DomainResultAssembler;
import org.hibernate.sql.results.graph.Initializer;
import org.hibernate.sql.results.jdbc.internal.StandardJdbcValuesMapping;
/**
@ -20,16 +29,54 @@ import org.hibernate.sql.results.jdbc.internal.StandardJdbcValuesMapping;
public class JdbcValuesMappingImpl extends StandardJdbcValuesMapping {
private final int rowSize;
private final Map<String, LockMode> registeredLockModes;
public JdbcValuesMappingImpl(
List<SqlSelection> sqlSelections,
List<DomainResult<?>> domainResults, int rowSize) {
List<DomainResult<?>> domainResults,
int rowSize,
Map<String, LockMode> registeredLockModes) {
super( sqlSelections, domainResults );
this.rowSize = rowSize;
this.registeredLockModes = registeredLockModes;
}
@Override
public int getRowSize() {
return rowSize;
}
@Override
public List<DomainResultAssembler<?>> resolveAssemblers(AssemblerCreationState creationState) {
final AssemblerCreationState finalCreationState;
if ( registeredLockModes == null ) {
finalCreationState = creationState;
}
else {
finalCreationState = new AssemblerCreationState() {
@Override
public LockMode determineEffectiveLockMode(String identificationVariable) {
final LockMode lockMode = registeredLockModes.get( identificationVariable );
if ( lockMode == null ) {
return creationState.determineEffectiveLockMode( identificationVariable );
}
return lockMode;
}
@Override
public Initializer resolveInitializer(
NavigablePath navigablePath,
ModelPart fetchedModelPart,
Supplier<Initializer> producer) {
return creationState.resolveInitializer( navigablePath, fetchedModelPart, producer );
}
@Override
public SqlAstCreationContext getSqlAstCreationContext() {
return creationState.getSqlAstCreationContext();
}
};
}
return super.resolveAssemblers( finalCreationState );
}
}

View File

@ -17,6 +17,7 @@ import java.util.function.Consumer;
import org.hibernate.Incubating;
import org.hibernate.Internal;
import org.hibernate.LockMode;
import org.hibernate.NotYetImplementedFor6Exception;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.internal.util.StringHelper;
@ -182,8 +183,8 @@ public class ResultSetMappingImpl implements ResultSetMapping {
domainResults.add( domainResult );
}
return new JdbcValuesMappingImpl( sqlSelections, domainResults, rowSize );
final Map<String, LockMode> registeredLockModes = creationState.getRegisteredLockModes();
return new JdbcValuesMappingImpl( sqlSelections, domainResults, rowSize, registeredLockModes );
}
private DomainResult<?> makeImplicitDomainResult(

View File

@ -11,8 +11,6 @@ import java.util.Collections;
import java.util.List;
import java.util.function.Consumer;
import org.hibernate.LockMode;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.metamodel.mapping.ModelPartContainer;
import org.hibernate.query.NavigablePath;
import org.hibernate.sql.ast.tree.from.TableGroup;
@ -33,7 +31,7 @@ public class TableGroupImpl implements TableGroup {
private List<TableGroupJoin> tableGroupJoins;
private final ModelPartContainer container;
private final LockMode lockMode;
private final String sourceAlias;
public TableGroupImpl(
@ -41,12 +39,12 @@ public class TableGroupImpl implements TableGroup {
String alias,
TableReference primaryTableReference,
ModelPartContainer container,
LockMode lockMode) {
String sourceAlias) {
this.navigablePath = navigablePath;
this.alias = alias;
this.primaryTableReference = primaryTableReference;
this.container = container;
this.lockMode = lockMode;
this.sourceAlias = sourceAlias;
}
@Override
@ -70,8 +68,8 @@ public class TableGroupImpl implements TableGroup {
}
@Override
public LockMode getLockMode() {
return lockMode;
public String getSourceAlias() {
return sourceAlias;
}
@Override

View File

@ -8,7 +8,6 @@ package org.hibernate.query.results.complete;
import java.util.function.BiFunction;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchTiming;
import org.hibernate.metamodel.mapping.BasicValuedModelPart;
import org.hibernate.query.NavigablePath;
@ -109,7 +108,6 @@ public class CompleteFetchBuilderBasicPart implements CompleteFetchBuilder, Mode
fetchPath,
FetchTiming.IMMEDIATE,
true,
LockMode.READ,
selectedAlias,
domainResultCreationState
);

View File

@ -81,7 +81,6 @@ public class CompleteResultBuilderEntityJpa implements CompleteResultBuilderEnti
np -> entityDescriptor.createRootTableGroup(
navigablePath,
null,
lockMode,
() -> predicate -> {},
impl.getSqlAstCreationState(),
impl.getSqlAstCreationState().getCreationContext()

View File

@ -73,7 +73,6 @@ public class CompleteResultBuilderEntityStandard implements CompleteResultBuilde
np -> entityDescriptor.createRootTableGroup(
navigablePath,
null,
lockMode,
() -> predicate -> {},
impl,
impl.getCreationContext()

View File

@ -109,7 +109,6 @@ public class DynamicFetchBuilderLegacy implements DynamicFetchBuilder, NativeQue
tableAlias,
SqlAstJoinType.INNER,
true,
LockMode.NONE,
s -> sqlAliasBase,
creationState.getSqlExpressionResolver(),
creationState.getCreationContext()

View File

@ -10,7 +10,6 @@ import java.util.ArrayList;
import java.util.List;
import java.util.function.BiFunction;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchTiming;
import org.hibernate.metamodel.mapping.BasicValuedMapping;
import org.hibernate.metamodel.mapping.SelectableConsumer;
@ -93,7 +92,6 @@ public class DynamicFetchBuilderStandard
fetchPath,
FetchTiming.IMMEDIATE,
true,
LockMode.NONE,
null,
creationStateImpl
);
@ -109,7 +107,6 @@ public class DynamicFetchBuilderStandard
fetchPath,
FetchTiming.DELAYED,
false,
LockMode.NONE,
null,
creationStateImpl
);

View File

@ -114,10 +114,13 @@ public class DynamicResultBuilderEntityCalculated implements DynamicResultBuilde
tableAlias,
tableReference,
entityMapping,
explicitLockMode
tableAlias
);
creationStateImpl.getFromClauseAccess().registerTableGroup( navigablePath, tableGroup );
if ( explicitLockMode != null ) {
domainResultCreationState.getSqlAstCreationState().registerLockMode( tableAlias, explicitLockMode );
}
return (EntityResult) entityMapping.createDomainResult(
navigablePath,

View File

@ -134,7 +134,6 @@ public class DynamicResultBuilderEntityStandard
navigablePath,
FetchTiming.IMMEDIATE,
true,
lockMode,
null,
domainResultCreationState
),
@ -157,7 +156,11 @@ public class DynamicResultBuilderEntityStandard
creationState.getSqlExpressionResolver(),
creationState.getCreationContext()
);
return new TableGroupImpl( navigablePath, tableAlias, tableReference, entityMapping, lockMode );
if ( lockMode != null ) {
domainResultCreationState.getSqlAstCreationState().registerLockMode( tableAlias, lockMode );
}
return new TableGroupImpl( navigablePath, tableAlias, tableReference, entityMapping, tableAlias );
}
);
final TableReference tableReference = tableGroup.getPrimaryTableReference();

View File

@ -11,7 +11,6 @@ import java.util.Map;
import java.util.function.BiFunction;
import java.util.function.Function;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchTiming;
import org.hibernate.query.NavigablePath;
import org.hibernate.query.results.Builders;
@ -89,7 +88,6 @@ public class ImplicitFetchBuilderEmbeddable implements ImplicitFetchBuilder {
null,
SqlAstJoinType.INNER,
true,
LockMode.READ,
creationStateImpl
);
return tableGroupJoin.getJoinedGroup();
@ -101,7 +99,6 @@ public class ImplicitFetchBuilderEmbeddable implements ImplicitFetchBuilder {
fetchPath,
FetchTiming.IMMEDIATE,
true,
LockMode.READ,
null,
creationState
);

View File

@ -12,7 +12,6 @@ import java.util.Map;
import java.util.function.BiFunction;
import java.util.function.Function;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchTiming;
import org.hibernate.metamodel.mapping.EmbeddableMappingType;
import org.hibernate.metamodel.mapping.ForeignKeyDescriptor;
@ -23,9 +22,6 @@ import org.hibernate.query.results.Builders;
import org.hibernate.query.results.DomainResultCreationStateImpl;
import org.hibernate.query.results.FetchBuilder;
import org.hibernate.query.results.dynamic.DynamicFetchBuilderLegacy;
import org.hibernate.sql.ast.SqlAstJoinType;
import org.hibernate.sql.ast.tree.from.TableGroup;
import org.hibernate.sql.ast.tree.from.TableGroupJoin;
import org.hibernate.sql.results.graph.DomainResultCreationState;
import org.hibernate.sql.results.graph.Fetch;
import org.hibernate.sql.results.graph.FetchParent;
@ -107,7 +103,6 @@ public class ImplicitFetchBuilderEntity implements ImplicitFetchBuilder {
fetchPath,
FetchTiming.DELAYED,
false,
LockMode.READ,
null,
creationState
);

View File

@ -8,7 +8,6 @@ package org.hibernate.query.results.implicit;
import java.util.function.BiFunction;
import org.hibernate.LockMode;
import org.hibernate.engine.FetchTiming;
import org.hibernate.metamodel.mapping.PluralAttributeMapping;
import org.hibernate.query.NavigablePath;
@ -50,7 +49,6 @@ public class ImplicitFetchBuilderPlural implements ImplicitFetchBuilder {
fetchPath,
FetchTiming.DELAYED,
false,
LockMode.READ,
null,
creationState
);

Some files were not shown because too many files have changed in this diff Show More