mybatis批量插入、批量更新常規寫法,及升級寫法
null value in column “xxx” violates not-null constraint mybatis批量操作報錯問題處理
批量插入
- 常規寫法
<insert id="insertUser" parameterType="com.test.UserEntity">
insert into t_com_user(user_name, age, gender)
values
<foreach collection ="list" item="item" index="index" open="(" close= ")" separator= "),(">
#{item.userName, jdbcType=VARCHAR},
#{item.age, jdbcType=INTEGER},
#{item.gender, jdbcType=INTEGER}
</foreach>
</insert>
假如我們在批量插入數據的時候,還想做一下關聯查詢,該怎麼辦?
如下寫法,免去了先查詢數據,然後遍歷list賦值,再批量插入的操作
<insert id="insertUser" parameterType="com.test.UserEntity">
insert into t_com_user(user_name, age, gender, dept_name)
select
t1.user_name, t1.age, t1.gender, t2.dept_name
from (
VALUES
<foreach collection ="list" item="item" index="index" open="(" close= ")" separator= "),(">
#{item.userName, jdbcType=VARCHAR},
#{item.age, jdbcType=INTEGER},
#{item.gender, jdbcType=INTEGER},
#{item.deptId, jdbcType=INTEGER}
</foreach>
) as t1 (user_name, age, gender, dept_id)
left_join t_com_dept t2 on t1.dept_id = t2.id
</insert>
批量更新
- 常規寫法
這種寫法實際執行過程是單條執行,即使使用的是id查找數據,但是效率較差
<update id="updateUser" parameterType="com.test.UserEntity">
<foreach collection ="list" item="item" index="index" separator= ";">
update t_com_user set
user_name = #{item.userName, jdbcType=VARCHAR},
age = #{item.age, jdbcType=INTEGER},
gender = #{item.gender, jdbcType=INTEGER}
where id = #{item.id, jdbcType=INTEGER}
</foreach>
</update>
- 升級寫法:參考批量插入操作,使用連表更新的語法
<update id="updateUser" parameterType="com.test.UserEntity">
update t_com_user t1 set
user_name = t2.user_name,
age = t2.age,
gender = t2.gender
from (
values
<foreach collection ="list" item="item" index="index" open="(" close= ")" separator= "),(">
#{item.id, jdbcType=INTEGER},
#{item.userName, jdbcType=VARCHAR},
#{item.age, jdbcType=INTEGER},
#{item.gender, jdbcType=INTEGER}
</foreach>
) as t2 (id, user_name, age, gender)
where t1.id = t2.id
</update>
ERROR: null value in column “user_name” violates not-null constraint mybatis 批量操作報錯問題處理
mybatis的批量操作過程,傳入的list對象集合中,對象的某個屬性難免會爲null,如果數據庫表該列恰好有not-null限制,則會報錯;處理辦法,本文以pgsql的批量更新爲例,親測可行:
方法一:
使用COALESCE(#{item.userName, jdbcType=VARCHAR}, '默認名稱')
或者:user_name = COALESCE(t2.user_name, '默認名稱')
二選一即可
<update id="updateUser" parameterType="com.test.UserEntity">
update t_com_user t1 set
user_name = COALESCE(t2.user_name, '默認名稱'),
age = t2.age,
gender = t2.gender
from (
values
<foreach collection ="list" item="item" index="index" open="(" close= ")" separator= "),(">
#{item.id, jdbcType=INTEGER},
COALESCE(#{item.userName, jdbcType=VARCHAR}, '默認名稱'),
#{item.age, jdbcType=INTEGER},
#{item.gender, jdbcType=INTEGER}
</foreach>
) as t2 (id, user_name, age, gender)
where t1.id = t2.id
</update>
mysql 使用IFNULL函數 pgsql 使用COALESCE函數
方法二:
在foreach中使用if標籤判斷
<if test= "item.userName != null">
#{item.userName, jdbcType=VARCHAR}
</if>
<if test= "item.userName == null">
'默認名稱'
</if>
Oracle mysql下,不支持 from (value (),()) as t 的寫法;可以參考
select * from (
select 1, '張三' from dual union
select 2, '李四' from dual
) t
整理編寫不易,覺得作者寫的好,麻煩給個贊!