Synchronize whole requests in auto login interceptor

This commit is contained in:
Mikołaj Pich 2024-01-03 01:31:46 +01:00
parent d9da6614e7
commit 049c428fd3
5 changed files with 18 additions and 32 deletions

View file

@ -30,8 +30,6 @@ import retrofit2.HttpException
import java.io.IOException
import java.net.CookieManager
import java.net.HttpURLConnection
import java.util.concurrent.locks.Lock
import java.util.concurrent.locks.ReentrantLock
internal class AutoLoginInterceptor(
private val loginType: LoginType,
@ -47,31 +45,29 @@ internal class AutoLoginInterceptor(
private val logger = LoggerFactory.getLogger(this::class.java)
}
private val lock: Lock = ReentrantLock()
override fun intercept(chain: Interceptor.Chain): Response {
val request: Request
val response: Response
val uri = chain.request().url
val url = uri.toString()
try {
request = chain.request()
checkRequest()
response = try {
chain.proceed(request)
} catch (e: Throwable) {
if (e is VulcanClientError) {
checkHttpErrorResponse(e, url)
synchronized(this) {
try {
request = chain.request()
checkRequest()
response = try {
chain.proceed(request)
} catch (e: Throwable) {
if (e is VulcanClientError) {
checkHttpErrorResponse(e, url)
}
throw e
}
throw e
}
if (response.body?.contentType()?.subtype != "json") {
val body = response.peekBody(Long.MAX_VALUE).byteStream()
checkResponse(Jsoup.parse(body, null, url), url)
}
} catch (e: NotLoggedInException) {
if (lock.tryLock()) {
if (response.body?.contentType()?.subtype != "json") {
val body = response.peekBody(Long.MAX_VALUE).byteStream()
checkResponse(Jsoup.parse(body, null, url), url)
}
} catch (e: NotLoggedInException) {
logger.debug("Not logged in. Login in...")
return try {
runBlocking {
@ -92,15 +88,7 @@ internal class AutoLoginInterceptor(
throw IOException("Unknown exception on login", e)
} finally {
logger.debug("Login finished. Release lock")
lock.unlock()
}
} else {
logger.debug("Wait for user to be logged in...")
lock.lock()
lock.unlock()
logger.debug("User logged in. Retry after login...")
return chain.proceed(chain.request().newBuilder().build())
}
}

View file

@ -59,7 +59,7 @@ internal class LoginHelper(
logger.info("Login ${loginType.name} started")
when {
res.title.startsWith("Witryna ucznia i rodzica") -> return HomePageResponse()
res.action.isBlank() -> throw VulcanException("Invalid certificate page: '${res.title}'. Try again")
res.action.isBlank() -> throw VulcanException("Invalid certificate page: '${res.title.ifBlank { res.toString().take(32) }}'. Try again")
}
val cert = sendCertificate(res, email)

View file

@ -7,7 +7,6 @@ import io.github.wulkanowy.sdk.scrapper.interceptor.ErrorInterceptor
import io.github.wulkanowy.sdk.scrapper.interceptor.HttpErrorInterceptor
import io.github.wulkanowy.sdk.scrapper.login.LoginHelper
import io.github.wulkanowy.sdk.scrapper.login.UrlGenerator
import io.github.wulkanowy.sdk.scrapper.register.RegisterTest
import io.github.wulkanowy.sdk.scrapper.repository.StudentRepository
import io.github.wulkanowy.sdk.scrapper.service.LoginService
import io.github.wulkanowy.sdk.scrapper.service.StudentPlusService

View file

@ -1,7 +1,6 @@
package io.github.wulkanowy.sdk.scrapper
import io.github.wulkanowy.sdk.scrapper.attendance.AttendanceSummaryTest
import io.github.wulkanowy.sdk.scrapper.register.RegisterTest
import kotlinx.coroutines.runBlocking
import org.junit.Test
@ -39,6 +38,7 @@ class ScrapperTest : BaseLocalTest() {
try {
runBlocking { api.getSubjects() }
} catch (e: Throwable) {
e.printStackTrace()
assert(false) //
}
}

View file

@ -13,7 +13,6 @@ import okhttp3.mockwebserver.MockResponse
import org.junit.Assert.assertEquals
import org.junit.Assert.assertFalse
import org.junit.Assert.assertTrue
import org.junit.Before
import org.junit.Test
import java.util.UUID