aboutsummaryrefslogtreecommitdiffstats
path: root/gallery_dl/extractor/mangadex.py
diff options
context:
space:
mode:
authorLibravatarUnit 193 <unit193@unit193.net>2025-09-23 07:44:44 -0400
committerLibravatarUnit 193 <unit193@unit193.net>2025-09-23 07:44:44 -0400
commit291c04af647559317fc9f9f392ad43841ec509ad (patch)
tree13a72906223927180001b362d086c82401cb7843 /gallery_dl/extractor/mangadex.py
parent065386e00c7a6c8bbe4bb23a545a7fc7b2c09a4a (diff)
parent42b62671fabfdcf983a9575221420d85f7fbcac1 (diff)
Update upstream source from tag 'upstream/1.30.8'
Update to upstream version '1.30.8' with Debian dir 51367313d3355f7d0d16a754c5c63135fb3c72e2
Diffstat (limited to 'gallery_dl/extractor/mangadex.py')
-rw-r--r--gallery_dl/extractor/mangadex.py69
1 files changed, 69 insertions, 0 deletions
diff --git a/gallery_dl/extractor/mangadex.py b/gallery_dl/extractor/mangadex.py
index 225560d..fbed328 100644
--- a/gallery_dl/extractor/mangadex.py
+++ b/gallery_dl/extractor/mangadex.py
@@ -96,6 +96,57 @@ class MangadexExtractor(Extractor):
return data
+class MangadexCoversExtractor(MangadexExtractor):
+ """Extractor for mangadex manga covers"""
+ subcategory = "covers"
+ directory_fmt = ("{category}", "{manga}", "Covers")
+ filename_fmt = "{volume:>02}_{lang}.{extension}"
+ archive_fmt = "c_{cover_id}"
+ pattern = (rf"{BASE_PATTERN}/(?:title|manga)/(?!follows|feed$)([0-9a-f-]+)"
+ r"(?:/[^/?#]+)?\?tab=art")
+ example = ("https://mangadex.org/title"
+ "/01234567-89ab-cdef-0123-456789abcdef?tab=art")
+
+ def items(self):
+ base = f"{self.root}/covers/{self.uuid}/"
+ for cover in self.api.covers_manga(self.uuid):
+ data = self._transform_cover(cover)
+ name = data["cover"]
+ text.nameext_from_url(name, data)
+ data["cover_id"] = data["filename"]
+ yield Message.Directory, data
+ yield Message.Url, f"{base}{name}", data
+
+ def _transform_cover(self, cover):
+ relationships = defaultdict(list)
+ for item in cover["relationships"]:
+ relationships[item["type"]].append(item)
+ manga = self.api.manga(relationships["manga"][0]["id"])
+ for item in manga["relationships"]:
+ relationships[item["type"]].append(item)
+
+ cattributes = cover["attributes"]
+ mattributes = manga["attributes"]
+
+ return {
+ "manga" : (mattributes["title"].get("en") or
+ next(iter(mattributes["title"].values()))),
+ "manga_id": manga["id"],
+ "status" : mattributes["status"],
+ "author" : [author["attributes"]["name"]
+ for author in relationships["author"]],
+ "artist" : [artist["attributes"]["name"]
+ for artist in relationships["artist"]],
+ "tags" : [tag["attributes"]["name"]["en"]
+ for tag in mattributes["tags"]],
+ "cover" : cattributes["fileName"],
+ "lang" : cattributes.get("locale"),
+ "volume" : text.parse_int(cattributes["volume"]),
+ "date" : text.parse_datetime(cattributes["createdAt"]),
+ "date_updated": text.parse_datetime(cattributes["updatedAt"]),
+ }
+
+
class MangadexChapterExtractor(MangadexExtractor):
"""Extractor for manga-chapters from mangadex.org"""
subcategory = "chapter"
@@ -239,6 +290,10 @@ class MangadexAPI():
params = {"includes[]": ("scanlation_group",)}
return self._call("/chapter/" + uuid, params)["data"]
+ def covers_manga(self, uuid):
+ params = {"manga[]": uuid}
+ return self._pagination_covers("/cover", params)
+
def list(self, uuid):
return self._call("/list/" + uuid, None, True)["data"]
@@ -374,6 +429,20 @@ class MangadexAPI():
return self._pagination(endpoint, params, auth)
+ def _pagination_covers(self, endpoint, params=None, auth=False):
+ if params is None:
+ params = {}
+
+ lang = self.extractor.config("lang")
+ if isinstance(lang, str) and "," in lang:
+ lang = lang.split(",")
+ params["locales"] = lang
+ params["contentRating"] = None
+ params["order[volume]"] = \
+ "desc" if self.extractor.config("chapter-reverse") else "asc"
+
+ return self._pagination(endpoint, params, auth)
+
def _pagination(self, endpoint, params, auth=False):
config = self.extractor.config