currently, in my app i have a few features (multi-...
# android-architecture
s
currently, in my app i have a few features (multi-module) which, when the user navigates to, they need to logged in. if they are not, then they will be navigated to login/register activity. the login/register activity is launched for result using the
registerForActivityResult
. question: how to share the
ActivityResultCallback
logic across multiple feature. user flow scenarios • login/register flow can be successful so they are navigated to the feature user intended to go to. • login/register flow can fail, login screen is closed and user is show error message at the entry point screen. (ill mention some approaches ive come up with in the thread)
1. create an interface that extends
ActivityResultCallback
Copy code
interface LoginResultCallback : ActivityResultCallback<ActivityResult> { // ... }
the interface implementation will have a flow that will emit result state
Copy code
class LoginResultCallbackImpl : LoginResultCallback {
 sealed class LoginResultEvent {
    object Success: LoginResultEvent()
    object Error: LoginResultEvent()
}

val resultEvent = flow<LoginResultEvent>()

// class will override `onActivityResult` and emit event to flow
all the features that require login, the VMs of those will also implement the interface and the implementation will provided as interface delegates
Copy code
class OrderDetailsVM (loginResult: LoginResultCallbackImpl): ViewModel(), LoginResultCallback by loginResult
next the vm will transform the events to the view accordingly to its event and finally in the view will use the VM in the
Copy code
registerForActivityResult(
   StartActForRes,
   vm
)
benefits: result callback parsing logic is separated, and going through vm allows some-what unit testing this flow downside: to many changes to existing code and isnt very dry (is this the cost of sharing ActivityResultCallback?)
2. Receiving an activity result in a separate class by providing
ActivityResultRegistry
, and registering the callback in this separate class. problem is, in this approach wont, vm cant be used (or i cant think of how to) as
activityResultRegistry
is retrieved from the view (Activity/Fragment) so its not possible to do constructor injection. as VM can outlive the view. the only way i can think of to go through the VM (for unit testing purpose) is to pass the flow through a function. im not convinced passing through function is a very good approach, let alone the overall approach itself