mirror of
				https://github.com/mihonapp/mihon.git
				synced 2025-11-04 08:08:55 +01:00 
			
		
		
		
	Extract user agent string from WebView
This commit is contained in:
		@@ -9,7 +9,6 @@ import android.webkit.WebSettings
 | 
			
		||||
import android.webkit.WebView
 | 
			
		||||
import android.widget.Toast
 | 
			
		||||
import eu.kanade.tachiyomi.R
 | 
			
		||||
import eu.kanade.tachiyomi.source.online.HttpSource
 | 
			
		||||
import eu.kanade.tachiyomi.util.lang.launchUI
 | 
			
		||||
import eu.kanade.tachiyomi.util.system.WebViewClientCompat
 | 
			
		||||
import eu.kanade.tachiyomi.util.system.WebViewUtil
 | 
			
		||||
@@ -99,7 +98,7 @@ class CloudflareInterceptor(private val context: Context) : Interceptor {
 | 
			
		||||
 | 
			
		||||
            // Avoid sending empty User-Agent, Chromium WebView will reset to default if empty
 | 
			
		||||
            webview.settings.userAgentString = request.header("User-Agent")
 | 
			
		||||
                ?: HttpSource.DEFAULT_USERAGENT
 | 
			
		||||
                ?: WebViewUtil.DEFAULT_USER_AGENT
 | 
			
		||||
 | 
			
		||||
            webview.webViewClient = object : WebViewClientCompat() {
 | 
			
		||||
                override fun onPageFinished(view: WebView, url: String) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,6 @@
 | 
			
		||||
package eu.kanade.tachiyomi.network
 | 
			
		||||
 | 
			
		||||
import eu.kanade.tachiyomi.source.online.HttpSource
 | 
			
		||||
import eu.kanade.tachiyomi.util.system.WebViewUtil
 | 
			
		||||
import okhttp3.Interceptor
 | 
			
		||||
import okhttp3.Response
 | 
			
		||||
 | 
			
		||||
@@ -12,7 +12,7 @@ class UserAgentInterceptor : Interceptor {
 | 
			
		||||
            val newRequest = originalRequest
 | 
			
		||||
                .newBuilder()
 | 
			
		||||
                .removeHeader("User-Agent")
 | 
			
		||||
                .addHeader("User-Agent", HttpSource.DEFAULT_USERAGENT)
 | 
			
		||||
                .addHeader("User-Agent", WebViewUtil.DEFAULT_USER_AGENT)
 | 
			
		||||
                .build()
 | 
			
		||||
            chain.proceed(newRequest)
 | 
			
		||||
        } else {
 | 
			
		||||
 
 | 
			
		||||
@@ -10,6 +10,7 @@ import eu.kanade.tachiyomi.source.model.MangasPage
 | 
			
		||||
import eu.kanade.tachiyomi.source.model.Page
 | 
			
		||||
import eu.kanade.tachiyomi.source.model.SChapter
 | 
			
		||||
import eu.kanade.tachiyomi.source.model.SManga
 | 
			
		||||
import eu.kanade.tachiyomi.util.system.WebViewUtil
 | 
			
		||||
import okhttp3.Headers
 | 
			
		||||
import okhttp3.OkHttpClient
 | 
			
		||||
import okhttp3.Request
 | 
			
		||||
@@ -74,7 +75,7 @@ abstract class HttpSource : CatalogueSource {
 | 
			
		||||
     * Headers builder for requests. Implementations can override this method for custom headers.
 | 
			
		||||
     */
 | 
			
		||||
    protected open fun headersBuilder() = Headers.Builder().apply {
 | 
			
		||||
        add("User-Agent", DEFAULT_USERAGENT)
 | 
			
		||||
        add("User-Agent", WebViewUtil.DEFAULT_USER_AGENT)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
@@ -369,8 +370,4 @@ abstract class HttpSource : CatalogueSource {
 | 
			
		||||
     * Returns the list of filters for the source.
 | 
			
		||||
     */
 | 
			
		||||
    override fun getFilterList() = FilterList()
 | 
			
		||||
 | 
			
		||||
    companion object {
 | 
			
		||||
        const val DEFAULT_USERAGENT = "Mozilla/5.0 (Windows NT 6.3; WOW64)"
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -1,26 +1,39 @@
 | 
			
		||||
package eu.kanade.tachiyomi.util.system
 | 
			
		||||
 | 
			
		||||
import android.annotation.SuppressLint
 | 
			
		||||
import android.content.Context
 | 
			
		||||
import android.content.pm.PackageManager
 | 
			
		||||
import android.webkit.CookieManager
 | 
			
		||||
import android.webkit.WebSettings
 | 
			
		||||
import android.webkit.WebView
 | 
			
		||||
import eu.kanade.tachiyomi.util.lang.launchUI
 | 
			
		||||
import timber.log.Timber
 | 
			
		||||
 | 
			
		||||
object WebViewUtil {
 | 
			
		||||
    val WEBVIEW_UA_VERSION_REGEX by lazy {
 | 
			
		||||
        Regex(""".*Chrome/(\d+)\..*""")
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    var DEFAULT_USER_AGENT: String = "Mozilla/5.0 (Windows NT 10.0; Win64; x64)"
 | 
			
		||||
        private set
 | 
			
		||||
 | 
			
		||||
    const val REQUESTED_WITH = "com.android.browser"
 | 
			
		||||
 | 
			
		||||
    const val MINIMUM_WEBVIEW_VERSION = 86
 | 
			
		||||
    const val MINIMUM_WEBVIEW_VERSION = 87
 | 
			
		||||
 | 
			
		||||
    fun supportsWebView(context: Context): Boolean {
 | 
			
		||||
        try {
 | 
			
		||||
            // May throw android.webkit.WebViewFactory$MissingWebViewPackageException if WebView
 | 
			
		||||
            // is not installed
 | 
			
		||||
            CookieManager.getInstance()
 | 
			
		||||
 | 
			
		||||
            launchUI {
 | 
			
		||||
                DEFAULT_USER_AGENT = WebView(context)
 | 
			
		||||
                    .getDefaultUserAgentString()
 | 
			
		||||
                    .replace("; wv", "")
 | 
			
		||||
            }
 | 
			
		||||
        } catch (e: Exception) {
 | 
			
		||||
            Timber.e(e)
 | 
			
		||||
            return false
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@@ -29,9 +42,10 @@ object WebViewUtil {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
fun WebView.isOutdated(): Boolean {
 | 
			
		||||
    return getWebViewMajorVersion(this) < WebViewUtil.MINIMUM_WEBVIEW_VERSION
 | 
			
		||||
    return getWebViewMajorVersion() < WebViewUtil.MINIMUM_WEBVIEW_VERSION
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@SuppressLint("SetJavaScriptEnabled")
 | 
			
		||||
fun WebView.setDefaultSettings() {
 | 
			
		||||
    with(settings) {
 | 
			
		||||
        javaScriptEnabled = true
 | 
			
		||||
@@ -44,22 +58,25 @@ fun WebView.setDefaultSettings() {
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Based on https://stackoverflow.com/a/29218966
 | 
			
		||||
private fun getWebViewMajorVersion(webview: WebView): Int {
 | 
			
		||||
    val originalUA: String = webview.settings.userAgentString
 | 
			
		||||
 | 
			
		||||
    // Next call to getUserAgentString() will get us the default
 | 
			
		||||
    webview.settings.userAgentString = null
 | 
			
		||||
 | 
			
		||||
    val uaRegexMatch = WebViewUtil.WEBVIEW_UA_VERSION_REGEX.matchEntire(webview.settings.userAgentString)
 | 
			
		||||
    val webViewVersion: Int = if (uaRegexMatch != null && uaRegexMatch.groupValues.size > 1) {
 | 
			
		||||
private fun WebView.getWebViewMajorVersion(): Int {
 | 
			
		||||
    val uaRegexMatch = WebViewUtil.WEBVIEW_UA_VERSION_REGEX.matchEntire(getDefaultUserAgentString())
 | 
			
		||||
    return if (uaRegexMatch != null && uaRegexMatch.groupValues.size > 1) {
 | 
			
		||||
        uaRegexMatch.groupValues[1].toInt()
 | 
			
		||||
    } else {
 | 
			
		||||
        0
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Based on https://stackoverflow.com/a/29218966
 | 
			
		||||
private fun WebView.getDefaultUserAgentString(): String {
 | 
			
		||||
    val originalUA: String = settings.userAgentString
 | 
			
		||||
 | 
			
		||||
    // Next call to getUserAgentString() will get us the default
 | 
			
		||||
    settings.userAgentString = null
 | 
			
		||||
    val defaultUserAgentString = settings.userAgentString
 | 
			
		||||
 | 
			
		||||
    // Revert to original UA string
 | 
			
		||||
    webview.settings.userAgentString = originalUA
 | 
			
		||||
    settings.userAgentString = originalUA
 | 
			
		||||
 | 
			
		||||
    return webViewVersion
 | 
			
		||||
    return defaultUserAgentString
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user