Hello all! Old school Android engineer here jumpin...
# compose
t
Hello all! Old school Android engineer here jumping back into being an engineer and starting a new role soon! I am working on testing my code. In the old Java+XML days about 9 or more years ago I was able to use the UI methods and mock the UI and felt like I could test practically anything. I just struggled a bit trying to get things working for unit tests in my UI Compose classes and I finally was forced to only using the AndroidTest instrument tests. Are there ways of testing my View methods or am I doing it correctly via Instrument testing only and I'm stuck in the past thinking I can do all those tests as Unit Tests? Additionally if I have to have them as instrument tests only, how do I handle the CI/CD for the instrument testing?
j
Are there ways of testing my View methods
What kind of view methods do you have? In an ideal world most of your logic would be in a view model where you can test with without instrumentation. The functionality that requires system components such context, BroadcastReceivers should be abstracted out as much from your Compose (UI) code as possible. Then only that specific functionality could be tested in separately.
t
That’s fair, my testing coverage was feeling “incomplete” but it turns out that it was my concept of modern testing was incomplete. Thank you for the validation! I’ll still continue the instrument testing to verify the testing tags on button presses and other spots and move forward.
j
Unsolicited advice: I recommend hoisting all events (click listeners, value change lambdas) out of your composable functions and forward the events to your ViewModel. It will make testing much easier (faster to since you don’t need a device/emulator). Especially where there is complex logic that happens based on events such as setting multiple state values.
💯 2
t
@Jonathan Thank you, that is what I ended up mostly doing to my class that works appropriately now. I have my screen, view model, UI state, and container. The Nav uses the Container that pulls everything together as the screen class just takes in the methods from the vm passed in and it enabled more abstracted functions and easier state to mock. Additionally I could use an Events interface for callbacks but I think the container is handling that portion of method handling for me in place of it. https://github.com/timkaragosian1/2025TrainingApp/blob/main/app/src/main/java/com/timkaragosian/proflowapp/presentation/home/HomeScreenContainer.kt
j
Looks pretty good. Some _suggestions_: 1. Your View Model should be assembling your UI state. That’s not the Job of the UI. 2. I would pass the “navigation event” into your Viewmodel. I would then have the Viewmodel would expose an event stream/flow of some kind that my UI would observe and call the “navigate” lambda (
onTaskResults
). This adds extra complexity but it allows the vm to be in charge. I can verify args as well as determine if navigations is allowed. This will also allow you to navigate based on some internal state. Lastly, its makes testing so much easier but in a generic way. You can verify that clicking buttons correctly trigger a “navigation” in your unit test (non-intrumented). 3. I think the onLogout event should be passed based to the ViewModel for the same reason as above. If for nothing else it, it would make logging your user out based on expired tokens, or remote sign-out event… Feel free to ignore but MVI has definitely made building apps in Compose easier for me.
thank you color 1
🔥 1