mybatis调用MySQL存储过程

本文介绍了一种使用MySQL实现的序列生成方案,通过建立专门的表和函数来生成唯一递增的序列号,适用于需要大量自增ID的场景。此外,还提供了一个MyBatis的XML映射文件示例,用于序列号的生成。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

一、建表
CREATE TABLE test.t_sequence (
  name varchar(50) NOT NULL COMMENT 'sequence名称',
  currentvalue bigint(20) NOT NULL COMMENT 'sequence当前值',
  increment int(10) NOT NULL COMMENT 'sequence每次增长的步长',
  PRIMARY KEY (name),
  UNIQUE INDEX pk_sequence (name)
)
ENGINE = INNODB
CHARACTER SET utf8
COLLATE utf8_general_ci;

二、创建函数
CREATE DEFINER = 'root'@'localhost'
FUNCTION test. currval(seq_name varchar(50))
  RETURNS bigint(20)
  DETERMINISTIC
begin
    select currentvalue into @val
        from t_sequence
        where name = seq_name;
    return @val;
end

CREATE DEFINER = 'root'@'localhost'
FUNCTION test. nextval(seq_name varchar(50))
  RETURNS bigint(20)
  DETERMINISTIC
BEGIN
  UPDATE t_sequence
  SET currentvalue = currentvalue + increment
  WHERE name = seq_name;
  RETURN currval(seq_name);
END

CREATE DEFINER = 'root'@'localhost'
FUNCTION test. setval(seq_name varchar(50),val integer)
  RETURNS bigint(20)
  DETERMINISTIC
begin
    update t_sequence
        set currentvalue = val
    where name = seq_name;
    return val;
end

CREATE DEFINER = 'root'@'localhost'
FUNCTION test. gen_id(seq_name varchar(100),source varchar(100),yearmonth varchar(6),dbtype varchar(3))
  RETURNS varchar(200) CHARSET utf8
BEGIN
    RETURN CONCAT(source,CONCAT(IFNULL(NULL,EXTRACT(YEAR_MONTH FROM NOW())),CONCAT(nextval(seq_name))),dbtype);
END

三、SequenceMapper.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="testwebapp.com.wangzuojia.dao.SequenceMapper" >
  <resultMap id="BaseResultMap" type="testwebapp.com.wangzuojia.entity.Sequence" >
    <id column="name" property="name" jdbcType="VARCHAR" />
    <result column="currentvalue" property="currentvalue" jdbcType="BIGINT" />
    <result column="increment" property="increment" jdbcType="INTEGER" />
  </resultMap>
  <select id="generateId" parameterType="java.util.Map"
        statementType="CALLABLE">
        {#{result,jdbcType=VARCHAR,mode=OUT} = call  gen_id(
        #{seq_name,jdbcType=VARCHAR,mode=IN},
        #{source,jdbcType=VARCHAR,mode=IN},
        #{yearmonth,jdbcType=VARCHAR,mode=IN},
        #{dbtype,jdbcType=VARCHAR,mode=IN})}
    </select>
  <insert id="insert" parameterType="testwebapp.com.wangzuojia.entity.Sequence" >
    insert into t_sequence (name, currentvalue, increment
      )
    values (#{name,jdbcType=VARCHAR}, #{currentvalue,jdbcType=BIGINT}, #{increment,jdbcType=INTEGER}
      )
  </insert>
  
</mapper>
### MyBatis 调用 MySQL 存储过程的示例 在 MyBatis调用 MySQL 存储过程需要定义存储过程的参数类型(如 `IN`、`OUT` 或 `INOUT`),并在 XML 映射文件中正确配置。以下是一个完整的示例,展示如何使用 MyBatis 调用 MySQL 存储过程。 #### 1. 创建存储过程 假设我们有一个名为 `PROC_REGISTER` 的存储过程,用于注册用户并返回结果代码: ```sql CREATE PROCEDURE PROC_REGISTER(IN p_id VARCHAR(50), IN p_kind INT, OUT result_code INT) BEGIN -- 示例逻辑 IF EXISTS (SELECT 1 FROM users WHERE id = p_id) THEN SET result_code = 1; -- 用户已存在 ELSE INSERT INTO users(id, kind) VALUES(p_id, p_kind); SET result_code = 0; -- 成功注册 END IF; END; ``` #### 2. 配置 MyBatis Mapper 文件 在 MyBatis 的 Mapper 文件中,定义一个 `<select>` 标签来调用存储过程。以下是具体的 XML 配置: ```xml <select id="callProcRegister" parameterType="map" statementType="CALLABLE"> {call PROC_REGISTER(#{id,jdbcType=VARCHAR,mode=IN}, #{kind,jdbcType=INTEGER,mode=IN}, #{result,jdbcType=INTEGER,mode=OUT})} </select> ``` 上述配置中: - `parameterType="map"` 表示传入的参数是一个 `Map`。 - `statementType="CALLABLE"` 表明这是一个存储过程调用。 - `jdbcType` 和 `mode` 分别指定了参数的 JDBC 类型和模式(`IN`、`OUT` 或 `INOUT`)[^1]。 #### 3. 编写 Java 代码 在 Java 代码中,可以通过 `Mapper` 接口调用存储过程。以下是一个示例: ```java public interface UserMapper { void callProcRegister(@Param("id") String id, @Param("kind") int kind, @Param("result") Integer result); } @Service public class UserService { @Autowired private UserMapper userMapper; public int registerUser(String id, int kind) { Map<String, Object> params = new HashMap<>(); params.put("id", id); params.put("kind", kind); params.put("result", null); userMapper.callProcRegister(params.get("id"), (Integer) params.get("kind"), (Integer) params.get("result")); return (Integer) params.get("result"); // 返回结果代码 } } ``` #### 4. 添加依赖 确保项目中包含以下 Maven 依赖项以支持 MyBatisMySQL 连接: ```xml <dependency> <groupId>org.mybatis.spring.boot</groupId> <artifactId>mybatis-spring-boot-starter</artifactId> <version>2.1.4</version> </dependency> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>8.0.23</version> </dependency> ``` #### 5. 测试存储过程调用 可以编写单元测试验证存储过程是否正常工作。例如: ```java @SpringBootTest public class UserMapperTest { @Autowired private UserMapper userMapper; @Test public void testCallProcRegister() { Map<String, Object> params = new HashMap<>(); params.put("id", "test_user"); params.put("kind", 1); params.put("result", null); userMapper.callProcRegister((String) params.get("id"), (Integer) params.get("kind"), (Integer) params.get("result")); assertNotNull(params.get("result")); System.out.println("Result Code: " + params.get("result")); } } ``` ### 注意事项 - 确保数据库中的存储过程已正确创建,并且参数名称与类型匹配。 - 如果存储过程返回多个结果集,则需要在 MyBatis 中使用 `<resultMap>` 定义映射规则[^3]。 - 在 Spring Boot 项目中,建议使用 `@MapperScan` 注解扫描 Mapper 接口[^2]。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值