kopia lustrzana https://github.com/meshtastic/Meshtastic-Android
				
				
				
			Redundant methods in `RadioConfigRepository` (#3198)
							rodzic
							
								
									8be9c38ae6
								
							
						
					
					
						commit
						8317b704ea
					
				| 
						 | 
				
			
			@ -19,7 +19,7 @@ package com.geeksville.mesh.ui.map
 | 
			
		|||
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.database.PacketRepository
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
import org.meshtastic.core.prefs.map.MapPrefs
 | 
			
		||||
import javax.inject.Inject
 | 
			
		||||
| 
						 | 
				
			
			@ -31,8 +31,8 @@ constructor(
 | 
			
		|||
    mapPrefs: MapPrefs,
 | 
			
		||||
    packetRepository: PacketRepository,
 | 
			
		||||
    nodeRepository: NodeRepository,
 | 
			
		||||
    radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
) : BaseMapViewModel(mapPrefs, nodeRepository, packetRepository, radioConfigRepository) {
 | 
			
		||||
    serviceRepository: ServiceRepository,
 | 
			
		||||
) : BaseMapViewModel(mapPrefs, nodeRepository, packetRepository, serviceRepository) {
 | 
			
		||||
 | 
			
		||||
    var mapStyleId: Int
 | 
			
		||||
        get() = mapPrefs.mapStyle
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -26,6 +26,7 @@ import com.geeksville.mesh.android.BuildUtils.debug
 | 
			
		|||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.database.PacketRepository
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import com.google.android.gms.maps.GoogleMap
 | 
			
		||||
import com.google.android.gms.maps.model.TileProvider
 | 
			
		||||
import com.google.android.gms.maps.model.UrlTileProvider
 | 
			
		||||
| 
						 | 
				
			
			@ -85,8 +86,9 @@ constructor(
 | 
			
		|||
    nodeRepository: NodeRepository,
 | 
			
		||||
    packetRepository: PacketRepository,
 | 
			
		||||
    radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    serviceRepository: ServiceRepository,
 | 
			
		||||
    private val customTileProviderRepository: CustomTileProviderRepository,
 | 
			
		||||
) : BaseMapViewModel(mapPrefs, nodeRepository, packetRepository, radioConfigRepository) {
 | 
			
		||||
) : BaseMapViewModel(mapPrefs, nodeRepository, packetRepository, serviceRepository) {
 | 
			
		||||
 | 
			
		||||
    private val _errorFlow = MutableSharedFlow<String>()
 | 
			
		||||
    val errorFlow: SharedFlow<String> = _errorFlow.asSharedFlow()
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -28,7 +28,7 @@ import com.geeksville.mesh.StoreAndForwardProtos
 | 
			
		|||
import com.geeksville.mesh.TelemetryProtos
 | 
			
		||||
import com.geeksville.mesh.android.Logging
 | 
			
		||||
import com.geeksville.mesh.database.MeshLogRepository
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.ui.debug.FilterMode
 | 
			
		||||
import com.google.protobuf.InvalidProtocolBufferException
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
| 
						 | 
				
			
			@ -202,7 +202,7 @@ class DebugViewModel
 | 
			
		|||
@Inject
 | 
			
		||||
constructor(
 | 
			
		||||
    private val meshLogRepository: MeshLogRepository,
 | 
			
		||||
    private val radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    private val nodeRepository: NodeRepository,
 | 
			
		||||
) : ViewModel(),
 | 
			
		||||
    Logging {
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -345,7 +345,7 @@ constructor(
 | 
			
		|||
    val presetFilters: List<String>
 | 
			
		||||
        get() = buildList {
 | 
			
		||||
            // Our address if available
 | 
			
		||||
            radioConfigRepository.myNodeInfo.value?.myNodeNum?.let { add("!%08x".format(it)) }
 | 
			
		||||
            nodeRepository.myNodeInfo.value?.myNodeNum?.let { add("!%08x".format(it)) }
 | 
			
		||||
            // broadcast
 | 
			
		||||
            add("!ffffffff")
 | 
			
		||||
            // decoded
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -36,10 +36,12 @@ import com.geeksville.mesh.Portnums.PortNum
 | 
			
		|||
import com.geeksville.mesh.TelemetryProtos.Telemetry
 | 
			
		||||
import com.geeksville.mesh.android.Logging
 | 
			
		||||
import com.geeksville.mesh.database.MeshLogRepository
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.repository.api.DeviceHardwareRepository
 | 
			
		||||
import com.geeksville.mesh.repository.api.FirmwareReleaseRepository
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.service.ServiceAction
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import com.geeksville.mesh.util.safeNumber
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
import kotlinx.coroutines.flow.MutableStateFlow
 | 
			
		||||
| 
						 | 
				
			
			@ -203,7 +205,9 @@ constructor(
 | 
			
		|||
    private val app: Application,
 | 
			
		||||
    private val dispatchers: CoroutineDispatchers,
 | 
			
		||||
    private val meshLogRepository: MeshLogRepository,
 | 
			
		||||
    private val radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    private val serviceRepository: ServiceRepository,
 | 
			
		||||
    private val nodeRepository: NodeRepository,
 | 
			
		||||
    private val deviceHardwareRepository: DeviceHardwareRepository,
 | 
			
		||||
    private val firmwareReleaseRepository: FirmwareReleaseRepository,
 | 
			
		||||
    private val mapPrefs: MapPrefs,
 | 
			
		||||
| 
						 | 
				
			
			@ -233,7 +237,7 @@ constructor(
 | 
			
		|||
        return Node(num = nodeNum, user = defaultUser)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun getUser(nodeNum: Int) = radioConfigRepository.getUser(nodeNum)
 | 
			
		||||
    fun getUser(nodeNum: Int) = nodeRepository.getUser(nodeNum)
 | 
			
		||||
 | 
			
		||||
    val tileSource
 | 
			
		||||
        get() = CustomTileSource.getTileSource(mapPrefs.mapStyle)
 | 
			
		||||
| 
						 | 
				
			
			@ -244,7 +248,7 @@ constructor(
 | 
			
		|||
        destNum?.let { meshLogRepository.deleteLogs(it, PortNum.POSITION_APP_VALUE) }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun onServiceAction(action: ServiceAction) = viewModelScope.launch { radioConfigRepository.onServiceAction(action) }
 | 
			
		||||
    fun onServiceAction(action: ServiceAction) = viewModelScope.launch { serviceRepository.onServiceAction(action) }
 | 
			
		||||
 | 
			
		||||
    private val _state = MutableStateFlow(MetricsState.Empty)
 | 
			
		||||
    val state: StateFlow<MetricsState> = _state
 | 
			
		||||
| 
						 | 
				
			
			@ -257,7 +261,7 @@ constructor(
 | 
			
		|||
 | 
			
		||||
    init {
 | 
			
		||||
        if (destNum != null) {
 | 
			
		||||
            radioConfigRepository.nodeDBbyNum
 | 
			
		||||
            nodeRepository.nodeDBbyNum
 | 
			
		||||
                .mapLatest { nodes -> nodes[destNum] to nodes.keys.firstOrNull() }
 | 
			
		||||
                .distinctUntilChanged()
 | 
			
		||||
                .onEach { (node, ourNode) ->
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -53,6 +53,7 @@ import com.geeksville.mesh.repository.radio.MeshActivity
 | 
			
		|||
import com.geeksville.mesh.repository.radio.RadioInterfaceService
 | 
			
		||||
import com.geeksville.mesh.service.MeshServiceNotifications
 | 
			
		||||
import com.geeksville.mesh.service.ServiceAction
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import com.geeksville.mesh.ui.node.components.NodeMenuAction
 | 
			
		||||
import com.geeksville.mesh.util.safeNumber
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
| 
						 | 
				
			
			@ -185,6 +186,7 @@ constructor(
 | 
			
		|||
    private val app: Application,
 | 
			
		||||
    private val nodeDB: NodeRepository,
 | 
			
		||||
    private val radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    private val serviceRepository: ServiceRepository,
 | 
			
		||||
    radioInterfaceService: RadioInterfaceService,
 | 
			
		||||
    private val meshLogRepository: MeshLogRepository,
 | 
			
		||||
    private val deviceHardwareRepository: DeviceHardwareRepository,
 | 
			
		||||
| 
						 | 
				
			
			@ -215,10 +217,10 @@ constructor(
 | 
			
		|||
            }
 | 
			
		||||
            .stateIn(scope = viewModelScope, started = SharingStarted.WhileSubscribed(5_000), initialValue = null)
 | 
			
		||||
 | 
			
		||||
    val clientNotification: StateFlow<MeshProtos.ClientNotification?> = radioConfigRepository.clientNotification
 | 
			
		||||
    val clientNotification: StateFlow<MeshProtos.ClientNotification?> = serviceRepository.clientNotification
 | 
			
		||||
 | 
			
		||||
    fun clearClientNotification(notification: MeshProtos.ClientNotification) {
 | 
			
		||||
        radioConfigRepository.clearClientNotification()
 | 
			
		||||
        serviceRepository.clearClientNotification()
 | 
			
		||||
        meshServiceNotifications.clearClientNotification(notification)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -275,7 +277,7 @@ constructor(
 | 
			
		|||
    }
 | 
			
		||||
 | 
			
		||||
    val meshService: IMeshService?
 | 
			
		||||
        get() = radioConfigRepository.meshService
 | 
			
		||||
        get() = serviceRepository.meshService
 | 
			
		||||
 | 
			
		||||
    private val localConfig = MutableStateFlow<LocalConfig>(LocalConfig.getDefaultInstance())
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -447,13 +449,13 @@ constructor(
 | 
			
		|||
    }
 | 
			
		||||
 | 
			
		||||
    init {
 | 
			
		||||
        radioConfigRepository.errorMessage
 | 
			
		||||
        serviceRepository.errorMessage
 | 
			
		||||
            .filterNotNull()
 | 
			
		||||
            .onEach {
 | 
			
		||||
                showAlert(
 | 
			
		||||
                    title = app.getString(R.string.client_notification),
 | 
			
		||||
                    message = it,
 | 
			
		||||
                    onConfirm = { radioConfigRepository.clearErrorMessage() },
 | 
			
		||||
                    onConfirm = { serviceRepository.clearErrorMessage() },
 | 
			
		||||
                    dismissable = false,
 | 
			
		||||
                )
 | 
			
		||||
            }
 | 
			
		||||
| 
						 | 
				
			
			@ -590,9 +592,8 @@ constructor(
 | 
			
		|||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun sendReaction(emoji: String, replyId: Int, contactKey: String) = viewModelScope.launch {
 | 
			
		||||
        radioConfigRepository.onServiceAction(ServiceAction.Reaction(emoji, replyId, contactKey))
 | 
			
		||||
    }
 | 
			
		||||
    fun sendReaction(emoji: String, replyId: Int, contactKey: String) =
 | 
			
		||||
        viewModelScope.launch { serviceRepository.onServiceAction(ServiceAction.Reaction(emoji, replyId, contactKey)) }
 | 
			
		||||
 | 
			
		||||
    private val _sharedContactRequested: MutableStateFlow<AdminProtos.SharedContact?> = MutableStateFlow(null)
 | 
			
		||||
    val sharedContactRequested: StateFlow<AdminProtos.SharedContact?>
 | 
			
		||||
| 
						 | 
				
			
			@ -603,7 +604,7 @@ constructor(
 | 
			
		|||
    }
 | 
			
		||||
 | 
			
		||||
    fun addSharedContact(sharedContact: AdminProtos.SharedContact) =
 | 
			
		||||
        viewModelScope.launch { radioConfigRepository.onServiceAction(ServiceAction.AddSharedContact(sharedContact)) }
 | 
			
		||||
        viewModelScope.launch { serviceRepository.onServiceAction(ServiceAction.AddSharedContact(sharedContact)) }
 | 
			
		||||
 | 
			
		||||
    fun requestTraceroute(destNum: Int) {
 | 
			
		||||
        info("Requesting traceroute for '$destNum'")
 | 
			
		||||
| 
						 | 
				
			
			@ -663,10 +664,10 @@ constructor(
 | 
			
		|||
 | 
			
		||||
    // Connection state to our radio device
 | 
			
		||||
    val connectionState
 | 
			
		||||
        get() = radioConfigRepository.connectionState
 | 
			
		||||
        get() = serviceRepository.connectionState
 | 
			
		||||
 | 
			
		||||
    val isConnectedStateFlow =
 | 
			
		||||
        radioConfigRepository.connectionState
 | 
			
		||||
        serviceRepository.connectionState
 | 
			
		||||
            .map { it.isConnected() }
 | 
			
		||||
            .stateIn(viewModelScope, SharingStarted.Eagerly, false)
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -701,7 +702,7 @@ constructor(
 | 
			
		|||
 | 
			
		||||
    fun favoriteNode(node: Node) = viewModelScope.launch {
 | 
			
		||||
        try {
 | 
			
		||||
            radioConfigRepository.onServiceAction(ServiceAction.Favorite(node))
 | 
			
		||||
            serviceRepository.onServiceAction(ServiceAction.Favorite(node))
 | 
			
		||||
        } catch (ex: RemoteException) {
 | 
			
		||||
            errormsg("Favorite node error:", ex)
 | 
			
		||||
        }
 | 
			
		||||
| 
						 | 
				
			
			@ -709,7 +710,7 @@ constructor(
 | 
			
		|||
 | 
			
		||||
    fun ignoreNode(node: Node) = viewModelScope.launch {
 | 
			
		||||
        try {
 | 
			
		||||
            radioConfigRepository.onServiceAction(ServiceAction.Ignore(node))
 | 
			
		||||
            serviceRepository.onServiceAction(ServiceAction.Ignore(node))
 | 
			
		||||
        } catch (ex: RemoteException) {
 | 
			
		||||
            errormsg("Ignore node error:", ex)
 | 
			
		||||
        }
 | 
			
		||||
| 
						 | 
				
			
			@ -817,10 +818,10 @@ constructor(
 | 
			
		|||
    }
 | 
			
		||||
 | 
			
		||||
    val tracerouteResponse: LiveData<String?>
 | 
			
		||||
        get() = radioConfigRepository.tracerouteResponse.asLiveData()
 | 
			
		||||
        get() = serviceRepository.tracerouteResponse.asLiveData()
 | 
			
		||||
 | 
			
		||||
    fun clearTracerouteResponse() {
 | 
			
		||||
        radioConfigRepository.clearTracerouteResponse()
 | 
			
		||||
        serviceRepository.clearTracerouteResponse()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun setNodeFilterText(text: String) {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -22,29 +22,14 @@ import com.geeksville.mesh.ChannelProtos.Channel
 | 
			
		|||
import com.geeksville.mesh.ChannelProtos.ChannelSettings
 | 
			
		||||
import com.geeksville.mesh.ClientOnlyProtos.DeviceProfile
 | 
			
		||||
import com.geeksville.mesh.ConfigProtos.Config
 | 
			
		||||
import com.geeksville.mesh.IMeshService
 | 
			
		||||
import com.geeksville.mesh.LocalOnlyProtos.LocalConfig
 | 
			
		||||
import com.geeksville.mesh.LocalOnlyProtos.LocalModuleConfig
 | 
			
		||||
import com.geeksville.mesh.MeshProtos
 | 
			
		||||
import com.geeksville.mesh.MeshProtos.DeviceMetadata
 | 
			
		||||
import com.geeksville.mesh.MeshProtos.MeshPacket
 | 
			
		||||
import com.geeksville.mesh.ModuleConfigProtos.ModuleConfig
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.deviceProfile
 | 
			
		||||
import com.geeksville.mesh.model.getChannelUrl
 | 
			
		||||
import com.geeksville.mesh.service.ConnectionState
 | 
			
		||||
import com.geeksville.mesh.service.ServiceAction
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import kotlinx.coroutines.coroutineScope
 | 
			
		||||
import kotlinx.coroutines.flow.Flow
 | 
			
		||||
import kotlinx.coroutines.flow.SharedFlow
 | 
			
		||||
import kotlinx.coroutines.flow.StateFlow
 | 
			
		||||
import kotlinx.coroutines.flow.combine
 | 
			
		||||
import kotlinx.coroutines.flow.first
 | 
			
		||||
import org.meshtastic.core.database.entity.MetadataEntity
 | 
			
		||||
import org.meshtastic.core.database.entity.MyNodeEntity
 | 
			
		||||
import org.meshtastic.core.database.entity.NodeEntity
 | 
			
		||||
import org.meshtastic.core.database.model.Node
 | 
			
		||||
import org.meshtastic.core.datastore.ChannelSetDataSource
 | 
			
		||||
import org.meshtastic.core.datastore.LocalConfigDataSource
 | 
			
		||||
import org.meshtastic.core.datastore.ModuleConfigDataSource
 | 
			
		||||
| 
						 | 
				
			
			@ -57,54 +42,11 @@ import javax.inject.Inject
 | 
			
		|||
class RadioConfigRepository
 | 
			
		||||
@Inject
 | 
			
		||||
constructor(
 | 
			
		||||
    private val serviceRepository: ServiceRepository,
 | 
			
		||||
    private val nodeDB: NodeRepository,
 | 
			
		||||
    private val channelSetDataSource: ChannelSetDataSource,
 | 
			
		||||
    private val localConfigDataSource: LocalConfigDataSource,
 | 
			
		||||
    private val moduleConfigDataSource: ModuleConfigDataSource,
 | 
			
		||||
) {
 | 
			
		||||
    val meshService: IMeshService?
 | 
			
		||||
        get() = serviceRepository.meshService
 | 
			
		||||
 | 
			
		||||
    // Connection state to our radio device
 | 
			
		||||
    val connectionState
 | 
			
		||||
        get() = serviceRepository.connectionState
 | 
			
		||||
 | 
			
		||||
    fun setConnectionState(state: ConnectionState) = serviceRepository.setConnectionState(state)
 | 
			
		||||
 | 
			
		||||
    /** Flow representing the unique userId of our node. */
 | 
			
		||||
    val myId: StateFlow<String?>
 | 
			
		||||
        get() = nodeDB.myId
 | 
			
		||||
 | 
			
		||||
    /** Flow representing the [MyNodeEntity] database. */
 | 
			
		||||
    val myNodeInfo: StateFlow<MyNodeEntity?>
 | 
			
		||||
        get() = nodeDB.myNodeInfo
 | 
			
		||||
 | 
			
		||||
    /** Flow representing the [Node] database. */
 | 
			
		||||
    val nodeDBbyNum: StateFlow<Map<Int, Node>>
 | 
			
		||||
        get() = nodeDB.nodeDBbyNum
 | 
			
		||||
 | 
			
		||||
    fun getUser(nodeNum: Int) = nodeDB.getUser(nodeNum)
 | 
			
		||||
 | 
			
		||||
    suspend fun getNodeDBbyNum() = nodeDB.getNodeDBbyNum().first()
 | 
			
		||||
 | 
			
		||||
    suspend fun upsert(node: NodeEntity) = nodeDB.upsert(node)
 | 
			
		||||
 | 
			
		||||
    suspend fun installMyNodeInfo(mi: MyNodeEntity) {
 | 
			
		||||
        nodeDB.installMyNodeInfo(mi)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    suspend fun installNodeDb(nodes: List<NodeEntity>) {
 | 
			
		||||
        nodeDB.installNodeDb(nodes)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    suspend fun insertMetadata(fromNum: Int, metadata: DeviceMetadata) {
 | 
			
		||||
        nodeDB.insertMetadata(MetadataEntity(fromNum, metadata))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    suspend fun clearNodeDB() {
 | 
			
		||||
        nodeDB.clearNodeDB()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /** Flow representing the [ChannelSet] data store. */
 | 
			
		||||
    val channelSetFlow: Flow<ChannelSet> = channelSetDataSource.channelSetFlow
 | 
			
		||||
| 
						 | 
				
			
			@ -185,50 +127,4 @@ constructor(
 | 
			
		|||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
    val clientNotification = serviceRepository.clientNotification
 | 
			
		||||
 | 
			
		||||
    fun setClientNotification(notification: MeshProtos.ClientNotification?) {
 | 
			
		||||
        serviceRepository.setClientNotification(notification)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun clearClientNotification() {
 | 
			
		||||
        serviceRepository.clearClientNotification()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    val errorMessage: StateFlow<String?>
 | 
			
		||||
        get() = serviceRepository.errorMessage
 | 
			
		||||
 | 
			
		||||
    fun setErrorMessage(text: String) {
 | 
			
		||||
        serviceRepository.setErrorMessage(text)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun clearErrorMessage() {
 | 
			
		||||
        serviceRepository.clearErrorMessage()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun setStatusMessage(text: String) {
 | 
			
		||||
        serviceRepository.setStatusMessage(text)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    val meshPacketFlow: SharedFlow<MeshPacket>
 | 
			
		||||
        get() = serviceRepository.meshPacketFlow
 | 
			
		||||
 | 
			
		||||
    suspend fun emitMeshPacket(packet: MeshPacket) = coroutineScope { serviceRepository.emitMeshPacket(packet) }
 | 
			
		||||
 | 
			
		||||
    val serviceAction: Flow<ServiceAction>
 | 
			
		||||
        get() = serviceRepository.serviceAction
 | 
			
		||||
 | 
			
		||||
    suspend fun onServiceAction(action: ServiceAction) = coroutineScope { serviceRepository.onServiceAction(action) }
 | 
			
		||||
 | 
			
		||||
    val tracerouteResponse: StateFlow<String?>
 | 
			
		||||
        get() = serviceRepository.tracerouteResponse
 | 
			
		||||
 | 
			
		||||
    fun setTracerouteResponse(value: String?) {
 | 
			
		||||
        serviceRepository.setTracerouteResponse(value)
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    fun clearTracerouteResponse() {
 | 
			
		||||
        setTracerouteResponse(null)
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -19,6 +19,7 @@ package com.geeksville.mesh.repository.network
 | 
			
		|||
 | 
			
		||||
import com.geeksville.mesh.MeshProtos.MqttClientProxyMessage
 | 
			
		||||
import com.geeksville.mesh.android.Logging
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.model.subscribeList
 | 
			
		||||
import com.geeksville.mesh.mqttClientProxyMessage
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
| 
						 | 
				
			
			@ -44,7 +45,12 @@ import javax.net.ssl.SSLContext
 | 
			
		|||
import javax.net.ssl.TrustManager
 | 
			
		||||
 | 
			
		||||
@Singleton
 | 
			
		||||
class MQTTRepository @Inject constructor(private val radioConfigRepository: RadioConfigRepository) : Logging {
 | 
			
		||||
class MQTTRepository
 | 
			
		||||
@Inject
 | 
			
		||||
constructor(
 | 
			
		||||
    private val radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    private val nodeRepository: NodeRepository,
 | 
			
		||||
) : Logging {
 | 
			
		||||
 | 
			
		||||
    companion object {
 | 
			
		||||
        /**
 | 
			
		||||
| 
						 | 
				
			
			@ -73,7 +79,7 @@ class MQTTRepository @Inject constructor(private val radioConfigRepository: Radi
 | 
			
		|||
    }
 | 
			
		||||
 | 
			
		||||
    val proxyMessageFlow: Flow<MqttClientProxyMessage> = callbackFlow {
 | 
			
		||||
        val ownerId = "MeshtasticAndroidMqttProxy-${radioConfigRepository.myId.value ?: generateClientId()}"
 | 
			
		||||
        val ownerId = "MeshtasticAndroidMqttProxy-${nodeRepository.myId.value ?: generateClientId()}"
 | 
			
		||||
        val channelSet = radioConfigRepository.channelSetFlow.first()
 | 
			
		||||
        val mqttConfig = radioConfigRepository.moduleConfigFlow.first().mqtt
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -55,6 +55,7 @@ import com.geeksville.mesh.android.hasLocationPermission
 | 
			
		|||
import com.geeksville.mesh.concurrent.handledLaunch
 | 
			
		||||
import com.geeksville.mesh.copy
 | 
			
		||||
import com.geeksville.mesh.database.MeshLogRepository
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.database.PacketRepository
 | 
			
		||||
import com.geeksville.mesh.fromRadio
 | 
			
		||||
import com.geeksville.mesh.model.NO_DEVICE_SELECTED
 | 
			
		||||
| 
						 | 
				
			
			@ -80,11 +81,13 @@ import kotlinx.coroutines.flow.MutableStateFlow
 | 
			
		|||
import kotlinx.coroutines.flow.StateFlow
 | 
			
		||||
import kotlinx.coroutines.flow.asStateFlow
 | 
			
		||||
import kotlinx.coroutines.flow.catch
 | 
			
		||||
import kotlinx.coroutines.flow.first
 | 
			
		||||
import kotlinx.coroutines.flow.flatMapLatest
 | 
			
		||||
import kotlinx.coroutines.flow.flowOf
 | 
			
		||||
import kotlinx.coroutines.flow.launchIn
 | 
			
		||||
import kotlinx.coroutines.flow.onEach
 | 
			
		||||
import org.meshtastic.core.database.entity.MeshLog
 | 
			
		||||
import org.meshtastic.core.database.entity.MetadataEntity
 | 
			
		||||
import org.meshtastic.core.database.entity.MyNodeEntity
 | 
			
		||||
import org.meshtastic.core.database.entity.NodeEntity
 | 
			
		||||
import org.meshtastic.core.database.entity.Packet
 | 
			
		||||
| 
						 | 
				
			
			@ -144,6 +147,10 @@ class MeshService :
 | 
			
		|||
 | 
			
		||||
    @Inject lateinit var radioConfigRepository: RadioConfigRepository
 | 
			
		||||
 | 
			
		||||
    @Inject lateinit var serviceRepository: ServiceRepository
 | 
			
		||||
 | 
			
		||||
    @Inject lateinit var nodeRepository: NodeRepository
 | 
			
		||||
 | 
			
		||||
    @Inject lateinit var mqttRepository: MQTTRepository
 | 
			
		||||
 | 
			
		||||
    @Inject lateinit var serviceNotifications: MeshServiceNotifications
 | 
			
		||||
| 
						 | 
				
			
			@ -215,7 +222,7 @@ class MeshService :
 | 
			
		|||
    private val clientPackages = mutableMapOf<String, String>()
 | 
			
		||||
    private val serviceBroadcasts =
 | 
			
		||||
        MeshServiceBroadcasts(this, clientPackages) {
 | 
			
		||||
            connectionState.also { radioConfigRepository.setConnectionState(it) }
 | 
			
		||||
            connectionState.also { serviceRepository.setConnectionState(it) }
 | 
			
		||||
        }
 | 
			
		||||
    private val packetHandler: PacketHandler by lazy {
 | 
			
		||||
        PacketHandler(
 | 
			
		||||
| 
						 | 
				
			
			@ -338,8 +345,8 @@ class MeshService :
 | 
			
		|||
        radioConfigRepository.localConfigFlow.onEach { localConfig = it }.launchIn(serviceScope)
 | 
			
		||||
        radioConfigRepository.moduleConfigFlow.onEach { moduleConfig = it }.launchIn(serviceScope)
 | 
			
		||||
        radioConfigRepository.channelSetFlow.onEach { channelSet = it }.launchIn(serviceScope)
 | 
			
		||||
        radioConfigRepository.serviceAction.onEach(::onServiceAction).launchIn(serviceScope)
 | 
			
		||||
        radioConfigRepository.myNodeInfo
 | 
			
		||||
        serviceRepository.serviceAction.onEach(::onServiceAction).launchIn(serviceScope)
 | 
			
		||||
        nodeRepository.myNodeInfo
 | 
			
		||||
            .flatMapLatest { myNodeEntity ->
 | 
			
		||||
                // When myNodeInfo changes, set up emissions for the "provide-location-nodeNum" pref.
 | 
			
		||||
                if (myNodeEntity == null) {
 | 
			
		||||
| 
						 | 
				
			
			@ -443,8 +450,8 @@ class MeshService :
 | 
			
		|||
 | 
			
		||||
    private fun loadSettings() = serviceScope.handledLaunch {
 | 
			
		||||
        discardNodeDB() // Get rid of any old state
 | 
			
		||||
        myNodeInfo = radioConfigRepository.myNodeInfo.value
 | 
			
		||||
        nodeDBbyNodeNum.putAll(radioConfigRepository.getNodeDBbyNum())
 | 
			
		||||
        myNodeInfo = nodeRepository.myNodeInfo.value
 | 
			
		||||
        nodeDBbyNodeNum.putAll(nodeRepository.getNodeDBbyNum().first())
 | 
			
		||||
        // Note: we do not haveNodeDB = true because that means we've got a valid db from a real
 | 
			
		||||
        // device (rather than
 | 
			
		||||
        // this possibly stale hint)
 | 
			
		||||
| 
						 | 
				
			
			@ -543,7 +550,7 @@ class MeshService :
 | 
			
		|||
            }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private fun getUserName(num: Int): String = with(radioConfigRepository.getUser(num)) { "$longName ($shortName)" }
 | 
			
		||||
    private fun getUserName(num: Int): String = with(nodeRepository.getUser(num)) { "$longName ($shortName)" }
 | 
			
		||||
 | 
			
		||||
    private val numNodes
 | 
			
		||||
        get() = nodeDBbyNodeNum.size
 | 
			
		||||
| 
						 | 
				
			
			@ -569,7 +576,7 @@ class MeshService :
 | 
			
		|||
        updateFn(info)
 | 
			
		||||
 | 
			
		||||
        if (info.user.id.isNotEmpty() && haveNodeDB) {
 | 
			
		||||
            serviceScope.handledLaunch { radioConfigRepository.upsert(info) }
 | 
			
		||||
            serviceScope.handledLaunch { nodeRepository.upsert(info) }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (withBroadcast) {
 | 
			
		||||
| 
						 | 
				
			
			@ -834,7 +841,7 @@ class MeshService :
 | 
			
		|||
                        val u = MeshProtos.Routing.parseFrom(data.payload)
 | 
			
		||||
 | 
			
		||||
                        if (u.errorReason == MeshProtos.Routing.Error.DUTY_CYCLE_LIMIT) {
 | 
			
		||||
                            radioConfigRepository.setErrorMessage(getString(R.string.error_duty_cycle))
 | 
			
		||||
                            serviceRepository.setErrorMessage(getString(R.string.error_duty_cycle))
 | 
			
		||||
                        }
 | 
			
		||||
 | 
			
		||||
                        handleAckNak(data.requestId, fromId, u.errorReasonValue)
 | 
			
		||||
| 
						 | 
				
			
			@ -884,7 +891,7 @@ class MeshService :
 | 
			
		|||
                                } else {
 | 
			
		||||
                                    full
 | 
			
		||||
                                }
 | 
			
		||||
                            radioConfigRepository.setTracerouteResponse(response)
 | 
			
		||||
                            serviceRepository.setTracerouteResponse(response)
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -934,7 +941,7 @@ class MeshService :
 | 
			
		|||
            AdminProtos.AdminMessage.PayloadVariantCase.GET_DEVICE_METADATA_RESPONSE -> {
 | 
			
		||||
                debug("Admin: received DeviceMetadata from $fromNodeNum")
 | 
			
		||||
                serviceScope.handledLaunch {
 | 
			
		||||
                    radioConfigRepository.insertMetadata(fromNodeNum, a.getDeviceMetadataResponse)
 | 
			
		||||
                    nodeRepository.insertMetadata(MetadataEntity(fromNodeNum, a.getDeviceMetadataResponse))
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -1188,7 +1195,7 @@ class MeshService :
 | 
			
		|||
                )
 | 
			
		||||
            insertMeshLog(packetToSave)
 | 
			
		||||
 | 
			
		||||
            serviceScope.handledLaunch { radioConfigRepository.emitMeshPacket(packet) }
 | 
			
		||||
            serviceScope.handledLaunch { serviceRepository.emitMeshPacket(packet) }
 | 
			
		||||
 | 
			
		||||
            // Update last seen for the node that sent the packet, but also for _our node_ because
 | 
			
		||||
            // anytime a packet
 | 
			
		||||
| 
						 | 
				
			
			@ -1488,7 +1495,7 @@ class MeshService :
 | 
			
		|||
        insertMeshLog(packetToSave)
 | 
			
		||||
        setLocalConfig(config)
 | 
			
		||||
        val configCount = localConfig.allFields.size
 | 
			
		||||
        radioConfigRepository.setStatusMessage("Device config ($configCount / $configTotal)")
 | 
			
		||||
        serviceRepository.setStatusMessage("Device config ($configCount / $configTotal)")
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private fun handleModuleConfig(config: ModuleConfigProtos.ModuleConfig) {
 | 
			
		||||
| 
						 | 
				
			
			@ -1504,7 +1511,7 @@ class MeshService :
 | 
			
		|||
        insertMeshLog(packetToSave)
 | 
			
		||||
        setLocalModuleConfig(config)
 | 
			
		||||
        val moduleCount = moduleConfig.allFields.size
 | 
			
		||||
        radioConfigRepository.setStatusMessage("Module config ($moduleCount / $moduleTotal)")
 | 
			
		||||
        serviceRepository.setStatusMessage("Module config ($moduleCount / $moduleTotal)")
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private fun handleChannel(ch: ChannelProtos.Channel) {
 | 
			
		||||
| 
						 | 
				
			
			@ -1520,7 +1527,7 @@ class MeshService :
 | 
			
		|||
        insertMeshLog(packetToSave)
 | 
			
		||||
        if (ch.role != ChannelProtos.Channel.Role.DISABLED) updateChannelSettings(ch)
 | 
			
		||||
        val maxChannels = myNodeInfo?.maxChannels ?: 8
 | 
			
		||||
        radioConfigRepository.setStatusMessage("Channels (${ch.index + 1} / $maxChannels)")
 | 
			
		||||
        serviceRepository.setStatusMessage("Channels (${ch.index + 1} / $maxChannels)")
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /** Convert a protobuf NodeInfo into our model objects and update our node DB */
 | 
			
		||||
| 
						 | 
				
			
			@ -1584,7 +1591,7 @@ class MeshService :
 | 
			
		|||
        insertMeshLog(packetToSave)
 | 
			
		||||
 | 
			
		||||
        newNodes.add(info)
 | 
			
		||||
        radioConfigRepository.setStatusMessage("Nodes (${newNodes.size})")
 | 
			
		||||
        serviceRepository.setStatusMessage("Nodes (${newNodes.size})")
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private var rawMyNodeInfo: MeshProtos.MyNodeInfo? = null
 | 
			
		||||
| 
						 | 
				
			
			@ -1619,7 +1626,7 @@ class MeshService :
 | 
			
		|||
                        deviceId = deviceId.toStringUtf8(),
 | 
			
		||||
                    )
 | 
			
		||||
                }
 | 
			
		||||
            serviceScope.handledLaunch { radioConfigRepository.insertMetadata(mi.myNodeNum, metadata) }
 | 
			
		||||
            serviceScope.handledLaunch { nodeRepository.insertMetadata(MetadataEntity(mi.myNodeNum, metadata)) }
 | 
			
		||||
            newMyNodeInfo = mi
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
| 
						 | 
				
			
			@ -1693,7 +1700,7 @@ class MeshService :
 | 
			
		|||
 | 
			
		||||
    private fun handleClientNotification(notification: MeshProtos.ClientNotification) {
 | 
			
		||||
        debug("Received clientNotification ${notification.toOneLineString()}")
 | 
			
		||||
        radioConfigRepository.setClientNotification(notification)
 | 
			
		||||
        serviceRepository.setClientNotification(notification)
 | 
			
		||||
        serviceNotifications.showClientNotification(notification)
 | 
			
		||||
        // if the future for the originating request is still in the queue, complete as unsuccessful
 | 
			
		||||
        // for now
 | 
			
		||||
| 
						 | 
				
			
			@ -1774,7 +1781,7 @@ class MeshService :
 | 
			
		|||
                    .onEach { message ->
 | 
			
		||||
                        packetHandler.sendToRadio(ToRadio.newBuilder().apply { mqttClientProxyMessage = message })
 | 
			
		||||
                    }
 | 
			
		||||
                    .catch { throwable -> radioConfigRepository.setErrorMessage("MqttClientProxy failed: $throwable") }
 | 
			
		||||
                    .catch { throwable -> serviceRepository.setErrorMessage("MqttClientProxy failed: $throwable") }
 | 
			
		||||
                    .launchIn(serviceScope)
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
| 
						 | 
				
			
			@ -1857,8 +1864,8 @@ class MeshService :
 | 
			
		|||
            newNodes.clear() // Just to save RAM ;-)
 | 
			
		||||
 | 
			
		||||
            serviceScope.handledLaunch {
 | 
			
		||||
                radioConfigRepository.installMyNodeInfo(myNodeInfo!!)
 | 
			
		||||
                radioConfigRepository.installNodeDb(nodeDBbyNodeNum.values.toList())
 | 
			
		||||
                nodeRepository.installMyNodeInfo(myNodeInfo!!)
 | 
			
		||||
                nodeRepository.installNodeDb(nodeDBbyNodeNum.values.toList())
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            haveNodeDB = true // we now have nodes from real hardware
 | 
			
		||||
| 
						 | 
				
			
			@ -2058,7 +2065,7 @@ class MeshService :
 | 
			
		|||
 | 
			
		||||
    fun clearDatabases() = serviceScope.handledLaunch {
 | 
			
		||||
        debug("Clearing nodeDB")
 | 
			
		||||
        radioConfigRepository.clearNodeDB()
 | 
			
		||||
        nodeRepository.clearNodeDB()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private fun updateLastAddress(deviceAddr: String?) {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -23,6 +23,7 @@ import com.geeksville.mesh.LocalOnlyProtos.LocalConfig
 | 
			
		|||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.repository.bluetooth.BluetoothRepository
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
import kotlinx.coroutines.flow.MutableStateFlow
 | 
			
		||||
import kotlinx.coroutines.flow.SharingStarted
 | 
			
		||||
| 
						 | 
				
			
			@ -39,6 +40,7 @@ class ConnectionsViewModel
 | 
			
		|||
@Inject
 | 
			
		||||
constructor(
 | 
			
		||||
    radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    serviceRepository: ServiceRepository,
 | 
			
		||||
    nodeRepository: NodeRepository,
 | 
			
		||||
    bluetoothRepository: BluetoothRepository,
 | 
			
		||||
    private val uiPrefs: UiPrefs,
 | 
			
		||||
| 
						 | 
				
			
			@ -50,7 +52,7 @@ constructor(
 | 
			
		|||
            LocalConfig.getDefaultInstance(),
 | 
			
		||||
        )
 | 
			
		||||
 | 
			
		||||
    val connectionState = radioConfigRepository.connectionState
 | 
			
		||||
    val connectionState = serviceRepository.connectionState
 | 
			
		||||
 | 
			
		||||
    val myNodeInfo: StateFlow<MyNodeEntity?> = nodeRepository.myNodeInfo
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -21,7 +21,7 @@ import androidx.lifecycle.ViewModel
 | 
			
		|||
import androidx.lifecycle.viewModelScope
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.database.PacketRepository
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import kotlinx.coroutines.flow.MutableStateFlow
 | 
			
		||||
import kotlinx.coroutines.flow.SharingStarted
 | 
			
		||||
import kotlinx.coroutines.flow.StateFlow
 | 
			
		||||
| 
						 | 
				
			
			@ -38,7 +38,7 @@ abstract class BaseMapViewModel(
 | 
			
		|||
    protected val mapPrefs: MapPrefs,
 | 
			
		||||
    nodeRepository: NodeRepository,
 | 
			
		||||
    packetRepository: PacketRepository,
 | 
			
		||||
    radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    serviceRepository: ServiceRepository,
 | 
			
		||||
) : ViewModel() {
 | 
			
		||||
 | 
			
		||||
    val nodes: StateFlow<List<Node>> =
 | 
			
		||||
| 
						 | 
				
			
			@ -72,7 +72,7 @@ abstract class BaseMapViewModel(
 | 
			
		|||
    val ourNodeInfo: StateFlow<Node?> = nodeRepository.ourNodeInfo
 | 
			
		||||
 | 
			
		||||
    val isConnected =
 | 
			
		||||
        radioConfigRepository.connectionState
 | 
			
		||||
        serviceRepository.connectionState
 | 
			
		||||
            .map { it.isConnected() }
 | 
			
		||||
            .stateIn(viewModelScope, SharingStarted.WhileSubscribed(5_000), false)
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -29,6 +29,7 @@ import com.geeksville.mesh.android.Logging
 | 
			
		|||
import com.geeksville.mesh.database.MeshLogRepository
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
import kotlinx.coroutines.Dispatchers
 | 
			
		||||
import kotlinx.coroutines.flow.MutableStateFlow
 | 
			
		||||
| 
						 | 
				
			
			@ -57,12 +58,14 @@ import java.util.Locale
 | 
			
		|||
import javax.inject.Inject
 | 
			
		||||
import kotlin.math.roundToInt
 | 
			
		||||
 | 
			
		||||
@Suppress("LongParameterList")
 | 
			
		||||
@HiltViewModel
 | 
			
		||||
class SettingsViewModel
 | 
			
		||||
@Inject
 | 
			
		||||
constructor(
 | 
			
		||||
    private val app: Application,
 | 
			
		||||
    private val radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    private val serviceRepository: ServiceRepository,
 | 
			
		||||
    private val nodeRepository: NodeRepository,
 | 
			
		||||
    private val meshLogRepository: MeshLogRepository,
 | 
			
		||||
    private val uiPrefs: UiPrefs,
 | 
			
		||||
| 
						 | 
				
			
			@ -77,7 +80,7 @@ constructor(
 | 
			
		|||
    val ourNodeInfo: StateFlow<Node?> = nodeRepository.ourNodeInfo
 | 
			
		||||
 | 
			
		||||
    val isConnected =
 | 
			
		||||
        radioConfigRepository.connectionState
 | 
			
		||||
        serviceRepository.connectionState
 | 
			
		||||
            .map { it.isConnected() }
 | 
			
		||||
            .stateIn(viewModelScope, SharingStarted.WhileSubscribed(5_000L), false)
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -89,7 +92,7 @@ constructor(
 | 
			
		|||
        )
 | 
			
		||||
 | 
			
		||||
    val meshService: IMeshService?
 | 
			
		||||
        get() = radioConfigRepository.meshService
 | 
			
		||||
        get() = serviceRepository.meshService
 | 
			
		||||
 | 
			
		||||
    val provideLocation: StateFlow<Boolean> =
 | 
			
		||||
        myNodeInfo
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -20,7 +20,7 @@ package com.geeksville.mesh.ui.settings.radio
 | 
			
		|||
import androidx.lifecycle.ViewModel
 | 
			
		||||
import androidx.lifecycle.viewModelScope
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
import kotlinx.coroutines.flow.MutableStateFlow
 | 
			
		||||
import kotlinx.coroutines.flow.asStateFlow
 | 
			
		||||
| 
						 | 
				
			
			@ -41,7 +41,7 @@ class CleanNodeDatabaseViewModel
 | 
			
		|||
@Inject
 | 
			
		||||
constructor(
 | 
			
		||||
    private val nodeRepository: NodeRepository,
 | 
			
		||||
    private val radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    private val serviceRepository: ServiceRepository,
 | 
			
		||||
) : ViewModel() {
 | 
			
		||||
    private val _olderThanDays = MutableStateFlow(30f)
 | 
			
		||||
    val olderThanDays = _olderThanDays.asStateFlow()
 | 
			
		||||
| 
						 | 
				
			
			@ -110,7 +110,7 @@ constructor(
 | 
			
		|||
            if (nodeNums.isNotEmpty()) {
 | 
			
		||||
                nodeRepository.deleteNodes(nodeNums)
 | 
			
		||||
 | 
			
		||||
                val service = radioConfigRepository.meshService
 | 
			
		||||
                val service = serviceRepository.meshService
 | 
			
		||||
                if (service != null) {
 | 
			
		||||
                    for (nodeNum in nodeNums) {
 | 
			
		||||
                        service.removeByNodenum(service.packetId, nodeNum)
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -45,6 +45,7 @@ import com.geeksville.mesh.android.GeeksvilleApplication
 | 
			
		|||
import com.geeksville.mesh.android.Logging
 | 
			
		||||
import com.geeksville.mesh.android.isAnalyticsAvailable
 | 
			
		||||
import com.geeksville.mesh.config
 | 
			
		||||
import com.geeksville.mesh.database.NodeRepository
 | 
			
		||||
import com.geeksville.mesh.deviceProfile
 | 
			
		||||
import com.geeksville.mesh.model.getChannelList
 | 
			
		||||
import com.geeksville.mesh.model.toChannelSet
 | 
			
		||||
| 
						 | 
				
			
			@ -54,6 +55,7 @@ import com.geeksville.mesh.navigation.ModuleRoute
 | 
			
		|||
import com.geeksville.mesh.repository.datastore.RadioConfigRepository
 | 
			
		||||
import com.geeksville.mesh.repository.location.LocationRepository
 | 
			
		||||
import com.geeksville.mesh.service.ConnectionState
 | 
			
		||||
import com.geeksville.mesh.service.ServiceRepository
 | 
			
		||||
import com.geeksville.mesh.util.UiText
 | 
			
		||||
import com.google.protobuf.MessageLite
 | 
			
		||||
import dagger.hilt.android.lifecycle.HiltViewModel
 | 
			
		||||
| 
						 | 
				
			
			@ -98,6 +100,7 @@ data class RadioConfigState(
 | 
			
		|||
    val analyticsEnabled: Boolean = false,
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
@Suppress("LongParameterList")
 | 
			
		||||
@HiltViewModel
 | 
			
		||||
class RadioConfigViewModel
 | 
			
		||||
@Inject
 | 
			
		||||
| 
						 | 
				
			
			@ -105,13 +108,15 @@ constructor(
 | 
			
		|||
    savedStateHandle: SavedStateHandle,
 | 
			
		||||
    private val app: Application,
 | 
			
		||||
    private val radioConfigRepository: RadioConfigRepository,
 | 
			
		||||
    private val serviceRepository: ServiceRepository,
 | 
			
		||||
    private val nodeRepository: NodeRepository,
 | 
			
		||||
    private val locationRepository: LocationRepository,
 | 
			
		||||
    private val mapConsentPrefs: MapConsentPrefs,
 | 
			
		||||
    private val analyticsPrefs: AnalyticsPrefs,
 | 
			
		||||
) : ViewModel(),
 | 
			
		||||
    Logging {
 | 
			
		||||
    private val meshService: IMeshService?
 | 
			
		||||
        get() = radioConfigRepository.meshService
 | 
			
		||||
        get() = serviceRepository.meshService
 | 
			
		||||
 | 
			
		||||
    private val destNum = savedStateHandle.toRoute<SettingsRoutes.Settings>().destNum
 | 
			
		||||
    private val _destNode = MutableStateFlow<Node?>(null)
 | 
			
		||||
| 
						 | 
				
			
			@ -137,7 +142,7 @@ constructor(
 | 
			
		|||
    }
 | 
			
		||||
 | 
			
		||||
    init {
 | 
			
		||||
        radioConfigRepository.nodeDBbyNum
 | 
			
		||||
        nodeRepository.nodeDBbyNum
 | 
			
		||||
            .mapLatest { nodes -> nodes[destNum] ?: nodes.values.firstOrNull() }
 | 
			
		||||
            .distinctUntilChanged()
 | 
			
		||||
            .onEach {
 | 
			
		||||
| 
						 | 
				
			
			@ -148,9 +153,9 @@ constructor(
 | 
			
		|||
 | 
			
		||||
        radioConfigRepository.deviceProfileFlow.onEach { _currentDeviceProfile.value = it }.launchIn(viewModelScope)
 | 
			
		||||
 | 
			
		||||
        radioConfigRepository.meshPacketFlow.onEach(::processPacketResponse).launchIn(viewModelScope)
 | 
			
		||||
        serviceRepository.meshPacketFlow.onEach(::processPacketResponse).launchIn(viewModelScope)
 | 
			
		||||
 | 
			
		||||
        combine(radioConfigRepository.connectionState, radioConfigState) { connState, configState ->
 | 
			
		||||
        combine(serviceRepository.connectionState, radioConfigState) { connState, configState ->
 | 
			
		||||
            _radioConfigState.update { it.copy(connected = connState == ConnectionState.CONNECTED) }
 | 
			
		||||
            if (connState == ConnectionState.DISCONNECTED && configState.responseState.isWaiting()) {
 | 
			
		||||
                sendError(R.string.disconnected)
 | 
			
		||||
| 
						 | 
				
			
			@ -158,7 +163,7 @@ constructor(
 | 
			
		|||
        }
 | 
			
		||||
            .launchIn(viewModelScope)
 | 
			
		||||
 | 
			
		||||
        radioConfigRepository.myNodeInfo
 | 
			
		||||
        nodeRepository.myNodeInfo
 | 
			
		||||
            .onEach { ni ->
 | 
			
		||||
                _radioConfigState.update { it.copy(isLocal = destNum == null || destNum == ni?.myNodeNum) }
 | 
			
		||||
            }
 | 
			
		||||
| 
						 | 
				
			
			@ -170,7 +175,7 @@ constructor(
 | 
			
		|||
    }
 | 
			
		||||
 | 
			
		||||
    private val myNodeInfo: StateFlow<MyNodeEntity?>
 | 
			
		||||
        get() = radioConfigRepository.myNodeInfo
 | 
			
		||||
        get() = nodeRepository.myNodeInfo
 | 
			
		||||
 | 
			
		||||
    val myNodeNum
 | 
			
		||||
        get() = myNodeInfo.value?.myNodeNum
 | 
			
		||||
| 
						 | 
				
			
			@ -342,7 +347,7 @@ constructor(
 | 
			
		|||
            "Request factory reset error",
 | 
			
		||||
        )
 | 
			
		||||
        if (destNum == myNodeNum) {
 | 
			
		||||
            viewModelScope.launch { radioConfigRepository.clearNodeDB() }
 | 
			
		||||
            viewModelScope.launch { nodeRepository.clearNodeDB() }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -353,7 +358,7 @@ constructor(
 | 
			
		|||
            "Request NodeDB reset error",
 | 
			
		||||
        )
 | 
			
		||||
        if (destNum == myNodeNum) {
 | 
			
		||||
            viewModelScope.launch { radioConfigRepository.clearNodeDB() }
 | 
			
		||||
            viewModelScope.launch { nodeRepository.clearNodeDB() }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Ładowanie…
	
		Reference in New Issue