Search in sources :

Example 1 with JdbcTypeIndicators

use of org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators in project hibernate-orm by hibernate.

the class SimpleValue method buildAttributeConverterTypeAdapter.

private <T> AttributeConverterTypeAdapter<T> buildAttributeConverterTypeAdapter(JpaAttributeConverter<T, ?> jpaAttributeConverter) {
    JavaType<T> domainJavaType = jpaAttributeConverter.getDomainJavaType();
    JavaType<?> relationalJavaType = jpaAttributeConverter.getRelationalJavaType();
    // build the SqlTypeDescriptor adapter ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    // Going back to the illustration, this should be a SqlTypeDescriptor that handles the Integer <-> String
    // conversions.  This is the more complicated piece.  First we need to determine the JDBC type code
    // corresponding to the AttributeConverter's declared "databaseColumnJavaType" (how we read that value out
    // of ResultSets).  See JdbcTypeJavaClassMappings for details.  Again, given example, this should return
    // VARCHAR/CHAR
    final JdbcType recommendedJdbcType = relationalJavaType.getRecommendedJdbcType(// todo (6.0) : handle the other JdbcRecommendedSqlTypeMappingContext methods
    new JdbcTypeIndicators() {

        @Override
        public TypeConfiguration getTypeConfiguration() {
            return metadata.getTypeConfiguration();
        }

        @Override
        public TimeZoneStorageStrategy getDefaultTimeZoneStorageStrategy() {
            return buildingContext.getBuildingOptions().getDefaultTimeZoneStorage();
        }
    });
    int jdbcTypeCode = recommendedJdbcType.getDefaultSqlTypeCode();
    if (isLob()) {
        if (LobTypeMappings.isMappedToKnownLobCode(jdbcTypeCode)) {
            jdbcTypeCode = LobTypeMappings.getLobCodeTypeMapping(jdbcTypeCode);
        } else {
            if (Serializable.class.isAssignableFrom(domainJavaType.getJavaTypeClass())) {
                jdbcTypeCode = Types.BLOB;
            } else {
                throw new IllegalArgumentException(String.format(Locale.ROOT, "JDBC type-code [%s (%s)] not known to have a corresponding LOB equivalent, and Java type is not Serializable (to use BLOB)", jdbcTypeCode, JdbcTypeNameMapper.getTypeName(jdbcTypeCode)));
            }
        }
    }
    if (isNationalized()) {
        jdbcTypeCode = NationalizedTypeMappings.toNationalizedTypeCode(jdbcTypeCode);
    }
    // todo : cache the AttributeConverterTypeAdapter in case that AttributeConverter is applied multiple times.
    return new AttributeConverterTypeAdapter<>(ConverterDescriptor.TYPE_NAME_PREFIX + jpaAttributeConverter.getConverterJavaType().getJavaType().getTypeName(), String.format("BasicType adapter for AttributeConverter<%s,%s>", domainJavaType.getJavaType().getTypeName(), relationalJavaType.getJavaType().getTypeName()), jpaAttributeConverter, // calls into the binding/extraction process...
    new AttributeConverterJdbcTypeAdapter(jpaAttributeConverter, metadata.getTypeConfiguration().getJdbcTypeRegistry().getDescriptor(jdbcTypeCode), relationalJavaType), relationalJavaType, domainJavaType, null);
}
Also used : JdbcTypeIndicators(org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators) AttributeConverterJdbcTypeAdapter(org.hibernate.type.descriptor.converter.AttributeConverterJdbcTypeAdapter) TimeZoneStorageStrategy(org.hibernate.TimeZoneStorageStrategy) JdbcType(org.hibernate.type.descriptor.jdbc.JdbcType) AttributeConverterTypeAdapter(org.hibernate.type.descriptor.converter.AttributeConverterTypeAdapter) TypeConfiguration(org.hibernate.type.spi.TypeConfiguration)

Example 2 with JdbcTypeIndicators

use of org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators in project hibernate-orm by hibernate.

the class VersionResolution method from.

