mirror of
https://github.com/hexated/cloudstream-extensions-hexated.git
synced 2024-08-15 00:03:22 +00:00
sora: fix some sources & solved #299
This commit is contained in:
parent
39de0eb2b6
commit
ab50fee8a5
18 changed files with 110 additions and 152 deletions
|
@ -93,11 +93,9 @@ open class DramaidProvider : MainAPI() {
|
||||||
val episodes = document.select(".eplister > ul > li").mapNotNull {
|
val episodes = document.select(".eplister > ul > li").mapNotNull {
|
||||||
val name = it.selectFirst("a > .epl-title")?.text()
|
val name = it.selectFirst("a > .epl-title")?.text()
|
||||||
val link = fixUrl(it.selectFirst("a")?.attr("href") ?: return@mapNotNull null)
|
val link = fixUrl(it.selectFirst("a")?.attr("href") ?: return@mapNotNull null)
|
||||||
val epNum = it.selectFirst(".epl-num")?.text()?.toIntOrNull()
|
|
||||||
Episode(
|
Episode(
|
||||||
link,
|
link,
|
||||||
name,
|
name,
|
||||||
episode = epNum
|
|
||||||
)
|
)
|
||||||
}.reversed()
|
}.reversed()
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@ package com.hexated
|
||||||
import com.lagradost.cloudstream3.extractors.Filesim
|
import com.lagradost.cloudstream3.extractors.Filesim
|
||||||
|
|
||||||
class Oppadrama : DramaidProvider() {
|
class Oppadrama : DramaidProvider() {
|
||||||
override var mainUrl = "http://185.217.95.34"
|
override var mainUrl = "http://185.217.95.30"
|
||||||
override var name = "Oppadrama"
|
override var name = "Oppadrama"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import org.jetbrains.kotlin.konan.properties.Properties
|
import org.jetbrains.kotlin.konan.properties.Properties
|
||||||
|
|
||||||
// use an integer for version numbers
|
// use an integer for version numbers
|
||||||
version = 17
|
version = 18
|
||||||
|
|
||||||
android {
|
android {
|
||||||
defaultConfig {
|
defaultConfig {
|
||||||
|
|
|
@ -25,6 +25,11 @@ class FilelionsTo : Filesim() {
|
||||||
override var mainUrl = "https://filelions.to"
|
override var mainUrl = "https://filelions.to"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class FilelionsOn : Filesim() {
|
||||||
|
override val name = "Filelions"
|
||||||
|
override var mainUrl = "https://filelions.online"
|
||||||
|
}
|
||||||
|
|
||||||
class Lylxan : Filesim() {
|
class Lylxan : Filesim() {
|
||||||
override val name = "Lylxan"
|
override val name = "Lylxan"
|
||||||
override var mainUrl = "https://lylxan.com"
|
override var mainUrl = "https://lylxan.com"
|
||||||
|
|
|
@ -21,5 +21,6 @@ class GomovPlugin: Plugin() {
|
||||||
registerExtractorAPI(Embedwish())
|
registerExtractorAPI(Embedwish())
|
||||||
registerExtractorAPI(Doods())
|
registerExtractorAPI(Doods())
|
||||||
registerExtractorAPI(Lylxan())
|
registerExtractorAPI(Lylxan())
|
||||||
|
registerExtractorAPI(FilelionsOn())
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -1,5 +1,5 @@
|
||||||
// use an integer for version numbers
|
// use an integer for version numbers
|
||||||
version = 18
|
version = 19
|
||||||
|
|
||||||
|
|
||||||
cloudstream {
|
cloudstream {
|
||||||
|
|
|
@ -44,46 +44,24 @@ class NontonAnimeIDProvider : MainAPI() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override val mainPage = mainPageOf(
|
||||||
|
"" to "Latest Update",
|
||||||
|
"ongoing-list/" to " Ongoing List",
|
||||||
|
"popular-series/" to "Popular Series",
|
||||||
|
)
|
||||||
|
|
||||||
override suspend fun getMainPage(page: Int, request : MainPageRequest): HomePageResponse {
|
override suspend fun getMainPage(page: Int, request : MainPageRequest): HomePageResponse {
|
||||||
val document = app.get(mainUrl).document
|
val document = app.get("$mainUrl/${request.data}").document
|
||||||
|
val home = document.select(".animeseries").mapNotNull {
|
||||||
val homePageList = ArrayList<HomePageList>()
|
it.toSearchResult()
|
||||||
|
|
||||||
document.select("section#postbaru").forEach { block ->
|
|
||||||
val header = block.selectFirst("h2")!!.text().trim()
|
|
||||||
val animes = block.select("article.animeseries").mapNotNull {
|
|
||||||
it.toSearchResult()
|
|
||||||
}
|
|
||||||
if (animes.isNotEmpty()) homePageList.add(HomePageList(header, animes))
|
|
||||||
}
|
}
|
||||||
|
return newHomePageResponse(request.name, home, hasNext = false)
|
||||||
document.select("aside#sidebar_right > div.side").forEach { block ->
|
|
||||||
val header = block.selectFirst("h3")!!.ownText().trim()
|
|
||||||
val animes = block.select("div.bor").mapNotNull {
|
|
||||||
it.toSearchResultPopular()
|
|
||||||
}
|
|
||||||
if (animes.isNotEmpty()) homePageList.add(HomePageList(header, animes))
|
|
||||||
}
|
|
||||||
|
|
||||||
return HomePageResponse(homePageList)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun Element.toSearchResult(): AnimeSearchResponse? {
|
private fun Element.toSearchResult(): AnimeSearchResponse {
|
||||||
val href = fixUrl(this.selectFirst("a")!!.attr("href"))
|
val href = fixUrl(this.selectFirst("a")!!.attr("href"))
|
||||||
val title = this.selectFirst("h3.title")?.text() ?: return null
|
val title = this.selectFirst(".title")?.text() ?: ""
|
||||||
val posterUrl = fixUrl(this.select("img").attr("src"))
|
val posterUrl = fixUrlNull(this.selectFirst("img")?.attr("data-src"))
|
||||||
|
|
||||||
return newAnimeSearchResponse(title, href, TvType.Anime) {
|
|
||||||
this.posterUrl = posterUrl
|
|
||||||
addDubStatus(dubExist = false, subExist = true)
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun Element.toSearchResultPopular(): AnimeSearchResponse? {
|
|
||||||
val href = fixUrl(this.selectFirst("a")!!.attr("href"))
|
|
||||||
val title = this.selectFirst("h4")?.text()?.trim() ?: return null
|
|
||||||
val posterUrl = fixUrl(this.select("img").attr("src"))
|
|
||||||
|
|
||||||
return newAnimeSearchResponse(title, href, TvType.Anime) {
|
return newAnimeSearchResponse(title, href, TvType.Anime) {
|
||||||
this.posterUrl = posterUrl
|
this.posterUrl = posterUrl
|
||||||
|
@ -207,7 +185,6 @@ class NontonAnimeIDProvider : MainAPI() {
|
||||||
): Boolean {
|
): Boolean {
|
||||||
|
|
||||||
val document = app.get(data).document
|
val document = app.get(data).document
|
||||||
val sources = ArrayList<String>()
|
|
||||||
|
|
||||||
document.select(".container1 > ul > li:not(.boxtab)").apmap {
|
document.select(".container1 > ul > li:not(.boxtab)").apmap {
|
||||||
val dataPost = it.attr("data-post")
|
val dataPost = it.attr("data-post")
|
||||||
|
@ -220,17 +197,14 @@ class NontonAnimeIDProvider : MainAPI() {
|
||||||
"action" to "player_ajax",
|
"action" to "player_ajax",
|
||||||
"post" to dataPost,
|
"post" to dataPost,
|
||||||
"nume" to dataNume,
|
"nume" to dataNume,
|
||||||
"type" to dataType
|
"type" to dataType,
|
||||||
|
"nonce" to "e4dd8e45c2"
|
||||||
),
|
),
|
||||||
referer = data,
|
referer = data,
|
||||||
headers = mapOf("X-Requested-With" to "XMLHttpRequest")
|
headers = mapOf("X-Requested-With" to "XMLHttpRequest")
|
||||||
).document.select("iframe").attr("src")
|
).document.selectFirst("iframe")?.attr("src")
|
||||||
|
|
||||||
sources.add(fixUrl(iframe))
|
loadExtractor(iframe ?: return@apmap , "$mainUrl/", subtitleCallback, callback)
|
||||||
}
|
|
||||||
|
|
||||||
sources.apmap {
|
|
||||||
loadExtractor(it, "$mainUrl/", subtitleCallback, callback)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return true
|
return true
|
||||||
|
@ -255,3 +229,15 @@ class KotakAnimeid2 : Hxfile() {
|
||||||
override val mainUrl = "https://embed2.kotakanimeid.com"
|
override val mainUrl = "https://embed2.kotakanimeid.com"
|
||||||
override val requiresReferer = true
|
override val requiresReferer = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class KotakAnimeidCom : Hxfile() {
|
||||||
|
override val name = "KotakAnimeid"
|
||||||
|
override val mainUrl = "https://nontonanimeid.com"
|
||||||
|
override val requiresReferer = true
|
||||||
|
}
|
||||||
|
|
||||||
|
class EmbedKotakAnimeid : Hxfile() {
|
||||||
|
override val name = "EmbedKotakAnimeid"
|
||||||
|
override val mainUrl = "https://embed2.kotakanimeid.com"
|
||||||
|
override val requiresReferer = true
|
||||||
|
}
|
||||||
|
|
|
@ -11,5 +11,7 @@ class NontonAnimeIDProviderPlugin: Plugin() {
|
||||||
// All providers should be added in this manner. Please don't edit the providers list directly.
|
// All providers should be added in this manner. Please don't edit the providers list directly.
|
||||||
registerMainAPI(NontonAnimeIDProvider())
|
registerMainAPI(NontonAnimeIDProvider())
|
||||||
registerExtractorAPI(KotakAnimeid2())
|
registerExtractorAPI(KotakAnimeid2())
|
||||||
|
registerExtractorAPI(KotakAnimeidCom())
|
||||||
|
registerExtractorAPI(EmbedKotakAnimeid())
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -1,5 +1,5 @@
|
||||||
// use an integer for version numbers
|
// use an integer for version numbers
|
||||||
version = 15
|
version = 16
|
||||||
|
|
||||||
|
|
||||||
cloudstream {
|
cloudstream {
|
||||||
|
|
|
@ -282,3 +282,8 @@ class DesuBeta : JWPlayer() {
|
||||||
override val name = "DesuBeta"
|
override val name = "DesuBeta"
|
||||||
override val mainUrl = "https://desustream.me/beta/"
|
override val mainUrl = "https://desustream.me/beta/"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class Desudesuhd : JWPlayer() {
|
||||||
|
override val name = "Desudesuhd"
|
||||||
|
override val mainUrl = "https://desustream.me/desudesuhd/"
|
||||||
|
}
|
||||||
|
|
|
@ -12,5 +12,6 @@ class OtakudesuProviderPlugin: Plugin() {
|
||||||
registerMainAPI(OtakudesuProvider())
|
registerMainAPI(OtakudesuProvider())
|
||||||
registerExtractorAPI(Moedesu())
|
registerExtractorAPI(Moedesu())
|
||||||
registerExtractorAPI(DesuBeta())
|
registerExtractorAPI(DesuBeta())
|
||||||
|
registerExtractorAPI(Desudesuhd())
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -14,7 +14,7 @@ import org.jsoup.Jsoup
|
||||||
import org.jsoup.nodes.Element
|
import org.jsoup.nodes.Element
|
||||||
|
|
||||||
class Samehadaku : MainAPI() {
|
class Samehadaku : MainAPI() {
|
||||||
override var mainUrl = "https://samehadaku.bond"
|
override var mainUrl = "https://samehadaku.help"
|
||||||
override var name = "Samehadaku"
|
override var name = "Samehadaku"
|
||||||
override val hasMainPage = true
|
override val hasMainPage = true
|
||||||
override var lang = "id"
|
override var lang = "id"
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
import org.jetbrains.kotlin.konan.properties.Properties
|
import org.jetbrains.kotlin.konan.properties.Properties
|
||||||
|
|
||||||
// use an integer for version numbers
|
// use an integer for version numbers
|
||||||
version = 175
|
version = 176
|
||||||
|
|
||||||
android {
|
android {
|
||||||
defaultConfig {
|
defaultConfig {
|
||||||
|
|
|
@ -1653,15 +1653,12 @@ object SoraExtractor : SoraStream() {
|
||||||
"$rStreamAPI/e/?tmdb=$id&s=$season&e=$episode"
|
"$rStreamAPI/e/?tmdb=$id&s=$season&e=$episode"
|
||||||
}
|
}
|
||||||
|
|
||||||
val res = app.get(url).text
|
val res = app.get(url, referer = "https://watcha.movie/").text
|
||||||
val link = Regex("\"file\":\"(http.*?)\"").find(res)?.groupValues?.getOrNull(1) ?: return
|
val link = Regex("\"file\":\"(http.*?)\"").find(res)?.groupValues?.getOrNull(1) ?: return
|
||||||
|
|
||||||
delay(1000)
|
|
||||||
if (!app.get(link, referer = rStreamAPI).isSuccessful) return
|
|
||||||
|
|
||||||
callback.invoke(
|
callback.invoke(
|
||||||
ExtractorLink(
|
ExtractorLink(
|
||||||
"RStream", "RStream", link, rStreamAPI, Qualities.P720.value, link.contains(".m3u8")
|
"RStream", "RStream", link, rStreamAPI, Qualities.P720.value, INFER_TYPE
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
@ -2057,7 +2054,7 @@ object SoraExtractor : SoraStream() {
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
suspend fun invokePrimewire(
|
suspend fun invokeGomovies(
|
||||||
title: String? = null,
|
title: String? = null,
|
||||||
year: Int? = null,
|
year: Int? = null,
|
||||||
season: Int? = null,
|
season: Int? = null,
|
||||||
|
@ -2070,10 +2067,10 @@ object SoraExtractor : SoraStream() {
|
||||||
season,
|
season,
|
||||||
episode,
|
episode,
|
||||||
callback,
|
callback,
|
||||||
primewireAPI,
|
gomoviesAPI,
|
||||||
"Primewire",
|
"Gomovies",
|
||||||
"RvnMfoxhgm",
|
"_smQamBQsETb",
|
||||||
"vvqUtffkId"
|
"_sBWcqbTBMaT"
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2175,7 +2172,6 @@ object SoraExtractor : SoraStream() {
|
||||||
|
|
||||||
suspend fun invokeWatchOnline(
|
suspend fun invokeWatchOnline(
|
||||||
imdbId: String? = null,
|
imdbId: String? = null,
|
||||||
tmdbId: Int? = null,
|
|
||||||
title: String? = null,
|
title: String? = null,
|
||||||
year: Int? = null,
|
year: Int? = null,
|
||||||
season: Int? = null,
|
season: Int? = null,
|
||||||
|
@ -2186,98 +2182,59 @@ object SoraExtractor : SoraStream() {
|
||||||
val id = imdbId?.removePrefix("tt")
|
val id = imdbId?.removePrefix("tt")
|
||||||
val slug = title.createSlug()
|
val slug = title.createSlug()
|
||||||
val url = if (season == null) {
|
val url = if (season == null) {
|
||||||
"$watchOnlineAPI/movies/view/$id-$slug-$year"
|
"$watchOnlineAPI/movies/play/$id-$slug-$year"
|
||||||
} else {
|
} else {
|
||||||
"$watchOnlineAPI/shows/view/$id-$slug-$year"
|
"$watchOnlineAPI/shows/play/$id-$slug-$year"
|
||||||
}
|
}
|
||||||
|
|
||||||
var res = app.get(url)
|
var res = app.get(url)
|
||||||
if (res.code == 403) return
|
if (res.code == 403) return
|
||||||
if (!res.isSuccessful) res = searchWatchOnline(title, season, imdbId, tmdbId) ?: return
|
if (!res.isSuccessful) res = searchWatchOnline(title, season, year) ?: return
|
||||||
val doc = res.document
|
val doc = res.document
|
||||||
val episodeId = if (season == null) {
|
val script = doc.selectFirst("script:containsData(hash:)")?.data()
|
||||||
doc.selectFirst("div.movie__buttons-items a")?.attr("data-watch-list-media-id")
|
|
||||||
} else {
|
|
||||||
doc.select("ul[data-season-episodes=$season] li").find {
|
|
||||||
it.select("div.episodes__number").text().equals("Episode $episode", true)
|
|
||||||
}?.attr("data-id-episode")
|
|
||||||
} ?: return
|
|
||||||
argamap({
|
|
||||||
invokeMonster(res.url.substringAfterLast("/"), episodeId, season, callback)
|
|
||||||
}, {
|
|
||||||
val videoUrl = if (season == null) {
|
|
||||||
"$watchOnlineAPI/api/v1/security/movie-access?id_movie=$episodeId"
|
|
||||||
} else {
|
|
||||||
"$watchOnlineAPI/api/v1/security/episode-access?id=$episodeId"
|
|
||||||
}
|
|
||||||
|
|
||||||
val json = app.get(videoUrl, referer = url).parsedSafe<WatchOnlineResponse>()
|
|
||||||
|
|
||||||
json?.streams?.mapKeys { source ->
|
|
||||||
callback.invoke(
|
|
||||||
ExtractorLink(
|
|
||||||
"WatchOnline",
|
|
||||||
"WatchOnline",
|
|
||||||
source.value,
|
|
||||||
"$watchOnlineAPI/",
|
|
||||||
getQualityFromName(source.key),
|
|
||||||
true
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
val subtitles = json?.subtitles as ArrayList<HashMap<String, String>>
|
|
||||||
subtitles.map { sub ->
|
|
||||||
subtitleCallback.invoke(
|
|
||||||
SubtitleFile(
|
|
||||||
sub["language"] ?: return@map,
|
|
||||||
fixUrl(sub["url"] ?: return@map, watchOnlineAPI)
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
private suspend fun invokeMonster(
|
|
||||||
urlSlug: String? = null,
|
|
||||||
episodeId: String? = null,
|
|
||||||
season: Int? = null,
|
|
||||||
callback: (ExtractorLink) -> Unit,
|
|
||||||
) {
|
|
||||||
val monsterMainUrl = "https://lookmovie.foundation"
|
|
||||||
val viewSlug = if (season == null) {
|
|
||||||
"movies/view/$urlSlug"
|
|
||||||
} else {
|
|
||||||
"shows/view/$urlSlug"
|
|
||||||
}
|
|
||||||
val streamUrl =
|
|
||||||
app.get("$monsterMainUrl/$viewSlug").document.select("a.round-button:first-child")
|
|
||||||
.attr("href")
|
|
||||||
val res = app.get(fixUrl(streamUrl, monsterMainUrl)).document
|
|
||||||
val script = res.selectFirst("script:containsData(hash:)")?.data()
|
|
||||||
val hash = Regex("hash:\\s*['\"](\\S+)['\"]").find(script ?: return)?.groupValues?.get(1)
|
val hash = Regex("hash:\\s*['\"](\\S+)['\"]").find(script ?: return)?.groupValues?.get(1)
|
||||||
val expires = Regex("expires:\\s*(\\d+)").find(script)?.groupValues?.get(1)
|
val expires = Regex("expires:\\s*(\\d+)").find(script)?.groupValues?.get(1)
|
||||||
|
val episodeId = (if(season == null) {
|
||||||
|
"""id_movie:\s*(\d+)"""
|
||||||
|
} else {
|
||||||
|
"""episode:\s*['"]$episode['"],[\n\s]+id_episode:\s*(\d+),[\n\s]+season:\s*['"]$season['"]"""
|
||||||
|
}).let { it.toRegex().find(script)?.groupValues?.get(1) }
|
||||||
|
|
||||||
val videoUrl = if (season == null) {
|
val videoUrl = if (season == null) {
|
||||||
"$monsterMainUrl/api/v1/security/movie-access?id_movie=$episodeId&hash=$hash&expires=$expires"
|
"$watchOnlineAPI/api/v1/security/movie-access?id_movie=$episodeId&hash=$hash&expires=$expires"
|
||||||
} else {
|
} else {
|
||||||
"$monsterMainUrl/api/v1/security/episode-access?id_episode=$episodeId&hash=$hash&expires=$expires"
|
"$watchOnlineAPI/api/v1/security/episode-access?id_episode=$episodeId&hash=$hash&expires=$expires"
|
||||||
}
|
}
|
||||||
|
|
||||||
app.get(
|
val sources = app.get(
|
||||||
videoUrl, referer = streamUrl, headers = mapOf("X-Requested-With" to "XMLHttpRequest")
|
videoUrl,
|
||||||
).parsedSafe<WatchOnlineResponse>()?.streams?.mapKeys { source ->
|
referer = url,
|
||||||
|
headers = mapOf("X-Requested-With" to "XMLHttpRequest")
|
||||||
|
).parsedSafe<WatchOnlineResponse>()
|
||||||
|
|
||||||
|
sources?.streams?.mapKeys { source ->
|
||||||
callback.invoke(
|
callback.invoke(
|
||||||
ExtractorLink(
|
ExtractorLink(
|
||||||
"WatchOnline",
|
"WatchOnline",
|
||||||
"WatchOnline",
|
"WatchOnline",
|
||||||
source.value,
|
source.value,
|
||||||
"$monsterMainUrl/",
|
"$watchOnlineAPI/",
|
||||||
getQualityFromName(source.key),
|
getQualityFromName(source.key),
|
||||||
true
|
true
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
sources?.subtitles?.map { sub ->
|
||||||
|
val file = sub.file.toString()
|
||||||
|
subtitleCallback.invoke(
|
||||||
|
SubtitleFile(
|
||||||
|
sub.language ?: return@map,
|
||||||
|
if(file.startsWith("[")) return@map else fixUrl(file, watchOnlineAPI),
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
suspend fun invokeNinetv(
|
suspend fun invokeNinetv(
|
||||||
|
|
|
@ -195,19 +195,25 @@ data class JikanResponse(
|
||||||
@JsonProperty("data") val data: JikanData? = null,
|
@JsonProperty("data") val data: JikanData? = null,
|
||||||
)
|
)
|
||||||
|
|
||||||
data class WatchOnlineItems(
|
data class WatchOnlineResults(
|
||||||
@JsonProperty("slug") val slug: String? = null,
|
@JsonProperty("slug") val slug: String? = null,
|
||||||
@JsonProperty("tmdb_id") val tmdb_id: Int? = null,
|
@JsonProperty("title") val title: String? = null,
|
||||||
@JsonProperty("imdb_id") val imdb_id: String? = null,
|
@JsonProperty("year") val year: String? = null,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
data class WatchOnlineSearch(
|
data class WatchOnlineSearch(
|
||||||
@JsonProperty("items") val items: ArrayList<WatchOnlineItems>? = arrayListOf(),
|
@JsonProperty("result") val result: ArrayList<WatchOnlineResults>? = arrayListOf(),
|
||||||
|
)
|
||||||
|
|
||||||
|
data class WatchOnlineSubtitles(
|
||||||
|
@JsonProperty("language") val language: String? = null,
|
||||||
|
@JsonProperty("file") val file: Any? = null,
|
||||||
)
|
)
|
||||||
|
|
||||||
data class WatchOnlineResponse(
|
data class WatchOnlineResponse(
|
||||||
@JsonProperty("streams") val streams: HashMap<String, String>? = null,
|
@JsonProperty("streams") val streams: HashMap<String, String>? = null,
|
||||||
@JsonProperty("subtitles") val subtitles: Any? = null,
|
@JsonProperty("subtitles") val subtitles: ArrayList<WatchOnlineSubtitles>? = arrayListOf(),
|
||||||
)
|
)
|
||||||
|
|
||||||
data class CryMoviesProxyHeaders(
|
data class CryMoviesProxyHeaders(
|
||||||
|
|
|
@ -42,7 +42,7 @@ import com.hexated.SoraExtractor.invokeMultimovies
|
||||||
import com.hexated.SoraExtractor.invokeNetflix
|
import com.hexated.SoraExtractor.invokeNetflix
|
||||||
import com.hexated.SoraExtractor.invokeNetmovies
|
import com.hexated.SoraExtractor.invokeNetmovies
|
||||||
import com.hexated.SoraExtractor.invokePobmovies
|
import com.hexated.SoraExtractor.invokePobmovies
|
||||||
import com.hexated.SoraExtractor.invokePrimewire
|
import com.hexated.SoraExtractor.invokeGomovies
|
||||||
import com.hexated.SoraExtractor.invokePutactor
|
import com.hexated.SoraExtractor.invokePutactor
|
||||||
import com.hexated.SoraExtractor.invokeTvMovies
|
import com.hexated.SoraExtractor.invokeTvMovies
|
||||||
import com.hexated.SoraExtractor.invokeUhdmovies
|
import com.hexated.SoraExtractor.invokeUhdmovies
|
||||||
|
@ -109,7 +109,7 @@ open class SoraStream : TmdbProvider() {
|
||||||
const val flixonAPI = "https://flixon.lol"
|
const val flixonAPI = "https://flixon.lol"
|
||||||
const val smashyStreamAPI = "https://embed.smashystream.com"
|
const val smashyStreamAPI = "https://embed.smashystream.com"
|
||||||
const val watchSomuchAPI = "https://watchsomuch.tv" // sub only
|
const val watchSomuchAPI = "https://watchsomuch.tv" // sub only
|
||||||
const val watchOnlineAPI = "https://watchonline.ag"
|
const val watchOnlineAPI = "https://lookmovie.foundation"
|
||||||
const val nineTvAPI = "https://moviesapi.club"
|
const val nineTvAPI = "https://moviesapi.club"
|
||||||
const val nowTvAPI = "https://myfilestorage.xyz"
|
const val nowTvAPI = "https://myfilestorage.xyz"
|
||||||
const val gokuAPI = "https://goku.sx"
|
const val gokuAPI = "https://goku.sx"
|
||||||
|
@ -121,7 +121,6 @@ open class SoraStream : TmdbProvider() {
|
||||||
const val netmoviesAPI = "https://netmovies.to"
|
const val netmoviesAPI = "https://netmovies.to"
|
||||||
const val momentAPI = "https://moment-explanation-i-244.site"
|
const val momentAPI = "https://moment-explanation-i-244.site"
|
||||||
const val doomoviesAPI = "https://doomovies.net"
|
const val doomoviesAPI = "https://doomovies.net"
|
||||||
const val primewireAPI = "https://real-primewire.club"
|
|
||||||
const val vidsrctoAPI = "https://vidsrc.to"
|
const val vidsrctoAPI = "https://vidsrc.to"
|
||||||
const val dramadayAPI = "https://dramaday.me"
|
const val dramadayAPI = "https://dramaday.me"
|
||||||
const val animetoshoAPI = "https://animetosho.org"
|
const val animetoshoAPI = "https://animetosho.org"
|
||||||
|
@ -132,6 +131,7 @@ open class SoraStream : TmdbProvider() {
|
||||||
const val netflixAPI = "https://m.netflixmirror.com"
|
const val netflixAPI = "https://m.netflixmirror.com"
|
||||||
const val hdmovies4uAPI = "https://hdmovies4u.name"
|
const val hdmovies4uAPI = "https://hdmovies4u.name"
|
||||||
const val watchflxAPI = "https://watchflx.tv"
|
const val watchflxAPI = "https://watchflx.tv"
|
||||||
|
const val gomoviesAPI = "https://gomovies-online.cam"
|
||||||
const val dotmoviesAPI = "https://dotmovies.today"
|
const val dotmoviesAPI = "https://dotmovies.today"
|
||||||
|
|
||||||
// INDEX SITE
|
// INDEX SITE
|
||||||
|
@ -585,7 +585,7 @@ open class SoraStream : TmdbProvider() {
|
||||||
)
|
)
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
if (!res.isAnime) invokePrimewire(res.title, res.year, res.season, res.episode, callback)
|
if (!res.isAnime) invokeGomovies(res.title, res.year, res.season, res.episode, callback)
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
if (!res.isAnime) invokePutactor(res.title, res.year, res.season, res.episode, callback)
|
if (!res.isAnime) invokePutactor(res.title, res.year, res.season, res.episode, callback)
|
||||||
|
@ -604,7 +604,6 @@ open class SoraStream : TmdbProvider() {
|
||||||
{
|
{
|
||||||
invokeWatchOnline(
|
invokeWatchOnline(
|
||||||
res.imdbId,
|
res.imdbId,
|
||||||
res.id,
|
|
||||||
res.title,
|
res.title,
|
||||||
res.airedYear ?: res.year,
|
res.airedYear ?: res.year,
|
||||||
res.season,
|
res.season,
|
||||||
|
|
|
@ -27,7 +27,7 @@ import com.hexated.SoraExtractor.invokeMoment
|
||||||
import com.hexated.SoraExtractor.invokeMultimovies
|
import com.hexated.SoraExtractor.invokeMultimovies
|
||||||
import com.hexated.SoraExtractor.invokeNetflix
|
import com.hexated.SoraExtractor.invokeNetflix
|
||||||
import com.hexated.SoraExtractor.invokeNetmovies
|
import com.hexated.SoraExtractor.invokeNetmovies
|
||||||
import com.hexated.SoraExtractor.invokePrimewire
|
import com.hexated.SoraExtractor.invokeGomovies
|
||||||
import com.hexated.SoraExtractor.invokePutactor
|
import com.hexated.SoraExtractor.invokePutactor
|
||||||
import com.hexated.SoraExtractor.invokeVidSrc
|
import com.hexated.SoraExtractor.invokeVidSrc
|
||||||
import com.hexated.SoraExtractor.invokeVidsrcto
|
import com.hexated.SoraExtractor.invokeVidsrcto
|
||||||
|
@ -207,7 +207,7 @@ class SoraStreamLite : SoraStream() {
|
||||||
if (!res.isAnime) invokeFlixon(res.id, res.imdbId, res.season, res.episode, callback)
|
if (!res.isAnime) invokeFlixon(res.id, res.imdbId, res.season, res.episode, callback)
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
if (!res.isAnime) invokePrimewire(res.title, res.year, res.season, res.episode, callback)
|
if (!res.isAnime) invokeGomovies(res.title, res.year, res.season, res.episode, callback)
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
if (!res.isAnime) invokePutactor(res.title, res.year, res.season, res.episode, callback)
|
if (!res.isAnime) invokePutactor(res.title, res.year, res.season, res.episode, callback)
|
||||||
|
@ -215,7 +215,6 @@ class SoraStreamLite : SoraStream() {
|
||||||
{
|
{
|
||||||
invokeWatchOnline(
|
invokeWatchOnline(
|
||||||
res.imdbId,
|
res.imdbId,
|
||||||
res.id,
|
|
||||||
res.title,
|
res.title,
|
||||||
res.airedYear ?: res.year,
|
res.airedYear ?: res.year,
|
||||||
res.season,
|
res.season,
|
||||||
|
|
|
@ -841,26 +841,25 @@ fun Document.findTvMoviesIframe(): String? {
|
||||||
suspend fun searchWatchOnline(
|
suspend fun searchWatchOnline(
|
||||||
title: String? = null,
|
title: String? = null,
|
||||||
season: Int? = null,
|
season: Int? = null,
|
||||||
imdbId: String? = null,
|
year: Int? = null,
|
||||||
tmdbId: Int? = null,
|
|
||||||
): NiceResponse? {
|
): NiceResponse? {
|
||||||
val wTitle = title?.dropLast(1) // weird but this will make search working
|
val wTitle = title?.dropLast(1) // weird but this will make search working
|
||||||
val mediaId = app.get(
|
val mediaId = app.get(
|
||||||
if (season == null) {
|
if (season == null) {
|
||||||
"${watchOnlineAPI}/api/v1/movies?filters[q]=$wTitle"
|
"${watchOnlineAPI}/api/v1/do-search/?q=$wTitle"
|
||||||
} else {
|
} else {
|
||||||
"${watchOnlineAPI}/api/v1/shows?filters[q]=$wTitle"
|
"${watchOnlineAPI}/api/v1/do-search/?q=$wTitle"
|
||||||
}
|
}
|
||||||
).parsedSafe<WatchOnlineSearch>()?.items?.find {
|
).parsedSafe<WatchOnlineSearch>()?.result?.find {
|
||||||
it.imdb_id == imdbId || it.tmdb_id == tmdbId || it.imdb_id == imdbId?.removePrefix("tt")
|
it.title.equals(title, true) && it.year.equals("$year")
|
||||||
}?.slug
|
}?.slug
|
||||||
|
|
||||||
return app.get(
|
return app.get(
|
||||||
fixUrl(
|
fixUrl(
|
||||||
mediaId ?: return null, if (season == null) {
|
mediaId ?: return null, if (season == null) {
|
||||||
"${watchOnlineAPI}/movies/view"
|
"${watchOnlineAPI}/movies/play"
|
||||||
} else {
|
} else {
|
||||||
"${watchOnlineAPI}/shows/view"
|
"${watchOnlineAPI}/shows/play"
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
Loading…
Reference in a new issue