From 933de075024ec9da751a00b5b4d029d7712ad181 Mon Sep 17 00:00:00 2001 From: Mario D'Andrea Date: Sat, 24 Jan 2026 18:10:31 +0100 Subject: [PATCH 1/2] fix: add error handling to API calls --- .../vertex/api/ProjectionService.kt | 3 - .../vertex/api/ReservationService.kt | 1 - .../bytestrick/vertex/api/RoomService.kt | 3 - .../bytestrick/vertex/api/SeatService.kt | 4 +- .../vertex/repository/ChatRepository.kt | 4 +- .../vertex/repository/MovieRepository.kt | 17 ++--- .../repository/ReservationRepository.kt | 2 +- .../vertex/repository/SeatRepository.kt | 18 +++-- .../vertex/repository/paging/PageMediator.kt | 11 ++- .../vertex/repository/paging/PageSource.kt | 9 ++- .../vertex/ui/auth/ResetPasswordViewModel.kt | 70 +++++++++++-------- .../vertex/ui/auth/SignUpViewModel.kt | 24 ++++--- .../vertex/ui/auth/VerifyEmailViewModel.kt | 9 ++- .../vertex/ui/profile/ProfileViewModel.kt | 18 +++-- 14 files changed, 109 insertions(+), 84 deletions(-) diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/api/ProjectionService.kt b/android/app/src/main/java/com/github/bytestrick/vertex/api/ProjectionService.kt index 41fc37cca..4b635ed27 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/api/ProjectionService.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/api/ProjectionService.kt @@ -17,9 +17,6 @@ import kotlin.time.Instant import kotlin.uuid.Uuid interface ProjectionService { - @GET("projections/{id}") - suspend fun getProjection(@Path("id") id: Uuid): Response - @GET("projections/date/{startDate}/{endDate}/cinema/{cinemaId}") suspend fun getByProjectionDateBetweenInCinema( @Path(value = "startDate") startDate: Instant, diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/api/ReservationService.kt b/android/app/src/main/java/com/github/bytestrick/vertex/api/ReservationService.kt index 173e18904..443589328 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/api/ReservationService.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/api/ReservationService.kt @@ -84,7 +84,6 @@ interface ReservationService { @POST("reservations/{reservationId}/payment") suspend fun payReservation(@Path("reservationId") reservationId: Uuid): Response - // @GET("reservations/projection/{projectionId}") @GET("reservations/projections/{projectionId}") suspend fun getUserReservationForProjection( @Path("projectionId") projectionId: Uuid, diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/api/RoomService.kt b/android/app/src/main/java/com/github/bytestrick/vertex/api/RoomService.kt index ffad80775..ff503bef7 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/api/RoomService.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/api/RoomService.kt @@ -8,9 +8,6 @@ import kotlin.time.Instant import kotlin.uuid.Uuid interface RoomService { - @GET("rooms/{id}") - suspend fun getRoom(@Path("id") id: Uuid): Response - @GET("rooms/cinema/{cinemaId}") suspend fun getCinemaRooms(@Path("cinemaId") cinemaId: Uuid): Response> diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/api/SeatService.kt b/android/app/src/main/java/com/github/bytestrick/vertex/api/SeatService.kt index 45cf747ac..0b5935b1e 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/api/SeatService.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/api/SeatService.kt @@ -8,5 +8,7 @@ import kotlin.uuid.Uuid interface SeatService { @GET("rooms/{projectionId}/seats/info") - suspend fun getSeatsInfo(@Path("projectionId") projectionId: Uuid): Response> + suspend fun getSeatsInfo( + @Path("projectionId") projectionId: Uuid + ): Response> } \ No newline at end of file diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/repository/ChatRepository.kt b/android/app/src/main/java/com/github/bytestrick/vertex/repository/ChatRepository.kt index b151d7e1a..8b4e5f30e 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/repository/ChatRepository.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/repository/ChatRepository.kt @@ -137,7 +137,7 @@ class ChatRepository @Inject constructor( suspend fun getOrCreateConversation( participants: ConversationParticipants, - ): Result { + ): Result = runCatching { val queryRemote = suspend { getConversationFromRemote { conversationService.getOrCreateConversation(participants) } } @@ -147,7 +147,7 @@ class ChatRepository @Inject constructor( } ?: queryRemote() } - suspend fun getConversation(conversationId: Uuid): Result { + suspend fun getConversation(conversationId: Uuid): Result = runCatching { val queryRemote = suspend { getConversationFromRemote { conversationService.getConversation(conversationId) } } diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/repository/MovieRepository.kt b/android/app/src/main/java/com/github/bytestrick/vertex/repository/MovieRepository.kt index 04a27b35d..6319dadb4 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/repository/MovieRepository.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/repository/MovieRepository.kt @@ -161,14 +161,15 @@ class MovieRepository @Inject constructor( suspend fun getMovieById(id: Uuid): Result = runCatching { val cached = movieDao.getMovieById(id) - return Result.success(if (cached != null) { - cached - } else { - withContext(Dispatchers.IO) { - fetchAndSaveMovie(id) - } - movieDao.getMovieById(id) - }) + return Result.success( + if (cached != null) { + cached + } else { + withContext(Dispatchers.IO) { + fetchAndSaveMovie(id) + } + movieDao.getMovieById(id) + }) } suspend fun fetchAndSaveMoviesProjectedInCinemaInTimeFrame( diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/repository/ReservationRepository.kt b/android/app/src/main/java/com/github/bytestrick/vertex/repository/ReservationRepository.kt index 9153e0071..058d8820e 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/repository/ReservationRepository.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/repository/ReservationRepository.kt @@ -134,7 +134,7 @@ class ReservationRepository @Inject constructor( } } - suspend fun createReservation(projectionId: Uuid): Result { + suspend fun createReservation(projectionId: Uuid): Result = runCatching { val response = reservationService.createReservation(projectionId) return if (response.isSuccessful) { Result.success( diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/repository/SeatRepository.kt b/android/app/src/main/java/com/github/bytestrick/vertex/repository/SeatRepository.kt index ad2627fb5..bf1552128 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/repository/SeatRepository.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/repository/SeatRepository.kt @@ -13,14 +13,20 @@ class SeatRepository @Inject constructor( ) { private val tag = this::class.simpleName - suspend fun getSeatsInfo(projectionId: Uuid): List { - with(seatService.getSeatsInfo(projectionId)) { - if (isSuccessful) { - return body()!!.map { it.toSeatModel() } - } else { - Log.e(tag, "request to fetch user failed with ${code()}: ${errorBody()?.string()}") + try { + with(seatService.getSeatsInfo(projectionId)) { + if (isSuccessful) { + return body()!!.map { it.toSeatModel() } + } else { + Log.e( + tag, + "request to fetch user failed with ${code()}: ${errorBody()?.string()}" + ) + } } + } catch (e: Exception) { + Log.e(tag, "Could not get seat info", e) } return listOf() } diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageMediator.kt b/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageMediator.kt index 31f1c59ff..9c3dd2455 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageMediator.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageMediator.kt @@ -1,5 +1,6 @@ package com.github.bytestrick.vertex.repository.paging +import android.util.Log import androidx.paging.LoadType import androidx.paging.PagingState import androidx.paging.RemoteMediator @@ -9,7 +10,6 @@ import com.github.bytestrick.vertex.data.AppDatabase import com.github.bytestrick.vertex.data.entity.RemoteKey import retrofit2.HttpException import retrofit2.Response -import java.io.IOException import kotlin.uuid.Uuid /** @@ -49,11 +49,8 @@ class PageMediator( onUpsert(slice.content.map { converter(it) }) } MediatorResult.Success(endOfPaginationReached = slice.last) - } catch (e: IOException) { - MediatorResult.Error(e) - } catch (e: HttpException) { - MediatorResult.Error(e) - } catch (e: Exception) { - MediatorResult.Error(e) + } catch (t: Throwable) { + Log.e("PageMediator", "Error loading page", t) + MediatorResult.Error(t) } } diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageSource.kt b/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageSource.kt index a349cd7ce..38e5bb9c1 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageSource.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageSource.kt @@ -1,11 +1,11 @@ package com.github.bytestrick.vertex.repository.paging +import android.util.Log import androidx.paging.PagingSource import androidx.paging.PagingState import com.github.bytestrick.vertex.api.dto.Slice import retrofit2.HttpException import retrofit2.Response -import java.io.IOException /** * Parametrized [PagingSource]. Used mainly for search. Deduplicates the content of the pages @@ -42,9 +42,8 @@ class PageSource( prevKey = if (position == 0) null else position - 1, nextKey = if (page?.last == true) null else position + 1 ) - } catch (e: IOException) { - LoadResult.Error(e) - } catch (e: HttpException) { - LoadResult.Error(e) + } catch (t: Throwable) { + Log.e("PageMediator", "Error loading page", t) + LoadResult.Error(t) } } diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/ResetPasswordViewModel.kt b/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/ResetPasswordViewModel.kt index eb3603c48..c5eb5c55c 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/ResetPasswordViewModel.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/ResetPasswordViewModel.kt @@ -15,6 +15,7 @@ import com.github.bytestrick.vertex.ui.common.validateEmail import com.github.bytestrick.vertex.ui.common.validatedPasswordAndConfirm import com.github.bytestrick.vertex.ui.navigation.ResetPassword import dagger.hilt.android.lifecycle.HiltViewModel +import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.flow.MutableStateFlow import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.flow.asStateFlow @@ -65,26 +66,32 @@ class ResetPasswordViewModel @Inject constructor( fun onEmailChange(email: String) = _uiState.update { it.copy(email = email, emailError = null) } - fun onEmailNext() = viewModelScope.launch { - _uiState.update { it.copy(isEmailCheckInProgress = true) } - // If the user is an OAuth2 user, the reset password flow should just set a new password, - // and enable them to sign in with the Google email and the new password. - val emailError = validateEmail(_uiState.value.email) ?: if (userService.isEmailTaken( - Email(_uiState.value.email) - ).code() != 200 - ) R.string.sign_in_incorrect_email else null - if (emailError == null) { - with(authService.forgotPassword(Email(_uiState.value.email.trim()))) { - if (isSuccessful) { - _uiState.update { it.copy(step = Step.Email(true)) } - } else { - Snackbar.show(R.string.rst_pw_send_verification_email_failure) + fun onEmailNext() = viewModelScope.launch(Dispatchers.IO) { + try { + _uiState.update { it.copy(isEmailCheckInProgress = true) } + // If the user is an OAuth2 user, the reset password flow should just set a new password, + // and enable them to sign in with the Google email and the new password. + val emailError = validateEmail(_uiState.value.email) ?: if (userService.isEmailTaken( + Email(_uiState.value.email) + ).code() != 200 + ) R.string.sign_in_incorrect_email else null + if (emailError == null) { + with(authService.forgotPassword(Email(_uiState.value.email.trim()))) { + if (isSuccessful) { + _uiState.update { it.copy(step = Step.Email(true)) } + } else { + Snackbar.show(R.string.rst_pw_send_verification_email_failure) + } } + } else { + _uiState.update { it.copy(emailError = emailError) } } - } else { - _uiState.update { it.copy(emailError = emailError) } + } catch (e: Exception) { + Snackbar.show() + Log.e(tag, "Error in forgot password flow", e) + } finally { + _uiState.update { it.copy(isEmailCheckInProgress = false) } } - _uiState.update { it.copy(isEmailCheckInProgress = false) } } fun onPasswordChange(password: String) { @@ -105,7 +112,7 @@ class ResetPasswordViewModel @Inject constructor( fun onBackToEmail() = viewModelScope.launch { _uiState.update { it.copy(step = Step.Email()) } } - fun onResetPassword() = viewModelScope.launch { + fun onResetPassword() = viewModelScope.launch(Dispatchers.IO) { val (passwordError, confirmPasswordError) = validatedPasswordAndConfirm( _uiState.value.password, _uiState.value.confirmPassword @@ -143,19 +150,24 @@ class ResetPasswordViewModel @Inject constructor( _uiState.update { it.copy(isPasswordResetInProgress = false) } } - fun onResendEmail() = viewModelScope.launch { - with(authService.resendMfaEmail(Email(_uiState.value.email))) { - if (isSuccessful) { - Snackbar.show(R.string.verify_email_resend_success) - } else when (code()) { - 401 -> { - Snackbar.show(R.string.verify_email_no_pending_verification_email) - _uiState.update { it.copy(step = Step.Terminated) } - } + fun onResendEmail() = viewModelScope.launch(Dispatchers.IO) { + try { + with(authService.resendMfaEmail(Email(_uiState.value.email))) { + if (isSuccessful) { + Snackbar.show(R.string.verify_email_resend_success) + } else when (code()) { + 401 -> { + Snackbar.show(R.string.verify_email_no_pending_verification_email) + _uiState.update { it.copy(step = Step.Terminated) } + } - 404 -> Snackbar.show(R.string.verify_email_user_not_found) - else -> Snackbar.show(R.string.verify_email_resend_default_error) + 404 -> Snackbar.show(R.string.verify_email_user_not_found) + else -> Snackbar.show(R.string.verify_email_resend_default_error) + } } + } catch (e: Exception) { + Log.e(tag, "Could not resend email", e) + Snackbar.show() } } } \ No newline at end of file diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/SignUpViewModel.kt b/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/SignUpViewModel.kt index e4f5435b2..b1c43a7b8 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/SignUpViewModel.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/SignUpViewModel.kt @@ -12,6 +12,7 @@ import com.github.bytestrick.vertex.ui.common.validateBirthday import com.github.bytestrick.vertex.ui.common.validateEmail import com.github.bytestrick.vertex.ui.common.validatedPasswordAndConfirm import dagger.hilt.android.lifecycle.HiltViewModel +import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.flow.MutableStateFlow import kotlinx.coroutines.flow.asStateFlow import kotlinx.coroutines.flow.update @@ -83,12 +84,18 @@ class SignUpViewModel @Inject constructor(private val userService: UserService) _uiState.update { it.copy(birthday = birthday, birthdayError = null) } } - fun onPersonalDetailsNext() = viewModelScope.launch { - _uiState.update { it.copy(isEmailCheckInProgress = true) } - if (arePersonalDetailsValid()) { - _uiState.update { it.copy(step = Step.Password) } + fun onPersonalDetailsNext() = viewModelScope.launch(Dispatchers.IO) { + try { + _uiState.update { it.copy(isEmailCheckInProgress = true) } + if (arePersonalDetailsValid()) { + _uiState.update { it.copy(step = Step.Password) } + } + } catch (e: Exception) { + Snackbar.show() + Log.e(tag, "Error while verifying email existence", e) + } finally { + _uiState.update { it.copy(isEmailCheckInProgress = false) } } - _uiState.update { it.copy(isEmailCheckInProgress = false) } } fun onBackToPersonalDetails() = viewModelScope.launch { @@ -148,9 +155,9 @@ class SignUpViewModel @Inject constructor(private val userService: UserService) } } - fun signUp() = viewModelScope.launch { - _uiState.update { it.copy(isSignUpInProgress = true) } + fun signUp() = viewModelScope.launch(Dispatchers.IO) { try { + _uiState.update { it.copy(isSignUpInProgress = true) } if (isPasswordValid()) { val res = userService.createUser( NewUser( @@ -172,7 +179,8 @@ class SignUpViewModel @Inject constructor(private val userService: UserService) } catch (e: Exception) { Log.e(tag, "sign up failed", e) Snackbar.show(R.string.sign_up_failed) + } finally { + _uiState.update { it.copy(isSignUpInProgress = false) } } - _uiState.update { it.copy(isSignUpInProgress = false) } } } diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/VerifyEmailViewModel.kt b/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/VerifyEmailViewModel.kt index bb32200d8..959df1cec 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/VerifyEmailViewModel.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/ui/auth/VerifyEmailViewModel.kt @@ -15,8 +15,11 @@ import com.github.bytestrick.vertex.ui.common.Snackbar import com.github.bytestrick.vertex.ui.navigation.VerifyEmail import dagger.hilt.android.lifecycle.HiltViewModel import jakarta.inject.Inject +import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.flow.MutableStateFlow import kotlinx.coroutines.flow.asStateFlow +import kotlinx.coroutines.flow.filterNotNull +import kotlinx.coroutines.flow.first import kotlinx.coroutines.flow.update import kotlinx.coroutines.launch @@ -62,14 +65,14 @@ class VerifyEmailViewModel @Inject constructor( } "verify-new-email" -> { + Snackbar.show(R.string.verify_new_email_deep_link_success) + userRepository.fetchAndSaveUser(userRepository.user.filterNotNull().first().id) _uiState.update { it.copy( step = Step.Terminated, reason = VerificationReason.EMAIL_UPDATED ) } - userRepository.user.value?.id?.let { userRepository.fetchAndSaveUser(it) } - Snackbar.show(R.string.verify_new_email_deep_link_success) } else -> { @@ -91,7 +94,7 @@ class VerifyEmailViewModel @Inject constructor( } } - fun onResendEmail() = viewModelScope.launch { + fun onResendEmail() = viewModelScope.launch(Dispatchers.IO) { try { val res = authService.resendMfaEmail(Email(_uiState.value.email!!)) if (res.isSuccessful) { diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/ui/profile/ProfileViewModel.kt b/android/app/src/main/java/com/github/bytestrick/vertex/ui/profile/ProfileViewModel.kt index 9b9053c65..fb747d56e 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/ui/profile/ProfileViewModel.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/ui/profile/ProfileViewModel.kt @@ -219,9 +219,9 @@ class ProfileViewModel @Inject constructor( return data } - fun onUpdateProfilePicture(imageBitmap: ImageBitmap) = viewModelScope.launch { + fun onUpdateProfilePicture(pic: ImageBitmap) = viewModelScope.launch(Dispatchers.Default) { try { - val data = compressBitmap(imageBitmap.asAndroidBitmap(), MAX_IMAGE_SIZE) + val data = compressBitmap(pic.asAndroidBitmap(), MAX_IMAGE_SIZE) require(data.size <= MAX_IMAGE_SIZE) { "Image too big" } val res = userService.updateProfilePicture( uiState.value.user!!.id, @@ -266,7 +266,7 @@ class ProfileViewModel @Inject constructor( _uiState.update { it.copy(isRemoveProfilePictureDialogOpen = false) } } - fun onRemoveProfilePictureConfirm() = viewModelScope.launch { + fun onRemoveProfilePictureConfirm() = viewModelScope.launch(Dispatchers.IO) { _uiState.update { it.copy(isRemoveProfilePictureDialogOpen = false) } uiState.value.user?.let { try { @@ -314,7 +314,11 @@ class ProfileViewModel @Inject constructor( fun onEditSurname() = viewModelScope.launch { _uiState.update { it.copy( - newSurname = if (uiState.value.isSurnameRowExpanded) null else uiState.value.user?.surname, + newSurname = if (uiState.value.isSurnameRowExpanded) { + null + } else { + uiState.value.user?.surname + }, isSurnameRowExpanded = !uiState.value.isSurnameRowExpanded, ) } @@ -342,7 +346,7 @@ class ProfileViewModel @Inject constructor( } } - fun onUpdatePersonalDetails() = viewModelScope.launch { + fun onUpdatePersonalDetails() = viewModelScope.launch(Dispatchers.IO) { _uiState.update { prevUiState -> prevUiState.copy( isEmailRowExpanded = _uiState.value.hasEmailChanged, @@ -450,7 +454,7 @@ class ProfileViewModel @Inject constructor( } } - fun onUpdatePassword() = viewModelScope.launch { + fun onUpdatePassword() = viewModelScope.launch(Dispatchers.IO) { val (passwordError, confirmPasswordError) = validatedPasswordAndConfirm( _uiState.value.newPassword, _uiState.value.confirmNewPassword @@ -575,7 +579,7 @@ class ProfileViewModel @Inject constructor( _uiState.update { it.copy(isDisconnectGoogleDialogOpen = false) } } - fun onDisconnectGoogleDialogConfirm() = viewModelScope.launch { + fun onDisconnectGoogleDialogConfirm() = viewModelScope.launch(Dispatchers.IO) { _uiState.update { it.copy( isDisconnectGoogleInProgress = true, From 70a023c08cccb39b0c1cc407e0c7f1d574bfd01d Mon Sep 17 00:00:00 2001 From: Mario D'Andrea Date: Sat, 24 Jan 2026 18:15:48 +0100 Subject: [PATCH 2/2] fix: deep links contained in MFA emails --- .../github/bytestrick/vertex/repository/paging/PageSource.kt | 2 +- .../bytestrick/vertex/ui/navigation/AuthenticationSubgraph.kt | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageSource.kt b/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageSource.kt index 38e5bb9c1..b29d010f9 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageSource.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/repository/paging/PageSource.kt @@ -43,7 +43,7 @@ class PageSource( nextKey = if (page?.last == true) null else position + 1 ) } catch (t: Throwable) { - Log.e("PageMediator", "Error loading page", t) + Log.e("PageSource", "Error loading page", t) LoadResult.Error(t) } } diff --git a/android/app/src/main/java/com/github/bytestrick/vertex/ui/navigation/AuthenticationSubgraph.kt b/android/app/src/main/java/com/github/bytestrick/vertex/ui/navigation/AuthenticationSubgraph.kt index 400026046..99344576e 100644 --- a/android/app/src/main/java/com/github/bytestrick/vertex/ui/navigation/AuthenticationSubgraph.kt +++ b/android/app/src/main/java/com/github/bytestrick/vertex/ui/navigation/AuthenticationSubgraph.kt @@ -107,12 +107,12 @@ fun NavGraphBuilder.authentication(windowPadding: PaddingValues, navController: composable( deepLinks = listOf( navDeepLink { - uriPattern = "$redirectionBase/redirect?reason=verify-email&error={error}" + uriPattern = "$redirectionBase/redirect/index.html?reason=verify-email&error={error}" action = Intent.ACTION_VIEW }, navDeepLink { uriPattern = - "$redirectionBase/redirect?reason=verify-new-email&error={error}" + "$redirectionBase/redirect/index.html?reason=verify-new-email&error={error}" action = Intent.ACTION_VIEW } )