I have a question regarding usage of Google APIs (in my case NavigationAPI) in clean architecture.
So in order to use google navigation it is necessary to have Navigator object from NavigationApi.getNavigator API. Initially I thought that it’s ok to put all necessary implementation in DATA layer, however this layer is supposed to only hold and provide access to data (local, remote). But then Navigator is highly dependent on SupportNavigationFragment which is in presentation layer. As we know, lower layers shouldn’t depend on higher layers.
So next I thought that all mentioned implementation should be moved to fragment, but I am not 100% sure if this is correct even if it sounds reasonable. Does anyone have any experience with google api in clean arch?
Functionality that I need:
private var navigator: Navigator? = null
override fun initializeNavigator(activity: FragmentActivity) {
NavigationApi.getNavigator(activity, object : NavigationApi.NavigatorListener {
override fun onNavigatorReady(navigator: Navigator?) {
navigator = navigator
addListeners()
}
override fun onError(errorCode: Int) {
handleError(errorCode)
}
})
}
override fun startNavigation() {
navigator?.setAudioGuidance(Navigator.AudioGuidance.VOICE_ALERTS_AND_GUIDANCE)
navigator?.startGuidance()
}
override fun stopNavigation() {
navigator?.stopGuidance()
navigator?.clearDestinations()
}
override fun getRouteSummary(waypoint: Waypoint, options: RoutingOptions) = callbackFlow {
navigator?.let { navigator ->
val pendingRoute = navigator.setDestination(waypoint, options)
pendingRoute.setOnResultListener { code ->
_navigationStateFlow.value = NavigationState.SUMMARY
val result = trySend(
NavigationSummary(
response = code,
meters = navigator.currentTimeAndDistance.meters,
seconds = navigator.currentTimeAndDistance.seconds
)
)
}
awaitClose {
…
}
}
}
private fun addListeners() {
val arrivalListener = Navigator.ArrivalListener {
navigator?.clearDestinations()
}
navigator?.addArrivalListener(arrivalListener)
val routeChangedListener = Navigator.RouteChangedListener {
…
}
navigator?.addRouteChangedListener(routeChangedListener)
}
private fun handleError(errorCode: Int) {
when (errorCode) {
NavigationApi.ErrorCode.NOT_AUTHORIZED -> {
…
}
NavigationApi.ErrorCode.TERMS_NOT_ACCEPTED -> {
...
}
NavigationApi.ErrorCode.NETWORK_ERROR -> {
…
}
NavigationApi.ErrorCode.LOCATION_PERMISSION_MISSING -> {
…
}
else -> {
...
}
}
}
SupportNavigationFragmentor the API forNavigator. Also,SupportNavigationFragmentis optional AFAICT. You might wish to explain, in detail, the nature of the dependency that worries you.