Spring Boot 中批量执行 SQL 脚本的实践

在Spring Boot应用中,有时候我们需要批量执行存储在数据库中的 SQL 脚本。本文将介绍一个实际的案例,演示如何通过 Spring Boot、MyBatis 和数据库来实现这一目标。

0、数据库层

CREATE TABLE batchUpdate (

    id INT AUTO_INCREMENT PRIMARY KEY,
    update_type VARCHAR(255) NOT NULL,
    success_flag BOOLEAN NOT NULL,
    failure_count INT NOT NULL,
    execution_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    sql_script TEXT NOT NULL
);

  


-- 第一条数据

INSERT INTO `batch_update` (`update_type`, `success_flag`, `failure_count`, `update_count`, `sql_script`)

VALUES

('update_type_1', 0, 0, 0,

'UPDATE batch_update SET success_flag = 1, update_count = update_count + 1 WHERE update_type = ''update_type_1'';

UPDATE batch_update SET success_flag = 1, update_count = update_count + 1 WHERE update_type = ''update_type_1'';

UPDATE batch_update SET failure_count = failure_count + 1, update_count = update_count + 1 WHERE update_type = ''update_type_1'';');

  


-- 第二条数据

INSERT INTO `batch_update` (`update_type`, `success_flag`, `failure_count`, `update_count`, `sql_script`)

VALUES

('update_type_2', 0, 0, 0,

'UPDATE batch_update SET success_flag = 1, update_count = update_count + 1 WHERE update_type = ''update_type_2'';

UPDATE batch_update SET success_flag = 1, update_count = update_count + 1 WHERE update_type = ''update_type_2'';

UPDATE batch_update SET failure_count = failure_count + 1, update_count = update_count + 1 WHERE update_type = ''update_type_2'';');

  


-- 第三条数据

INSERT INTO `batch_update` (`update_type`, `success_flag`, `failure_count`, `update_count`, `sql_script`)

VALUES

('update_type_1', 0, 0, 0,

'UPDATE batch_update SET success_flag = 1, update_count = update_count + 1 WHERE update_type = ''update_type_1'';

UPDATE batch_update SET success_flag = 1, update_count = update_count + 1 WHERE update_type = ''update_type_1'';

UPDATE batch_update SET failure_count = failure_count + 1, update_count = update_count + 1 WHERE update_type = ''update_type_1'';');

  


-- 第四条数据

INSERT INTO `batch_update` (`update_type`, `success_flag`, `failure_count`, `update_count`, `sql_script`)

VALUES

('update_type_2', 0, 0, 0,

'UPDATE batch_update SET success_flag = 1, update_count = update_count + 1 WHERE update_type = ''update_type_2'';

UPDATE batch_update SET success_flag = 1, update_count = update_count + 1 WHERE update_type = ''update_type_2'';

UPDATE batch_update SET failure_count = failure_count + 1, update_count = update_count + 1 WHERE update_type = ''update_type_2'';');

1. 控制器层(Controller)

@RestController
@RequestMapping("/batchUpdate")
@AllArgsConstructor
public class BatchUpdateController {

    private BatchUpdateService batchUpdateService;

    @PostMapping("/executeScript/{updateType}")
    public String executeScript(@PathVariable String updateType) {
        List<BatchUpdateEntity> batchUpdateEntities = batchUpdateService.findByUpdateType(updateType);

        if (batchUpdateEntities.isEmpty()) {
            return "Update type not found.";
        }

        for (BatchUpdateEntity batchUpdateEntity : batchUpdateEntities) {
            batchUpdateService.executeSqlScriptBatch(batchUpdateEntity);
        }

        return "SQL scripts executed successfully.";
    }
}

2. 服务层(Service)

javaCopy code
@Service
@AllArgsConstructor
public class BatchUpdateService {

    private BatchUpdateMapper batchUpdateMapper;

    public List<BatchUpdateEntity> findByUpdateType(String updateType) {
        return batchUpdateMapper.findByUpdateType(updateType);
    }

    public void executeSqlScriptBatch(BatchUpdateEntity batchUpdateEntity) {
        String sqlScript = batchUpdateEntity.getSqlScript();
        List<String> sqlScripts = Arrays.stream(sqlScript.split(";"))
                .map(String::trim)
                .filter(s -> !s.isEmpty())
                .toList();
        System.out.println(sqlScripts.size());
        sqlScripts.forEach(sql -> {
            System.out.println("要执行的sql:" + sql);
            batchUpdateMapper.executeSqlScript(sql);
            System.out.println("已执行的sql:" + sql);
        });
    }
}

3. 数据访问层(Mapper)

@Mapper
public interface BatchUpdateMapper {

    List<BatchUpdateEntity> findByUpdateType(@Param("updateType") String updateType);
    void executeSqlScript(@Param("sql") String sql);
}

4. MyBatis 配置文件(BatchUpdateMapper.xml)

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.lfsun.sqlscript.BatchUpdateMapper">

    <resultMap id="BatchUpdateEntityResultMap" type="com.lfsun.sqlscript.BatchUpdateEntity">
        <id property="id" column="id" />
        <result property="updateType" column="update_type" />
        <result property="successFlag" column="success_flag" />
        <result property="failureCount" column="failure_count" />
        <result property="executionTime" column="execution_time" />
        <result property="sqlScript" column="sql_script" />
    </resultMap>

    <select id="findByUpdateType" resultMap="BatchUpdateEntityResultMap">
        SELECT * FROM batch_update WHERE update_type = #{updateType}
    </select>
    <update id="executeSqlScript">
        ${sql}
    </update>
</mapper>

image.png

image.png

通过这个案例,可以学到如何在 Spring Boot 中通过 MyBatis 实现批量执行 SQL 脚本的功能。在控制器层中,我们通过 @PostMapping 注解定义了一个接口,接收 updateType 作为路径参数,然后调用服务层的方法。服务层中,我们通过 MyBatis 执行 SQL 脚本,实现了对数据库的批量操作。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/312116.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

策略模式-实践

俗话说&#xff1a;条条大路通罗马。在很多情况下&#xff0c;实现某个目标的途径不止一条&#xff0c;例如我们在外出 旅游时可以选择多种不同的出行方式&#xff0c;如骑自行车、坐汽车、坐火车或者坐飞机&#xff0c;可根据实 际情况&#xff08;目的地、旅游预算、旅游时间…

vue2 el-table行悬停时弹出提示信息el-popover

实现方法&#xff0c;用到了cell-mouse-enter、cell-mouse-leave两个事件&#xff0c;然后在表格的首列字段中&#xff0c;加个el-popover组件&#xff0c;当然你也可以选择在其他字段的位置来显示提示框&#xff0c;看自己的需求了。 示例代码&#xff1a; <el-table cell…

每日coding

2645、构造有效字符串的最少插入数 给你一个字符串 word &#xff0c;你可以向其中任何位置插入 "a"、"b" 或 "c" 任意次&#xff0c;返回使 word 有效 需要插入的最少字母数。 如果字符串可以由 "abc" 串联多次得到&#xff0c;则认…

【HarmonyOS4.0】第九篇-ArkUI布局容器组件(一)

容器组件指的是它可以包含一个或多个子组件的组件&#xff0c;除了前边介绍过的公共属性外。 一、线性布局容器&#xff08;Row、Column&#xff09; 线性容器类表示按照水平方向或者竖直方向排列子组件的容器&#xff0c;ArkUI开发框架通过 Row 和 Colum 来实现线性布局。 …

Web3与物联网:去中心化设备互联的未来

Web3技术的崛起正引领着数字世界向着更加开放、去中心化的方向迈进&#xff0c;而物联网&#xff08;Internet of Things, IoT&#xff09;作为连接实体世界的桥梁&#xff0c;也在这场变革中经历着深刻的改变。本文将深入探讨Web3技术如何与物联网相结合&#xff0c;构建去中心…

【椒盐玉兔】GPTs Store 商店的TOP100 自定义GPT使用报告

详细的图文报告有100张图&#xff0c;因为太长就放网盘链接 链接&#xff1a;百度网盘 请输入提取码 提取码&#xff1a;ub2n 解压密码&#xff1a;heehel 更多作品&#xff1a;长期更新国内外&#xff0c;中英文AI人工智能作品 整理获取 通过算法&#xff0c;筛选出了目前访…

天津港强集团携手黄向墨创立的玉湖冷链 头部企业加强交流合作

玉湖集团是总部设于香港的有二十多年历史的跨国实业投资集团&#xff0c;由祖籍广东的香港企业家、著名爱国侨领黄向墨先生创立。黄向墨先生现任中国和平统一促进会常务理事、中华海外联谊会常务理事、香港选委会委员及香港全国人大代表选举会议成员。 新年第一天&#xff0c;…

Java:常见算法

认识算法 什么是算法&#xff1f; 解决某个实际问题的过程和方法 学习算法的技巧 先搞清楚算法的流程直接去推敲如何写代码 排序算法 冒泡排序 每次从数组中找出最大值放在数组的后面去。 实现冒泡排序的关键步骤分析 确认总共需要做几轮&#xff1a;数组的长度-1每轮比较…

Logback框架基本认识

文章目录 一.什么是Logback1.1 初识Logbcak 二.Logbcak的结构三.日志的级别四.配置组件详解4.1 logger 日志记录器属性的介绍如何在配置文件里配置 4.2 appender 附加器 配合日志记录器的输出格式4.2.1 控制台附加器4.2.2 文件附加器4.3.3滚动文件附加器 4.3 Filter: 过滤器&am…

【分布式微服务专题】从单体到分布式(四、SpringCloud整合Sentinel)

目录 前言阅读对象阅读导航前置知识一、什么是服务雪崩1.1 基本介绍1.2 解决方案 二、什么是Sentinel2.1 基本介绍2.2 设计目的2.3 基本概念 三、Sentinel 功能和设计理念3.1 流量控制3.2 熔断降级3.3 系统负载保护 四、Sentinel 是如何工作的 笔记正文一、简单整合Sentinel1.1…

计算机毕业设计-----SSH高校科研管理系统平台

项目介绍 本项目包含超级管理员、管理员、教师三种角色&#xff1b; 超级管理员角色包含以下功能&#xff1a; 登录,教师管理,管理员管理等功能。 管理员角色包含以下功能&#xff1a; 登录,专业参赛奖项管理,科技论文发表管理,出版专业著作管理,科研项目立项管理,科研项目结…

qt初入门3:文件,目录,临时文件,监视相关demo

参考qt的书籍demo&#xff0c;做练习 目录和文件相关操作&#xff1a; QCoreApplication类 主要处理获取app所在目录&#xff0c;路径&#xff0c;app名称&#xff0c;lib库路径等。 QFile类 主要实现文件拷贝&#xff0c;校验存在&#xff0c;删除&#xff0c;重命名&#xf…

Open CASCADE学习|参数化球面的奇异性

参数曲面的奇异性是一个相对复杂的概念&#xff0c;它涉及到参数曲面的几何特性和参数化过程中的一些特殊情况。参数曲面通常用于描述三维空间中的复杂形状&#xff0c;通过参数方程将二维参数域映射到三维空间中。然而&#xff0c;在某些情况下&#xff0c;参数曲面可能会表现…

ROS2学习笔记三:话题Topic

目录 前言 1 话题简介 2 常用指令 3 RCLCPP实现实现话题 3.1 创建工作空间 3.2 代码编写 3.2.1 发布端编写 3.2.2 发布端编写 前言 ROS2中的一个重要概念是话题&#xff08;Topic&#xff09;。话题是一种通过发布者和订阅者之间进行异步通信的机制。发布者&#xff0…

TiDB 在全球头部物流企业计费管理系统的应用实践

本文介绍了某全球头部物流企业采用 TiDB 解决计费管理系统性能瓶颈的实践。原系统采用的云数据库受限于架构而无法水平扩展&#xff0c;导致高并发性能问题。该企业通过选择 TiDB&#xff0c;成功打破了性能瓶颈&#xff0c;实现了无缝水平扩展&#xff0c;降低了开发和运维负担…

SpringIOC之support模块GenericXmlApplicationContext

博主介绍&#xff1a;✌全网粉丝5W&#xff0c;全栈开发工程师&#xff0c;从事多年软件开发&#xff0c;在大厂呆过。持有软件中级、六级等证书。可提供微服务项目搭建与毕业项目实战&#xff0c;博主也曾写过优秀论文&#xff0c;查重率极低&#xff0c;在这方面有丰富的经验…

内网穿透的应用-使用Docker部署开源建站工具—Halo,并实现个人博客公网访问

文章目录 1. Docker部署Halo1.1 检查Docker版本如果未安装Docker可参考已安装Docker步骤&#xff1a;1.2 在Docker中部署Halo 2. Linux安装Cpolar2.1 打开服务器防火墙2.2 安装cpolar内网穿透 3. 配置Halo个人博客公网地址4. 固定Halo公网地址 本篇文章介绍如何在CentOS下使用D…

详解java中ArrayList

目录 前言 一、ArrayList是什么 二、ArrayList使用 1、ArrayList的构造 2 、ArrayList常见操作 3、 ArrayList的遍历 4、 ArrayList的扩容机制 三、来个练习 前言 当你看到这篇文章我觉得很好笑&#xff0c;因为我开始也不懂ArrayList现在轮到你了&#xff0c;嘻嘻嘻&am…

ChatGPT新出Team号 年付费

之前一直传的团队版ChatGPT终于来了&#xff0c;这个对拼单的比较合算。每人每月25美元&#xff0c;只能按年支付。 团队版比普通版多的权益有&#xff1a; ◈更多的GPT-4消息上限&#xff0c;三小时100次。 ◈可以创建与团队内部共享的GPTs。 ◈用于工作空间管理的管理员控…

【深度学习:视觉基础模型】视觉基础模型 (VFM) 解释

【深度学习&#xff1a;视觉基础模型】视觉基础模型 VFM 解释 了解视觉基础模型从 CNN 到 Transformer 的演变自我监督和适应能力 流行的视觉基础模型DINO&#xff08;自蒸馏&#xff0c;无标签&#xff09;SAM&#xff08;分段任意模型&#xff09;SegGPTMicrosofts Visual Ch…