Yomiroll: Remove season grouping (#1362)
as it is creating more problems than the tracker issue and cr is fixing their duplicate season stuff anyway
This commit is contained in:
@ -6,7 +6,7 @@ ext {
|
|||||||
extName = 'Yomiroll'
|
extName = 'Yomiroll'
|
||||||
pkgNameSuffix = 'all.kamyroll'
|
pkgNameSuffix = 'all.kamyroll'
|
||||||
extClass = '.Yomiroll'
|
extClass = '.Yomiroll'
|
||||||
extVersionCode = 18
|
extVersionCode = 19
|
||||||
libVersion = '13'
|
libVersion = '13'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -132,7 +132,7 @@ data class EpisodeResult(
|
|||||||
@SerialName("episode_air_date")
|
@SerialName("episode_air_date")
|
||||||
val airDate: String? = null,
|
val airDate: String? = null,
|
||||||
val versions: ArrayList<Version>? = null,
|
val versions: ArrayList<Version>? = null,
|
||||||
val streams_link: String,
|
val streams_link: String? = null,
|
||||||
) {
|
) {
|
||||||
@Serializable
|
@Serializable
|
||||||
data class Version(
|
data class Version(
|
||||||
@ -143,14 +143,6 @@ data class EpisodeResult(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
data class TempEpisode(
|
|
||||||
var epData: EpisodeData,
|
|
||||||
var name: String,
|
|
||||||
var episode_number: Float,
|
|
||||||
var date_upload: Long,
|
|
||||||
var scanlator: String?,
|
|
||||||
)
|
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
data class EpisodeData(
|
data class EpisodeData(
|
||||||
val ids: List<Pair<String, String>>,
|
val ids: List<Pair<String, String>>,
|
||||||
|
@ -94,7 +94,9 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
val queries = response.request.url.encodedQuery ?: "0"
|
val queries = response.request.url.encodedQuery ?: "0"
|
||||||
val position = if (queries.contains("start=")) {
|
val position = if (queries.contains("start=")) {
|
||||||
queries.substringAfter("start=").substringBefore("&").toInt()
|
queries.substringAfter("start=").substringBefore("&").toInt()
|
||||||
} else { 0 }
|
} else {
|
||||||
|
0
|
||||||
|
}
|
||||||
return AnimesPage(animeList, position + 36 < parsed.total)
|
return AnimesPage(animeList, position + 36 < parsed.total)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -142,7 +144,9 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
val queries = response.request.url.encodedQuery ?: "0"
|
val queries = response.request.url.encodedQuery ?: "0"
|
||||||
val position = if (queries.contains("start=")) {
|
val position = if (queries.contains("start=")) {
|
||||||
queries.substringAfter("start=").substringBefore("&").toInt()
|
queries.substringAfter("start=").substringBefore("&").toInt()
|
||||||
} else { 0 }
|
} else {
|
||||||
|
0
|
||||||
|
}
|
||||||
return AnimesPage(animeList, position + 36 < total)
|
return AnimesPage(animeList, position + 36 < total)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -165,7 +169,8 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
author = info.data.first().content_provider
|
author = info.data.first().content_provider
|
||||||
status = SAnime.COMPLETED
|
status = SAnime.COMPLETED
|
||||||
if (genre.isNullOrBlank()) {
|
if (genre.isNullOrBlank()) {
|
||||||
genre = info.data.first().genres?.joinToString { gen -> gen.replaceFirstChar { it.uppercase() } }
|
genre =
|
||||||
|
info.data.first().genres?.joinToString { gen -> gen.replaceFirstChar { it.uppercase() } }
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
@ -187,56 +192,44 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
override fun episodeListParse(response: Response): List<SEpisode> {
|
override fun episodeListParse(response: Response): List<SEpisode> {
|
||||||
val seasons = json.decodeFromString<SeasonResult>(response.body.string())
|
val seasons = json.decodeFromString<SeasonResult>(response.body.string())
|
||||||
val series = response.request.url.encodedPath.contains("series/")
|
val series = response.request.url.encodedPath.contains("series/")
|
||||||
// Why all this? well crunchy sends same season twice with different quality eg. One Piece
|
|
||||||
// which causes the number of episodes to be higher that what it actually is.
|
|
||||||
return if (series) {
|
return if (series) {
|
||||||
seasons.data.sortedBy { it.season_number }.groupBy { it.season_number }
|
seasons.data.sortedBy { it.season_number }.chunked(6).map { chunk ->
|
||||||
.map { (_, sList) ->
|
chunk.parallelMap { seasonData ->
|
||||||
sList.parallelMap { seasonData ->
|
runCatching {
|
||||||
runCatching {
|
val episodeResp =
|
||||||
val episodeResp =
|
client.newCall(GET("$crUrl/content/v2/cms/seasons/${seasonData.id}/episodes"))
|
||||||
client.newCall(GET("$crUrl/content/v2/cms/seasons/${seasonData.id}/episodes"))
|
.execute()
|
||||||
.execute()
|
val body = episodeResp.body.string()
|
||||||
val episodes =
|
val episodes =
|
||||||
json.decodeFromString<EpisodeResult>(episodeResp.body.string())
|
json.decodeFromString<EpisodeResult>(body)
|
||||||
episodes.data.sortedBy { it.episode_number }.parallelMap { ep ->
|
episodes.data.sortedBy { it.episode_number }.parallelMap { ep ->
|
||||||
TempEpisode(
|
|
||||||
epData = EpisodeData(
|
|
||||||
ep.versions?.map { Pair(it.mediaId, it.audio_locale) }
|
|
||||||
?: listOf(
|
|
||||||
Pair(
|
|
||||||
ep.streams_link.substringAfter("videos/")
|
|
||||||
.substringBefore("/streams"),
|
|
||||||
ep.audio_locale,
|
|
||||||
),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
name = if (ep.episode_number > 0 && ep.episode.isNumeric()) {
|
|
||||||
"Season ${seasonData.season_number} Ep ${df.format(ep.episode_number)}: " + ep.title
|
|
||||||
} else {
|
|
||||||
ep.title
|
|
||||||
},
|
|
||||||
episode_number = ep.episode_number,
|
|
||||||
date_upload = ep.airDate?.let { parseDate(it) } ?: 0L,
|
|
||||||
scanlator = ep.versions?.sortedBy { it.audio_locale }
|
|
||||||
?.joinToString { it.audio_locale.substringBefore("-") }
|
|
||||||
?: ep.audio_locale.substringBefore("-"),
|
|
||||||
)
|
|
||||||
}
|
|
||||||
}.getOrNull()
|
|
||||||
}.asSequence().filterNotNull().flatten().groupBy { it.episode_number }
|
|
||||||
.map { (_, eList) ->
|
|
||||||
val versions = EpisodeData(eList.parallelMap { it.epData.ids }.flatten()).toJsonString()
|
|
||||||
val ep = eList.first()
|
|
||||||
SEpisode.create().apply {
|
SEpisode.create().apply {
|
||||||
this.url = versions
|
url = EpisodeData(
|
||||||
this.name = ep.name
|
ep.versions?.map { Pair(it.mediaId, it.audio_locale) }
|
||||||
this.episode_number = ep.episode_number
|
?: listOf(
|
||||||
this.date_upload = ep.date_upload
|
Pair(
|
||||||
this.scanlator = eList.map { it.scanlator }.joinToString()
|
ep.streams_link!!.substringAfter("videos/")
|
||||||
|
.substringBefore("/streams"),
|
||||||
|
ep.audio_locale,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
).toJsonString()
|
||||||
|
name = if (ep.episode_number > 0 && ep.episode.isNumeric()) {
|
||||||
|
"Season ${seasonData.season_number} Ep ${df.format(ep.episode_number)}: " + ep.title
|
||||||
|
} else {
|
||||||
|
ep.title
|
||||||
|
}
|
||||||
|
episode_number = ep.episode_number
|
||||||
|
date_upload = ep.airDate?.let { parseDate(it) } ?: 0L
|
||||||
|
scanlator = ep.versions?.sortedBy { it.audio_locale }
|
||||||
|
?.joinToString { it.audio_locale.substringBefore("-") }
|
||||||
|
?: ep.audio_locale.substringBefore("-")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}.flatten().reversed()
|
}.getOrNull()
|
||||||
|
}.filterNotNull().flatten()
|
||||||
|
}.flatten().reversed()
|
||||||
} else {
|
} else {
|
||||||
seasons.data.mapIndexed { index, movie ->
|
seasons.data.mapIndexed { index, movie ->
|
||||||
SEpisode.create().apply {
|
SEpisode.create().apply {
|
||||||
@ -269,17 +262,22 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
|
|
||||||
// ============================= Utilities ==============================
|
// ============================= Utilities ==============================
|
||||||
|
|
||||||
private fun extractVideo(media: Pair<String, String>, proxyToken: AccessToken, localToken: AccessToken?): List<Video> {
|
private fun extractVideo(
|
||||||
|
media: Pair<String, String>,
|
||||||
|
proxyToken: AccessToken,
|
||||||
|
localToken: AccessToken?,
|
||||||
|
): List<Video> {
|
||||||
val (mediaId, aud) = media
|
val (mediaId, aud) = media
|
||||||
val response = client.newCall(getVideoRequest(mediaId, proxyToken)).execute()
|
val response = client.newCall(getVideoRequest(mediaId, proxyToken)).execute()
|
||||||
val streams = json.decodeFromString<VideoStreams>(response.body.string())
|
val streams = json.decodeFromString<VideoStreams>(response.body.string())
|
||||||
|
|
||||||
val localStreams = if (aud == "ja-JP" && preferences.getBoolean(PREF_FETCH_LOCAL_SUBS, false)) {
|
val localStreams =
|
||||||
val localResponse = client.newCall(getVideoRequest(mediaId, localToken!!)).execute()
|
if (aud == "ja-JP" && preferences.getBoolean(PREF_FETCH_LOCAL_SUBS, false)) {
|
||||||
json.decodeFromString(localResponse.body.string())
|
val localResponse = client.newCall(getVideoRequest(mediaId, localToken!!)).execute()
|
||||||
} else {
|
json.decodeFromString(localResponse.body.string())
|
||||||
VideoStreams()
|
} else {
|
||||||
}
|
VideoStreams()
|
||||||
|
}
|
||||||
|
|
||||||
var subsList = emptyList<Track>()
|
var subsList = emptyList<Track>()
|
||||||
val subLocale = preferences.getString("preferred_sub", "en-US")!!.getLocale()
|
val subLocale = preferences.getString("preferred_sub", "en-US")!!.getLocale()
|
||||||
@ -299,7 +297,8 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
{ it.lang.contains(subLocale) },
|
{ it.lang.contains(subLocale) },
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
} catch (_: Error) {}
|
} catch (_: Error) {
|
||||||
|
}
|
||||||
|
|
||||||
val audLang = aud.ifBlank { streams.audio_locale } ?: localStreams.audio_locale ?: "ja-JP"
|
val audLang = aud.ifBlank { streams.audio_locale } ?: localStreams.audio_locale ?: "ja-JP"
|
||||||
val videoList = mutableListOf<Video>()
|
val videoList = mutableListOf<Video>()
|
||||||
@ -313,7 +312,11 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
return videoList.distinctBy { it.quality }
|
return videoList.distinctBy { it.quality }
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getStreams(streams: VideoStreams, audLang: String, subsList: List<Track>): List<Video> {
|
private fun getStreams(
|
||||||
|
streams: VideoStreams,
|
||||||
|
audLang: String,
|
||||||
|
subsList: List<Track>,
|
||||||
|
): List<Video> {
|
||||||
return streams.streams?.adaptive_hls?.entries?.parallelMap { (_, value) ->
|
return streams.streams?.adaptive_hls?.entries?.parallelMap { (_, value) ->
|
||||||
val stream = json.decodeFromString<HlsLinks>(value.jsonObject.toString())
|
val stream = json.decodeFromString<HlsLinks>(value.jsonObject.toString())
|
||||||
runCatching {
|
runCatching {
|
||||||
@ -559,7 +562,9 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
Thread {
|
Thread {
|
||||||
runBlocking {
|
runBlocking {
|
||||||
if (new) {
|
if (new) {
|
||||||
withContext(Dispatchers.IO) { summary = getTokenDetail(true) }
|
withContext(Dispatchers.IO) {
|
||||||
|
summary = getTokenDetail(true)
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
tokenInterceptor.removeLocalToken()
|
tokenInterceptor.removeLocalToken()
|
||||||
summary = """Token location:
|
summary = """Token location:
|
||||||
@ -584,7 +589,9 @@ class Yomiroll : ConfigurableAnimeSource, AnimeHttpSource() {
|
|||||||
private fun getTokenDetail(force: Boolean = false): String {
|
private fun getTokenDetail(force: Boolean = false): String {
|
||||||
return try {
|
return try {
|
||||||
val storedToken = tokenInterceptor.getLocalToken(force)
|
val storedToken = tokenInterceptor.getLocalToken(force)
|
||||||
"""Token location: ${storedToken?.bucket?.substringAfter("/")?.substringBefore("/") ?: ""}
|
"""Token location: ${
|
||||||
|
storedToken?.bucket?.substringAfter("/")?.substringBefore("/") ?: ""
|
||||||
|
}
|
||||||
|Expires: ${storedToken?.policyExpire?.let { DateFormatter.format(it) } ?: ""}
|
|Expires: ${storedToken?.policyExpire?.let { DateFormatter.format(it) } ?: ""}
|
||||||
""".trimMargin()
|
""".trimMargin()
|
||||||
} catch (e: Exception) {
|
} catch (e: Exception) {
|
||||||
|
Reference in New Issue
Block a user