最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

mybatis-plus如何根據(jù)任意字段saveOrUpdateBatch

 更新時(shí)間:2025年09月01日 08:57:54   作者:孤海島主  
MyBatisPlus saveOrUpdateBatch默認(rèn)按主鍵判斷操作類型,若需按其他唯一字段(如agentId、period、type組合)判斷,需在service層重寫方法,通過(guò)predicate定義插入條件并結(jié)合consumer執(zhí)行更新邏輯,適用于批量和單條數(shù)據(jù)操作場(chǎng)景

使用場(chǎng)景

mybatisplus Iservice接口下的saveOrUpdateBatch方法默認(rèn)是根據(jù)主鍵來(lái)決定是要更新還是插入的,

如果要根據(jù)其他字段(必須是唯一約束,唯一約束字段可以是多個(gè))更新的話,則需要在項(xiàng)目的service層重寫該方法。

方法源碼

@Transactional(
        rollbackFor = {Exception.class}
    )
    public boolean saveOrUpdateBatch(Collection<T> entityList, int batchSize) {
        TableInfo tableInfo = TableInfoHelper.getTableInfo(this.entityClass);
        Assert.notNull(tableInfo, "error: can not execute. because can not find cache of TableInfo for entity!", new Object[0]);
        String keyProperty = tableInfo.getKeyProperty();
        Assert.notEmpty(keyProperty, "error: can not execute. because can not find column for id from entity!", new Object[0]);
        return SqlHelper.saveOrUpdateBatch(this.entityClass, this.mapperClass, this.log, entityList, batchSize, (sqlSession, entity) -> {
            Object idVal = ReflectionKit.getFieldValue(entity, keyProperty);
            return StringUtils.checkValNull(idVal) || CollectionUtils.isEmpty(sqlSession.selectList(this.getSqlStatement(SqlMethod.SELECT_BY_ID), entity));
        }, (sqlSession, entity) -> {
            MapperMethod.ParamMap<T> param = new MapperMethod.ParamMap();
            param.put("et", entity);
            sqlSession.update(this.getSqlStatement(SqlMethod.UPDATE_BY_ID), param);
        });
    }

從源碼中可以看出實(shí)現(xiàn)saveOrUpdateBatch的主要方法就是SqlHelper.saveOrUpdateBatch

public static <E> boolean saveOrUpdateBatch(Class<?> entityClass, Class<?> mapper, Log log, Collection<E> list, int batchSize, BiPredicate<SqlSession, E> predicate, BiConsumer<SqlSession, E> consumer) {
        String sqlStatement = getSqlStatement(mapper, SqlMethod.INSERT_ONE);
        return executeBatch(entityClass, log, list, batchSize, (sqlSession, entity) -> {
            if (predicate.test(sqlSession, entity)) {
                sqlSession.insert(sqlStatement, entity);
            } else {
                consumer.accept(sqlSession, entity);
            }

        });
    }

該方法的最后兩個(gè)參數(shù)predicate,consumer

predicate 這個(gè)函數(shù)是用于判斷是否要進(jìn)行插入操作 true插入,false:則通過(guò)consumer 函數(shù)執(zhí)行更新

方法改造

注意:寫在項(xiàng)目操作對(duì)應(yīng)表的service層

首先在service層定義接口

boolean saveOrUpdateBatchByAgentIdAndPeriodAndType(List<Entity> list);

類為數(shù)據(jù)庫(kù)表對(duì)應(yīng)的實(shí)體類,agentId,period,type,這個(gè)三個(gè)字段為表的唯一約束,即當(dāng)表中存在這三個(gè)字段組合對(duì)應(yīng)的記錄時(shí)則進(jìn)行更新操作,不存在則進(jìn)行插入操作

service層接口實(shí)現(xiàn)

@Transactional(rollbackFor = Exception.class)
    @DS("XXXX")//如果為多數(shù)據(jù)源,這里要指明具體操作的數(shù)據(jù)源名稱
    public boolean saveOrUpdateBatchByAgentIdAndPeriodAndType(List<Entity> list) {

        return SqlHelper.saveOrUpdateBatch(entityClass, this.mapperClass, super.log, list, DEFAULT_BATCH_SIZE, (sqlSession, entity) -> {//這里主要是查詢唯一約束對(duì)應(yīng)的記錄是否存在
            LambdaQueryWrapper<Entity> queryWrapper = Wrappers.<Entity>lambdaQuery()
                    .eq(Entity::getAgentId, entity.getAgentId()).eq(Entity::getPeriod,entity.getPeriod())
                    .eq(Entity::getType,entity.getType());
            Map<String, Object> map = CollectionUtils.newHashMapWithExpectedSize(1);
            map.put(Constants.WRAPPER, queryWrapper);
            return CollectionUtils.isEmpty(sqlSession.selectList(getSqlStatement(SqlMethod.SELECT_LIST), map));
        }, (sqlSession, entity) -> {
            LambdaUpdateWrapper<Entity> lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
            lambdaUpdateWrapper.eq(Entity::getAgentId, entity.getAgentId()).eq(Entity::getPeriod,entity.getPeriod())
                    .eq(Entity::getType,entity.getType());
            Map<String, Object> param = CollectionUtils.newHashMapWithExpectedSize(2);
            param.put(Constants.ENTITY, entity);
            param.put(Constants.WRAPPER, lambdaUpdateWrapper);
            sqlSession.update(getSqlStatement(SqlMethod.UPDATE), param);
        });
    }

