Implement URL input format checks

This commit is contained in:
Kirill Kamakin
2021-11-27 12:27:25 +03:00
parent ebba1889c7
commit 339f8327de
6 changed files with 52 additions and 2 deletions

View File

@@ -1,10 +1,14 @@
package gq.kirmanak.mealient.data.auth.impl
import android.net.Uri
import androidx.annotation.VisibleForTesting
import gq.kirmanak.mealient.data.auth.AuthDataSource
import gq.kirmanak.mealient.data.auth.AuthRepo
import gq.kirmanak.mealient.data.auth.AuthStorage
import gq.kirmanak.mealient.data.auth.impl.AuthenticationError.MalformedUrl
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.map
import okhttp3.HttpUrl.Companion.toHttpUrl
import timber.log.Timber
import javax.inject.Inject
@@ -18,7 +22,7 @@ class AuthRepoImpl @Inject constructor(
baseUrl: String
) {
Timber.v("authenticate() called with: username = $username, password = $password, baseUrl = $baseUrl")
val url = if (baseUrl.startsWith("http")) baseUrl else "https://$baseUrl"
val url = parseBaseUrl(baseUrl)
val accessToken = dataSource.authenticate(username, password, url)
Timber.d("authenticate result is $accessToken")
storage.storeAuthData(accessToken, url)
@@ -40,4 +44,17 @@ class AuthRepoImpl @Inject constructor(
Timber.v("logout() called")
storage.clearAuthData()
}
@VisibleForTesting
fun parseBaseUrl(baseUrl: String): String = try {
val withScheme = Uri.parse(baseUrl).let {
if (it.scheme == null) it.buildUpon().scheme("https").build()
else it
}.toString()
withScheme.toHttpUrl().toString()
} catch (e: Throwable) {
Timber.e(e, "authenticate: can't parse base url $baseUrl")
throw MalformedUrl(e)
}
}

View File

@@ -4,4 +4,5 @@ sealed class AuthenticationError(cause: Throwable) : RuntimeException(cause) {
class Unauthorized(cause: Throwable) : AuthenticationError(cause)
class NoServerConnection(cause: Throwable) : AuthenticationError(cause)
class NotMealie(cause: Throwable) : AuthenticationError(cause)
class MalformedUrl(cause: Throwable) : AuthenticationError(cause)
}

View File

@@ -85,9 +85,13 @@ class AuthenticationFragment : Fragment() {
is Unauthorized -> getString(R.string.fragment_authentication_credentials_incorrect)
else -> null
}
urlInputLayout.error = when (it.exceptionOrNull()) {
urlInputLayout.error = when (val exception = it.exceptionOrNull()) {
is NoServerConnection -> getString(R.string.fragment_authentication_no_connection)
is NotMealie -> getString(R.string.fragment_authentication_unexpected_response)
is MalformedUrl -> {
val cause = exception.cause?.message ?: exception.message
getString(R.string.fragment_authentication_url_invalid, cause)
}
is Unauthorized, null -> null
else -> getString(R.string.fragment_authentication_unknown_error)
}