欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

mybatis-plus批量更新updateBatchById問題

 更新時(shí)間:2023年07月14日 10:38:52   作者:KevinPan_1992  
這篇文章主要介紹了mybatis-plus批量更新updateBatchById問題,具有很好的參考價(jià)值,希望對大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教

前言

在使用mybatis-plus過程中,有很多插件都特別優(yōu)秀,不僅使我們代碼更加優(yōu)雅,也提升了效率。

其中有個(gè)批量插入的插件insertBatchSomeColumn使用起來也挺方便的,但是批量更新一直沒有官方插件,網(wǎng)絡(luò)上面也沒有找到靠譜的,于是就參照mybatis-plus這些官方的方法自定義了一個(gè)批量更新的方法。

實(shí)現(xiàn)效果

案例:用戶排序

最終更新語句:

UPDATE sys_user 
SET user_order =
CASE
		id 
		WHEN 1 THEN	1 
		WHEN 2 THEN	2 
		WHEN 3 THEN	3 
		WHEN 4 THEN	4 
END 
WHERE tenant_id = 1 
AND id IN (1,2,3,4)

批量新增插件的配置

定義一個(gè)自己的BaseMapper繼承自mybatis-plus的BaseMapper,聲明批量新增方法,如下:

public interface MyBaseMapper<T> extends BaseMapper<T> {
    /**
     * 批量插入
     *
     * @param entityList 實(shí)體列表
     * @return 影響行數(shù)
     */
    int insertBatchSomeColumn(Collection<T> entityList);
}

把批量新增方法添加到方法列表中:

/**
 * 通用方法注入
 */
public class MySqlInjector extends DefaultSqlInjector {
    @Override
    public List<AbstractMethod> getMethodList(Class<?> mapperClass) {
        List<AbstractMethod> methodList = super.getMethodList(mapperClass);
        // 添加批量新增方法
        methodList.add(new InsertBatchSomeColumn());
        return methodList;
    }
}

MybatisPlusConfig配置中注入bean:

    @Bean
    public MySqlInjector mySqlInjector() {
        return new MySqlInjector();
    }

業(yè)務(wù)Mapper繼承自自定義的MyBaseMapper,則就可以使用批量新增方法了。

下面進(jìn)入正題

updateBatchById實(shí)現(xiàn)

自定義方法枚舉

參照官方的SqlMethod,創(chuàng)建枚舉MySqlMethod,并定義批量更新方法,如下:

public enum MySqlMethod {
    UPDATE_BATCH_BY_ID("updateBatchById", "通過主鍵批量更新數(shù)據(jù)", "<script>UPDATE %s \n%s \nWHERE %s IN %s\n</script>");
    private final String method;
    private final String desc;
    private final String sql;
    MySqlMethod(String method, String desc, String sql) {
        this.method = method;
        this.desc = desc;
        this.sql = sql;
    }
    public String getMethod() {
        return this.method;
    }
    public String getDesc() {
        return this.desc;
    }
    public String getSql() {
        return this.sql;
    }
}

自定義批量更新方法

定義UpdateBatchById繼承自AbstractMethod,實(shí)現(xiàn)其抽象方法injectMappedStatement,功能就是拼接sql,具體實(shí)現(xiàn)如下:

/**
 * 通過ID批量更新
 */
