使用反引号将表名/列名括起来会使得 Hibernate 在生成 SQL 时将该表名/列名括起来,一般是用双引号,但 SQL Server 使用中括号,而 MySQL 使用反引号。
Hibernate 使用反引号 escape SQL 关键字,但 JPA 使用双引号(double quotes)
Hibernate legacy quoting
package org.example.demo.hibernate;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EntityManagerFactory;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Persistence;
public class Test {
public static void main(String[] args) throws Exception {
EntityManagerFactory factory = Persistence.createEntityManagerFactory("test");
factory.close();
}
@Entity(name = "Product")
public static class Product {
@Id
@GeneratedValue
Long id;
@Column(name = "`name`")
String name;
@Column(name = "`number`")
String number;
}
}
生成 SQL
drop table if exists Product cascade
drop sequence if exists hibernate_sequence
create sequence hibernate_sequence start 1 increment 1
create table Product (id int8 not null, "name" varchar(255), "number" varchar(255), primary key (id))
JPA quoting
package org.example.demo.hibernate;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EntityManagerFactory;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.Persistence;
public class Test {
public static void main(String[] args) throws Exception {
EntityManagerFactory factory = Persistence.createEntityManagerFactory("test");
factory.close();
}
@Entity(name = "Product")
public static class Product {
@Id
@GeneratedValue
Long id;
@Column(name = "\"name\"")
String name;
@Column(name = "\"number\"")
String number;
}
}
生成 SQL
drop table if exists Product cascade
drop sequence if exists hibernate_sequence
create sequence hibernate_sequence start 1 increment 1
create table Product (id int8 not null, "name" varchar(255), "number" varchar(255), primary key (id))
Global quoting
可以配置 hibernate.globally_quoted_identifiers 选项以在全局范围内将所有 identifiers (表名、列名等)都括起来。
package org.example.demo.hibernate;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import org.hibernate.SessionFactory;
import org.hibernate.boot.Metadata;
import org.hibernate.boot.MetadataSources;
import org.hibernate.boot.registry.StandardServiceRegistryBuilder;
import org.hibernate.cfg.AvailableSettings;
import org.hibernate.service.ServiceRegistry;
public class Test {
public static void main(String[] args) throws Exception {
ServiceRegistry standardRegistry = new StandardServiceRegistryBuilder()
.applySetting("hibernate.connection.url", "jdbc:p6spy:postgresql://localhost:5432/test")
.applySetting("hibernate.connection.username", "postgres")
.applySetting("hibernate.connection.password", "postgres")
.applySetting(AvailableSettings.GLOBALLY_QUOTED_IDENTIFIERS, true)
.applySetting("hibernate.hbm2ddl.auto", "create").build();
Metadata metadata = new MetadataSources(standardRegistry).addAnnotatedClass(Product.class).getMetadataBuilder()
.build();
SessionFactory sessionFactory = metadata.getSessionFactoryBuilder().build();
sessionFactory.close();
}
@Entity(name = "Product")
public static class Product {
@Id
@GeneratedValue
Long id;
String name;
String number;
}
}
生成 SQL
drop table if exists "Product" cascade
drop sequence if exists "hibernate_sequence"
create sequence "hibernate_sequence" start 1 increment 1
create table "Product" ("id" int8 not null, "name" varchar(255), "number" varchar(255), primary key ("id"))