Services and ViewModels in Android MVVM - How do they interact?

After some toying with different structures, the Service has found it's place in MVVM. What was throwing me off in this situation was thinking a Service shouldn't be started from a ViewModel and the fact that two repositories were necessary: Room Database to store Timers and a Service to represent the state of ongoing timers (onTick, play/pause status, etc). A ViewModel should not have any reference to views, but application context is OK. So starting the Service from a ViewModel is doable by extending the AndroidViewModel class. Here is the final structure:

Model Layer

  • Service - Maintains a list of active timers, emits onTick() EventBus events, maintains active timer play/pause status. Ends itself once there are no active timers.
  • Room Database - Stores timers for future use (name, total time, etc.)

ViewModel

  • ViewModel - Listens for UI events, performs business logic, and emits EventBus posts. Any change in Model is communicated through the ViewModel

UI

  • Activity - performs application flow tasks. Listens for relevant ViewModel communications to swap fragments/start new activities, etc.
  • Fragment - handles animations and UI. Also notifies ViewModel of user interaction

The services should be treated as AndroidViewModel which has application context in MVVM architecture. Because, the service is doing something with the data as ViewModels do.

Services cannot talk directly to Databases. But it should talk to Repositories which intern talk to databases like SQLite/Room/Server.

As ViewModel has views like Fragment/Activity. Service transforms itself into Foreground Service with status bar Notification as it's view to update. We do not use LiveData for Notification's view, but update the notification itself (we can assume this as Activity/Fragment recreated).