From 948dd7fb9e47869cd520af65d185b0238f204006 Mon Sep 17 00:00:00 2001 From: Rodrigo Verdiani Date: Mon, 27 Oct 2025 14:53:13 -0300 Subject: [PATCH] feat: implement rate limiting for image downloads in MangaChapterService --- .../com/magamochi/mangamochi/config/RateLimiterConfig.java | 5 +++++ .../magamochi/mangamochi/service/MangaChapterService.java | 7 ++++++- 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/src/main/java/com/magamochi/mangamochi/config/RateLimiterConfig.java b/src/main/java/com/magamochi/mangamochi/config/RateLimiterConfig.java index c48799e..1120da5 100644 --- a/src/main/java/com/magamochi/mangamochi/config/RateLimiterConfig.java +++ b/src/main/java/com/magamochi/mangamochi/config/RateLimiterConfig.java @@ -15,4 +15,9 @@ public class RateLimiterConfig { public RateLimiter jikanRateLimiter() { return RateLimiter.create(1); } + + @Bean + public RateLimiter imageDownloadRateLimiter() { + return RateLimiter.create(10); + } } diff --git a/src/main/java/com/magamochi/mangamochi/service/MangaChapterService.java b/src/main/java/com/magamochi/mangamochi/service/MangaChapterService.java index ce9e217..1cef271 100644 --- a/src/main/java/com/magamochi/mangamochi/service/MangaChapterService.java +++ b/src/main/java/com/magamochi/mangamochi/service/MangaChapterService.java @@ -1,5 +1,6 @@ package com.magamochi.mangamochi.service; +import com.google.common.util.concurrent.RateLimiter; import com.magamochi.mangamochi.exception.UnprocessableException; import com.magamochi.mangamochi.model.dto.MangaChapterArchiveDTO; import com.magamochi.mangamochi.model.dto.MangaChapterImagesDTO; @@ -36,6 +37,8 @@ public class MangaChapterService { private final ContentProviderFactory contentProviderFactory; + private final RateLimiter imageDownloadRateLimiter; + @Transactional public void fetchChapter(Long chapterId) { var chapter = getMangaChapterThrowIfNotFound(chapterId); @@ -50,9 +53,11 @@ public class MangaChapterService { } var chapterImages = - chapterImagesUrls.entrySet().stream() + chapterImagesUrls.entrySet().parallelStream() .map( entry -> { + imageDownloadRateLimiter.acquire(); + try { var inputStream = new BufferedInputStream(