Skip to content

Conversation

cy245
Copy link
Contributor

@cy245 cy245 commented Oct 1, 2025

No description provided.

@cy245
Copy link
Contributor Author

cy245 commented Oct 1, 2025

/gemini review

Copy link

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request successfully migrates the CredentialManager sample app from the traditional View system (Fragments and XML) to Jetpack Compose. The migration is comprehensive, replacing all UI components, navigation, and adapting the logic to a ViewModel-based architecture. The code is now more modern and follows many Compose best practices.

However, there are a few significant areas for improvement. The most critical is the downgrading of several key AndroidX and Kotlin libraries in build.gradle, which is a regression and should be reverted. Additionally, there are architectural concerns, primarily passing Activity and Context instances into ViewModels, which violates MVVM principles and can lead to memory leaks. I've also left comments on improving navigation logic, state handling, and making Compose Previews more robust.

Overall, this is a great step forward for the sample app. Addressing the feedback will make it an even better example of a modern Android application.

Comment on lines +78 to +87
Button(
onClick = {
if (activity != null) {
viewModel.signIn(activity, context)
}
},
shape = RoundedCornerShape(4.dp),
enabled = !isLoading && activity != null,
modifier = Modifier.fillMaxWidth()
) {

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

Passing the Activity or Context to the ViewModel (viewModel.signIn(activity, context)) is a violation of MVVM architecture. ViewModels should not hold references to UI-layer components, as this can lead to memory leaks and makes them difficult to test.

The CredentialManager API requires an Activity, so the call to credentialManager.getCredential should be initiated from the UI layer (e.g., inside this onClick lambda). The result can then be passed to the ViewModel for processing.

private val _navigationEvent = MutableSharedFlow<NavigationEvent>()
val navigationEvent = _navigationEvent.asSharedFlow()

fun signIn(activity: Activity, context: Context) {

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

The signIn function accepts Activity and Context parameters. This tightly couples the ViewModel to the Android framework, making it difficult to unit test and potentially causing memory leaks. The responsibility of interacting with framework components like CredentialManager (which requires an Activity) should be handled in the UI layer (the Composable screen), and only the results (or data) should be passed to the ViewModel for processing.

Comment on lines +141 to +152
Button(
onClick = {
if (activity != null) {
viewModel.signUpWithPasskey(activity, context)
}
},
shape = RoundedCornerShape(4.dp),
enabled = !isLoading && activity != null,
modifier = Modifier.fillMaxWidth()
) {
Text("Sign Up with passkey")
}

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

Passing the Activity and Context to the ViewModel (viewModel.signUpWithPasskey(activity, context)) is a violation of MVVM architecture. ViewModels should not hold references to UI-layer components, as this can lead to memory leaks and makes them difficult to test. The CredentialManager API call should be initiated from the UI layer (e.g., inside this onClick lambda), and the result can then be passed to the ViewModel for processing.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

1 participant