public class UpdateBatchById extends AbstractMethod {
    private static final long serialVersionUID = 4198102405483580486L;
    @Override
    public MappedStatement injectMappedStatement(Class<?> mapperClass, Class<?> modelClass, TableInfo tableInfo) {
        MySqlMethod sqlMethod = MySqlMethod.UPDATE_BATCH_BY_ID;
        String sql = String.format(sqlMethod.getSql(), tableInfo.getTableName(), this.sqlSet(tableInfo), tableInfo.getKeyColumn(), this.sqlIn(tableInfo.getKeyProperty()));
        SqlSource sqlSource = this.languageDriver.createSqlSource(this.configuration, sql, modelClass);
        return this.addUpdateMappedStatement(mapperClass, modelClass, sqlMethod.getMethod(), sqlSource);
    }
    private String sqlSet(TableInfo tableInfo) {
        List<TableFieldInfo> fieldList = tableInfo.getFieldList();
        StringBuilder sb = new StringBuilder();
        for (TableFieldInfo fieldInfo : fieldList) {
            sb.append("<if test=\"ew.updateFields.contains(&quot;").append(fieldInfo.getColumn()).append("&quot;)\">")
                    .append(fieldInfo.getColumn()).append(" =\n")
                    .append("CASE ").append(tableInfo.getKeyColumn()).append("\n")
                    .append("<foreach collection=\"list\" item=\"et\" >\n")
                    .append("WHEN #{et.").append(tableInfo.getKeyProperty()).append("} THEN #{et.").append(fieldInfo.getProperty()).append("}\n")
                    .append("</foreach>\n").append("END ,\n")
                    .append("</if>\n");
        }
        return "<set>\n" + sb + "</set>";
    }
    private String sqlIn(String keyProperty) {
        StringBuilder sb = new StringBuilder();
        sb.append("<foreach collection=\"list\" item=\"et\" separator=\",\" open=\"(\" close=\")\">\n")
                .append("#{et.").append(keyProperty).append("}")
                .append("</foreach>\n");
        return sb.toString();
    }
}

到了這一步已經(jīng)能夠基本實(shí)現(xiàn)功能了,但是無法控制需要更新的字段,繼續(xù)看下面。

自定義更新wrapper

自定義UpdateBatchWrapper繼承自AbstractLambdaWrapper,此類主要為updateFields屬性設(shè)置值,拼接sql的時(shí)候只對設(shè)置的屬性更新,其他屬性不變。

public class UpdateBatchWrapper<T> extends AbstractLambdaWrapper<T, UpdateBatchWrapper<T>> {
    private static final long serialVersionUID = 114684162001472707L;
    /**
     * 需要更新的字段
     */
    private List<String> updateFields = null;
    @Override
    protected UpdateBatchWrapper<T> instance() {
        this.updateFields = new ArrayList<>();
        return this;
    }
	/**
     * 關(guān)鍵代碼,為屬性設(shè)置值
     */
    @SafeVarargs
    public final UpdateBatchWrapper<T> setUpdateFields(SFunction<T, ?>... columns) {
        this.updateFields = Arrays.asList(columnsToString(columns).split(","));
        return this;
    }
    public List<String> getUpdateFields() {
        return updateFields;
    }
}

參照批量新增把方法添加到方法列表

MyBaseMapper增加配置:

 /**
     * 通過ID批量更新數(shù)據(jù)
     *
     * @param entityList 實(shí)體列表
     * @return 影響行數(shù)
     */
    int updateBatchById(@Param("list") Collection<T> entityList, @Param("ew") Wrapper<T> updateWrapper);

MySqlInjector增加配置:

// 添加批量更新方法
methodList.add(new UpdateBatchById());

測試updateBatchById

創(chuàng)建一個(gè)接口saveUserOrder實(shí)現(xiàn)用戶排序,進(jìn)而檢查批量更新方法。

controller層

    @PostMapping("saveUserOrder")
    @ApiOperation("用戶排序")
    public Result saveUserOrder(@RequestBody List<OrderUserSO> soList) {
        sysService.saveUserOrder(soList);
        return Result.success();
    }

service層

@Override
    public void saveUserOrder(List<OrderUserSO> soList) {
        // 業(yè)務(wù)實(shí)體轉(zhuǎn)換為數(shù)據(jù)庫實(shí)體
        List<SysUser> userList = JSONUtil.toList(JSONUtil.toJsonStr(soList), SysUser.class);
        // 批量更新-設(shè)置更新字段為userOrder
        sysUserMapper.updateBatchById(userList,
                new UpdateBatchWrapper<SysUser>()
                        .setUpdateFields(SysUser::getUserOrder));
    }

OrderUserSO實(shí)體

@Data
@ApiModel("用戶排序業(yè)務(wù)實(shí)體")
public class OrderUserSO implements Serializable {
    private static final long serialVersionUID = 509541044282315352L;
    @ApiModelProperty(value = "用戶ID", required = true)
    @NotNull
    private Integer id;
    @ApiModelProperty(value = "用戶順序", required = true)
    @NotNull
    private Integer userOrder;
}

