詳解MyBatis如何在大數(shù)據(jù)量下使用流式查詢進(jìn)行數(shù)據(jù)同步
通常的數(shù)據(jù)同步中,如果數(shù)據(jù)量比較少的話可以直接全量同步,默認(rèn)情況下,完整的檢索結(jié)果集會(huì)將其存儲(chǔ)在內(nèi)存中。在大多數(shù)情況下,這是最有效的操作方式,并且由于 MySQL 網(wǎng)絡(luò)協(xié)議的設(shè)計(jì),因此更易于實(shí)現(xiàn)。但是如果數(shù)據(jù)量很大的話,全量同步需要大量的內(nèi)存,如果內(nèi)存不足的話則可能會(huì)導(dǎo)致內(nèi)存溢出。
通常的會(huì)采用分頁(yè)的方式,一批一批的同步,大體的實(shí)現(xiàn)方式如下:
int page = 1;
int pageNum = 1000;
while (true){
UserQueryRequest request = new UserQueryRequest();
request.setPage(page);
request.setPageSize(pageNum);
PageInfo<User> pageInfo = userMapper.getUserPage(request);
if (CollectionUtils.isEmpty(pageInfo.getList()) ){
break;
}
List<User> userList = pageInfo.getList();
// 具體的處理邏輯 省略
page ++;
}這種實(shí)現(xiàn)方式雖然可以實(shí)現(xiàn)分批同步,但是同步的數(shù)據(jù)必須先提供實(shí)現(xiàn)分頁(yè)的查詢方式,如果數(shù)據(jù)源是通過(guò)復(fù)雜的連表查詢來(lái)的,先實(shí)現(xiàn)一個(gè)分頁(yè)查詢更是會(huì)增加實(shí)現(xiàn)的復(fù)雜度。解決這個(gè)問(wèn)題可以使用一種更為優(yōu)雅的解決方式,即使用流失查詢。
流式查詢,會(huì)建立長(zhǎng)連接,利用服務(wù)端游標(biāo),每次讀取一條加載到 JVM 內(nèi)存,因此不會(huì)導(dǎo)致內(nèi)存溢出。
MyBatis 如何使用流式查詢:
配置mapper.xml文件:
<select id="selectUsers" resultType="User" fetchSize="1000"> SELECT userId from t_user </select>
自定義一個(gè)ResultHandler:
User是自定義的同步對(duì)象的實(shí)體對(duì)象,需要自己定義
import lombok.extern.slf4j.Slf4j;
import model.User;
import org.apache.ibatis.session.ResultContext;
import org.apache.ibatis.session.ResultHandler;
import java.util.ArrayList;
import java.util.List;
/**
* @author: jie
* @create: 2023/3/29 16:51
* @description:
*/
@Slf4j
public class SyncDataHandler implements ResultHandler<User> {
/**
* 每批處理數(shù)量
*/
private final static int BATCH_SIZE = 1000;
/**
* 緩存數(shù)據(jù)
*/
private List<User> cacheList = new ArrayList<>();
/**
* 同步熟慮
*/
private int total = 0;
@Override
public void handleResult(ResultContext<? extends User> resultContext) {
User coreInfoCyDTO = resultContext.getResultObject();
this.cacheList.add(coreInfoCyDTO);
//每到達(dá)BATCH_SIZE 條數(shù)據(jù)處理一次
if (this.cacheList.size() >= BATCH_SIZE) {
this.handle();
}
total++;
}
/**
* 處理緩存數(shù)據(jù)
*/
private void handle() {
try {
// 具體的處理邏輯 省略
} finally {
// 清除處理過(guò)的緩存數(shù)據(jù)
this.cacheList.clear();
}
}
/**
* 處理最后一批沒(méi)有進(jìn)行處理的數(shù)據(jù)
*/
public int end() {
this.end();
return total;
}
}
使用代碼示例:
SyncDataHandler syncDataHandler = new SyncDataHandler();
userMapper.getUserList("selectUsers", syncDataHandler);
syncDataHandler.end();結(jié)言
流式查詢可以避免 OOM,,數(shù)據(jù)量大可以考慮此方案,其占用內(nèi)存大小取決于批處理大小BATCH_SIZE的設(shè)置。所以BATCH_SIZE應(yīng)該根據(jù)業(yè)務(wù)情況設(shè)置合適的大小。但是這這種方式會(huì)占用數(shù)據(jù)庫(kù)連接,使用中不會(huì)釋放,所以線上針對(duì)大數(shù)據(jù)量業(yè)務(wù)用到流式操作,一定要進(jìn)行并發(fā)控制。
到此這篇關(guān)于詳解MyBatis如何在大數(shù)據(jù)量下使用流式查詢進(jìn)行數(shù)據(jù)同步的文章就介紹到這了,更多相關(guān)MyBatis流式查詢內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Java中的接口以及常見(jiàn)的Cloneable接口用法
這篇文章主要介紹了Java中的接口以及常見(jiàn)的Cloneable接口用法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2024-02-02
借助Maven搭建Hadoop開(kāi)發(fā)環(huán)境的最詳細(xì)教程分享
在Maven插件的幫助下,VSCode寫Java其實(shí)非常方便,所以本文就來(lái)和大家詳細(xì)講講如何借助maven用VScode搭建Hadoop開(kāi)發(fā)環(huán)境,需要的可以參考下2023-05-05
SpringBoot項(xiàng)目nohup啟動(dòng)運(yùn)行日志過(guò)大的解決方案
這篇文章主要介紹了SpringBoot項(xiàng)目nohup啟動(dòng)運(yùn)行日志過(guò)大的解決方案,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2024-05-05
如何在Spring Boot中實(shí)現(xiàn)異步處理與并發(fā)控制
本文我們將深入探討如何在Spring Boot中實(shí)現(xiàn)異步處理與并發(fā)控制,這一過(guò)程涉及到異步任務(wù)的執(zhí)行、線程池的配置、以及并發(fā)控制的實(shí)踐,以幫助我們提升應(yīng)用的性能和響應(yīng)能力,感興趣的朋友跟隨小編一起看看吧2024-07-07
SpringBoot集成Nacos實(shí)現(xiàn)注冊(cè)中心與配置中心流程詳解
這篇文章主要介紹了SpringBoot集成Nacos實(shí)現(xiàn)注冊(cè)中心與配置中心流程,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)吧2023-02-02
IDEA中的pom.xml文件無(wú)法識(shí)別問(wèn)題及解決
這篇文章主要介紹了IDEA中的pom.xml文件無(wú)法識(shí)別問(wèn)題及解決方案,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-11-11
SpringBoot項(xiàng)目設(shè)置斷點(diǎn)debug調(diào)試無(wú)效忽略web.xml問(wèn)題的解決
這篇文章主要介紹了SpringBoot項(xiàng)目設(shè)置斷點(diǎn)debug調(diào)試無(wú)效忽略web.xml問(wèn)題的解決,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2019-08-08
springboot+knife4j+nacos實(shí)踐
這篇文章主要介紹了springboot+knife4j+nacos實(shí)踐,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2025-06-06

