Handle specific 401 errors by logging out the user

Adds logic to check the error message from the API response
when a 401 error is received. If the error indicates
invalid credentials or missing authentication headers, the
user is automatically logged out.
This commit is contained in:
Hafiz 2025-07-02 13:29:27 -05:00
parent 8de67c8416
commit 55132e0c57

View file

@ -56,6 +56,7 @@ import okhttp3.Cache
import okhttp3.OkHttpClient
import okhttp3.Request
import okhttp3.logging.HttpLoggingInterceptor
import org.json.JSONObject
import retrofit2.Converter
import retrofit2.HttpException
import retrofit2.Retrofit
@ -158,12 +159,33 @@ class ApiClientImpl(
when (response.code) {
401 -> {
val path = response.request.url.encodedPath
if (!path.contains("user/auth/update-password")) {
// token has been revoked/rotated elsewhere
HabiticaBaseApplication.logout(context)
if (!path.contains("/user/auth/update-password")) {
val bodyStr = try {
response.peekBody(1024).string()
} catch (_: Exception) {
""
}
val (errField, msgField) = try {
val obj = JSONObject(bodyStr)
obj.optString("error", "") to obj.optString("message", "")
} catch (_: Exception) {
"" to ""
}
val shouldLogout = errField.equals("missingAuthHeaders", ignoreCase = true)
|| errField.equals("invalidCredentials", ignoreCase = true)
|| msgField.contains("invalidCredentials", ignoreCase = true)
|| msgField.contains("Missing authentication headers", ignoreCase = true)
|| msgField.contains("There is no account that uses those credentials", ignoreCase = true)
if (shouldLogout) {
HabiticaBaseApplication.logout(context)
}
}
return@addNetworkInterceptor response
}
404 -> {
// The server is returning a 404 error, which means the requested resource was not found.
// In this case - we want to actually cache the response, and handle it in the app