巧用Hibernate 完成多数据库的DDL脚本创建

本文涉及的产品
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
云数据库 RDS MySQL,高可用系列 2核4GB
RDS MySQL Serverless 高可用系列,价值2615元额度,1个月
简介: 巧用Hibernate 完成多数据库的DDL脚本创建

巧用Hibernate 完成多数据库的DDL脚本创建

spring boot jpa 默认的orm框架就是Hibernate。 由hibernate完成数据库的读写也是主流的方式之一。但是不同数据库之间,建表、建索引的方言语句都有较多差别,很难做到一套SQL在所有数据库上进行执行。

那么Hibernate可以做到DML等语句通用,DDL可以吗? 当然,是可以的。

Hibernate兼容全靠org.hibernate.dialect.Dialect下的具体实现类。

下面我们来简单演示如何基于hibernate的注解,来生成DDL语句。

定义一个Entity

使用hibernate的注解描述一个Entity,我们定义了其表名,id,name属性,并指定id为主键列。

// hibernate 6.x 开始,注解移动到了jakarta.persistence包下
import jakarta.persistence.*;
@Entity
@Table(name = "my_entity")
public class MyEntity {
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "id", nullable = false)
    private Long id;
    @Column(name = "name", nullable = true, length = 256)
    private String name;
    public Long getId() {
        return id;
    }
    public void setId(Long id) {
        this.id = id;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
}

期待生成的SQL

我们在建表的时候,还要创建序列,指定执行引擎。要知道,MYSQL如果使用MyISAM将无法使用会话。

oracle

create sequence my_entity_SEQ start with 1 increment by 50;
create table my_entity (id number(19,0) not null, name varchar2(256 char), primary key (id));

mysql

create table my_entity (id bigint not null, name varchar(256), primary key (id)) engine=InnoDB;
create table my_entity_SEQ (next_val bigint) engine=InnoDB;
insert into my_entity_SEQ values ( 1 );

具体实现

具体实现并不难,主要是调用org.hibernate.tool.hbm2ddl.SchemaExport进行导出,主要方法如下:

/**
     * 导出
     *
     * @param classes    导出的类
     * @param dialect    数据库方言
     * @param action     导出动作
     * @param targetType 导出方式
     * @param scriptPath 脚本位置
     */
  public static void export0(List<Class> classes,
        Class<? extends Dialect> dialect,
        SchemaExport.Action action,
        TargetType targetType,
        String scriptPath) {
        Properties p = new Properties();
        // 数据库方言,最终输出的方言
        p.put("hibernate.dialect", dialect.getName());
        // 自动执行的动作
        p.put("hibernate.hbm2dll.auto", action.name());
        // 分隔符,默认为空
        p.put("hibernate.hbm2ddl.delimiter", ";");
        // 是否展示SQL
        p.put("show_sql", true);
        // 是否使用默认的jdbc元数据,默认为true,读取项目自身的元数据
        p.put("hibernate.temp.use_jdbc_metadata_defaults", false);
        ConfigurationHelper.resolvePlaceHolders(p);
        ServiceRegistry registry = new StandardServiceRegistryBuilder()
            .applySettings(p)
            .build();
        // org.dark.migration.demo
        MetadataSources metadataSources = new MetadataSources(registry);
        classes.forEach(metadataSources::addAnnotatedClass);
        Metadata metadata = metadataSources.buildMetadata();
        SchemaExport export = new SchemaExport();
        export.setOverrideOutputFileContent();
        export.setOutputFile(scriptPath);
        export.execute(EnumSet.of(targetType), action, metadata);
    }

调用方法如下:

public static void main(String[] args) {
        List<Class> classes = new ArrayList<>();
        classes.add(MyEntity.class);
//        export0(classes, Oracle12cDialect.class,
        export0(classes, MySQL8Dialect.class,
            SchemaExport.Action.CREATE,
            TargetType.SCRIPT, "test-output2.txt");
    }

最终就会在"test-output2.txt"中生成我们期待的SQL。

支持的数据库方言

通过查看Dialect的子类,可以看到除了主流的mysql、Oracle、postgre、DB2等,像TIDB、CockroachDB等等数据库等均有方言支持。

总结

利用好hibernate的多数据源方言兼容性,我们仅维护一套注解即可创建多数据源DDL。文章代码库位置:

