From 1d9e0109b60a54f6ce529916741d73f6626c10fb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Miko=C5=82aj=20Pich?= Date: Tue, 26 Mar 2024 18:08:24 +0100 Subject: [PATCH] Add new behavior handling of not logged in user on old student module --- build.gradle | 2 +- .../interceptor/AutoLoginInterceptor.kt | 31 ++++++++++++++----- .../sdk/scrapper/service/ServiceManager.kt | 1 + .../wulkanowy/sdk/scrapper/BaseLocalTest.kt | 3 +- .../interceptor/AutoLoginInterceptorTest.kt | 1 + 5 files changed, 29 insertions(+), 9 deletions(-) diff --git a/build.gradle b/build.gradle index 6767ec58..3b707524 100644 --- a/build.gradle +++ b/build.gradle @@ -18,7 +18,7 @@ ext { moshi = "1.13.0" } -version = "2.5.4" +version = "2.5.5-SNAPSHOT" group = "io.github.wulkanowy" nexusPublishing { diff --git a/sdk-scrapper/src/main/kotlin/io/github/wulkanowy/sdk/scrapper/interceptor/AutoLoginInterceptor.kt b/sdk-scrapper/src/main/kotlin/io/github/wulkanowy/sdk/scrapper/interceptor/AutoLoginInterceptor.kt index 344a9052..dda6fb5f 100644 --- a/sdk-scrapper/src/main/kotlin/io/github/wulkanowy/sdk/scrapper/interceptor/AutoLoginInterceptor.kt +++ b/sdk-scrapper/src/main/kotlin/io/github/wulkanowy/sdk/scrapper/interceptor/AutoLoginInterceptor.kt @@ -1,5 +1,6 @@ package io.github.wulkanowy.sdk.scrapper.interceptor +import io.github.wulkanowy.sdk.scrapper.ApiResponse import io.github.wulkanowy.sdk.scrapper.CookieJarCabinet import io.github.wulkanowy.sdk.scrapper.Scrapper.LoginType import io.github.wulkanowy.sdk.scrapper.Scrapper.LoginType.ADFS @@ -19,6 +20,7 @@ import io.github.wulkanowy.sdk.scrapper.repository.AccountRepository.Companion.S import io.github.wulkanowy.sdk.scrapper.repository.AccountRepository.Companion.SELECTOR_ADFS_LIGHT import io.github.wulkanowy.sdk.scrapper.repository.AccountRepository.Companion.SELECTOR_STANDARD import kotlinx.coroutines.runBlocking +import kotlinx.serialization.json.Json import okhttp3.HttpUrl import okhttp3.Interceptor import okhttp3.MediaType @@ -49,6 +51,7 @@ internal class AutoLoginInterceptor( private val emptyCookieJarIntercept: Boolean = false, private val notLoggedInCallback: suspend () -> LoginResult, private val fetchModuleCookies: (UrlGenerator.Site) -> Pair, + private val json: Json, ) : Interceptor { companion object { @@ -76,7 +79,7 @@ internal class AutoLoginInterceptor( if (response.body?.contentType()?.subtype != "json") { val body = response.peekBody(Long.MAX_VALUE).byteStream() val html = Jsoup.parse(body, null, url) - checkResponse(html, url) + checkResponse(html, url, response) saveModuleHeaders(html, uri) } } catch (e: NotLoggedInException) { @@ -182,7 +185,7 @@ internal class AutoLoginInterceptor( } } - private fun checkResponse(doc: Document, url: String) { + private fun checkResponse(doc: Document, url: String, response: Response) { // if (chain.request().url().toString().contains("/Start.mvc/Get")) { if (url.contains("/Start.mvc/")) { // /Index return error too in 19.09.0000.34977 doc.select(".errorBlock").let { @@ -201,12 +204,26 @@ internal class AutoLoginInterceptor( throw NotLoggedInException("User not logged in") } + // old style val bodyContent = doc.body().text() - when { - // uonetplus-uczen - "The custom error module" in bodyContent -> { - throw NotLoggedInException(bodyContent) - } + if ("The custom error module" in bodyContent) { + throw NotLoggedInException(bodyContent) + } + + // new style + val isCodeMatch = response.code == HttpURLConnection.HTTP_OK + val isJsonContent = bodyContent.startsWith("{") + val isSubdomainMatch = "uonetplus-uczen" in url + if (isCodeMatch && isJsonContent && isSubdomainMatch) { + runCatching { json.decodeFromString>(bodyContent) } + .onFailure { logger.error("Can't deserialize content body", it) } + .onSuccess { + it.feedback?.message?.let { errorMessage -> + if ("Brak uprawnieĊ„" in errorMessage) { + throw NotLoggedInException(errorMessage) + } + } + } } } diff --git a/sdk-scrapper/src/main/kotlin/io/github/wulkanowy/sdk/scrapper/service/ServiceManager.kt b/sdk-scrapper/src/main/kotlin/io/github/wulkanowy/sdk/scrapper/service/ServiceManager.kt index 7cd2996d..f14599d9 100644 --- a/sdk-scrapper/src/main/kotlin/io/github/wulkanowy/sdk/scrapper/service/ServiceManager.kt +++ b/sdk-scrapper/src/main/kotlin/io/github/wulkanowy/sdk/scrapper/service/ServiceManager.kt @@ -104,6 +104,7 @@ internal class ServiceManager( cookieJarCabinet = cookieJarCabinet, emptyCookieJarIntercept = emptyCookieJarIntercept, notLoggedInCallback = ::userLogin, + json = json, fetchModuleCookies = { site -> loginHelper.loginModule(site) }, ) to false, UserAgentInterceptor(androidVersion, buildTag, userAgentTemplate) to false, diff --git a/sdk-scrapper/src/test/kotlin/io/github/wulkanowy/sdk/scrapper/BaseLocalTest.kt b/sdk-scrapper/src/test/kotlin/io/github/wulkanowy/sdk/scrapper/BaseLocalTest.kt index ad674781..d223d65b 100644 --- a/sdk-scrapper/src/test/kotlin/io/github/wulkanowy/sdk/scrapper/BaseLocalTest.kt +++ b/sdk-scrapper/src/test/kotlin/io/github/wulkanowy/sdk/scrapper/BaseLocalTest.kt @@ -91,7 +91,7 @@ abstract class BaseLocalTest : BaseTest() { } @OptIn(ExperimentalSerializationApi::class) - private val json = Json { + val json = Json { explicitNulls = false ignoreUnknownKeys = true encodeDefaults = true @@ -159,6 +159,7 @@ abstract class BaseLocalTest : BaseTest() { } }, fetchModuleCookies = { _ -> "http://localhost".toHttpUrl() to Document("") }, + json = json, ) } } diff --git a/sdk-scrapper/src/test/kotlin/io/github/wulkanowy/sdk/scrapper/interceptor/AutoLoginInterceptorTest.kt b/sdk-scrapper/src/test/kotlin/io/github/wulkanowy/sdk/scrapper/interceptor/AutoLoginInterceptorTest.kt index 2cb6833b..2cf730c0 100644 --- a/sdk-scrapper/src/test/kotlin/io/github/wulkanowy/sdk/scrapper/interceptor/AutoLoginInterceptorTest.kt +++ b/sdk-scrapper/src/test/kotlin/io/github/wulkanowy/sdk/scrapper/interceptor/AutoLoginInterceptorTest.kt @@ -193,6 +193,7 @@ class AutoLoginInterceptorTest : BaseLocalTest() { emptyCookieJarIntercept = checkJar, notLoggedInCallback = notLoggedInCallback, fetchModuleCookies = fetchModuleCookies, + json = json, ) val okHttp = getOkHttp(autoLogin = true, autoLoginInterceptorOn = true, autoLoginInterceptor = interceptor) return getService(