mirror of
https://github.com/hexated/cloudstream-extensions-hexated.git
synced 2024-08-15 00:03:22 +00:00
[Sora] Scraping only highest res in UHD
This commit is contained in:
parent
d267b0791f
commit
463dd39857
3 changed files with 91 additions and 31 deletions
|
@ -1,5 +1,5 @@
|
||||||
// use an integer for version numbers
|
// use an integer for version numbers
|
||||||
version = 57
|
version = 58
|
||||||
|
|
||||||
|
|
||||||
cloudstream {
|
cloudstream {
|
||||||
|
|
|
@ -843,8 +843,10 @@ object SoraExtractor : SoraStream() {
|
||||||
}
|
}
|
||||||
|
|
||||||
json?.definitionList?.apmap { video ->
|
json?.definitionList?.apmap { video ->
|
||||||
val body = """[{"category":$type,"contentId":"$id","episodeId":${json.id},"definition":"${video.code}"}]""".toRequestBody(
|
val body =
|
||||||
RequestBodyTypes.JSON.toMediaTypeOrNull())
|
"""[{"category":$type,"contentId":"$id","episodeId":${json.id},"definition":"${video.code}"}]""".toRequestBody(
|
||||||
|
RequestBodyTypes.JSON.toMediaTypeOrNull()
|
||||||
|
)
|
||||||
val response = app.post(
|
val response = app.post(
|
||||||
"${vipAPI}/media/bathGetplayInfo",
|
"${vipAPI}/media/bathGetplayInfo",
|
||||||
requestBody = body,
|
requestBody = body,
|
||||||
|
@ -879,7 +881,10 @@ object SoraExtractor : SoraStream() {
|
||||||
}
|
}
|
||||||
|
|
||||||
val doc = app.get(url).text
|
val doc = app.get(url).text
|
||||||
val link = Regex("[\"|']file[\"|']:\\s?[\"|'](http.*?.mp4)[\"|'],").find(doc)?.groupValues?.getOrNull(1)
|
val link =
|
||||||
|
Regex("[\"|']file[\"|']:\\s?[\"|'](http.*?.mp4)[\"|'],").find(doc)?.groupValues?.getOrNull(
|
||||||
|
1
|
||||||
|
)
|
||||||
|
|
||||||
callback.invoke(
|
callback.invoke(
|
||||||
ExtractorLink(
|
ExtractorLink(
|
||||||
|
@ -1197,38 +1202,49 @@ object SoraExtractor : SoraStream() {
|
||||||
|
|
||||||
val detailDoc = app.get(script?.first ?: return).document
|
val detailDoc = app.get(script?.first ?: return).document
|
||||||
|
|
||||||
val iframe =
|
val iframeList = detailDoc.select("div.entry-content p").map { it }
|
||||||
detailDoc.select("div.entry-content p").map { it }
|
.filter { it.text().filterIframe(season, lastSeason, year) }
|
||||||
.filter { it.text().filterIframe(season, lastSeason, year) }
|
.mapNotNull {
|
||||||
.mapNotNull {
|
if (season == null) {
|
||||||
if (season == null) {
|
it.text() to it.nextElementSibling()?.select("a")?.attr("href")
|
||||||
it.text() to it.nextElementSibling()?.select("a")?.attr("href")
|
} else {
|
||||||
} else {
|
it.text() to it.nextElementSibling()?.select("a:contains(Episode $episode)")
|
||||||
it.text() to it.nextElementSibling()?.select("a:contains(Episode $episode)")
|
?.attr("href")
|
||||||
?.attr("href")
|
}
|
||||||
}
|
}.filter { it.second?.contains(Regex("(https:)|(http:)")) == true }
|
||||||
}.filter { it.second?.contains(Regex("(https:)|(http:)")) == true }
|
|
||||||
|
|
||||||
val base = getBaseUrl(iframe.first().second ?: return)
|
val iframe = if (iframeList.any { it.first.contains("2160p", true) }) iframeList.filter {
|
||||||
|
it.first.contains(
|
||||||
|
"2160p",
|
||||||
|
true
|
||||||
|
)
|
||||||
|
} else iframeList.filter { it.first.contains("1080p", true) }
|
||||||
|
|
||||||
|
val base = "https://drivebit.in"
|
||||||
iframe.apmap { (quality, link) ->
|
iframe.apmap { (quality, link) ->
|
||||||
delay(2000)
|
delay(2000)
|
||||||
val res = app.get(link ?: return@apmap null).document
|
val driveLink = bypassHrefli(link ?: return@apmap null)
|
||||||
|
val res = app.get(driveLink ?: return@apmap null).document
|
||||||
val resDoc = res.selectFirst("script")?.data()?.substringAfter("replace(\"")
|
val resDoc = res.selectFirst("script")?.data()?.substringAfter("replace(\"")
|
||||||
?.substringBefore("\")")?.let {
|
?.substringBefore("\")")?.let {
|
||||||
app.get(fixUrl(it, base)).document
|
app.get(fixUrl(it, base)).document
|
||||||
}
|
}
|
||||||
val bitLink = resDoc?.selectFirst("a.btn.btn-outline-success")?.attr("href")
|
val bitLink = resDoc?.selectFirst("a.btn.btn-outline-success")?.attr("href")
|
||||||
val downloadLink = if(bitLink.isNullOrEmpty()) {
|
val downloadLink = if (bitLink.isNullOrEmpty()) {
|
||||||
val backupIframe = resDoc?.select("a.btn.btn-outline-warning")?.attr("href")
|
val backupIframe = resDoc?.select("a.btn.btn-outline-warning")?.attr("href")
|
||||||
extractBackupUHD(backupIframe ?: return@apmap null)
|
extractBackupUHD(backupIframe ?: return@apmap null)
|
||||||
} else {
|
} else {
|
||||||
extractMirrorUHD(bitLink, base)
|
extractMirrorUHD(bitLink, base)
|
||||||
}
|
}
|
||||||
|
|
||||||
val videoQuality = Regex("\\d{3,4}p\\.?(.*?)\\[").find(quality)?.groupValues?.getOrNull(1)?.trim() ?: ""
|
val videoQuality =
|
||||||
val qualities = Regex("(\\d{3,4})p").find(quality)?.groupValues?.getOrNull(1)?.toIntOrNull()
|
Regex("\\d{3,4}p\\.?(.*?)\\[").find(quality)?.groupValues?.getOrNull(1)?.trim()
|
||||||
|
?: ""
|
||||||
|
val qualities =
|
||||||
|
Regex("(\\d{3,4})p").find(quality)?.groupValues?.getOrNull(1)?.toIntOrNull()
|
||||||
?: Qualities.Unknown.value
|
?: Qualities.Unknown.value
|
||||||
val size = Regex("(?i)\\[(\\S+\\s?(gb|mb))[]/]").find(quality)?.groupValues?.getOrNull(1)
|
val size =
|
||||||
|
Regex("(?i)\\[(\\S+\\s?(gb|mb))[]/]").find(quality)?.groupValues?.getOrNull(1)
|
||||||
?.let { "[$it]" } ?: quality
|
?.let { "[$it]" } ?: quality
|
||||||
callback.invoke(
|
callback.invoke(
|
||||||
ExtractorLink(
|
ExtractorLink(
|
||||||
|
@ -1431,17 +1447,21 @@ object SoraExtractor : SoraStream() {
|
||||||
val link = fixUrl(script?.third ?: return, m4uhdAPI)
|
val link = fixUrl(script?.third ?: return, m4uhdAPI)
|
||||||
val request = app.get(link)
|
val request = app.get(link)
|
||||||
var cookiesSet = request.headers.filter { it.first == "set-cookie" }
|
var cookiesSet = request.headers.filter { it.first == "set-cookie" }
|
||||||
var xsrf = cookiesSet.find { it.second.contains("XSRF-TOKEN") }?.second?.substringAfter("XSRF-TOKEN=")
|
var xsrf =
|
||||||
?.substringBefore(";")
|
cookiesSet.find { it.second.contains("XSRF-TOKEN") }?.second?.substringAfter("XSRF-TOKEN=")
|
||||||
var session = cookiesSet.find { it.second.contains("laravel_session") }?.second?.substringAfter("laravel_session=")
|
?.substringBefore(";")
|
||||||
?.substringBefore(";")
|
var session =
|
||||||
|
cookiesSet.find { it.second.contains("laravel_session") }?.second?.substringAfter("laravel_session=")
|
||||||
|
?.substringBefore(";")
|
||||||
|
|
||||||
val doc = request.document
|
val doc = request.document
|
||||||
val token = doc.selectFirst("meta[name=csrf-token]")?.attr("content")
|
val token = doc.selectFirst("meta[name=csrf-token]")?.attr("content")
|
||||||
val m4uData = if (season == null) {
|
val m4uData = if (season == null) {
|
||||||
doc.select("div.le-server span#fem").attr("data")
|
doc.select("div.le-server span#fem").attr("data")
|
||||||
} else {
|
} else {
|
||||||
val episodeData = doc.selectFirst("div.col-lg-9.col-xl-9 p:matches((?i)S0?$season-E0?$episode$)") ?: return
|
val episodeData =
|
||||||
|
doc.selectFirst("div.col-lg-9.col-xl-9 p:matches((?i)S0?$season-E0?$episode$)")
|
||||||
|
?: return
|
||||||
val idepisode = episodeData.select("button").attr("idepisode") ?: return
|
val idepisode = episodeData.select("button").attr("idepisode") ?: return
|
||||||
val requestEmbed = app.post(
|
val requestEmbed = app.post(
|
||||||
"$m4uhdAPI/ajaxtv",
|
"$m4uhdAPI/ajaxtv",
|
||||||
|
@ -1459,10 +1479,12 @@ object SoraExtractor : SoraStream() {
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
cookiesSet = requestEmbed.headers.filter { it.first == "set-cookie" }
|
cookiesSet = requestEmbed.headers.filter { it.first == "set-cookie" }
|
||||||
xsrf = cookiesSet.find { it.second.contains("XSRF-TOKEN") }?.second?.substringAfter("XSRF-TOKEN=")
|
xsrf =
|
||||||
?.substringBefore(";")
|
cookiesSet.find { it.second.contains("XSRF-TOKEN") }?.second?.substringAfter("XSRF-TOKEN=")
|
||||||
session = cookiesSet.find { it.second.contains("laravel_session") }?.second?.substringAfter("laravel_session=")
|
?.substringBefore(";")
|
||||||
?.substringBefore(";")
|
session =
|
||||||
|
cookiesSet.find { it.second.contains("laravel_session") }?.second?.substringAfter("laravel_session=")
|
||||||
|
?.substringBefore(";")
|
||||||
requestEmbed.document.select("span#fem").attr("data")
|
requestEmbed.document.select("span#fem").attr("data")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1609,7 +1631,7 @@ object SoraExtractor : SoraStream() {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
class StreamM4u: XStreamCdn() {
|
class StreamM4u : XStreamCdn() {
|
||||||
override val name: String = "StreamM4u"
|
override val name: String = "StreamM4u"
|
||||||
override val mainUrl: String = "https://streamm4u.club"
|
override val mainUrl: String = "https://streamm4u.club"
|
||||||
}
|
}
|
||||||
|
|
|
@ -228,6 +228,44 @@ suspend fun bypassFdAds(url: String): String? {
|
||||||
return app.get(finalLink ?: return null, verify = false).url
|
return app.get(finalLink ?: return null, verify = false).url
|
||||||
}
|
}
|
||||||
|
|
||||||
|
suspend fun bypassHrefli(url: String): String? {
|
||||||
|
val direct = url.removePrefix("https://href.li/?")
|
||||||
|
|
||||||
|
val res = app.get(direct).document
|
||||||
|
val formLink = res.select("form#landing").attr("action")
|
||||||
|
val wpHttp = res.select("input[name=_wp_http]").attr("value")
|
||||||
|
|
||||||
|
val res2 = app.post(formLink, data = mapOf("_wp_http" to wpHttp)).document
|
||||||
|
val formLink2 = res2.select("form#landing").attr("action")
|
||||||
|
val wpHttp2 = res2.select("input[name=_wp_http2]").attr("value")
|
||||||
|
val token = res2.select("input[name=token]").attr("value")
|
||||||
|
|
||||||
|
val res3 = app.post(
|
||||||
|
formLink2, data = mapOf(
|
||||||
|
"_wp_http2" to wpHttp2, "token" to token
|
||||||
|
)
|
||||||
|
).document
|
||||||
|
|
||||||
|
val script = res3.selectFirst("script:containsData(verify_button)")?.data()
|
||||||
|
val directLink = script?.substringAfter("\"href\",\"")?.substringBefore("\")")
|
||||||
|
val matchCookies =
|
||||||
|
Regex("sumitbot_\\('(\\S+?)',\n|.?'(\\S+?)',").findAll(script ?: return null).map {
|
||||||
|
it.groupValues[1] to it.groupValues[2]
|
||||||
|
}.toList()
|
||||||
|
|
||||||
|
val cookeName = matchCookies.firstOrNull()?.second ?: return null
|
||||||
|
val cookeValue = matchCookies.lastOrNull()?.second ?: return null
|
||||||
|
|
||||||
|
val cookies = mapOf(
|
||||||
|
cookeName to cookeValue
|
||||||
|
)
|
||||||
|
|
||||||
|
return app.get(
|
||||||
|
directLink ?: return null,
|
||||||
|
cookies = cookies
|
||||||
|
).document.selectFirst("meta[http-equiv=refresh]")?.attr("content")?.substringAfter("url=")
|
||||||
|
}
|
||||||
|
|
||||||
suspend fun getTvMoviesServer(url: String, season: Int?, episode: Int?): Pair<String, String?>? {
|
suspend fun getTvMoviesServer(url: String, season: Int?, episode: Int?): Pair<String, String?>? {
|
||||||
|
|
||||||
val req = app.get(url)
|
val req = app.get(url)
|
||||||
|
|
Loading…
Reference in a new issue