diff --git a/AnimeIndoProvider/build.gradle.kts b/AnimeIndoProvider/build.gradle.kts index f6e8b592..af852c5c 100644 --- a/AnimeIndoProvider/build.gradle.kts +++ b/AnimeIndoProvider/build.gradle.kts @@ -1,5 +1,5 @@ // use an integer for version numbers -version = 14 +version = 15 cloudstream { diff --git a/AnimeIndoProvider/src/main/kotlin/com/hexated/AnimeIndoProvider.kt b/AnimeIndoProvider/src/main/kotlin/com/hexated/AnimeIndoProvider.kt index 5f3d09bd..af29b007 100644 --- a/AnimeIndoProvider/src/main/kotlin/com/hexated/AnimeIndoProvider.kt +++ b/AnimeIndoProvider/src/main/kotlin/com/hexated/AnimeIndoProvider.kt @@ -4,9 +4,12 @@ import com.lagradost.cloudstream3.* import com.lagradost.cloudstream3.LoadResponse.Companion.addAniListId import com.lagradost.cloudstream3.LoadResponse.Companion.addMalId import com.lagradost.cloudstream3.LoadResponse.Companion.addTrailer +import com.lagradost.cloudstream3.network.CloudflareKiller import com.lagradost.cloudstream3.utils.ExtractorLink import com.lagradost.cloudstream3.utils.httpsify import com.lagradost.cloudstream3.utils.loadExtractor +import okhttp3.Interceptor +import okhttp3.Response import org.jsoup.Jsoup import org.jsoup.nodes.Element @@ -15,13 +18,26 @@ class AnimeIndoProvider : MainAPI() { override var name = "AnimeIndo" override val hasMainPage = true override var lang = "id" - + private val cloudflareKiller by lazy { CloudflareKiller() } + private val interceptor by lazy { CloudflareInterceptor(cloudflareKiller) } override val supportedTypes = setOf( TvType.Anime, TvType.AnimeMovie, TvType.OVA ) + class CloudflareInterceptor(private val cloudflareKiller: CloudflareKiller): Interceptor { + override fun intercept(chain: Interceptor.Chain): Response { + val request = chain.request() + val response = chain.proceed(request) + val doc = Jsoup.parse(response.peekBody(1024 * 1024).string()) + if (doc.select("title").text() == "Just a moment...") { + return cloudflareKiller.intercept(chain) + } + return response + } + } + companion object { fun getType(t: String): TvType { return if (t.contains("OVA", true) || t.contains("Special")) TvType.OVA @@ -51,7 +67,7 @@ class AnimeIndoProvider : MainAPI() { request: MainPageRequest ): HomePageResponse { val url = "$mainUrl/${request.data}/page/$page" - val document = app.get(url).document + val document = app.get(url, interceptor = interceptor).document val home = document.select("main#main div.animposx").mapNotNull { it.toSearchResult() } @@ -85,6 +101,7 @@ class AnimeIndoProvider : MainAPI() { return newAnimeSearchResponse(title, href, TvType.Anime) { this.posterUrl = posterUrl addSub(epNum) + posterHeaders = cloudflareKiller.getCookieHeaders(mainUrl).toMap() } } @@ -93,7 +110,7 @@ class AnimeIndoProvider : MainAPI() { val anime = mutableListOf() (1..2).forEach { page -> val link = "$mainUrl/page/$page/?s=$query" - val document = app.get(link).document + val document = app.get(link, interceptor = interceptor).document val media = document.select(".site-main.relat > article").mapNotNull { val title = it.selectFirst("div.title > h2")!!.ownText().trim() val href = it.selectFirst("a")!!.attr("href") @@ -101,6 +118,7 @@ class AnimeIndoProvider : MainAPI() { val type = getType(it.select("div.type").text().trim()) newAnimeSearchResponse(title, href, type) { this.posterUrl = posterUrl + posterHeaders = cloudflareKiller.getCookieHeaders(mainUrl).toMap() } } if(media.isNotEmpty()) anime.addAll(media) @@ -109,7 +127,7 @@ class AnimeIndoProvider : MainAPI() { } override suspend fun load(url: String): LoadResponse? { - val document = app.get(url).document + val document = app.get(url, interceptor = interceptor).document val title = document.selectFirst("h1.entry-title")?.text()?.replace("Subtitle Indonesia", "") ?.trim() ?: return null @@ -150,6 +168,7 @@ class AnimeIndoProvider : MainAPI() { addTrailer(trailer) addMalId(tracker?.malId) addAniListId(tracker?.aniId?.toIntOrNull()) + posterHeaders = cloudflareKiller.getCookieHeaders(mainUrl).toMap() } } @@ -160,12 +179,12 @@ class AnimeIndoProvider : MainAPI() { callback: (ExtractorLink) -> Unit ): Boolean { - val document = app.get(data).document + val document = app.get(data, interceptor = interceptor).document document.select("div.itemleft > .mirror > option").mapNotNull { fixUrl(Jsoup.parse(base64Decode(it.attr("value"))).select("iframe").attr("src")) }.apmap { if (it.startsWith(mainUrl)) { - app.get(it, referer = "$mainUrl/").document.select("iframe").attr("src") + app.get(it, referer = "$mainUrl/", interceptor = interceptor).document.select("iframe").attr("src") } else { it } diff --git a/PhimmoichillProvider/build.gradle.kts b/PhimmoichillProvider/build.gradle.kts index 0e836afc..ec3f3dc3 100644 --- a/PhimmoichillProvider/build.gradle.kts +++ b/PhimmoichillProvider/build.gradle.kts @@ -1,5 +1,5 @@ // use an integer for version numbers -version = 5 +version = 6 cloudstream { diff --git a/PhimmoichillProvider/src/main/kotlin/com/hexated/PhimmoichillProvider.kt b/PhimmoichillProvider/src/main/kotlin/com/hexated/PhimmoichillProvider.kt index aa7c4f5d..2d0d256f 100644 --- a/PhimmoichillProvider/src/main/kotlin/com/hexated/PhimmoichillProvider.kt +++ b/PhimmoichillProvider/src/main/kotlin/com/hexated/PhimmoichillProvider.kt @@ -3,13 +3,14 @@ package com.hexated import com.lagradost.cloudstream3.* import com.lagradost.cloudstream3.LoadResponse.Companion.addActors import com.lagradost.cloudstream3.LoadResponse.Companion.addTrailer -import com.lagradost.cloudstream3.mvvm.safeApiCall import com.lagradost.cloudstream3.utils.* import org.jsoup.nodes.Element +import java.net.URI import java.net.URLDecoder class PhimmoichillProvider : MainAPI() { - override var mainUrl = "https://phimmoichillg.net" + override var mainUrl = "https://phimmoichillh.net" + private var directUrl = mainUrl override var name = "Phimmoichill" override val hasMainPage = true override var lang = "vi" @@ -89,26 +90,33 @@ class PhimmoichillProvider : MainAPI() { } } - override suspend fun load( url: String ): LoadResponse { - val document = app.get(url).document + override suspend fun load(url: String): LoadResponse { + val request = app.get(url) + directUrl = getBaseUrl(request.url) + val document = request.document val title = document.selectFirst("h1[itemprop=name]")?.text()?.trim().toString() val link = document.select("ul.list-button li:last-child a").attr("href") val poster = document.selectFirst("div.image img[itemprop=image]")?.attr("src") - val tags = document.select("ul.entry-meta.block-film li:nth-child(4) a").map { it.text()!!.substringAfter("Phim") } + val tags = document.select("ul.entry-meta.block-film li:nth-child(4) a") + .map { it.text().substringAfter("Phim") } val year = document.select("ul.entry-meta.block-film li:nth-child(2) a").text().trim() .toIntOrNull() val tvType = if (document.select("div.latest-episode").isNotEmpty() ) TvType.TvSeries else TvType.Movie - val description = document.select("div#film-content").text().substringAfter("Full HD Vietsub Thuyết Minh").substringBefore("@phimmoi").trim() + val description = + document.select("div#film-content").text().substringAfter("Full HD Vietsub Thuyết Minh") + .substringBefore("@phimmoi").trim() val trailer = document.select("body script") - .find { it.data().contains("youtube.com") }?.data()?.substringAfterLast("file: \"")?.substringBefore("\",") + .find { it.data().contains("youtube.com") }?.data()?.substringAfterLast("file: \"") + ?.substringBefore("\",") val rating = document.select("ul.entry-meta.block-film li:nth-child(7) span").text().toRatingInt() val actors = document.select("ul.entry-meta.block-film li:last-child a").map { it.text() } val recommendations = document.select("ul#list-film-realted li.item").map { it.toSearchResult().apply { - this.posterUrl = decode(it.selectFirst("img")!!.attr("data-src").substringAfter("url=")) + this.posterUrl = + decode(it.selectFirst("img")!!.attr("data-src").substringAfter("url=")) } } @@ -148,7 +156,7 @@ class PhimmoichillProvider : MainAPI() { } } } - + override suspend fun loadLinks( data: String, isCasting: Boolean, @@ -159,39 +167,43 @@ class PhimmoichillProvider : MainAPI() { val key = document.select("div#content script") .find { it.data().contains("filmInfo.episodeID =") }?.data()?.let { script -> - val id = script.substringAfter("filmInfo.episodeID = parseInt('") + val id = script.substringAfter("parseInt('").substringBefore("'") app.post( - url = "${this.mainUrl}/chillsplayer.php", - data = mapOf("qcao" to id, "sv" to "0"), + url = "$directUrl/chillsplayer.php", + data = mapOf("qcao" to id), referer = data, headers = mapOf( "X-Requested-With" to "XMLHttpRequest", "Content-Type" to "application/x-www-form-urlencoded; charset=UTF-8" ) ).text.substringAfterLast("iniPlayers(\"") - .substringBefore("\",") + .substringBefore("\"") } listOf( - Pair("https://so-trym.topphimmoi.org/raw/$key/index.m3u8", "PMFAST"), + Pair("https://sotrim.topphimmoi.org/raw/$key/index.m3u8", "PMFAST"), Pair("https://dash.megacdn.xyz/raw/$key/index.m3u8", "PMHLS"), Pair("https://so-trym.phimchill.net/dash/$key/index.m3u8", "PMPRO"), Pair("https://dash.megacdn.xyz/dast/$key/index.m3u8", "PMBK") - ).apmap { (link, source) -> - safeApiCall { - callback.invoke( - ExtractorLink( - source, - source, - link, - referer = "$mainUrl/", - quality = Qualities.P1080.value, - isM3u8 = true, - ) + ).map { (link, source) -> + callback.invoke( + ExtractorLink( + source, + source, + link, + referer = "$directUrl/", + quality = Qualities.P1080.value, + INFER_TYPE, ) - } + ) } return true } + private fun getBaseUrl(url: String): String { + return URI(url).let { + "${it.scheme}://${it.host}" + } + } + }