Spring Boot Hibernate 5 忽略@Table 和@Column [英] Spring Boot Hibernate 5 Ignoring @Table and @Column
问题描述
这让我发疯.
我正在实施 Spring Social,它要求您有一个名为 UserConnection
的数据库表(而不是使用使用下划线分隔两个词的标准命名约定).
因此,在我天真的世界观中,我认为通过指定 @Table(name="UserConnection")
可以轻松解决这个问题……但不,那太容易了.>
注释被忽略,表被创建为 user_connection
然后导致 Spring Social 有一个嘶嘶声.
请告诉我,有一些简单的方法可以告诉我的 Spring Boot 应用程序只命名该表(及其对应的列)以使用驼峰命名约定而不是标准命名约定.
TL;博士
将以下内容添加到您的 application.yml
文件中:
弹簧:日文:休眠:命名:物理策略:org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
或者你的application.properties
:
spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
详细解答
作为 Spring Boot 1.4 发行说明指出:
<块引用>SpringNamingStrategy
不再使用,因为 Hibernate 5.1 已删除支持旧的 NamingStrategy
接口.一个新的SpringPhysicalNamingStrategy
现在是自动配置的,用于结合 Hibernate 的默认 ImplicitNamingStrategy
.这个应该非常接近(如果不相同)到 Spring Boot 1.3默认值,但是,您应该检查您的数据库架构是否正确升级时.
这个新的 PhysicalNamingStrategy
遵循 Spring 推荐的命名约定.无论如何,如果您想完全控制物理命名,最好使用 org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
.您可以通过将以下内容添加到您的 application.yml
来切换到该命名策略:
弹簧:日文:休眠:命名:物理策略:org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
<块引用>
注解被忽略,表被创建为user_connection
然后导致 Spring Social 发出嘶嘶声.
apply
SpringPhysicalNamingStrategy
的方法是理解这种行为的关键:
private Identifier apply(Identifier name, JdbcEnvironment jdbcEnvironment) {如果(名称 == 空){返回空;}StringBuilder builder = new StringBuilder(name.getText().replace('.', '_'));for (int i = 1; i < builder.length() - 1; i++) {如果 (isUnderscoreRequired(builder.charAt(i - 1), builder.charAt(i),builder.charAt(i + 1))) {builder.insert(i++, '_');}}返回 getIdentifier(builder.toString(), name.isQuoted(), jdbcEnvironment);}private boolean isUnderscoreRequired(char before, char current, char after) {返回 Character.isLowerCase(before) &&Character.isUpperCase(当前)&&Character.isLowerCase(之后);}
它基本上取代了任何 .
和 case 变化(看看 isUnderscoreRequired
方法),带下划线.
This is driving me mad.
I'm implementing Spring Social and it requires you to have a database table named UserConnection
(instead of using the standard naming convention of using an underscore to separate the two words).
So in my naive world view, I assumed it would be easily solved by specifying @Table(name="UserConnection")
... but no, that would be all too easy.
The annotation is ignored and the table is created as user_connection
which then causes Spring Social to have a hissy fit.
Please tell me there's some easy way to tell my Spring Boot app to just name that one table (and its corresponding columns) to use a camel-case naming convention instead of the standard one.
TL; DR
Add the following to your application.yml
file:
spring:
jpa:
hibernate:
naming:
physical-strategy: org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
Or your application.properties
:
spring.jpa.hibernate.naming.physical-strategy=org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
Detailed Answer
As Spring Boot 1.4 release notes states:
SpringNamingStrategy
is no longer used as Hibernate 5.1 has removed support for the oldNamingStrategy
interface. A newSpringPhysicalNamingStrategy
is now auto-configured which is used in combination with Hibernate’s defaultImplicitNamingStrategy
. This should be very close to (if not identical) to Spring Boot 1.3 defaults, however, you should check your Database schema is correct when upgrading.
This new PhysicalNamingStrategy
follows Spring recommended naming conventions. Anyway if you want total control over physical naming, you're better off using the org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
. You can switch to that naming strategy by adding the following to your application.yml
:
spring:
jpa:
hibernate:
naming:
physical-strategy: org.hibernate.boot.model.naming.PhysicalNamingStrategyStandardImpl
The annotation is ignored and the table is created as
user_connection
which then causes Spring Social to have a hissy fit.
The apply
method of SpringPhysicalNamingStrategy
is the key to understand this behavior:
private Identifier apply(Identifier name, JdbcEnvironment jdbcEnvironment) {
if (name == null) {
return null;
}
StringBuilder builder = new StringBuilder(name.getText().replace('.', '_'));
for (int i = 1; i < builder.length() - 1; i++) {
if (isUnderscoreRequired(builder.charAt(i - 1), builder.charAt(i),
builder.charAt(i + 1))) {
builder.insert(i++, '_');
}
}
return getIdentifier(builder.toString(), name.isQuoted(), jdbcEnvironment);
}
private boolean isUnderscoreRequired(char before, char current, char after) {
return Character.isLowerCase(before) && Character.isUpperCase(current)
&& Character.isLowerCase(after);
}
It basically replaces any .
and case changes (take a look at isUnderscoreRequired
method) with an underscore.
这篇关于Spring Boot Hibernate 5 忽略@Table 和@Column的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!