Emerald: handle obfuscated image URLs (fixes #4524)
This commit is contained in:
parent
6e3141397a
commit
245e3f0d7e
|
@ -5,7 +5,7 @@ ext {
|
||||||
extName = 'Emerald'
|
extName = 'Emerald'
|
||||||
pkgNameSuffix = 'all.emerald'
|
pkgNameSuffix = 'all.emerald'
|
||||||
extClass = '.EmeraldFactory'
|
extClass = '.EmeraldFactory'
|
||||||
extVersionCode = 2
|
extVersionCode = 3
|
||||||
libVersion = '1.2'
|
libVersion = '1.2'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package eu.kanade.tachiyomi.extension.all.emerald
|
package eu.kanade.tachiyomi.extension.all.emerald
|
||||||
|
|
||||||
|
import com.squareup.duktape.Duktape
|
||||||
import eu.kanade.tachiyomi.network.GET
|
import eu.kanade.tachiyomi.network.GET
|
||||||
import eu.kanade.tachiyomi.source.model.Filter
|
import eu.kanade.tachiyomi.source.model.Filter
|
||||||
import eu.kanade.tachiyomi.source.model.FilterList
|
import eu.kanade.tachiyomi.source.model.FilterList
|
||||||
|
@ -10,6 +11,7 @@ import eu.kanade.tachiyomi.source.online.ParsedHttpSource
|
||||||
import okhttp3.HttpUrl
|
import okhttp3.HttpUrl
|
||||||
import okhttp3.OkHttpClient
|
import okhttp3.OkHttpClient
|
||||||
import okhttp3.Request
|
import okhttp3.Request
|
||||||
|
import org.json.JSONArray
|
||||||
import org.json.JSONObject
|
import org.json.JSONObject
|
||||||
import org.jsoup.nodes.Document
|
import org.jsoup.nodes.Document
|
||||||
import org.jsoup.nodes.Element
|
import org.jsoup.nodes.Element
|
||||||
|
@ -34,7 +36,7 @@ open class Emerald(
|
||||||
return GET("$baseUrl/browse?langs=$Mtlang&sort=update&page=$page")
|
return GET("$baseUrl/browse?langs=$Mtlang&sort=update&page=$page")
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun latestUpdatesSelector() = "div#series-list div.col-24"
|
override fun latestUpdatesSelector() = "div#series-list div.col"
|
||||||
|
|
||||||
override fun latestUpdatesFromElement(element: Element): SManga {
|
override fun latestUpdatesFromElement(element: Element): SManga {
|
||||||
val manga = SManga.create()
|
val manga = SManga.create()
|
||||||
|
@ -265,9 +267,10 @@ open class Emerald(
|
||||||
|
|
||||||
override fun pageListParse(document: Document): List<Page> {
|
override fun pageListParse(document: Document): List<Page> {
|
||||||
val pages = mutableListOf<Page>()
|
val pages = mutableListOf<Page>()
|
||||||
|
|
||||||
val script = document.select("script").html()
|
val script = document.select("script").html()
|
||||||
.substringAfter("var images = ").substringBefore(";")
|
if (script.contains("var images =")) {
|
||||||
val imgJson = JSONObject(script)
|
val imgJson = JSONObject(script.substringAfter("var images = ").substringBefore(";"))
|
||||||
val imgNames = imgJson.names()
|
val imgNames = imgJson.names()
|
||||||
|
|
||||||
if (imgNames != null) {
|
if (imgNames != null) {
|
||||||
|
@ -277,10 +280,35 @@ open class Emerald(
|
||||||
pages.add(Page(i, "", imgUrl))
|
pages.add(Page(i, "", imgUrl))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
} else if (script.contains("const server =")) {
|
||||||
|
val duktape = Duktape.create()
|
||||||
|
val encryptedServer = script.substringAfter("const server = ").substringBefore(";")
|
||||||
|
val batojs = duktape.evaluate(script.substringAfter("const batojs = ").substringBefore(";")).toString()
|
||||||
|
val decryptScript = cryptoJS + "CryptoJS.AES.decrypt($encryptedServer, \"$batojs\").toString(CryptoJS.enc.Utf8);"
|
||||||
|
val server = duktape.evaluate(decryptScript).toString().replace("\"", "")
|
||||||
|
duktape.close()
|
||||||
|
|
||||||
|
val imgArray = JSONArray(script.substringAfter("const images = ").substringBefore(";"))
|
||||||
|
if (imgArray != null) {
|
||||||
|
for (i in 0 until imgArray.length()) {
|
||||||
|
val imgUrl = imgArray.get(i)
|
||||||
|
pages.add(Page(i, "", "https:${server}$imgUrl"))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return pages
|
return pages
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private val cryptoJS by lazy {
|
||||||
|
client.newCall(
|
||||||
|
GET(
|
||||||
|
"https://cdnjs.cloudflare.com/ajax/libs/crypto-js/4.0.0/crypto-js.min.js",
|
||||||
|
headers
|
||||||
|
)
|
||||||
|
).execute().body()!!.string()
|
||||||
|
}
|
||||||
|
|
||||||
override fun imageUrlParse(document: Document): String = throw UnsupportedOperationException("Not used")
|
override fun imageUrlParse(document: Document): String = throw UnsupportedOperationException("Not used")
|
||||||
|
|
||||||
private class AuthorFilter : Filter.Text("Author / Artist")
|
private class AuthorFilter : Filter.Text("Author / Artist")
|
||||||
|
|
Loading…
Reference in New Issue