Fix some column type definitions in dialects regarding their maximum capacities. Allow the dialect to resolve the length based on type code, type name, precision, scale and display size. Fix some dialect related issues with tests. Fix untyped null parameter binding issues
This commit is contained in:
parent
7fd3706a18
commit
d8b984ed7f
|
@ -107,6 +107,7 @@ public class CUBRIDDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -114,7 +115,13 @@ public class CUBRIDDialect extends Dialect {
|
|||
if ( jdbcTypeCode == Types.BIT ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BOOLEAN );
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -89,6 +89,7 @@ public class CacheDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -96,7 +97,13 @@ public class CacheDialect extends Dialect {
|
|||
if ( jdbcTypeCode == Types.BIT ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BOOLEAN );
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -165,6 +165,7 @@ public class FirebirdDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -172,7 +173,13 @@ public class FirebirdDialect extends Dialect {
|
|||
if ( jdbcTypeCode == Types.BIT ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BOOLEAN );
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -174,6 +174,7 @@ public class IngresDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -181,7 +182,13 @@ public class IngresDialect extends Dialect {
|
|||
if ( jdbcTypeCode == Types.BIT ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BOOLEAN );
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -67,6 +67,7 @@ public class MaxDBDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -78,7 +79,13 @@ public class MaxDBDialect extends Dialect {
|
|||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BIGINT );
|
||||
}
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -114,6 +114,7 @@ public class RDMSOS2200Dialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -121,7 +122,13 @@ public class RDMSOS2200Dialect extends Dialect {
|
|||
if ( jdbcTypeCode == Types.BIT ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BOOLEAN );
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -126,7 +126,7 @@ public class TeradataDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
int jdbcTypeCode,
|
||||
String columnTypeName, int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
JdbcTypeDescriptorRegistry jdbcTypeDescriptorRegistry) {
|
||||
|
@ -139,7 +139,13 @@ public class TeradataDialect extends Dialect {
|
|||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BIGINT );
|
||||
}
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -102,6 +102,7 @@ public class TimesTenDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -109,7 +110,13 @@ public class TimesTenDialect extends Dialect {
|
|||
if ( jdbcTypeCode == Types.BIT ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BOOLEAN );
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -71,6 +71,7 @@ public abstract class AbstractTransactSQLDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -78,7 +79,13 @@ public abstract class AbstractTransactSQLDialect extends Dialect {
|
|||
if ( jdbcTypeCode == Types.BIT ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BOOLEAN );
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -7,6 +7,7 @@
|
|||
package org.hibernate.dialect;
|
||||
|
||||
import org.hibernate.LockOptions;
|
||||
import org.hibernate.boot.model.TypeContributions;
|
||||
import org.hibernate.query.NullPrecedence;
|
||||
import org.hibernate.cfg.Environment;
|
||||
import org.hibernate.dialect.function.CommonFunctionFactory;
|
||||
|
@ -32,6 +33,7 @@ import org.hibernate.query.TemporalUnit;
|
|||
import org.hibernate.query.spi.QueryEngine;
|
||||
import org.hibernate.query.sqm.mutation.internal.cte.CteStrategy;
|
||||
import org.hibernate.query.sqm.mutation.spi.SqmMultiTableMutationStrategy;
|
||||
import org.hibernate.service.ServiceRegistry;
|
||||
import org.hibernate.sql.ast.SqlAstTranslator;
|
||||
import org.hibernate.sql.ast.SqlAstTranslatorFactory;
|
||||
import org.hibernate.sql.ast.spi.StandardSqlAstTranslatorFactory;
|
||||
|
@ -40,6 +42,7 @@ import org.hibernate.sql.exec.spi.JdbcOperation;
|
|||
import org.hibernate.tool.schema.extract.internal.SequenceInformationExtractorDB2DatabaseImpl;
|
||||
import org.hibernate.tool.schema.extract.internal.SequenceInformationExtractorNoOpImpl;
|
||||
import org.hibernate.tool.schema.extract.spi.SequenceInformationExtractor;
|
||||
import org.hibernate.type.JavaObjectType;
|
||||
import org.hibernate.type.StandardBasicTypes;
|
||||
import org.hibernate.type.descriptor.jdbc.*;
|
||||
|
||||
|
@ -85,8 +88,8 @@ public class DB2Dialect extends Dialect {
|
|||
|
||||
registerColumnType( Types.TINYINT, "smallint" ); //no tinyint
|
||||
|
||||
//HHH-12827: map them both to the same type to
|
||||
// avoid problems with schema update
|
||||
//HHH-12827: map them both to the same type to avoid problems with schema update
|
||||
//Note that 31 is the maximum precision DB2 supports
|
||||
// registerColumnType( Types.DECIMAL, "decimal($p,$s)" );
|
||||
registerColumnType( Types.NUMERIC, "decimal($p,$s)" );
|
||||
|
||||
|
@ -106,7 +109,8 @@ public class DB2Dialect extends Dialect {
|
|||
registerColumnType( Types.TIMESTAMP_WITH_TIMEZONE, "timestamp($p)" );
|
||||
registerColumnType( Types.TIME_WITH_TIMEZONE, "time" );
|
||||
|
||||
registerColumnType( Types.LONGVARCHAR, "long varchar" );
|
||||
// The long varchar data type was deprecated in DB2 and shouldn't be used anymore
|
||||
registerColumnType( Types.LONGVARCHAR, "clob($l)" );
|
||||
|
||||
//not keywords, at least not in DB2 11,
|
||||
//but perhaps they were in older versions?
|
||||
|
@ -570,6 +574,24 @@ public class DB2Dialect extends Dialect {
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void contributeTypes(TypeContributions typeContributions, ServiceRegistry serviceRegistry) {
|
||||
super.contributeTypes( typeContributions, serviceRegistry );
|
||||
|
||||
// DB2 requires a custom binder for binding untyped nulls that resolves the type through the statement
|
||||
typeContributions.contributeJdbcTypeDescriptor( ObjectNullResolvingJdbcTypeDescriptor.INSTANCE );
|
||||
|
||||
// Until we remove StandardBasicTypes, we have to keep this
|
||||
typeContributions.contributeType(
|
||||
new JavaObjectType(
|
||||
ObjectNullResolvingJdbcTypeDescriptor.INSTANCE,
|
||||
typeContributions.getTypeConfiguration()
|
||||
.getJavaTypeDescriptorRegistry()
|
||||
.getDescriptor( Object.class )
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String formatBinaryLiteral(byte[] bytes) {
|
||||
return "BX'" + StandardBasicTypes.BINARY.toString( bytes ) + "'";
|
||||
|
|
|
@ -23,9 +23,7 @@ import org.hibernate.sql.ast.tree.expression.CaseSearchedExpression;
|
|||
import org.hibernate.sql.ast.tree.expression.CaseSimpleExpression;
|
||||
import org.hibernate.sql.ast.tree.expression.ColumnReference;
|
||||
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.insert.InsertStatement;
|
||||
|
|
|
@ -9,6 +9,7 @@ package org.hibernate.dialect;
|
|||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.NotYetImplementedFor6Exception;
|
||||
import org.hibernate.boot.TempTableDdlTransactionHandling;
|
||||
import org.hibernate.boot.model.TypeContributions;
|
||||
import org.hibernate.cfg.Environment;
|
||||
import org.hibernate.dialect.function.CommonFunctionFactory;
|
||||
import org.hibernate.dialect.function.DerbyConcatFunction;
|
||||
|
@ -41,6 +42,7 @@ import org.hibernate.query.sqm.mutation.internal.idtable.IdTable;
|
|||
import org.hibernate.query.sqm.mutation.internal.idtable.LocalTemporaryTableStrategy;
|
||||
import org.hibernate.query.sqm.mutation.internal.idtable.TempIdTableExporter;
|
||||
import org.hibernate.query.sqm.mutation.spi.SqmMultiTableMutationStrategy;
|
||||
import org.hibernate.service.ServiceRegistry;
|
||||
import org.hibernate.sql.CaseFragment;
|
||||
import org.hibernate.sql.DerbyCaseFragment;
|
||||
import org.hibernate.sql.ast.SqlAstNodeRenderingMode;
|
||||
|
@ -52,9 +54,11 @@ import org.hibernate.sql.exec.spi.JdbcOperation;
|
|||
import org.hibernate.tool.schema.extract.internal.SequenceInformationExtractorDerbyDatabaseImpl;
|
||||
import org.hibernate.tool.schema.extract.internal.SequenceInformationExtractorNoOpImpl;
|
||||
import org.hibernate.tool.schema.extract.spi.SequenceInformationExtractor;
|
||||
import org.hibernate.type.JavaObjectType;
|
||||
import org.hibernate.type.StandardBasicTypes;
|
||||
import org.hibernate.type.descriptor.jdbc.DecimalTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.ObjectNullResolvingJdbcTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.SmallIntTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.TimestampTypeDescriptor;
|
||||
|
||||
|
@ -108,14 +112,16 @@ public class DerbyDialect extends Dialect {
|
|||
registerColumnType( Types.TINYINT, "smallint" ); //no tinyint
|
||||
registerColumnType( Types.CHAR, 254, "char($l)" );
|
||||
|
||||
//HHH-12827: map them both to the same type to
|
||||
// avoid problems with schema update
|
||||
//HHH-12827: map them both to the same type to avoid problems with schema update
|
||||
//Note that 31 is the maximum precision Derby supports
|
||||
// registerColumnType( Types.DECIMAL, "decimal($p,$s)" );
|
||||
registerColumnType( Types.NUMERIC, "decimal($p,$s)" );
|
||||
|
||||
registerColumnType( Types.BINARY, "varchar($l) for bit data" );
|
||||
registerColumnType( Types.BINARY, 254, "char($l) for bit data" );
|
||||
registerColumnType( Types.VARBINARY, "varchar($l) for bit data" );
|
||||
registerColumnType( Types.BINARY, 32672, "varchar($l) for bit data" );
|
||||
registerColumnType( Types.BINARY, "long varchar for bit data" );
|
||||
registerColumnType( Types.VARBINARY, 32672, "varchar($l) for bit data" );
|
||||
registerColumnType( Types.VARBINARY, "long varchar for bit data" );
|
||||
|
||||
registerColumnType( Types.BLOB, "blob($l)" );
|
||||
registerColumnType( Types.CLOB, "clob($l)" );
|
||||
|
@ -539,6 +545,24 @@ public class DerbyDialect extends Dialect {
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void contributeTypes(TypeContributions typeContributions, ServiceRegistry serviceRegistry) {
|
||||
super.contributeTypes( typeContributions, serviceRegistry );
|
||||
|
||||
// Derby requires a custom binder for binding untyped nulls that resolves the type through the statement
|
||||
typeContributions.contributeJdbcTypeDescriptor( ObjectNullResolvingJdbcTypeDescriptor.INSTANCE );
|
||||
|
||||
// Until we remove StandardBasicTypes, we have to keep this
|
||||
typeContributions.contributeType(
|
||||
new JavaObjectType(
|
||||
ObjectNullResolvingJdbcTypeDescriptor.INSTANCE,
|
||||
typeContributions.getTypeConfiguration()
|
||||
.getJavaTypeDescriptorRegistry()
|
||||
.getDescriptor( Object.class )
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getNotExpression( String expression ) {
|
||||
return "not (" + expression + ")";
|
||||
|
|
|
@ -247,6 +247,7 @@ public abstract class Dialect implements ConversionContext {
|
|||
}
|
||||
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -254,6 +255,22 @@ public abstract class Dialect implements ConversionContext {
|
|||
return jdbcTypeDescriptorRegistry.getDescriptor( jdbcTypeCode );
|
||||
}
|
||||
|
||||
public int resolveSqlTypeLength(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
int displaySize) {
|
||||
// It seems MariaDB/MySQL return the precision in bytes depending on the charset,
|
||||
// so to detect whether we have a single character here, we check the display size
|
||||
if ( jdbcTypeCode == Types.CHAR && precision <= 4 ) {
|
||||
return displaySize;
|
||||
}
|
||||
else {
|
||||
return precision;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Useful conversion for databases which represent the
|
||||
* precision of a float(p) using p expressed in decimal
|
||||
|
|
|
@ -17,6 +17,7 @@ import org.hibernate.engine.jdbc.env.spi.IdentifierCaseStrategy;
|
|||
import org.hibernate.engine.jdbc.env.spi.IdentifierHelper;
|
||||
import org.hibernate.engine.jdbc.env.spi.IdentifierHelperBuilder;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.query.CastType;
|
||||
import org.hibernate.query.spi.QueryEngine;
|
||||
import org.hibernate.sql.ast.SqlAstTranslator;
|
||||
import org.hibernate.sql.ast.SqlAstTranslatorFactory;
|
||||
|
@ -92,6 +93,26 @@ public class MariaDBDialect extends MySQLDialect {
|
|||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public String castPattern(CastType from, CastType to) {
|
||||
if ( to == CastType.INTEGER_BOOLEAN ) {
|
||||
switch ( from ) {
|
||||
case STRING:
|
||||
case INTEGER:
|
||||
case LONG:
|
||||
case YN_BOOLEAN:
|
||||
case TF_BOOLEAN:
|
||||
case BOOLEAN:
|
||||
break;
|
||||
default:
|
||||
// MariaDB doesn't support casting to bit
|
||||
return "abs(sign(?1))";
|
||||
}
|
||||
}
|
||||
return super.castPattern( from, to );
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean supportsRowValueConstructorSyntaxInInList() {
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -57,7 +57,6 @@ import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
|
|||
import org.hibernate.type.descriptor.jdbc.spi.JdbcTypeDescriptorRegistry;
|
||||
|
||||
import java.sql.CallableStatement;
|
||||
import java.sql.Connection;
|
||||
import java.sql.DatabaseMetaData;
|
||||
import java.sql.ResultSet;
|
||||
import java.sql.SQLException;
|
||||
|
@ -295,6 +294,7 @@ public class MySQLDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -302,7 +302,13 @@ public class MySQLDialect extends Dialect {
|
|||
if ( jdbcTypeCode == Types.BIT ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.BOOLEAN );
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -56,9 +56,13 @@ import org.hibernate.sql.ast.tree.Statement;
|
|||
import org.hibernate.sql.exec.spi.JdbcOperation;
|
||||
import org.hibernate.tool.schema.extract.internal.SequenceInformationExtractorOracleDatabaseImpl;
|
||||
import org.hibernate.tool.schema.extract.spi.SequenceInformationExtractor;
|
||||
import org.hibernate.type.JavaObjectType;
|
||||
import org.hibernate.type.NullType;
|
||||
import org.hibernate.type.StandardBasicTypes;
|
||||
import org.hibernate.type.descriptor.jdbc.BlobTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.NullJdbcTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.ObjectNullAsNullTypeJdbcTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.spi.JdbcTypeDescriptorRegistry;
|
||||
|
||||
import java.sql.CallableStatement;
|
||||
|
@ -536,6 +540,10 @@ public class OracleDialect extends Dialect {
|
|||
registerColumnType( Types.TINYINT, "number(3,0)" );
|
||||
registerColumnType( Types.INTEGER, "number(10,0)" );
|
||||
|
||||
// Oracle has DOUBLE semantics for the REAL type, so we map it to float(24)
|
||||
registerColumnType( Types.REAL, "float(24)" );
|
||||
|
||||
// // Note that 38 is the maximum precision Oracle supports
|
||||
registerColumnType( Types.NUMERIC, "number($p,$s)" );
|
||||
registerColumnType( Types.DECIMAL, "number($p,$s)" );
|
||||
}
|
||||
|
@ -593,6 +601,7 @@ public class OracleDialect extends Dialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -600,6 +609,13 @@ public class OracleDialect extends Dialect {
|
|||
// This is the reverse of what registerNumericTypeMappings registers
|
||||
switch ( jdbcTypeCode ) {
|
||||
case Types.NUMERIC:
|
||||
// For some reason, the Oracle JDBC driver reports floats as numerics with scale -127
|
||||
if ( scale == -127 ) {
|
||||
if ( precision <= getFloatPrecision() ) {
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.FLOAT );
|
||||
}
|
||||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.DOUBLE );
|
||||
}
|
||||
case Types.DECIMAL:
|
||||
if ( scale == 0 ) {
|
||||
switch ( precision ) {
|
||||
|
@ -616,7 +632,13 @@ public class OracleDialect extends Dialect {
|
|||
}
|
||||
}
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -648,6 +670,28 @@ public class OracleDialect extends Dialect {
|
|||
|
||||
typeContributions.contributeJdbcTypeDescriptor( descriptor );
|
||||
}
|
||||
|
||||
// Oracle requires a custom binder for binding untyped nulls with the NULL type
|
||||
typeContributions.contributeJdbcTypeDescriptor( NullJdbcTypeDescriptor.INSTANCE );
|
||||
typeContributions.contributeJdbcTypeDescriptor( ObjectNullAsNullTypeJdbcTypeDescriptor.INSTANCE );
|
||||
|
||||
// Until we remove StandardBasicTypes, we have to keep this
|
||||
typeContributions.contributeType(
|
||||
new NullType(
|
||||
NullJdbcTypeDescriptor.INSTANCE,
|
||||
typeContributions.getTypeConfiguration()
|
||||
.getJavaTypeDescriptorRegistry()
|
||||
.getDescriptor( Object.class )
|
||||
)
|
||||
);
|
||||
typeContributions.contributeType(
|
||||
new JavaObjectType(
|
||||
ObjectNullAsNullTypeJdbcTypeDescriptor.INSTANCE,
|
||||
typeContributions.getTypeConfiguration()
|
||||
.getJavaTypeDescriptorRegistry()
|
||||
.getDescriptor( Object.class )
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -57,11 +57,13 @@ import org.hibernate.sql.ast.SqlAstTranslatorFactory;
|
|||
import org.hibernate.sql.ast.spi.StandardSqlAstTranslatorFactory;
|
||||
import org.hibernate.sql.ast.tree.Statement;
|
||||
import org.hibernate.sql.exec.spi.JdbcOperation;
|
||||
import org.hibernate.type.JavaObjectType;
|
||||
import org.hibernate.type.PostgresUUIDType;
|
||||
import org.hibernate.type.StandardBasicTypes;
|
||||
import org.hibernate.type.descriptor.jdbc.BlobTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.ClobTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.ObjectNullAsBinaryTypeJdbcTypeDescriptor;
|
||||
|
||||
import static org.hibernate.exception.spi.TemplatedViolatedConstraintNameExtractor.extractUsingTemplate;
|
||||
import static org.hibernate.query.TemporalUnit.*;
|
||||
|
@ -903,5 +905,18 @@ public class PostgreSQLDialect extends Dialect {
|
|||
// HHH-9562
|
||||
typeContributions.contributeType( PostgresUUIDType.INSTANCE );
|
||||
}
|
||||
|
||||
// PostgreSQL requires a custom binder for binding untyped nulls as VARBINARY
|
||||
typeContributions.contributeJdbcTypeDescriptor( ObjectNullAsBinaryTypeJdbcTypeDescriptor.INSTANCE );
|
||||
|
||||
// Until we remove StandardBasicTypes, we have to keep this
|
||||
typeContributions.contributeType(
|
||||
new JavaObjectType(
|
||||
ObjectNullAsBinaryTypeJdbcTypeDescriptor.INSTANCE,
|
||||
typeContributions.getTypeConfiguration()
|
||||
.getJavaTypeDescriptorRegistry()
|
||||
.getDescriptor( Object.class )
|
||||
)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -148,6 +148,11 @@ public class SybaseASEDialect extends SybaseDialect {
|
|||
return ansiNull;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getFloatPrecision() {
|
||||
return 15;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getDoublePrecision() {
|
||||
return 48;
|
||||
|
@ -195,6 +200,22 @@ public class SybaseASEDialect extends SybaseDialect {
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public int resolveSqlTypeLength(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
int displaySize) {
|
||||
// Sybase ASE reports the "actual" precision in the display size
|
||||
switch ( jdbcTypeCode ) {
|
||||
case Types.REAL:
|
||||
case Types.DOUBLE:
|
||||
return displaySize;
|
||||
}
|
||||
return super.resolveSqlTypeLength( columnTypeName, jdbcTypeCode, precision, scale, displaySize );
|
||||
}
|
||||
|
||||
@Override
|
||||
public String currentDate() {
|
||||
return "current_date()";
|
||||
|
|
|
@ -23,9 +23,7 @@ import org.hibernate.sql.ast.tree.expression.CaseSearchedExpression;
|
|||
import org.hibernate.sql.ast.tree.expression.CaseSimpleExpression;
|
||||
import org.hibernate.sql.ast.tree.expression.ColumnReference;
|
||||
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.from.TableGroup;
|
||||
|
@ -222,12 +220,10 @@ public class SybaseASESqlAstTranslator<T extends JdbcOperation> extends Abstract
|
|||
// The ansinull setting only matters if using a parameter or literal and the eq operator according to the docs
|
||||
// http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.infocenter.dc32300.1570/html/sqlug/sqlug89.htm
|
||||
boolean rhsNotNullPredicate =
|
||||
lhs instanceof NullnessLiteral
|
||||
|| lhs instanceof Literal
|
||||
lhs instanceof Literal
|
||||
|| isParameter( lhs );
|
||||
boolean lhsNotNullPredicate =
|
||||
rhs instanceof NullnessLiteral
|
||||
|| rhs instanceof Literal
|
||||
rhs instanceof Literal
|
||||
|| isParameter( rhs );
|
||||
if ( rhsNotNullPredicate || lhsNotNullPredicate ) {
|
||||
lhs.accept( this );
|
||||
|
|
|
@ -37,10 +37,12 @@ import org.hibernate.sql.ast.spi.StandardSqlAstTranslatorFactory;
|
|||
import org.hibernate.sql.ast.tree.Statement;
|
||||
import org.hibernate.sql.ast.tree.select.SelectStatement;
|
||||
import org.hibernate.sql.exec.spi.JdbcOperation;
|
||||
import org.hibernate.type.JavaObjectType;
|
||||
import org.hibernate.type.descriptor.jdbc.BlobTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.ClobTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.JdbcTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.NClobTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.ObjectNullAsNullTypeJdbcTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.SmallIntTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.TinyIntTypeDescriptor;
|
||||
import org.hibernate.type.descriptor.jdbc.spi.JdbcTypeDescriptorRegistry;
|
||||
|
@ -85,6 +87,7 @@ public class SybaseDialect extends AbstractTransactSQLDialect {
|
|||
|
||||
@Override
|
||||
public JdbcTypeDescriptor resolveSqlTypeDescriptor(
|
||||
String columnTypeName,
|
||||
int jdbcTypeCode,
|
||||
int precision,
|
||||
int scale,
|
||||
|
@ -100,9 +103,16 @@ public class SybaseDialect extends AbstractTransactSQLDialect {
|
|||
return jdbcTypeDescriptorRegistry.getDescriptor( Types.SMALLINT );
|
||||
}
|
||||
}
|
||||
return super.resolveSqlTypeDescriptor( jdbcTypeCode, precision, scale, jdbcTypeDescriptorRegistry );
|
||||
return super.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
jdbcTypeCode,
|
||||
precision,
|
||||
scale,
|
||||
jdbcTypeDescriptorRegistry
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
public JdbcTypeDescriptor remapSqlTypeDescriptor(JdbcTypeDescriptor jdbcTypeDescriptor) {
|
||||
if ( jtdsDriver && TinyIntTypeDescriptor.INSTANCE == jdbcTypeDescriptor ) {
|
||||
return SmallIntTypeDescriptor.INSTANCE;
|
||||
|
@ -174,6 +184,19 @@ public class SybaseDialect extends AbstractTransactSQLDialect {
|
|||
);
|
||||
typeContributions.contributeJdbcTypeDescriptor( ClobTypeDescriptor.CLOB_BINDING );
|
||||
}
|
||||
|
||||
// Sybase requires a custom binder for binding untyped nulls with the NULL type
|
||||
typeContributions.contributeJdbcTypeDescriptor( ObjectNullAsNullTypeJdbcTypeDescriptor.INSTANCE );
|
||||
|
||||
// Until we remove StandardBasicTypes, we have to keep this
|
||||
typeContributions.contributeType(
|
||||
new JavaObjectType(
|
||||
ObjectNullAsNullTypeJdbcTypeDescriptor.INSTANCE,
|
||||
typeContributions.getTypeConfiguration()
|
||||
.getJavaTypeDescriptorRegistry()
|
||||
.getDescriptor( Object.class )
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -173,7 +173,13 @@ public class ParameterMetadataImpl implements ParameterMetadataImplementor {
|
|||
if ( sqmParameters == null || sqmParameters.isEmpty() ) {
|
||||
return null;
|
||||
}
|
||||
return sqmParameters.get( 0 ).getNodeType();
|
||||
for ( SqmParameter sqmParameter : sqmParameters ) {
|
||||
final AllowableParameterType nodeType = sqmParameter.getNodeType();
|
||||
if ( nodeType != null ) {
|
||||
return nodeType;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -18,7 +18,6 @@ import org.hibernate.query.QueryParameter;
|
|||
import org.hibernate.query.spi.QueryParameterBinding;
|
||||
import org.hibernate.query.spi.QueryParameterBindingTypeResolver;
|
||||
import org.hibernate.query.spi.QueryParameterBindingValidator;
|
||||
import org.hibernate.type.NullType;
|
||||
import org.hibernate.type.descriptor.java.CoercionException;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
@ -119,8 +118,7 @@ public class QueryParameterBindingImpl<T> implements QueryParameterBinding<T>, J
|
|||
}
|
||||
|
||||
if ( resolveJdbcTypeIfNecessary && bindType == null && value == null ) {
|
||||
//noinspection unchecked
|
||||
bindType = (AllowableParameterType<T>) NullType.INSTANCE;
|
||||
bindType = getTypeConfiguration().getBasicTypeRegistry().getRegisteredType( "null" );
|
||||
}
|
||||
bindValue( value );
|
||||
}
|
||||
|
@ -297,19 +295,24 @@ public class QueryParameterBindingImpl<T> implements QueryParameterBinding<T>, J
|
|||
}
|
||||
|
||||
@Override
|
||||
public void setType(MappingModelExpressable type) {
|
||||
public boolean setType(MappingModelExpressable type) {
|
||||
this.type = type;
|
||||
if ( bindType == null ) {
|
||||
if ( bindType == null || bindType.getJavaType() == Object.class ) {
|
||||
if ( type instanceof AllowableParameterType<?> ) {
|
||||
final boolean changed = bindType != null && type != bindType;
|
||||
this.bindType = (AllowableParameterType<T>) type;
|
||||
return changed;
|
||||
}
|
||||
else if ( type instanceof BasicValuedMapping ) {
|
||||
final JdbcMapping jdbcMapping = ( (BasicValuedMapping) type ).getJdbcMapping();
|
||||
if ( jdbcMapping instanceof AllowableParameterType<?> ) {
|
||||
final boolean changed = bindType != null && jdbcMapping != bindType;
|
||||
this.bindType = (AllowableParameterType<T>) jdbcMapping;
|
||||
return changed;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private void validate(T value) {
|
||||
|
|
|
@ -31,7 +31,6 @@ import jakarta.persistence.LockModeType;
|
|||
import jakarta.persistence.NoResultException;
|
||||
import jakarta.persistence.Parameter;
|
||||
import jakarta.persistence.TemporalType;
|
||||
import jakarta.persistence.TransactionRequiredException;
|
||||
|
||||
import org.hibernate.CacheMode;
|
||||
import org.hibernate.FlushMode;
|
||||
|
@ -46,7 +45,6 @@ import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
|||
import org.hibernate.graph.spi.RootGraphImplementor;
|
||||
import org.hibernate.internal.EntityManagerMessageLogger;
|
||||
import org.hibernate.internal.HEMLogging;
|
||||
import org.hibernate.internal.log.DeprecationLogger;
|
||||
import org.hibernate.jpa.QueryHints;
|
||||
import org.hibernate.jpa.internal.util.ConfigurationHelper;
|
||||
import org.hibernate.jpa.internal.util.FlushModeTypeHelper;
|
||||
|
@ -415,8 +413,8 @@ public abstract class AbstractQuery<R> implements QueryImplementor<R> {
|
|||
|
||||
if ( getCacheMode() != null ) {
|
||||
putIfNotNull( hints, HINT_CACHE_MODE, getCacheMode() );
|
||||
putIfNotNull( hints, JAKARTA_SHARED_CACHE_RETRIEVE_MODE, CacheModeHelper.interpretCacheRetrieveMode( getCacheMode() ) );
|
||||
putIfNotNull( hints, JAKARTA_SHARED_CACHE_STORE_MODE, CacheModeHelper.interpretCacheStoreMode( getCacheMode() ) );
|
||||
putIfNotNull( hints, JAKARTA_SHARED_CACHE_RETRIEVE_MODE, getQueryOptions().getCacheRetrieveMode() );
|
||||
putIfNotNull( hints, JAKARTA_SHARED_CACHE_STORE_MODE, getQueryOptions().getCacheStoreMode() );
|
||||
putIfNotNull( hints, JPA_SHARED_CACHE_RETRIEVE_MODE, getQueryOptions().getCacheRetrieveMode() );
|
||||
putIfNotNull( hints, JPA_SHARED_CACHE_STORE_MODE, getQueryOptions().getCacheStoreMode() );
|
||||
}
|
||||
|
|
|
@ -121,6 +121,7 @@ public interface QueryParameterBinding<T> {
|
|||
* Sets the mapping model expressable for this parameter.
|
||||
*
|
||||
* @param type The mapping model expressable
|
||||
* @return Whether the bind type was changed
|
||||
*/
|
||||
void setType(MappingModelExpressable<T> type);
|
||||
boolean setType(MappingModelExpressable<T> type);
|
||||
}
|
||||
|
|
|
@ -60,11 +60,13 @@ import org.hibernate.metamodel.mapping.EntityMappingType;
|
|||
import org.hibernate.metamodel.mapping.EntityValuedModelPart;
|
||||
import org.hibernate.metamodel.mapping.EntityVersionMapping;
|
||||
import org.hibernate.metamodel.mapping.ForeignKeyDescriptor;
|
||||
import org.hibernate.metamodel.mapping.JdbcMapping;
|
||||
import org.hibernate.metamodel.mapping.JdbcMappingContainer;
|
||||
import org.hibernate.metamodel.mapping.MappingModelExpressable;
|
||||
import org.hibernate.metamodel.mapping.ModelPart;
|
||||
import org.hibernate.metamodel.mapping.ModelPartContainer;
|
||||
import org.hibernate.metamodel.mapping.PluralAttributeMapping;
|
||||
import org.hibernate.metamodel.mapping.SqlExpressable;
|
||||
import org.hibernate.metamodel.mapping.ValueMapping;
|
||||
import org.hibernate.metamodel.mapping.internal.EmbeddedCollectionPart;
|
||||
import org.hibernate.metamodel.mapping.internal.EntityCollectionPart;
|
||||
|
@ -2935,7 +2937,13 @@ public abstract class BaseSqmToSqlAstConverter<T extends Statement> extends Base
|
|||
|
||||
final QueryParameterImplementor<?> queryParameter = domainParameterXref.getQueryParameter( sqmParameter );
|
||||
final QueryParameterBinding<?> binding = domainParameterBindings.getBinding( queryParameter );
|
||||
binding.setType( valueMapping );
|
||||
if ( binding.setType( valueMapping ) ) {
|
||||
replaceJdbcParametersType(
|
||||
sqmParameter,
|
||||
domainParameterXref.getSqmParameters( queryParameter ),
|
||||
valueMapping
|
||||
);
|
||||
}
|
||||
return new SqmParameterInterpretation(
|
||||
sqmParameter,
|
||||
queryParameter,
|
||||
|
@ -2945,6 +2953,32 @@ public abstract class BaseSqmToSqlAstConverter<T extends Statement> extends Base
|
|||
);
|
||||
}
|
||||
|
||||
private void replaceJdbcParametersType(
|
||||
SqmParameter sourceSqmParameter,
|
||||
List<SqmParameter> sqmParameters,
|
||||
MappingModelExpressable<?> valueMapping) {
|
||||
final JdbcMapping jdbcMapping = valueMapping.getJdbcMappings().get( 0 );
|
||||
for ( SqmParameter<?> sqmParameter : sqmParameters ) {
|
||||
if ( sqmParameter == sourceSqmParameter ) {
|
||||
continue;
|
||||
}
|
||||
sqmParameterMappingModelTypes.put( sqmParameter, valueMapping );
|
||||
final List<List<JdbcParameter>> jdbcParamsForSqmParameter = jdbcParamsBySqmParam.get( sqmParameter );
|
||||
if ( jdbcParamsForSqmParameter != null ) {
|
||||
for ( List<JdbcParameter> parameters : jdbcParamsForSqmParameter ) {
|
||||
assert parameters.size() == 1;
|
||||
final JdbcParameter jdbcParameter = parameters.get( 0 );
|
||||
if ( ( (SqlExpressable) jdbcParameter ).getJdbcMapping() != valueMapping ) {
|
||||
final JdbcParameter newJdbcParameter = new JdbcParameterImpl( jdbcMapping );
|
||||
parameters.set( 0, newJdbcParameter );
|
||||
jdbcParameters.getJdbcParameters().remove( jdbcParameter );
|
||||
jdbcParameters.getJdbcParameters().add( newJdbcParameter );
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected Expression consumeSqmParameter(SqmParameter sqmParameter) {
|
||||
if ( sqmParameter.allowMultiValuedBinding() ) {
|
||||
final QueryParameterImplementor<?> domainParam = domainParameterXref.getQueryParameter( sqmParameter );
|
||||
|
@ -2996,7 +3030,13 @@ public abstract class BaseSqmToSqlAstConverter<T extends Statement> extends Base
|
|||
|
||||
final QueryParameterImplementor<?> queryParameter = domainParameterXref.getQueryParameter( sqmParameter );
|
||||
final QueryParameterBinding<?> binding = domainParameterBindings.getBinding( queryParameter );
|
||||
binding.setType( valueMapping );
|
||||
if ( binding.setType( valueMapping ) ) {
|
||||
replaceJdbcParametersType(
|
||||
sqmParameter,
|
||||
domainParameterXref.getSqmParameters( queryParameter ),
|
||||
valueMapping
|
||||
);
|
||||
}
|
||||
return new SqmParameterInterpretation(
|
||||
sqmParameter,
|
||||
queryParameter,
|
||||
|
|
|
@ -9,10 +9,10 @@ package org.hibernate.sql.results.jdbc.internal;
|
|||
import java.sql.ResultSet;
|
||||
import java.sql.ResultSetMetaData;
|
||||
import java.sql.SQLException;
|
||||
import java.sql.Types;
|
||||
|
||||
import javax.persistence.EnumType;
|
||||
import jakarta.persistence.EnumType;
|
||||
|
||||
import org.hibernate.dialect.Dialect;
|
||||
import org.hibernate.engine.jdbc.spi.JdbcServices;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.sql.results.jdbc.spi.JdbcValuesMetadata;
|
||||
|
@ -77,18 +77,22 @@ public interface ResultSetAccess extends JdbcValuesMetadata {
|
|||
final JdbcServices jdbcServices = getFactory().getJdbcServices();
|
||||
try {
|
||||
final ResultSetMetaData metaData = getResultSet().getMetaData();
|
||||
final String columnTypeName = metaData.getColumnTypeName( position );
|
||||
final int columnType = metaData.getColumnType( position );
|
||||
final int scale = metaData.getScale( position );
|
||||
final int precision = metaData.getPrecision( position );
|
||||
final int length;
|
||||
if ( columnType == Types.CHAR && precision == 0 ) {
|
||||
length = metaData.getColumnDisplaySize( position );
|
||||
}
|
||||
else {
|
||||
length = precision;
|
||||
}
|
||||
final JdbcTypeDescriptor resolvedJdbcTypeDescriptor = jdbcServices.getDialect()
|
||||
final int displaySize = metaData.getColumnDisplaySize( position );
|
||||
final Dialect dialect = jdbcServices.getDialect();
|
||||
final int length = dialect.resolveSqlTypeLength(
|
||||
columnTypeName,
|
||||
columnType,
|
||||
precision,
|
||||
scale,
|
||||
displaySize
|
||||
);
|
||||
final JdbcTypeDescriptor resolvedJdbcTypeDescriptor = dialect
|
||||
.resolveSqlTypeDescriptor(
|
||||
columnTypeName,
|
||||
columnType,
|
||||
length,
|
||||
scale,
|
||||
|
|
|
@ -24,4 +24,13 @@ public class NullType extends JavaObjectType {
|
|||
public NullType() {
|
||||
super( ObjectNullResolvingJdbcTypeDescriptor.INSTANCE, JavaObjectTypeDescriptor.INSTANCE );
|
||||
}
|
||||
|
||||
public NullType(JdbcTypeDescriptor jdbcTypeDescriptor, JavaTypeDescriptor<Object> javaTypeDescriptor) {
|
||||
super( jdbcTypeDescriptor, javaTypeDescriptor );
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return "null";
|
||||
}
|
||||
}
|
||||
|
|
|
@ -949,6 +949,13 @@ public final class StandardBasicTypes {
|
|||
"object", Object.class.getName()
|
||||
);
|
||||
|
||||
handle(
|
||||
NullType.INSTANCE,
|
||||
null,
|
||||
basicTypeRegistry,
|
||||
"null"
|
||||
);
|
||||
|
||||
// todo (6.0) - ? how to handle DbTimestampType?
|
||||
// DbTimestampType was really just a variant of TimestampType with overridden
|
||||
// version (opt lock) support
|
||||
|
|
|
@ -12,6 +12,7 @@ import java.sql.ResultSet;
|
|||
import java.sql.SQLException;
|
||||
import java.sql.Types;
|
||||
|
||||
import org.hibernate.engine.jdbc.spi.JdbcServices;
|
||||
import org.hibernate.type.descriptor.ValueBinder;
|
||||
import org.hibernate.type.descriptor.ValueExtractor;
|
||||
import org.hibernate.type.descriptor.WrapperOptions;
|
||||
|
@ -56,6 +57,9 @@ public class FloatTypeDescriptor implements JdbcTypeDescriptor {
|
|||
Integer length,
|
||||
Integer scale,
|
||||
TypeConfiguration typeConfiguration) {
|
||||
if ( length != null && length <= typeConfiguration.getServiceRegistry().getService( JdbcServices.class ).getDialect().getFloatPrecision() ) {
|
||||
return (BasicJavaDescriptor<T>) typeConfiguration.getJavaTypeDescriptorRegistry().getDescriptor( Float.class );
|
||||
}
|
||||
return (BasicJavaDescriptor<T>) typeConfiguration.getJavaTypeDescriptorRegistry().getDescriptor( Double.class );
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,70 @@
|
|||
/*
|
||||
* 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.type.descriptor.jdbc;
|
||||
|
||||
import java.sql.CallableStatement;
|
||||
import java.sql.PreparedStatement;
|
||||
import java.sql.SQLException;
|
||||
import java.sql.Types;
|
||||
|
||||
import org.hibernate.type.descriptor.ValueBinder;
|
||||
import org.hibernate.type.descriptor.ValueExtractor;
|
||||
import org.hibernate.type.descriptor.WrapperOptions;
|
||||
import org.hibernate.type.descriptor.java.JavaTypeDescriptor;
|
||||
|
||||
/**
|
||||
* Descriptor for binding nulls with Types.NULL
|
||||
*
|
||||
* @author Christian Beikov
|
||||
*/
|
||||
public class NullJdbcTypeDescriptor implements JdbcTypeDescriptor {
|
||||
/**
|
||||
* Singleton access
|
||||
*/
|
||||
public static final NullJdbcTypeDescriptor INSTANCE = new NullJdbcTypeDescriptor();
|
||||
|
||||
@Override
|
||||
public int getJdbcTypeCode() {
|
||||
return Types.NULL;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean canBeRemapped() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <X> ValueExtractor<X> getExtractor(JavaTypeDescriptor<X> javaTypeDescriptor) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public <X> ValueBinder<X> getBinder(JavaTypeDescriptor<X> javaTypeDescriptor) {
|
||||
return new BasicBinder<X>( javaTypeDescriptor, this ) {
|
||||
|
||||
@Override
|
||||
protected void doBindNull(PreparedStatement st, int index, WrapperOptions options) throws SQLException {
|
||||
st.setNull( index, Types.NULL );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doBindNull(CallableStatement st, String name, WrapperOptions options) throws SQLException {
|
||||
st.setNull( name, Types.NULL );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doBind(PreparedStatement st, X value, int index, WrapperOptions options) {
|
||||
throw new UnsupportedOperationException( getClass().getName() + " should only be used to bind null!" );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void doBind(CallableStatement st, X value, String name, WrapperOptions options) {
|
||||
throw new UnsupportedOperationException( getClass().getName() + " should only be used to bind null!" );
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
|
@ -11,7 +11,7 @@ import jakarta.persistence.Column;
|
|||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.GeneratedValue;
|
||||
import jakarta.persistence.Id;
|
||||
import javax.persistence.TypedQuery;
|
||||
import jakarta.persistence.TypedQuery;
|
||||
|
||||
import org.hibernate.dialect.PostgreSQLDialect;
|
||||
|
||||
|
|
|
@ -10,7 +10,7 @@ import jakarta.persistence.EntityManagerFactory;
|
|||
import java.util.Arrays;
|
||||
|
||||
import org.hibernate.orm.test.jpa.TestingEntityManagerFactoryGenerator;
|
||||
import org.hibernate.jpa.AvailableSettings;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
import org.hibernate.testing.orm.junit.BaseUnitTest;
|
||||
|
|
|
@ -10,7 +10,7 @@ import jakarta.persistence.EntityManagerFactory;
|
|||
import java.util.Arrays;
|
||||
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.jpa.test.TestingEntityManagerFactoryGenerator;
|
||||
import org.hibernate.orm.test.jpa.TestingEntityManagerFactoryGenerator;
|
||||
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
import org.hibernate.testing.orm.junit.BaseUnitTest;
|
||||
|
|
|
@ -47,13 +47,7 @@ public class ReadWriteExpressionChange extends BaseEnversJPAFunctionalTestCase {
|
|||
em.getTransaction().begin();
|
||||
List resultList = em.createNativeQuery( "select size_in_cm from t_staff_AUD where id =" + id ).getResultList();
|
||||
Assert.assertEquals( 1, resultList.size() );
|
||||
Double sizeInCm = null;
|
||||
if ( getDialect() instanceof OracleDialect ) {
|
||||
sizeInCm = ((BigDecimal) resultList.get( 0 )).doubleValue();
|
||||
}
|
||||
else {
|
||||
sizeInCm = (Double) resultList.get( 0 );
|
||||
}
|
||||
Double sizeInCm = (Double) resultList.get( 0 );
|
||||
em.getTransaction().commit();
|
||||
Assert.assertEquals( HEIGHT_CENTIMETERS, sizeInCm.doubleValue(), 0.00000001 );
|
||||
}
|
||||
|
|
|
@ -20,7 +20,7 @@ import jakarta.persistence.SequenceGenerator;
|
|||
import jakarta.persistence.Table;
|
||||
|
||||
import org.hibernate.dialect.PostgreSQLDialect;
|
||||
import org.hibernate.jpa.test.BaseEntityManagerFunctionalTestCase;
|
||||
import org.hibernate.orm.test.jpa.BaseEntityManagerFunctionalTestCase;
|
||||
|
||||
import org.hibernate.testing.RequiresDialect;
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
|
|
Loading…
Reference in New Issue