見證奇跡的時(shí)刻到了…去文章開頭見證奇跡吧。

總結(jié)

以上為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。

相關(guān)文章

  • java中優(yōu)化大量if...else...方法總結(jié)

    java中優(yōu)化大量if...else...方法總結(jié)

    在我們平時(shí)的開發(fā)過程中,經(jīng)??赡軙霈F(xiàn)大量If else的場景,代碼顯的很臃腫,非常不優(yōu)雅,下面這篇文章主要給大家介紹了關(guān)于java中優(yōu)化大量if...else...方法的相關(guān)資料,需要的朋友可以參考下
    2023-03-03
  • springboot實(shí)現(xiàn)SSE(Server?Sent?Event)的示例代碼

    springboot實(shí)現(xiàn)SSE(Server?Sent?Event)的示例代碼

    SSE?全稱Server?Sent?Event,直譯一下就是服務(wù)器發(fā)送事件,本文主要為大家詳細(xì)介紹了springboot實(shí)現(xiàn)SSE的相關(guān)知識,需要的可以參考一下
    2024-04-04
  • Spring Boot2.0中SpringWebContext找不到無法使用的解決方法

    Spring Boot2.0中SpringWebContext找不到無法使用的解決方法

    這篇文章主要給大家介紹了關(guān)于Spring Boot2.0中SpringWebContext找不到無法使用的解決方法,文中通過示例代碼介紹的非常詳細(xì),需要的朋友可以參考借鑒,下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2018-12-12
  • java 如何實(shí)現(xiàn)正確的刪除集合中的元素

    java 如何實(shí)現(xiàn)正確的刪除集合中的元素

    這篇文章主要介紹了java 如何實(shí)現(xiàn)正確的刪除集合中的元素,具有很好的參考價(jià)值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2020-09-09
  • SpringBoot2線程池定義使用方法解析

    SpringBoot2線程池定義使用方法解析

    這篇文章主要介紹了SpringBoot2線程池定義使用方法解析,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-03-03
  • springboot注解Aspect實(shí)現(xiàn)方案

    springboot注解Aspect實(shí)現(xiàn)方案

    本文提供一種自定義注解,來實(shí)現(xiàn)業(yè)務(wù)審批操作的DEMO,不包含審批流程的配置功能。對springboot注解Aspect實(shí)現(xiàn)方案感興趣的朋友一起看看吧
    2022-01-01
  • springcloud3 Sentinel的搭建及案例操作方法

    springcloud3 Sentinel的搭建及案例操作方法

    Sentinel是分布式系統(tǒng)流量控制的哨兵,阿里開源的一套服務(wù)容錯(cuò)的綜合性解決方案,這篇文章主要介紹了springcloud3 Sentinel的搭建以及案例操作,需要的朋友可以參考下
    2023-01-01
  • Spring MVC保證Controller并發(fā)安全的方法小結(jié)

    Spring MVC保證Controller并發(fā)安全的方法小結(jié)

    在 Spring MVC 中,默認(rèn)情況下,@Controller 是單例的,這意味著所有請求共享一個(gè) Controller 實(shí)例,為確保并發(fā)安全,Spring 并不會自動對 Controller 進(jìn)行線程安全保護(hù),本文給大家介紹了Spring MVC保證Controller并發(fā)安全的方法,需要的朋友可以參考下
    2024-11-11
  • java實(shí)現(xiàn)注冊登錄系統(tǒng)

    java實(shí)現(xiàn)注冊登錄系統(tǒng)

    這篇文章主要為大家詳細(xì)介紹了java實(shí)現(xiàn)注冊登錄系統(tǒng),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2022-04-04
  • Java+Spring+MySql環(huán)境中安裝和配置MyBatis的教程

    Java+Spring+MySql環(huán)境中安裝和配置MyBatis的教程

    這篇文章主要介紹了Java+Spring+MySql環(huán)境中安裝和配置MyBatis的教程,MyBatis一般被用來增強(qiáng)數(shù)據(jù)庫操作,文中對MyBatis的主配置文件有較為詳細(xì)的講解,需要的朋友可以參考下
    2016-04-04

最新評論