From a45f9bfc58f372e4facbbdaf8cd9ea0b15c6cc68 Mon Sep 17 00:00:00 2001 From: Koitharu Date: Mon, 10 Oct 2022 15:13:30 +0300 Subject: [PATCH] ReaperScansID parser #83 --- .../koitharu/kotatsu/parsers/MangaParser.kt | 2 +- .../parsers/site/madara/ReaperScansParser.kt | 88 +++++++++++++++++++ 2 files changed, 89 insertions(+), 1 deletion(-) create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ReaperScansParser.kt diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/MangaParser.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/MangaParser.kt index 2788529c..0c2bc8fd 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/MangaParser.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/MangaParser.kt @@ -25,7 +25,7 @@ abstract class MangaParser @InternalParsersApi constructor(val source: MangaSour val config by lazy { context.getConfig(source) } - val sourceLocale: Locale? + open val sourceLocale: Locale? get() = source.locale?.let { Locale(it) } /** diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ReaperScansParser.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ReaperScansParser.kt new file mode 100644 index 00000000..7e3a2002 --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ReaperScansParser.kt @@ -0,0 +1,88 @@ +package org.koitharu.kotatsu.parsers.site.madara + +import org.jsoup.nodes.Element +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.* +import org.koitharu.kotatsu.parsers.util.* +import java.util.* + +@MangaSourceParser("REAPER_SCANS_ID", "ReaperScansID", "in") +internal class ReaperScansParser(context: MangaLoaderContext) : + Madara6Parser(context, MangaSource.REAPER_SCANS_ID, "reaperscans.id") { + + override val datePattern = "MMMM dd, yyyy" + override val tagPrefix = "genre/" + override val sourceLocale: Locale = Locale.ENGLISH + + override fun String.asMangaState(): MangaState? = when (this) { + "OnGoing", + "Upcoming", + -> MangaState.ONGOING + + "Completed", + "Dropped", + -> MangaState.FINISHED + + else -> null + } + + override fun parseDetails(manga: Manga, body: Element, chapters: List): Manga { + val root = body.selectFirstOrThrow(".site-content") + val postContent = root.requireElementById("nav-info") + val tags = postContent.getElementsContainingOwnText("GĂȘnero") + .firstOrNull()?.tableValue() + ?.getElementsByAttributeValueContaining("href", tagPrefix) + ?.mapToSet { a -> a.asMangaTag() } ?: manga.tags + return manga.copy( + rating = postContent.selectFirstOrThrow(".post-rating") + .selectFirstOrThrow(".total_votes").text().toFloat() / 5f, + largeCoverUrl = root.selectFirst(".summary_image") + ?.selectFirst("img[data-src]") + ?.attrAsAbsoluteUrlOrNull("data-src") + .assertNotNull("largeCoverUrl"), + description = root.requireElementById("nav-profile") + .selectFirstOrThrow(".description-summary") + .firstElementChild()?.html(), + author = postContent.getElementsContainingOwnText("Author(s)") + .firstOrNull()?.tableValue()?.text()?.trim(), + altTitle = postContent.getElementsContainingOwnText("Alternative") + .firstOrNull()?.tableValue()?.text()?.trim(), + state = postContent.getElementsContainingOwnText("Status") + .firstOrNull()?.tableValue()?.text()?.asMangaState(), + tags = tags, + isNsfw = body.hasClass("adult-content"), + chapters = chapters, + ) + } + + override suspend fun getTags(): Set { + val doc = context.httpGet("https://${getDomain()}/semua-komik/").parseHtml() + val body = doc.body() + val root1 = body.selectFirst("header")?.selectFirst("ul.second-menu") + val root2 = body.selectFirst("div.genres_wrap")?.selectFirst("ul.list-unstyled") + if (root1 == null && root2 == null) { + doc.parseFailed("Root not found") + } + val list = root1?.select("li").orEmpty() + root2?.select("li").orEmpty() + val keySet = HashSet(list.size) + return list.mapNotNullToSet { li -> + val a = li.selectFirst("a") ?: return@mapNotNullToSet null + val href = a.attr("href").removeSuffix("/") + .substringAfterLast(tagPrefix, "") + if (href.isEmpty() || !keySet.add(href)) { + return@mapNotNullToSet null + } + MangaTag( + key = href, + title = a.ownText().trim().ifEmpty { + a.selectFirst(".menu-image-title")?.text()?.trim() ?: return@mapNotNullToSet null + }.toTitleCase(), + source = source, + ) + } + } + + override fun getFaviconUrl(): String = + "https://wuz.${getDomain()}/wp-content/uploads/2022/03/20063242/cropped-ms-icon-310x310-2-192x192.png" +} \ No newline at end of file