// todo (6.0) : support explicit JTD?
// todo (6.0) : support explicit STD?
@SuppressWarnings({ "rawtypes", "unchecked" })
public static <E> VersionResolution<E> from(Function<TypeConfiguration, java.lang.reflect.Type> implicitJavaTypeAccess, Function<TypeConfiguration, BasicJavaType> explicitJtdAccess, Function<TypeConfiguration, JdbcType> explicitStdAccess, TimeZoneStorageType timeZoneStorageType, TypeConfiguration typeConfiguration, @SuppressWarnings("unused") MetadataBuildingContext context) {
    // todo (6.0) : add support for Dialect-specific interpretation?
    final java.lang.reflect.Type implicitJavaType = implicitJavaTypeAccess.apply(typeConfiguration);
    final JavaType registered = typeConfiguration.getJavaTypeRegistry().resolveDescriptor(implicitJavaType);
    final BasicJavaType jtd = (BasicJavaType) registered;
    final JdbcType recommendedJdbcType = jtd.getRecommendedJdbcType(new JdbcTypeIndicators() {

        @Override
        public TypeConfiguration getTypeConfiguration() {
            return typeConfiguration;
        }

        @Override
        public TemporalType getTemporalPrecision() {
            // if it is a temporal version, it needs to be a TIMESTAMP
            return TemporalType.TIMESTAMP;
        }

        @Override
        public TimeZoneStorageStrategy getDefaultTimeZoneStorageStrategy() {
            if (timeZoneStorageType != null) {
                switch(timeZoneStorageType) {
                    case NATIVE:
                        return TimeZoneStorageStrategy.NATIVE;
                    case NORMALIZE:
                        return TimeZoneStorageStrategy.NORMALIZE;
                }
            }
            return context.getBuildingOptions().getDefaultTimeZoneStorage();
        }
    });
    final BasicType<?> basicType = typeConfiguration.getBasicTypeRegistry().resolve(jtd, recommendedJdbcType);
    final BasicType legacyType = typeConfiguration.getBasicTypeRegistry().getRegisteredType(jtd.getJavaType());
    assert legacyType.getJdbcType().equals(recommendedJdbcType);
    return new VersionResolution<>(jtd, recommendedJdbcType, basicType, legacyType);
}
Also used : JdbcTypeIndicators(org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators) TimeZoneStorageStrategy(org.hibernate.TimeZoneStorageStrategy) BasicType(org.hibernate.type.BasicType) JdbcType(org.hibernate.type.descriptor.jdbc.JdbcType) BasicJavaType(org.hibernate.type.descriptor.java.BasicJavaType) JavaType(org.hibernate.type.descriptor.java.JavaType) BasicJavaType(org.hibernate.type.descriptor.java.BasicJavaType) TypeConfiguration(org.hibernate.type.spi.TypeConfiguration) TemporalType(jakarta.persistence.TemporalType)

Example 3 with JdbcTypeIndicators

use of org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators in project hibernate-orm by hibernate.

the class ArgumentTypesValidator method validate.

/**
 * We do an initial validation phase with just the SQM tree, even though we don't
 * have all typing information available here (in particular, we don't have the
 * final JDBC type codes for things with converters) because this is the phase
 * that is run at startup for named queries, and can be done in an IDE.
 */
@Override
public void validate(List<? extends SqmTypedNode<?>> arguments, String functionName, QueryEngine queryEngine) {
    delegate.validate(arguments, functionName, queryEngine);
    int count = 0;
    for (SqmTypedNode<?> argument : arguments) {
        JdbcTypeIndicators indicators = queryEngine.getTypeConfiguration().getCurrentBaseSqlTypeIndicators();
        SqmExpressible<?> nodeType = argument.getNodeType();
        FunctionParameterType type = count < types.length ? types[count++] : types[types.length - 1];
        if (nodeType != null) {
            JavaType<?> javaType = nodeType.getExpressibleJavaType();
            if (javaType != null) {
                try {
                    JdbcType jdbcType = javaType.getRecommendedJdbcType(indicators);
                    checkType(count, functionName, type, jdbcType.getJdbcTypeCode(), javaType.getJavaTypeClass());
                } catch (JdbcTypeRecommendationException e) {
                // it's a converter or something like that, and we will check it later
                }
            }
            switch(type) {
                case TEMPORAL_UNIT:
                    if (!(argument instanceof SqmExtractUnit) && !(argument instanceof SqmDurationUnit)) {
                        throwError(type, Object.class, functionName, count);
                    }
                    break;
                // something crazy by the parser
                case TRIM_SPEC:
                    if (!(argument instanceof SqmTrimSpecification)) {
                        throwError(type, Object.class, functionName, count);
                    }
                    break;
                case COLLATION:
                    if (!(argument instanceof SqmCollation)) {
                        throwError(type, Object.class, functionName, count);
                    }
                    break;
            }
        } else {
        // TODO: appropriate error?
        }
    }
}
Also used : JdbcTypeRecommendationException(org.hibernate.type.descriptor.java.spi.JdbcTypeRecommendationException) JdbcTypeIndicators(org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators) SqmTrimSpecification(org.hibernate.query.sqm.tree.expression.SqmTrimSpecification) SqmExtractUnit(org.hibernate.query.sqm.tree.expression.SqmExtractUnit) SqmDurationUnit(org.hibernate.query.sqm.tree.expression.SqmDurationUnit) JdbcType(org.hibernate.type.descriptor.jdbc.JdbcType) SqmCollation(org.hibernate.query.sqm.tree.expression.SqmCollation)

