When the JPA meets MySQL table names all uppercase lowercase + + + hump four Hungarian style

I always know that MySQL has on Linux sensitive issue field watches name, etc., so in order to avoid this problem, select the underscore and all lowercase, the heart that although we use the JPA, just use notes to write clearly table and field names are uppercase, it is not all right. For example this

When the JPA meets MySQL table names all uppercase lowercase + + + hump four Hungarian style

In fact it proved rich in imagination than moving bricks life. Pro, I use JPA implementation time table look-up operation, Exception jumped out table does not exist, because the table name is all lowercase, what I can ┑ (¯Д ¯) ┍. Next, toss has only just begun ...... wish to look at the log, abnormal heart heavy

2019-09-24 17:31:16.407 ERROR 25864 --- [  XNIO-2 task-1] o.h.engine.jdbc.spi.SqlExceptionHelper   : (conn=348) Table '4a.t_assets_mgr' doesn't exist
2019-09-24 17:31:16.420 ERROR 25864 --- [  XNIO-2 task-1] c.s.xxxx.aop.logging.LoggingAspect       : Exception in com.xxx.yyyy.service.StaticQuadraa.initLevel() with cause = 'org.hibernate.exception.SQLGrammarException: could not extract ResultSet' and exception = 'could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet'

org.springframework.dao.InvalidDataAcce***esourceUsageException: could not extract ResultSet; SQL [n/a]; nested exception is org.hibernate.exception.SQLGrammarException: could not extract ResultSet
    at org.springframework.orm.jpa.vendor.HibernateJpaDialect.convertHibernateAccessException(HibernateJpaDialect.java:242)
    at org.springframework.orm.jpa.vendor.HibernateJpaDialect.translateExceptionIfPossible(HibernateJpaDialect.java:225)
    at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.translateExceptionIfPossible(AbstractEntityManagerFactoryBean.java:527)
    at org.springframework.dao.support.ChainedPersistenceExceptionTranslator.translateExceptionIfPossible(ChainedPersistenceExceptionTranslator.java:61)
    at org.springframework.dao.support.DataAccessUtils.translateIfNecessary(DataAccessUtils.java:242)
    at org.springframework.dao.support.PersistenceExceptionTranslationInterceptor.invoke(PersistenceExceptionTranslationInterceptor.java:153)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:185)
    at org.springframework.data.jpa.repository.support.CrudMethodMetadataPostProcessor$CrudMethodMetadataPopulatingMethodInterceptor.invoke(CrudMethodMetadataPostProcessor.java:135)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:185)
    at org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:92)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:185)
    at org.springframework.data.repository.core.support.SurroundingTransactionDetectorMethodInterceptor.invoke(SurroundingTransactionDetectorMethodInterceptor.java:61)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:185)
    at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:212)
    at com.sun.proxy.$Proxy195.getAllByBusinessName(Unknown Source)

To solve this problem is usually the case, if your database is set up at the windows above, but you still write their own play, the first step must be to change the MySQL cnf, change is not case sensitive, so always possible? But now are under docker environment, operation, die ah, then put on a Oracle and troublesome, how to do it? Since MySQL there to solve problems, we think of a way in which Java. Simple analysis process, point the browser button initiates a request to the background, upon request by the Controller service to find the corresponding DTO, DTO has found Hibernate JPA specification to achieve through the Spring Data, reconverted to execute SQL statements sent to the database . So long as the table name changed to uppercase before sending it will solve the problem.
Then the table name changed to uppercase or lowercase, where is it performed? Remember, JPA on the field there is a conversion, such as a_b converted to aB. This is certainly not a kernel implementation of Java, Hibernate JPA implementation this is done. Specific to the code, this thing is org.springframework.boot.orm.jpa.hibernate.SpringPhysicalNamingStrategy in the spring, is the default. Hibernate achieve this is to convert camelCasing function. I write notes in the table name is capitalized, but sql statement output in lowercase, no doubt, here are converted to lowercase code. At present, spring data jpa based Hibernate5, and Hibernate5 on the configuration database naming policy of the previous version is slightly different, which uses implicit-strategy and physical-strategy two configuration items are controlled naming policy

spring.jpa.hibernate.naming.implicit-strategy=org.hibernate.boot.model.naming.ImplicitNamingStrategyJpaCompliantImpl
spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl

These two strategies is still a little small difference:

  • Object hierarchy implicit-strategy model is responsible for processing the object model handled as a logical name
  • physical-strategy responsible for mapping the data to process the real name, the above-described process logical name physical name.
  • When not using @Table and @Column notes, implicit-strategy configuration items will only be used when the object model has been specified, implicit-strategy does not work.
  • physical-strategy will be applied, whether explicitly specify the column name with the object model has been unrelated or implicit decision.

Provided here are two solutions:

  1. Configuration can add lines in the configuration file in springboot project, named set without modification naming policy:

    spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
  2. Rewrite naming policy change table named lowercase:

    @Component
    public class MySQLUpperCaseStrategy extends PhysicalNamingStrategyStandardImpl {
    private static final long serialVersionUID = 1383021413247872469L;
    
    @Override
    public Identifier toPhysicalTableName(Identifier name, JdbcEnvironment context) {
        // 将表名全部转换成大写
        String tableName = name.getText().toUpperCase();
    
        return name.toIdentifier(name.getText());
    }
    }

    After the required relevant in our .ymlusage policies to achieve their own files

    spring.jpa.hibernate.naming:physical-strategy: xx.xx.xx.config.Strategy.MySQLUpperCaseStrategy

    Here I used the method, since in the subsequent development, the development of our predecessors, this database poison, a share of the hump, Hungary, underline, all lowercase four kinds naming style, almost no before or since, read the world the lengthy, passed away early while it is willing to sparkle today, will start to blue buff robbed, the wind will comeback, less a 7 Landlords 3456, high-speed rail instant noodles small fork, buy every stock will fall.
    Here I used the method can be relatively free to modify the mapping table, rather than relying on their naming style that salute to ancestors! !

When the JPA meets MySQL table names all uppercase lowercase + + + hump four Hungarian style

Guess you like

Origin blog.51cto.com/yerikyu/2440787