MyBatis在插入自增ID列有值情况下的处理

我们有个功能大意是这样的:

有个实体,对应的表中有个ID 列是从 SEQUENCE 里取值的,本地页面操作导致数据的插入就从 SEQUENCE 取值赋给 ID。如果是第三方通过 REST 操作本应用资源导致的数据插入(此时的数据的ID列是有值的,但是能够保证绝不会和本地的 ID 值重复。),接口应当也要满足。即需要持久层对应用透明。

我们使用的是 MyBatis 做 ORM 的,所以 insert 语句使用了 <selectKey>,写法如下:

<selectKey keyProperty="id" order="BEFORE" resultType="long">        
	select ADVANCED_VARIABLE_SEQ.nextval from dual			
</selectKey>

我们就在 selectKey 块里面加上判断,如果 ID 有值,就直接使用,不从 SEQUENCE 里拿。

<insert id="insert" parameterType="com.hebta.vinci.model.AdvancedVariable">
	<selectKey keyProperty="id" order="BEFORE" resultType="long">
		 <choose>
			<when test="id == null">
				select ADVANCED_VARIABLE_SEQ.nextval from dual
			</when>
			<when test="id != null">
				select #{id,jdbcType=BIGINT} from dual
			</when>
		</choose>
	</selectKey>
	insert into ADVANCED_VARIABLE (ID, ADVANCED_ANALYSIS_ID, VAR_NAME, 
	  VAR_TYPE, QUERY, NOTE)
	values (#{id,jdbcType=BIGINT}, #{advancedAnalysisId,jdbcType=BIGINT}, #{varName,jdbcType=VARCHAR}, 
	  #{varType,jdbcType=VARCHAR}, #{query,jdbcType=VARCHAR}, #{note,jdbcType=VARCHAR})
</insert>

这个对单个的 insert 语句是管用的。但是对于 batchInsert 语句,其写法和原理如  mybatis使用foreach批次插入,解决sequence只查询一次的问题  所说,我们无法在 <foreach> 块外获得当前的 ID 列值。带有 SEQUENCE 的 batchInsert 的简单写法如下也是一样。

<insert id="insertAll" parameterType="java.util.List">
   insert into COHORT_VARIABLE
	select COHORT_VAR_SEQUENCE.NEXTVAL, A.* from (
	<foreach collection="list" index="index" item="item" separator="UNION">
		SELECT
			#{item.advancedAnalysisId,jdbcType=BIGINT},
			#{item.varName,jdbcType=VARCHAR},
			#{item.varType,jdbcType=VARCHAR},
			#{item.query,jdbcType=VARCHAR},
			#{item.note,jdbcType=VARCHAR}
		from dual 
	</foreach> ) A
</insert>

有个解决办法,就是在业务层判断一下List 里面的对象的 ID 是否有值,没有就使用 SEQUENCE 插入,否则就用普通的 batchInsert 语句。



  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值