Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

HHH-18783 cast(x as Character) on MySQL and Maria #9200

Merged
merged 3 commits into from
Nov 4, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -401,5 +401,4 @@ protected void renderStringContainsExactlyPredicate(Expression haystack, Express
needle.accept( this );
appendSql( ",'~','~~'),'?','~?'),'%','~%'),'%') escape '~'" );
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,7 @@ public class MySQLDialect extends Dialect {
private static final DatabaseVersion MINIMUM_VERSION = DatabaseVersion.make( 8 );

private final MySQLStorageEngine storageEngine = createStorageEngine();

private final SizeStrategy sizeStrategy = new SizeStrategyImpl() {
@Override
public Size resolveSize(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,6 @@
*/
package org.hibernate.dialect;

import java.util.ArrayList;
import java.util.List;
import java.util.Locale;

import org.hibernate.engine.jdbc.Size;
import org.hibernate.engine.spi.SessionFactoryImplementor;
import org.hibernate.internal.util.collections.Stack;
Expand Down Expand Up @@ -41,6 +37,10 @@
import org.hibernate.sql.exec.spi.JdbcOperation;
import org.hibernate.sql.exec.spi.JdbcOperationQueryInsert;

import java.util.ArrayList;
import java.util.List;
import java.util.Locale;

/**
* A SQL AST translator for MySQL.
*
Expand All @@ -57,6 +57,10 @@ public static String getSqlType(CastTarget castTarget, SessionFactoryImplementor
return getSqlType( castTarget, sqlType, factory.getJdbcServices().getDialect() );
}

//TODO: this is really, really bad since it circumvents the whole machinery we have in DdlType
// and in the Dialect for doing this in a unified way! These mappings should be held in
// the DdlTypes themselves and should be set up in registerColumnTypes(). Doing it here
// means we have problems distinguishing, say, the 'as Character' special case
private static String getSqlType(CastTarget castTarget, String sqlType, Dialect dialect) {
if ( sqlType != null ) {
int parenthesesIndex = sqlType.indexOf( '(' );
Expand All @@ -72,23 +76,30 @@ private static String getSqlType(CastTarget castTarget, String sqlType, Dialect
case "float":
case "real":
case "double precision":
final int precision = castTarget.getPrecision() == null ?
dialect.getDefaultDecimalPrecision() :
castTarget.getPrecision();
final int precision = castTarget.getPrecision() == null
? dialect.getDefaultDecimalPrecision()
: castTarget.getPrecision();
final int scale = castTarget.getScale() == null ? Size.DEFAULT_SCALE : castTarget.getScale();
return "decimal(" + precision + "," + scale + ")";
case "char":
case "varchar":
case "nchar":
case "nvarchar":
return castTarget.getLength() == null
? "char"
: ( "char(" + castTarget.getLength() + ")" );
if ( castTarget.getLength() == null ) {
// TODO: this is ugly and fragile, but could easily be handled in a DdlType
if ( castTarget.getJdbcMapping().getJdbcJavaType().getJavaType() == Character.class ) {
return "char(1)";
}
else {
return "char";
}
}
return "char(" + castTarget.getLength() + ")";
case "binary":
case "varbinary":
return castTarget.getLength() == null
? "binary"
: ( "binary(" + castTarget.getLength() + ")" );
: "binary(" + castTarget.getLength() + ")";
}
}
return sqlType;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5746,20 +5746,20 @@ else if ( isParameter( expression ) ) {
renderCasted( expression );
}
}
else if ( expression instanceof CaseSimpleExpression ) {
visitCaseSimpleExpression( (CaseSimpleExpression) expression, true );
else if ( expression instanceof CaseSimpleExpression caseSimpleExpression ) {
visitCaseSimpleExpression( caseSimpleExpression, true );
}
else if ( expression instanceof CaseSearchedExpression ) {
visitCaseSearchedExpression( (CaseSearchedExpression) expression, true );
else if ( expression instanceof CaseSearchedExpression caseSearchedExpression ) {
visitCaseSearchedExpression( caseSearchedExpression, true );
}
else {
renderExpressionAsClauseItem( expression );
}
}

protected void renderCasted(Expression expression) {
if ( expression instanceof SqmParameterInterpretation ) {
expression = ( (SqmParameterInterpretation) expression ).getResolvedExpression();
if ( expression instanceof SqmParameterInterpretation parameterInterpretation ) {
expression = parameterInterpretation.getResolvedExpression();
}
final List<SqlAstNode> arguments = new ArrayList<>( 2 );
arguments.add( expression );
Expand Down Expand Up @@ -5935,8 +5935,8 @@ assert getStatementStack().getCurrent() instanceof UpdateStatement
processNestedTableGroupJoins( tableGroup, null );
processTableGroupJoins( tableGroup );
ModelPartContainer modelPart = tableGroup.getModelPart();
if ( modelPart instanceof EntityPersister ) {
String[] querySpaces = (String[]) ( (EntityPersister) modelPart ).getQuerySpaces();
if ( modelPart instanceof EntityPersister persister ) {
final String[] querySpaces = (String[]) persister.getQuerySpaces();
for ( int i = 0; i < querySpaces.length; i++ ) {
registerAffectedTable( querySpaces[i] );
}
Expand Down Expand Up @@ -6113,7 +6113,7 @@ else if ( referenceJoinIndexForPredicateSwap == TableGroupHelper.NO_TABLE_GROUP_

ModelPartContainer modelPart = tableGroup.getModelPart();
if ( modelPart instanceof EntityPersister persister ) {
String[] querySpaces = (String[]) persister.getQuerySpaces();
final String[] querySpaces = (String[]) persister.getQuerySpaces();
for ( int i = 0; i < querySpaces.length; i++ ) {
registerAffectedTable( querySpaces[i] );
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1131,7 +1131,6 @@ public void testCastFunctionHexToBinary(SessionFactoryScope scope) {

@Test
@SkipForDialect( dialectClass = AltibaseDialect.class, reason = "Altibase cast to char does not do truncatation")
@SkipForDialect( dialectClass = MySQLDialect.class, matchSubTypes = true, reason = "MySQL cast does not do truncatation")
public void testCastFunctionWithLength(SessionFactoryScope scope) {
scope.inTransaction(
session -> {
Expand All @@ -1140,9 +1139,18 @@ public void testCastFunctionWithLength(SessionFactoryScope scope) {
assertEquals( 'A',
session.createQuery("select cast('ABCDEF' as Character)", Character.class)
.getSingleResult() );
assertEquals( ' ',
session.createQuery("select cast(' X ' as Character)", Character.class)
.getSingleResult() );
assertEquals( "ABC",
session.createQuery("select cast('ABCDEF' as String(3))", String.class)
.getSingleResult() );
assertEquals( "ABC",
session.createQuery("select cast('ABC' as String(6))", String.class)
.getSingleResult() );
assertEquals( "ABC ",
session.createQuery("select cast('ABC DEF' as String(4))", String.class)
.getSingleResult() );
}
);
}
Expand Down
Loading