From a1a17c02d7bb71294fbafa775e99b3cbe193e024 Mon Sep 17 00:00:00 2001 From: devi Date: Wed, 6 Dec 2023 19:23:46 +0100 Subject: [PATCH] Add, fix sources Add language on Bato.To --- .../kotatsu/parsers/site/all/BatoToParser.kt | 19 ++++- .../parsers/site/all/ExHentaiParser.kt | 50 ++++++----- .../parsers/site/madara/MadaraParser.kt | 17 ++-- .../parsers/site/madara/ar/MangaLekCom.kt | 39 +++++++++ .../parsers/site/madara/ar/MangaLike.kt | 2 +- .../parsers/site/madara/en/FireScans.kt | 84 +++++++++++++++++++ .../parsers/site/madara/es/HouseMangas.kt | 10 +++ .../parsers/site/madara/es/Lectorunm.kt | 12 +++ .../site/madara/es/NoblesseTranslations.kt | 6 +- .../parsers/site/madara/es/RichtoScan.kt | 14 ++++ .../kotatsu/parsers/site/madara/fr/FrScan.kt | 37 +++++++- .../kotatsu/parsers/site/madara/pt/CvnScan.kt | 11 +++ .../site/madara/vi/TruyenTranhDamMyy.kt | 42 ++++++++++ .../parsers/site/mangareader/en/AgsComics.kt | 12 +++ .../site/mangareader/en/AscalonScans.kt | 10 +++ .../parsers/site/mangareader/en/KaiScans.kt | 2 +- .../parsers/site/mangareader/en/RavenScans.kt | 1 - .../site/mangareader/en/ReadersPoint.kt | 12 +++ 18 files changed, 343 insertions(+), 37 deletions(-) create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/en/FireScans.kt create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/HouseMangas.kt create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/Lectorunm.kt create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/RichtoScan.kt create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/pt/CvnScan.kt create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/vi/TruyenTranhDamMyy.kt create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/AgsComics.kt create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/AscalonScans.kt create mode 100644 src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/ReadersPoint.kt diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/all/BatoToParser.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/all/BatoToParser.kt index 39c95502..dcb0b387 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/all/BatoToParser.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/all/BatoToParser.kt @@ -96,7 +96,11 @@ internal class BatoToParser(context: MangaLoaderContext) : PagedMangaParser( }, ) } - // langs= en ... + + filter.locale?.let { + append("&langs=") + append(it.language) + } if (filter.tags.isNotEmpty()) { append("&genres=") @@ -211,6 +215,19 @@ internal class BatoToParser(context: MangaLoaderContext) : PagedMangaParser( throw ParseException("Cannot find gernes list", scripts[0].baseUri()) } + override suspend fun getAvailableLocales(): Set { + val jsRaw = webClient.httpGet("https://$domain/amsta/build/jss-btoto_v22.js").parseRaw() + val langRaw = jsRaw.substringAfter("items: {").substringBefore(",\"_t\"").split("code\":\"").drop(1) + return langRaw.mapNotNullToSet { + val lang = it.substringBefore("\",\"") + if (lang.contains("-")) { + return@mapNotNullToSet null + } else { + Locale(lang) + } + } + } + private suspend fun search(page: Int, query: String): List { val url = buildString { append("https://") diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/all/ExHentaiParser.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/all/ExHentaiParser.kt index 268ab02e..22993dfa 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/all/ExHentaiParser.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/all/ExHentaiParser.kt @@ -65,38 +65,45 @@ internal class ExHentaiParser( paginator.firstPage = 0 } - override suspend fun getListPage( - page: Int, - query: String?, - tags: Set?, - sortOrder: SortOrder, - ): List { - var search = query?.urlEncoded().orEmpty() + override suspend fun getListPage(page: Int, filter: MangaListFilter?): List { val next = nextPages.get(page, 0L) + if (page > 0 && next == 0L) { assert(false) { "Page timestamp not found" } return emptyList() } + + var search = "" + val url = buildString { append("https://") append(domain) append("/?next=") append(next) - if (!tags.isNullOrEmpty()) { - var fCats = 0 - for (tag in tags) { - tag.key.toIntOrNull()?.let { fCats = fCats or it } ?: run { - search += tag.key + " " - } + when (filter) { + + is MangaListFilter.Search -> { + search += filter.query.urlEncoded() + append("&f_search=") + append(search.trim().replace(' ', '+')) } - if (fCats != 0) { - append("&f_cats=") - append(1023 - fCats) + + is MangaListFilter.Advanced -> { + if (filter.tags.isNotEmpty()) { + var fCats = 0 + for (tag in filter.tags) { + tag.key.toIntOrNull()?.let { fCats = fCats or it } ?: run { + search += tag.key + " " + } + } + if (fCats != 0) { + append("&f_cats=") + append(1023 - fCats) + } + } } - } - if (search.isNotEmpty()) { - append("&f_search=") - append(search.trim().replace(' ', '+')) + + null -> {} } // by unknown reason cookie "sl=dm_2" is ignored, so, we should request it again if (updateDm) { @@ -107,6 +114,7 @@ internal class ExHentaiParser( append("&f_sh=on") } } + val body = webClient.httpGet(url).parseHtml().body() val root = body.selectFirst("table.itg") ?.selectFirst("tbody") @@ -114,7 +122,7 @@ internal class ExHentaiParser( body.parseFailed("Cannot find root") } else { updateDm = true - return getListPage(page, query, tags, sortOrder) + return getListPage(page, filter) } updateDm = false nextPages[page + 1] = getNextTimestamp(body) diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/MadaraParser.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/MadaraParser.kt index 405afa56..c6a18378 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/MadaraParser.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/MadaraParser.kt @@ -158,8 +158,7 @@ internal abstract class MadaraParser( protected open val listUrl = "manga/" override suspend fun getListPage(page: Int, filter: MangaListFilter?): List { - - val doc = if (withoutAjax) { + if (withoutAjax) { val pages = page + 1 val url = buildString { @@ -224,7 +223,7 @@ internal abstract class MadaraParser( } } } - webClient.httpGet(url).parseHtml() + return parseMangaList(webClient.httpGet(url).parseHtml()) } else { val payload = if (filter?.sortOrder == SortOrder.RATING) { createRequestTemplate(ratingRequest) @@ -274,12 +273,16 @@ internal abstract class MadaraParser( } } - webClient.httpPost( - "https://$domain/wp-admin/admin-ajax.php", - payload, - ).parseHtml() + return parseMangaList( + webClient.httpPost( + "https://$domain/wp-admin/admin-ajax.php", + payload, + ).parseHtml(), + ) } + } + protected open fun parseMangaList(doc: Document): List { return doc.select("div.row.c-tabs-item__content").ifEmpty { doc.select("div.page-item-detail") }.map { div -> diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ar/MangaLekCom.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ar/MangaLekCom.kt index 88360559..f091ed68 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ar/MangaLekCom.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ar/MangaLekCom.kt @@ -1,13 +1,52 @@ package org.koitharu.kotatsu.parsers.site.madara.ar +import org.jsoup.nodes.Document import org.koitharu.kotatsu.parsers.MangaLoaderContext import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaChapter import org.koitharu.kotatsu.parsers.model.MangaSource import org.koitharu.kotatsu.parsers.site.madara.MadaraParser +import org.koitharu.kotatsu.parsers.util.attrAsRelativeUrlOrNull +import org.koitharu.kotatsu.parsers.util.domain +import org.koitharu.kotatsu.parsers.util.generateUid +import org.koitharu.kotatsu.parsers.util.mapChapters +import org.koitharu.kotatsu.parsers.util.parseFailed +import org.koitharu.kotatsu.parsers.util.parseHtml +import org.koitharu.kotatsu.parsers.util.removeSuffix +import org.koitharu.kotatsu.parsers.util.toAbsoluteUrl +import java.text.SimpleDateFormat @MangaSourceParser("MANGA_LEK", "Manga-Lek", "ar") internal class MangaLekCom(context: MangaLoaderContext) : MadaraParser(context, MangaSource.MANGA_LEK, "manga-lek.com") { override val listUrl = "mangalek/" override val postReq = true + + override suspend fun loadChapters(mangaUrl: String, document: Document): List { + val mangaId = document.select("div#manga-chapters-holder").attr("data-id") + val url = "https://$domain/wp-admin/admin-ajax.php" + val postData = "action=manga_get_chapters&manga=$mangaId" + val doc = webClient.httpPost(url, postData).parseHtml() + val dateFormat = SimpleDateFormat(datePattern, sourceLocale) + return doc.select(selectChapter).mapChapters { i, li -> + val a = li.selectFirst("a") + val href = a?.attrAsRelativeUrlOrNull("href") ?: li.parseFailed("Link is missing") + val link = href + stylePage + val dateText = li.selectFirst("a.c-new-tag")?.attr("title") ?: li.selectFirst(selectDate)?.text() + val name = a.selectFirst("p")?.text() ?: a.ownText() + MangaChapter( + id = generateUid(href), + url = link, + name = name, + number = i + 1, + branch = null, + uploadDate = parseChapterDate( + dateFormat, + dateText, + ), + scanlator = null, + source = source, + ) + } + } } diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ar/MangaLike.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ar/MangaLike.kt index 0dbf8e23..a2489414 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ar/MangaLike.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/ar/MangaLike.kt @@ -5,6 +5,6 @@ import org.koitharu.kotatsu.parsers.MangaSourceParser import org.koitharu.kotatsu.parsers.model.MangaSource import org.koitharu.kotatsu.parsers.site.madara.MadaraParser -@MangaSourceParser("MANGALIKE", "MangaLike", "ar") +@MangaSourceParser("MANGALIKE", "MangaLike.net", "ar") internal class MangaLike(context: MangaLoaderContext) : MadaraParser(context, MangaSource.MANGALIKE, "manga-like.net", pageSize = 10) diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/en/FireScans.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/en/FireScans.kt new file mode 100644 index 00000000..633b2170 --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/en/FireScans.kt @@ -0,0 +1,84 @@ +package org.koitharu.kotatsu.parsers.site.madara.en + +import org.json.JSONObject +import org.jsoup.nodes.Document +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.* +import org.koitharu.kotatsu.parsers.site.madara.MadaraParser +import org.koitharu.kotatsu.parsers.util.* + +@MangaSourceParser("FIRESCANS", "FireScans", "en") +internal class FireScans(context: MangaLoaderContext) : + MadaraParser(context, MangaSource.FIRESCANS, "firescans.xyz", 10) { + + override fun parseMangaList(doc: Document): List { + return doc.select("div.row.c-tabs-item__content").ifEmpty { + doc.select("div.page-item-detail") + }.map { div -> + val href = div.selectFirst("h3 a")?.attrAsRelativeUrlOrNull("href") ?: div.parseFailed("Link not found") + val summary = div.selectFirst(".tab-summary") ?: div.selectFirst(".item-summary") + Manga( + id = generateUid(href), + url = href, + publicUrl = href.toAbsoluteUrl(div.host ?: domain), + coverUrl = div.selectFirst("img")?.src().orEmpty(), + title = (summary?.selectFirst("h3") ?: summary?.selectFirst("h4") + ?: div.selectFirst(".manga-name"))?.text().orEmpty(), + altTitle = null, + rating = div.selectFirst("span.total_votes")?.ownText()?.toFloatOrNull()?.div(5f) ?: -1f, + tags = summary?.selectFirst(".mg_genres")?.select("a")?.mapNotNullToSet { a -> + MangaTag( + key = a.attr("href").removeSuffix('/').substringAfterLast('/'), + title = a.text().ifEmpty { return@mapNotNullToSet null }.toTitleCase(), + source = source, + ) + }.orEmpty(), + author = summary?.selectFirst(".mg_author")?.selectFirst("a")?.ownText(), + state = when (summary?.selectFirst(".mg_status")?.selectFirst(".summary-content")?.ownText()) { + in ongoing -> MangaState.ONGOING + in finished -> MangaState.FINISHED + in abandoned -> MangaState.ABANDONED + in paused -> MangaState.PAUSED + else -> null + }, + source = source, + isNsfw = isNsfwSource, + ) + } + } + + override suspend fun getPages(chapter: MangaChapter): List { + val fullUrl = chapter.url.toAbsoluteUrl(domain) + val doc = webClient.httpGet(fullUrl).parseHtml() + val chapterProtector = doc.requireElementById("chapter-protector-data") + val chapterProtectorHtml = + context.decodeBase64(chapterProtector.attr("src").removePrefix("data:text/javascript;base64,")) + .toString(Charsets.UTF_8) + val password = chapterProtectorHtml.substringAfter("wpmangaprotectornonce='").substringBefore("';") + val chapterData = JSONObject( + chapterProtectorHtml.substringAfter("chapter_data='").substringBefore("';").replace("\\/", "/"), + ) + val unsaltedCiphertext = context.decodeBase64(chapterData.getString("ct")) + val salt = chapterData.getString("s").toString().decodeHex() + val ciphertext = "Salted__".toByteArray(Charsets.UTF_8) + salt + unsaltedCiphertext + val rawImgArray = CryptoAES(context).decrypt(context.encodeBase64(ciphertext), password) + val imgArrayString = rawImgArray.filterNot { c -> c == '[' || c == ']' || c == '\\' || c == '"' } + + return imgArrayString.split(",").map { url -> + MangaPage( + id = generateUid(url), + url = url, + preview = null, + source = source, + ) + } + } + + fun String.decodeHex(): ByteArray { + check(length % 2 == 0) { "Must have an even length" } + + return chunked(2).map { it.toInt(16).toByte() }.toByteArray() + } + +} diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/HouseMangas.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/HouseMangas.kt new file mode 100644 index 00000000..82596c66 --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/HouseMangas.kt @@ -0,0 +1,10 @@ +package org.koitharu.kotatsu.parsers.site.madara.es + +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaSource +import org.koitharu.kotatsu.parsers.site.madara.MadaraParser + +@MangaSourceParser("HOUSEMANGAS", "HouseMangas", "es") +internal class HouseMangas(context: MangaLoaderContext) : + MadaraParser(context, MangaSource.HOUSEMANGAS, "housemangas.com") diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/Lectorunm.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/Lectorunm.kt new file mode 100644 index 00000000..76dfcbbd --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/Lectorunm.kt @@ -0,0 +1,12 @@ +package org.koitharu.kotatsu.parsers.site.madara.es + +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaSource +import org.koitharu.kotatsu.parsers.site.madara.MadaraParser + +@MangaSourceParser("LECTORUNM", "Lectorunm.life", "es") +internal class Lectorunm(context: MangaLoaderContext) : + MadaraParser(context, MangaSource.LECTORUNM, "lectorunm.life") { + override val datePattern = "dd/MM/yyyy" +} diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/NoblesseTranslations.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/NoblesseTranslations.kt index fe5a4e4d..4462e6f7 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/NoblesseTranslations.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/NoblesseTranslations.kt @@ -5,8 +5,6 @@ import org.koitharu.kotatsu.parsers.MangaSourceParser import org.koitharu.kotatsu.parsers.model.MangaSource import org.koitharu.kotatsu.parsers.site.madara.MadaraParser -@MangaSourceParser("NOBLESSETRANSLATIONS", "Noblesse Translations", "es") +@MangaSourceParser("NOBLESSETRANSLATIONS", "NoblesseTranslations", "es") internal class NoblesseTranslations(context: MangaLoaderContext) : - MadaraParser(context, MangaSource.NOBLESSETRANSLATIONS, "noblessetranslations.com") { - override val datePattern = "d MMMM, yyyy" -} + MadaraParser(context, MangaSource.NOBLESSETRANSLATIONS, "www.noblessev1.com") diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/RichtoScan.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/RichtoScan.kt new file mode 100644 index 00000000..6ccdaf2c --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/es/RichtoScan.kt @@ -0,0 +1,14 @@ +package org.koitharu.kotatsu.parsers.site.madara.es + +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaSource +import org.koitharu.kotatsu.parsers.site.madara.MadaraParser +import java.util.Locale + +@MangaSourceParser("RICHTOSCAN", "RichtoScan", "es") +internal class RichtoScan(context: MangaLoaderContext) : + MadaraParser(context, MangaSource.RICHTOSCAN, "richtoscan.com") { + override val tagPrefix = "manga-generos/" + override val sourceLocale: Locale = Locale.ENGLISH +} diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/fr/FrScan.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/fr/FrScan.kt index 09a09a3c..abfbd96a 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/fr/FrScan.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/fr/FrScan.kt @@ -2,9 +2,44 @@ package org.koitharu.kotatsu.parsers.site.madara.fr import org.koitharu.kotatsu.parsers.MangaLoaderContext import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaChapter +import org.koitharu.kotatsu.parsers.model.MangaPage import org.koitharu.kotatsu.parsers.model.MangaSource import org.koitharu.kotatsu.parsers.site.madara.MadaraParser +import org.koitharu.kotatsu.parsers.util.* @MangaSourceParser("FRSCAN", "Fr-Scan", "fr") internal class FrScan(context: MangaLoaderContext) : - MadaraParser(context, MangaSource.FRSCAN, "fr-scan.com") + MadaraParser(context, MangaSource.FRSCAN, "fr-scan.com") { + override val stylePage = "" + + override suspend fun getPages(chapter: MangaChapter): List { + val fullUrl = chapter.url.toAbsoluteUrl(domain) + val doc = webClient.httpGet(fullUrl).parseHtml() + val preloadImg = doc.getElementById("chapter_preloaded_images") + if (preloadImg != null) { + val img = preloadImg.data().substringAfter("[").substringBeforeLast("]") + .replace("\\", "").replace("\"", "").split(",") + return img.map { url -> + MangaPage( + id = generateUid(url), + url = url, + preview = null, + source = source, + ) + } + } else { + return doc.body().selectFirstOrThrow(selectBodyPage).select(selectPage).map { div -> + val img = div.selectFirstOrThrow("img") + val url = img.src()?.toRelativeUrl(domain) ?: div.parseFailed("Image src not found") + MangaPage( + id = generateUid(url), + url = url, + preview = null, + source = source, + ) + } + } + + } +} diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/pt/CvnScan.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/pt/CvnScan.kt new file mode 100644 index 00000000..709d92e2 --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/pt/CvnScan.kt @@ -0,0 +1,11 @@ +package org.koitharu.kotatsu.parsers.site.madara.pt + +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.ContentType +import org.koitharu.kotatsu.parsers.model.MangaSource +import org.koitharu.kotatsu.parsers.site.madara.MadaraParser + +@MangaSourceParser("CVNSCAN", "CvnScan", "pt", ContentType.HENTAI) +internal class CvnScan(context: MangaLoaderContext) : + MadaraParser(context, MangaSource.CVNSCAN, "cvnscan.com") diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/vi/TruyenTranhDamMyy.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/vi/TruyenTranhDamMyy.kt new file mode 100644 index 00000000..d7a366f1 --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/madara/vi/TruyenTranhDamMyy.kt @@ -0,0 +1,42 @@ +package org.koitharu.kotatsu.parsers.site.madara.vi + +import org.jsoup.nodes.Document +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaChapter +import org.koitharu.kotatsu.parsers.model.MangaSource +import org.koitharu.kotatsu.parsers.site.madara.MadaraParser +import org.koitharu.kotatsu.parsers.util.attrAsRelativeUrlOrNull +import org.koitharu.kotatsu.parsers.util.domain +import org.koitharu.kotatsu.parsers.util.generateUid +import org.koitharu.kotatsu.parsers.util.mapChapters +import org.koitharu.kotatsu.parsers.util.parseFailed +import org.koitharu.kotatsu.parsers.util.parseHtml + +@MangaSourceParser("TRUYENTRANHDAMMYY", "TruyenTranhDamMyy", "vi") +internal class TruyenTranhDamMyy(context: MangaLoaderContext) : + MadaraParser(context, MangaSource.TRUYENTRANHDAMMYY, "truyentranhdammyy.com") { + override val postReq = true + override suspend fun loadChapters(mangaUrl: String, document: Document): List { + val mangaId = document.select("div#manga-chapters-holder").attr("data-id") + val url = "https://$domain/wp-admin/admin-ajax.php" + val postData = "action=manga_get_chapters&manga=$mangaId" + val doc = webClient.httpPost(url, postData).parseHtml() + return doc.select(selectChapter).mapChapters(reversed = true) { i, li -> + val a = li.selectFirst("a") + val href = a?.attrAsRelativeUrlOrNull("href") ?: li.parseFailed("Link is missing") + val link = href + stylePage + val name = a.selectFirst("p")?.text() ?: a.ownText() + MangaChapter( + id = generateUid(href), + url = link, + name = name, + number = i + 1, + branch = null, + uploadDate = 0, // Correct datePattern not found. + scanlator = null, + source = source, + ) + } + } +} diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/AgsComics.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/AgsComics.kt new file mode 100644 index 00000000..e7d8ecaa --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/AgsComics.kt @@ -0,0 +1,12 @@ +package org.koitharu.kotatsu.parsers.site.mangareader.en + +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaSource +import org.koitharu.kotatsu.parsers.site.mangareader.MangaReaderParser + +@MangaSourceParser("AGSCOMICS", "AgsComics", "en") +internal class AgsComics(context: MangaLoaderContext) : + MangaReaderParser(context, MangaSource.AGSCOMICS, "agscomics.com", pageSize = 20, searchPageSize = 10) { + override val listUrl = "/series" +} diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/AscalonScans.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/AscalonScans.kt new file mode 100644 index 00000000..8718a83d --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/AscalonScans.kt @@ -0,0 +1,10 @@ +package org.koitharu.kotatsu.parsers.site.mangareader.en + +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaSource +import org.koitharu.kotatsu.parsers.site.mangareader.MangaReaderParser + +@MangaSourceParser("ASCALONSCANS", "AscalonScans", "en") +internal class AscalonScans(context: MangaLoaderContext) : + MangaReaderParser(context, MangaSource.ASCALONSCANS, "ascalonscans.com", pageSize = 20, searchPageSize = 10) diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/KaiScans.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/KaiScans.kt index dd936eb8..86628692 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/KaiScans.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/KaiScans.kt @@ -7,6 +7,6 @@ import org.koitharu.kotatsu.parsers.site.mangareader.MangaReaderParser @MangaSourceParser("KAISCANS", "KaiScans", "en") internal class KaiScans(context: MangaLoaderContext) : - MangaReaderParser(context, MangaSource.KAISCANS, "kaiscans.com", pageSize = 20, searchPageSize = 10) { + MangaReaderParser(context, MangaSource.KAISCANS, "www.kaiscans.com", pageSize = 20, searchPageSize = 10) { override val listUrl = "/series" } diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/RavenScans.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/RavenScans.kt index 0352045c..d623ed6f 100644 --- a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/RavenScans.kt +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/RavenScans.kt @@ -8,6 +8,5 @@ import org.koitharu.kotatsu.parsers.site.mangareader.MangaReaderParser @MangaSourceParser("RAVENSCANS", "RavenScans", "en") internal class RavenScans(context: MangaLoaderContext) : MangaReaderParser(context, MangaSource.RAVENSCANS, "ravenscans.com", pageSize = 10, searchPageSize = 10) { - override val datePattern = "MMM d, yyyy" } diff --git a/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/ReadersPoint.kt b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/ReadersPoint.kt new file mode 100644 index 00000000..c7edb24d --- /dev/null +++ b/src/main/kotlin/org/koitharu/kotatsu/parsers/site/mangareader/en/ReadersPoint.kt @@ -0,0 +1,12 @@ +package org.koitharu.kotatsu.parsers.site.mangareader.en + +import org.koitharu.kotatsu.parsers.MangaLoaderContext +import org.koitharu.kotatsu.parsers.MangaSourceParser +import org.koitharu.kotatsu.parsers.model.MangaSource +import org.koitharu.kotatsu.parsers.site.mangareader.MangaReaderParser + +@MangaSourceParser("READERSPOINT", "ReadersPoint", "en") +internal class ReadersPoint(context: MangaLoaderContext) : + MangaReaderParser(context, MangaSource.READERSPOINT, "readers-point.space", pageSize = 20, searchPageSize = 10) { + override val listUrl = "/series" +}