Example 4 with JdbcTypeIndicators

use of org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators in project hibernate-orm by hibernate.

the class ResultSetAccess method resolveType.

@Override
default <J> BasicType<J> resolveType(int position, JavaType<J> explicitJavaType, SessionFactoryImplementor sessionFactory) {
    final TypeConfiguration typeConfiguration = getFactory().getTypeConfiguration();
    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 displaySize = metaData.getColumnDisplaySize(position);
        final Dialect dialect = jdbcServices.getDialect();
        final int length = dialect.resolveSqlTypeLength(columnTypeName, columnType, precision, scale, displaySize);
        final JdbcType resolvedJdbcType = dialect.resolveSqlTypeDescriptor(columnTypeName, columnType, length, scale, typeConfiguration.getJdbcTypeRegistry());
        final JavaType<J> javaType;
        final JdbcType jdbcType;
        // If there is an explicit JavaType, then prefer its recommended JDBC type
        if (explicitJavaType != null) {
            javaType = explicitJavaType;
            jdbcType = explicitJavaType.getRecommendedJdbcType(new JdbcTypeIndicators() {

                @Override
                public TypeConfiguration getTypeConfiguration() {
                    return typeConfiguration;
                }

                @Override
                public long getColumnLength() {
                    return length;
                }

                @Override
                public int getColumnPrecision() {
                    return precision;
                }

                @Override
                public int getColumnScale() {
                    return scale;
                }

                @Override
                public EnumType getEnumeratedType() {
                    return resolvedJdbcType.isNumber() ? EnumType.ORDINAL : EnumType.STRING;
                }
            });
        } else {
            jdbcType = resolvedJdbcType;
            javaType = jdbcType.getJdbcRecommendedJavaTypeMapping(length, scale, typeConfiguration);
        }
        return typeConfiguration.getBasicTypeRegistry().resolve(javaType, jdbcType);
    } catch (SQLException e) {
        throw jdbcServices.getSqlExceptionHelper().convert(e, "Unable to determine JDBC type code for ResultSet position " + position);
    }
}
Also used : ResultSetMetaData(java.sql.ResultSetMetaData) JdbcTypeIndicators(org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators) SQLException(java.sql.SQLException) Dialect(org.hibernate.dialect.Dialect) JdbcType(org.hibernate.type.descriptor.jdbc.JdbcType) JdbcServices(org.hibernate.engine.jdbc.spi.JdbcServices) TypeConfiguration(org.hibernate.type.spi.TypeConfiguration)

Aggregations

JdbcType (org.hibernate.type.descriptor.jdbc.JdbcType)4 JdbcTypeIndicators (org.hibernate.type.descriptor.jdbc.JdbcTypeIndicators)4 TypeConfiguration (org.hibernate.type.spi.TypeConfiguration)3 TimeZoneStorageStrategy (org.hibernate.TimeZoneStorageStrategy)2 TemporalType (jakarta.persistence.TemporalType)1 ResultSetMetaData (java.sql.ResultSetMetaData)1 SQLException (java.sql.SQLException)1 Dialect (org.hibernate.dialect.Dialect)1 JdbcServices (org.hibernate.engine.jdbc.spi.JdbcServices)1 SqmCollation (org.hibernate.query.sqm.tree.expression.SqmCollation)1 SqmDurationUnit (org.hibernate.query.sqm.tree.expression.SqmDurationUnit)1 SqmExtractUnit (org.hibernate.query.sqm.tree.expression.SqmExtractUnit)1 SqmTrimSpecification (org.hibernate.query.sqm.tree.expression.SqmTrimSpecification)1 BasicType (org.hibernate.type.BasicType)1 AttributeConverterJdbcTypeAdapter (org.hibernate.type.descriptor.converter.AttributeConverterJdbcTypeAdapter)1 AttributeConverterTypeAdapter (org.hibernate.type.descriptor.converter.AttributeConverterTypeAdapter)1 BasicJavaType (org.hibernate.type.descriptor.java.BasicJavaType)1 JavaType (org.hibernate.type.descriptor.java.JavaType)1 JdbcTypeRecommendationException (org.hibernate.type.descriptor.java.spi.JdbcTypeRecommendationException)1