非批量的saveOrUpdate也可以按照這種方式進(jìn)行改造

總結(jié)

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

相關(guān)文章

  • Java中把一個(gè)文件夾下的所有文件復(fù)制到另一個(gè)文件夾的完整實(shí)現(xiàn)方案

    Java中把一個(gè)文件夾下的所有文件復(fù)制到另一個(gè)文件夾的完整實(shí)現(xiàn)方案

    這篇文章主要介紹了如何使用Java原生API實(shí)現(xiàn)文件夾復(fù)制,支持多級(jí)目錄、空文件夾和文件覆蓋等場(chǎng)景,并提供了基于File和FileChannel的實(shí)現(xiàn)方案,此外,還介紹了使用Java 7的Files工具類進(jìn)行簡(jiǎn)化實(shí)現(xiàn),需要的朋友可以參考下
    2026-01-01
  • Spring裝配Bean之用Java代碼安裝配置bean詳解

    Spring裝配Bean之用Java代碼安裝配置bean詳解

    這篇文章主要給大家介紹了關(guān)于Spring裝配Bean之用Java代碼安裝配置bean的相關(guān)資料,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家學(xué)習(xí)或者使用spring具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來(lái)一起學(xué)習(xí)學(xué)習(xí)吧。
    2017-10-10
  • 基于javamelody監(jiān)控springboot項(xiàng)目過(guò)程詳解

    基于javamelody監(jiān)控springboot項(xiàng)目過(guò)程詳解

    這篇文章主要介紹了基于javamelody監(jiān)控springboot項(xiàng)目過(guò)程詳解,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2019-11-11
  • SpringMVC實(shí)現(xiàn)全局異常處理器的經(jīng)典案例

    SpringMVC實(shí)現(xiàn)全局異常處理器的經(jīng)典案例

    文章介紹了如何使用@ControllerAdvice和相關(guān)注解實(shí)現(xiàn)SpringMVC的全局異常處理,通過(guò)統(tǒng)一的異常處理類和自定義業(yè)務(wù)異常類,可以將所有控制器的異常集中處理,并以JSON格式返回給前端,感興趣的朋友一起看看吧
    2025-03-03
  • Java指令重排在多線程環(huán)境下的解決方式

    Java指令重排在多線程環(huán)境下的解決方式

    這篇文章介紹了Java指令重排在多線程環(huán)境下的解決方式,文中通過(guò)示例代碼介紹的非常詳細(xì)。對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2022-04-04
  • 詳解SpringBoot中META-INF的作用與功能

    詳解SpringBoot中META-INF的作用與功能

    SpringBoot開發(fā)的應(yīng)用程序中,META-INF目錄扮演著非常重要的角色,本文就來(lái)介紹一下 META-INF的作用及用處,具有一定的參考價(jià)值,感興趣的可以了解一下
    2025-07-07
  • SpringBoot + 微信公眾號(hào)JSAPI支付功能的實(shí)現(xiàn)

    SpringBoot + 微信公眾號(hào)JSAPI支付功能的實(shí)現(xiàn)

    這篇文章主要介紹了SpringBoot + 微信公眾號(hào)JSAPI支付功能的實(shí)現(xiàn),本文通過(guò)實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2021-03-03
  • Spring Boot 訪問(wèn)安全之認(rèn)證和鑒權(quán)詳解

    Spring Boot 訪問(wèn)安全之認(rèn)證和鑒權(quán)詳解

    這篇文章主要介紹了Spring Boot 訪問(wèn)安全之認(rèn)證和鑒權(quán),具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2021-11-11
  • Java判斷字符串是否在List中的方案詳解(忽略大小寫)

    Java判斷字符串是否在List中的方案詳解(忽略大小寫)

    對(duì)于需要頻繁調(diào)用且數(shù)據(jù)量大的情況,有幾種優(yōu)化方案可以選擇,下面給大家分享三種方案給大家詳細(xì)介紹java字符串判斷是否在list中,感興趣的朋友一起看看吧
    2025-05-05
  • MyBatis-Plus聯(lián)表查詢及分頁(yè)代碼舉例

    MyBatis-Plus聯(lián)表查詢及分頁(yè)代碼舉例

    本文介紹了mybatis-plus-join工具的使用,該工具可以簡(jiǎn)化mybatis-plus的聯(lián)表查詢,使得開發(fā)者可以以類似QueryWrapper的方式進(jìn)行聯(lián)表查詢,無(wú)需手動(dòng)編寫xml文件,感興趣的朋友跟隨小編一起看看吧
    2025-03-03

最新評(píng)論

长武县| 汉沽区| 原阳县| 宝坻区| 霍林郭勒市| 平江县| 印江| 富蕴县| 蒙城县| 西乌珠穆沁旗| 贡觉县| 安塞县| 南岸区| 抚宁县| 织金县| 宜昌市| 邵武市| 北京市| 伊吾县| 许昌县| 西青区| 井研县| 佳木斯市| 中卫市| 监利县| 苏尼特右旗| 柳河县| 疏勒县| 丰顺县| 收藏| 昆明市| 诸暨市| 麻江县| 泗阳县| 汾阳市| 南昌县| 藁城市| 湛江市| 台东市| 平乐县| 巴里|