--Unable to recognize Spring Data JDBC DM dialect
Table of contents
--Unable to recognize Spring Data JDBC DM dialect
1 Spring Data REST @Idclass not recognized
2 Spring JDBC and Firebird database
3 Spring Data JDBC/Spring Data JPA 与 Hibernate
The four project configurations are as follows
1 The length of the word field is fixed
Unrecognized Spring Data JDBC Firebird dialect - Stack Overflow
The magical effect of spring.factories - Programmer Sought
https://blog.csdn.net/mamamalululu00000000/article/details/86711079
a similar problem
1 Spring Data REST @Idclass not recognized
2 Spring JDBC and Firebird database
3 Spring Data JDBC/Spring Data JPA 与 Hibernate
Two problem description
I am trying to connect to a DM database using Spring Data JDBC and Spring Boot. I have created a simple application using Spring Tools. Spring Data JDBC does not recognize the dialect. I believe the problem is that DM is not supported DialectResolver
.
@Nullable
private static Dialect getDialect(Connection connection) throws SQLException {
DatabaseMetaData metaData = connection.getMetaData();
String name = metaData.getDatabaseProductName().toLowerCase(Locale.ENGLISH);
if (name.contains("hsql")) {
return HsqlDbDialect.INSTANCE;
} else if (name.contains("h2")) {
return H2Dialect.INSTANCE;
} else if (!name.contains("mysql") && !name.contains("mariadb")) {
if (name.contains("postgresql")) {
return PostgresDialect.INSTANCE;
} else if (name.contains("microsoft")) {
return SqlServerDialect.INSTANCE;
} else if (name.contains("db2")) {
return Db2Dialect.INSTANCE;
} else {
DialectResolver.LOG.info(String.format("Couldn't determine Dialect for \"%s\"", name));
return null;
}
} else {
return new MySqlDialect(getIdentifierProcessing(metaData));
}
}
Three errors are as follows
1 Error screenshot
2 error message
[email protected]/java.lang.Thread.run(Thread.java:834)
2021-12-22 19:56:38.216 [TID: N/A] [main] INFO logger_name:o.s.b.a.l.ConditionEvaluationReportLoggingListener -
Error starting ApplicationContext. To display the conditions report re-run your application with 'debug' enabled.
2021-12-22 19:56:38.390 [TID: N/A] [main] ERROR logger_name:o.s.boot.SpringApplication - Application run failed
org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'jdbcConverter' defined in class path resource [org/springframework/boot/autoconfigure/data/jdbc/JdbcRepositoriesAutoConfiguration$SpringBootJdbcConfiguration.class]: Unsatisfied dependency expressed through method 'jdbcConverter' parameter 4;
nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'jdbcDialect' defined in class path resource [org/springframework/boot/autoconfigure/data/jdbc/JdbcRepositoriesAutoConfiguration$SpringBootJdbcConfiguration.class]: Bean instantiation via factory method failed; nested exception is
org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.data.relational.core.dialect.Dialect]: Factory method 'jdbcDialect' threw exception; nested exception is org.springframework.data.jdbc.repository.config.DialectResolver$NoDialectException: Cannot determine a dialect for
org.springframework.jdbc.core.JdbcTemplate@499a93a9. Please provide a Dialect.
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'jdbcDialect' defined in class path resource [org/springframework/boot/autoconfigure/data/jdbc/JdbcRepositoriesAutoConfiguration$SpringBootJdbcConfiguration.class]: Bean instantiation via factory method failed;
nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.data.relational.core.dialect.Dialect]: Factory method 'jdbcDialect' threw exception; nested exception is org.springframework.data.jdbc.repository.config.DialectResolver$NoDialectException: Cannot determine a dialect
for org.springframework.jdbc.core.JdbcTemplate@499a93a9. Please provide a Dialect.
Caused by: org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.data.relational.core.dialect.Dialect]: Factory method 'jdbcDialect' threw exception; nested exception is org.springframework.data.jdbc.repository.config.DialectResolver$NoDialectException: Cannot determine a dialect for
org.springframework.jdbc.core.JdbcTemplate@499a93a9. Please provide a Dialect.
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:185)
at org.springframework.beans.factory.support.ConstructorResolver.instantiate(ConstructorResolver.java:652)
... 34 common frames omitted
Caused by: org.springframework.data.jdbc.repository.config.DialectResolver$NoDialectException: Cannot determine a dialect for org.springframework.jdbc.core.JdbcTemplate@499a93a9. Please provide a Dialect.
The four project configurations are as follows
1 Maven dependency added
<dependency>
<groupId>com.dameng</groupId>
<artifactId>Dm8JdbcDriver18</artifactId>
<version>8.1.1.49</version>
</dependency>
<dependency>
<groupId>com.dameng</groupId>
<artifactId>DmDialect-for-hibernate5.0</artifactId>
<version>8.1.1.49</version>
</dependency>
Five solutions
The Spring Data JDBC library itself does not include a ready-made DM, the Firebird dialect, so you need to provide one yourself. Annotate the underlying configuration of the Spring JDBC documentation :
Dialects are resolved JdbcOperations
by JdbcDialectResolver
the pass inspection, usually by inspection . You can let Spring auto-discover the creation of pass Connection
by registering classes that implement the following . Discovery uses Spring's classpath to implement the dialect provider from within the dialect .Dialect
org.springframework.data.jdbc.repository.config.DialectResolver$JdbcDialectProvider
META-INF/spring.factories
DialectResolver
SpringFactoriesLoader
To use DM, Firebird, you need to define three things:
- dialect
- Dialect parser
- Configuration files for Spring to find dialect resolvers
The dialect could be something like ( note that this dialect assumes DM , Firebird 3 or later ):
package spring.dm;
import org.springframework.data.relational.core.dialect.AnsiDialect;
import org.springframework.data.relational.core.dialect.ArrayColumns;
import org.springframework.data.relational.core.dialect.LockClause;
import org.springframework.data.relational.core.sql.LockOptions;
public class DMDialect extends AnsiDialect {
public static final DMDialect INSTANCE = new DMDialect();
@Override
public LockClause lock() {
return LOCK_CLAUSE;
}
@Override
public ArrayColumns getArraySupport() {
return ArrayColumns.Unsupported.INSTANCE;
}
private static final LockClause LOCK_CLAUSE = new LockClause() {
@Override
public String getLock(LockOptions lockOptions) {
return "WITH LOCK";
}
@Override
public Position getClausePosition() {
return Position.AFTER_ORDER_BY;
}
};
}
Dialect resolver, returns the dialect if connected to a Firebird database .
package spring.dm;
import org.springframework.data.jdbc.repository.config.DialectResolver;
import org.springframework.data.relational.core.dialect.Dialect;
import org.springframework.jdbc.core.ConnectionCallback;
import org.springframework.jdbc.core.JdbcOperations;
import java.sql.Connection;
import java.sql.DatabaseMetaData;
import java.sql.SQLException;
import java.util.Locale;
import java.util.Optional;
public class DMDialectResolver implements DialectResolver.JdbcDialectProvider {
@Override
public Optional<Dialect> getDialect(JdbcOperations jdbcOperations) {
return Optional.ofNullable(
jdbcOperations.execute((ConnectionCallback<Dialect>)DMDialectResolver::getDialect )
);
}
private static Dialect getDialect(Connection connection) throws SQLException {
DatabaseMetaData metaData = connection.getMetaData();
String name = metaData.getDatabaseProductName().toLowerCase( Locale.ROOT);
if (name.contains("dm dbms")) {
return DMDialect.INSTANCE;
}
return null;
}
}
Finally, you need to define a resource named spring.factoriesMETA-INF , this file must contain the following line
org.springframework.data.jdbc.repository.config.DialectResolver$JdbcDialectProvider=spring.firebird.FirebirdDialectResolver
This allows Spring Data JDBC to discover the dialect resolver and use it
Six other questions
1. The field length of Dameng word is fixed
The field length of Dameng database will not increase automatically. For example, if the string length is 50, an error will be reported if the stored string exceeds 50, but mysql will not.