相关实践学习
每个IT人都想学的“Web应用上云经典架构”实战
本实验从Web应用上云这个最基本的、最普遍的需求出发,帮助IT从业者们通过“阿里云Web应用上云解决方案”,了解一个企业级Web应用上云的常见架构,了解如何构建一个高可用、可扩展的企业级应用架构。
MySQL数据库入门学习
本课程通过最流行的开源数据库MySQL带你了解数据库的世界。 &nbsp; 相关的阿里云产品:云数据库RDS MySQL 版 阿里云关系型数据库RDS(Relational Database Service)是一种稳定可靠、可弹性伸缩的在线数据库服务,提供容灾、备份、恢复、迁移等方面的全套解决方案,彻底解决数据库运维的烦恼。 了解产品详情:&nbsp;https://www.aliyun.com/product/rds/mysql&nbsp;
目录
相关文章
|
7月前
|
前端开发 数据库
会议室管理系统源码(含数据库脚本)
会议室管理系统源码(含数据库脚本)
124 0
|
2月前
|
SQL 数据管理 BI
数据库操作三基石:DDL、DML、DQL 技术入门指南
本文围绕数据库操作核心语言 DDL、DML、DQL 展开入门讲解。DDL 作为 “结构建筑师”,通过CREATE(建库 / 表)、ALTER(修改表)、DROP(删除)等命令定义数据库结构;DML 作为 “数据管理员”,以INSERT(插入)、UPDATE(更新)、DELETE(删除)操作数据表记录,需搭配WHERE条件避免误操作;DQL 作为 “数据检索师”,通过SELECT结合WHERE、ORDER BY、LIMIT等子句实现数据查询与统计。三者相辅相成,是数据库操作的基础,使用时需注意 DDL 的不可撤销性、DML 的条件约束及 DQL 的效率优化,为数据库学习与实践奠定基础。
|
7月前
|
SQL 人工智能 数据可视化
16.1k star! 只需要DDL就能一键生成数据库关系图!开源神器ChartDB让你的数据结构"看得见"
ChartDB是一款开源的数据库可视化神器,通过一句智能查询就能自动生成专业的数据库关系图。无需安装客户端、不用暴露数据库密码,打开网页就能完成从数据建模到迁移的全流程操作,堪称开发者的"数据库透视镜"。
1510 67
|
6月前
|
关系型数据库 MySQL Linux
实现MySQL数据库的定时自动备份脚本。
拿走,不谢,这个脚本配方(指引)保证你的数据库数据像蛋糕店一样地天天更新,还能确保老旧的蛋糕(数据)不会堆积满仓库。这下可好,数据安全有保障,数据库管理员也能轻松一点,偶尔闲下来的时候,煮杯咖啡,看个剧岂不美哉?别忘了偶尔检查一下你的自动备份是否正常工作,以防万一蛋糕机器出了点小差错。
313 20
|
5月前
|
SQL 存储 关系型数据库
一、数据库和表的基本操作 DDL
在使用 MySQL 做项目或写业务逻辑时,离不开对数据库和数据表的基本操作。我们这次从创建数据库讲起,一步步带你掌握如何新建表、查看表结构、修改字段、重命名、删除等常用命令。每一个知识点都有示例代码可直接上手,还准备了一套完整的动手练习,帮助你把概念变成熟练技能。如果你刚入门 SQL,或者想系统梳理一遍 DDL 基础,这篇会是不错的起点。
357 1
|
7月前
|
Java 数据库
jsp CRM客户管理系统(含数据库脚本以及文档)
jsp CRM客户管理系统(含数据库脚本以及文档)
156 10
|
7月前
|
Java 关系型数据库 MySQL
Java汽车租赁系统源码(含数据库脚本)
Java汽车租赁系统源码(含数据库脚本)
158 4
|
8月前
|
关系型数据库 Shell 网络安全
定期备份数据库:基于 Shell 脚本的自动化方案
本篇文章分享一个简单的 Shell 脚本,用于定期备份 MySQL 数据库,并自动将备份传输到远程服务器,帮助防止数据丢失。
|
关系型数据库 MySQL 数据库连接
python脚本:连接数据库,检查直播流是否可用
【10月更文挑战第13天】本脚本使用 `mysql-connector-python` 连接MySQL数据库,检查 `live_streams` 表中每个直播流URL的可用性。通过 `requests` 库发送HTTP请求,输出每个URL的检查结果。需安装 `mysql-connector-python` 和 `requests` 库,并配置数据库连接参数。
261 68
|
8月前
|
SQL 关系型数据库 数据库连接

热门文章

最新文章