NSCv1,v3: improve sync

This commit is contained in:
Milos Kozak 2023-08-09 22:40:29 +02:00
parent 911c446190
commit fb94393c1c
21 changed files with 969 additions and 957 deletions

View file

@ -0,0 +1,3 @@
package info.nightscout.rx.events
class EventDeviceStatusChange : Event()

View file

@ -21,22 +21,23 @@ interface DataSyncSelector {
val value: Any
val id: Long
var confirmed: Boolean
}
data class PairTemporaryTarget(override val value: TemporaryTarget, override val id: Long) : DataPair
data class PairGlucoseValue(override val value: GlucoseValue, override val id: Long) : DataPair
data class PairTherapyEvent(override val value: TherapyEvent, override val id: Long) : DataPair
data class PairFood(override val value: Food, override val id: Long) : DataPair
data class PairBolus(override val value: Bolus, override val id: Long) : DataPair
data class PairCarbs(override val value: Carbs, override val id: Long) : DataPair
data class PairBolusCalculatorResult(override val value: BolusCalculatorResult, override val id: Long) : DataPair
data class PairTemporaryBasal(override val value: TemporaryBasal, override val id: Long) : DataPair
data class PairExtendedBolus(override val value: ExtendedBolus, override val id: Long) : DataPair
data class PairProfileSwitch(override val value: ProfileSwitch, override val id: Long) : DataPair
data class PairEffectiveProfileSwitch(override val value: EffectiveProfileSwitch, override val id: Long) : DataPair
data class PairOfflineEvent(override val value: OfflineEvent, override val id: Long) : DataPair
data class PairProfileStore(override val value: JSONObject, override val id: Long) : DataPair
data class PairDeviceStatus(override val value: DeviceStatus, override val id: Long) : DataPair
data class PairTemporaryTarget(override val value: TemporaryTarget, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairGlucoseValue(override val value: GlucoseValue, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairTherapyEvent(override val value: TherapyEvent, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairFood(override val value: Food, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairBolus(override val value: Bolus, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairCarbs(override val value: Carbs, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairBolusCalculatorResult(override val value: BolusCalculatorResult, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairTemporaryBasal(override val value: TemporaryBasal, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairExtendedBolus(override val value: ExtendedBolus, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairProfileSwitch(override val value: ProfileSwitch, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairEffectiveProfileSwitch(override val value: EffectiveProfileSwitch, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairOfflineEvent(override val value: OfflineEvent, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairProfileStore(override val value: JSONObject, override val id: Long, override var confirmed: Boolean = false) : DataPair
data class PairDeviceStatus(override val value: DeviceStatus, override val id: Long, override var confirmed: Boolean = false) : DataPair
fun queueSize(): Long

View file

@ -1,46 +0,0 @@
package info.nightscout.interfaces.sync
interface DataSyncSelectorV1 : DataSyncSelector {
fun confirmLastBolusIdIfGreater(lastSynced: Long)
suspend fun processChangedBoluses()
fun confirmLastCarbsIdIfGreater(lastSynced: Long)
suspend fun processChangedCarbs()
fun confirmLastBolusCalculatorResultsIdIfGreater(lastSynced: Long)
suspend fun processChangedBolusCalculatorResults()
fun confirmLastTempTargetsIdIfGreater(lastSynced: Long)
suspend fun processChangedTempTargets()
fun confirmLastGlucoseValueIdIfGreater(lastSynced: Long)
suspend fun processChangedGlucoseValues()
fun confirmLastTherapyEventIdIfGreater(lastSynced: Long)
suspend fun processChangedTherapyEvents()
fun confirmLastFoodIdIfGreater(lastSynced: Long)
suspend fun processChangedFoods()
fun confirmLastDeviceStatusIdIfGreater(lastSynced: Long)
suspend fun processChangedDeviceStatuses()
fun confirmLastTemporaryBasalIdIfGreater(lastSynced: Long)
suspend fun processChangedTemporaryBasals()
fun confirmLastExtendedBolusIdIfGreater(lastSynced: Long)
suspend fun processChangedExtendedBoluses()
fun confirmLastProfileSwitchIdIfGreater(lastSynced: Long)
suspend fun processChangedProfileSwitches()
fun confirmLastEffectiveProfileSwitchIdIfGreater(lastSynced: Long)
suspend fun processChangedEffectiveProfileSwitches()
fun confirmLastOfflineEventIdIfGreater(lastSynced: Long)
suspend fun processChangedOfflineEvents()
fun confirmLastProfileStore(lastSynced: Long)
suspend fun processChangedProfileStore()
}

View file

@ -1,3 +0,0 @@
package info.nightscout.interfaces.sync
interface DataSyncSelectorV3 : DataSyncSelector

View file

@ -5,6 +5,7 @@ import androidx.room.Entity
import androidx.room.Index
import androidx.room.PrimaryKey
import info.nightscout.database.entities.embedments.InterfaceIDs
import info.nightscout.database.entities.interfaces.DBEntry
import info.nightscout.database.entities.interfaces.DBEntryWithTime
import java.util.TimeZone
@ -17,7 +18,7 @@ import java.util.TimeZone
])
data class DeviceStatus(
@PrimaryKey(autoGenerate = true)
var id: Long = 0,
override var id: Long = 0,
@Embedded
var interfaceIDs_backing: InterfaceIDs? = null,
override var timestamp: Long,
@ -31,7 +32,7 @@ data class DeviceStatus(
var isCharging: Boolean?,
var configuration: String? = null
) : DBEntryWithTime {
) : DBEntry, DBEntryWithTime {
var interfaceIDs: InterfaceIDs
get() {

View file

@ -254,6 +254,7 @@ import kotlin.math.roundToInt
fun insert(word: UserEntry) {
database.userEntryDao.insert(word)
changeSubject.onNext(mutableListOf(word)) // Not TraceableDao
}
// PROFILE SWITCH
@ -712,8 +713,10 @@ import kotlin.math.roundToInt
database.bolusCalculatorResultDao.getLastId()
// DEVICE STATUS
fun insert(deviceStatus: DeviceStatus): Long =
fun insert(deviceStatus: DeviceStatus) {
database.deviceStatusDao.insert(deviceStatus)
changeSubject.onNext(mutableListOf(deviceStatus)) // Not TraceableDao
}
/*
* returns a Pair of the next entity to sync and the ID of the "update".
@ -727,10 +730,6 @@ import kotlin.math.roundToInt
database.deviceStatusDao.getNextModifiedOrNewAfter(id)
.subscribeOn(Schedulers.io())
fun getModifiedDeviceStatusDataFromId(lastId: Long): Single<List<DeviceStatus>> =
database.deviceStatusDao.getModifiedFrom(lastId)
.subscribeOn(Schedulers.io())
fun getLastDeviceStatusId(): Long? =
database.deviceStatusDao.getLastId()

View file

@ -3,6 +3,7 @@ package info.nightscout.implementation.db
import android.content.Context
import info.nightscout.database.entities.Bolus
import info.nightscout.database.entities.Carbs
import info.nightscout.database.entities.DeviceStatus
import info.nightscout.database.entities.EffectiveProfileSwitch
import info.nightscout.database.entities.ExtendedBolus
import info.nightscout.database.entities.Food
@ -15,6 +16,7 @@ import info.nightscout.database.entities.TherapyEvent
import info.nightscout.database.impl.AppRepository
import info.nightscout.interfaces.ui.UiInteraction
import info.nightscout.rx.bus.RxBus
import info.nightscout.rx.events.EventDeviceStatusChange
import info.nightscout.rx.events.EventEffectiveProfileSwitchChanged
import info.nightscout.rx.events.EventExtendedBolusChange
import info.nightscout.rx.events.EventFoodDatabaseChanged
@ -109,5 +111,9 @@ class CompatDBHelper @Inject constructor(
aapsLogger.debug(LTag.DATABASE, "Firing EventOfflineChange $oe")
rxBus.send(EventOfflineChange())
}
it.filterIsInstance<DeviceStatus>().firstOrNull()?.let { ds ->
aapsLogger.debug(LTag.DATABASE, "Firing EventDeviceStatusChange $ds")
rxBus.send(EventDeviceStatusChange())
}
}
}

View file

@ -11,12 +11,9 @@ import info.nightscout.interfaces.XDripBroadcast
import info.nightscout.interfaces.nsclient.NSSettingsStatus
import info.nightscout.interfaces.nsclient.ProcessedDeviceStatusData
import info.nightscout.interfaces.nsclient.StoreDataForDb
import info.nightscout.interfaces.sync.DataSyncSelectorV1
import info.nightscout.interfaces.sync.DataSyncSelectorV3
import info.nightscout.interfaces.sync.DataSyncSelectorXdrip
import info.nightscout.plugins.sync.nsShared.NSClientFragment
import info.nightscout.plugins.sync.nsShared.StoreDataForDbImpl
import info.nightscout.plugins.sync.nsclient.DataSyncSelectorV1Impl
import info.nightscout.plugins.sync.nsclient.data.NSSettingsStatusImpl
import info.nightscout.plugins.sync.nsclient.data.ProcessedDeviceStatusDataImpl
import info.nightscout.plugins.sync.nsclient.services.NSClientService
@ -24,8 +21,14 @@ import info.nightscout.plugins.sync.nsclient.workers.NSClientAddAckWorker
import info.nightscout.plugins.sync.nsclient.workers.NSClientAddUpdateWorker
import info.nightscout.plugins.sync.nsclient.workers.NSClientMbgWorker
import info.nightscout.plugins.sync.nsclient.workers.NSClientUpdateRemoveAckWorker
import info.nightscout.plugins.sync.nsclientV3.DataSyncSelectorV3Impl
import info.nightscout.plugins.sync.nsclientV3.workers.*
import info.nightscout.plugins.sync.nsclientV3.workers.DataSyncWorker
import info.nightscout.plugins.sync.nsclientV3.workers.LoadBgWorker
import info.nightscout.plugins.sync.nsclientV3.workers.LoadDeviceStatusWorker
import info.nightscout.plugins.sync.nsclientV3.workers.LoadFoodsWorker
import info.nightscout.plugins.sync.nsclientV3.workers.LoadLastModificationWorker
import info.nightscout.plugins.sync.nsclientV3.workers.LoadProfileStoreWorker
import info.nightscout.plugins.sync.nsclientV3.workers.LoadStatusWorker
import info.nightscout.plugins.sync.nsclientV3.workers.LoadTreatmentsWorker
import info.nightscout.plugins.sync.tidepool.TidepoolFragment
import info.nightscout.plugins.sync.xdrip.DataSyncSelectorXdripImpl
import info.nightscout.plugins.sync.xdrip.XdripFragment
@ -75,8 +78,6 @@ abstract class SyncModule {
@Binds fun bindProcessedDeviceStatusData(processedDeviceStatusDataImpl: ProcessedDeviceStatusDataImpl): ProcessedDeviceStatusData
@Binds fun bindNSSettingsStatus(nsSettingsStatusImpl: NSSettingsStatusImpl): NSSettingsStatus
@Binds fun bindDataSyncSelectorV1Interface(dataSyncSelectorV1Impl: DataSyncSelectorV1Impl): DataSyncSelectorV1
@Binds fun bindDataSyncSelectorV3Interface(dataSyncSelectorV3Impl: DataSyncSelectorV3Impl): DataSyncSelectorV3
@Binds fun bindDataSyncSelectorXdripInterface(dataSyncSelectorXdripImpl: DataSyncSelectorXdripImpl): DataSyncSelectorXdrip
@Binds fun bindStoreDataForDb(storeDataForDbImpl: StoreDataForDbImpl): StoreDataForDb
@Binds fun bindXDripBroadcastInterface(xDripBroadcastImpl: XdripPlugin): XDripBroadcast

View file

@ -123,7 +123,7 @@ class NSClientFragment : DaggerFragment(), MenuProvider, PluginFragment {
nsClientPlugin?.listLog?.let {
synchronized(it) {
it.clear()
_binding?.recyclerview?.swapAdapter(RecyclerViewAdapter(it), true)
updateLog()
}
}
true
@ -211,6 +211,7 @@ class NSClientFragment : DaggerFragment(), MenuProvider, PluginFragment {
.subscribe({ updateStatus() }, fabricPrivacy::logException)
updateStatus()
updateQueue()
updateLog()
}
@Synchronized
@ -231,6 +232,9 @@ class NSClientFragment : DaggerFragment(), MenuProvider, PluginFragment {
binding.status.text = nsClientPlugin?.status
}
private fun updateLog() {
_binding?.recyclerview?.swapAdapter(RecyclerViewAdapter(nsClientPlugin?.listLog ?: arrayListOf()), true)
}
private inner class RecyclerViewAdapter(private var logList: List<EventNSClientNewLog>) : RecyclerView.Adapter<RecyclerViewAdapter.NsClientLogViewHolder>() {
override fun onCreateViewHolder(viewGroup: ViewGroup, viewType: Int): NsClientLogViewHolder =

View file

@ -0,0 +1,807 @@
package info.nightscout.plugins.sync.nsclient
import info.nightscout.core.utils.waitMillis
import info.nightscout.database.impl.AppRepository
import info.nightscout.interfaces.plugin.ActivePlugin
import info.nightscout.interfaces.profile.ProfileFunction
import info.nightscout.interfaces.sync.DataSyncSelector
import info.nightscout.interfaces.utils.JsonHelper
import info.nightscout.plugins.sync.R
import info.nightscout.plugins.sync.nsShared.events.EventNSClientUpdateGuiQueue
import info.nightscout.plugins.sync.nsShared.events.EventNSClientUpdateGuiStatus
import info.nightscout.rx.bus.RxBus
import info.nightscout.rx.events.EventNSClientNewLog
import info.nightscout.rx.logging.AAPSLogger
import info.nightscout.rx.logging.LTag
import info.nightscout.shared.sharedPreferences.SP
import info.nightscout.shared.utils.DateUtil
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.SupervisorJob
import kotlinx.coroutines.async
import javax.inject.Inject
import javax.inject.Singleton
@Singleton
class DataSyncSelectorV1 @Inject constructor(
private val sp: SP,
private val aapsLogger: AAPSLogger,
private val dateUtil: DateUtil,
private val profileFunction: ProfileFunction,
private val activePlugin: ActivePlugin,
private val appRepository: AppRepository,
private val rxBus: RxBus
) : DataSyncSelector {
private var scope = CoroutineScope(Dispatchers.IO + SupervisorJob())
class QueueCounter(
var bolusesRemaining: Long = -1L,
var carbsRemaining: Long = -1L,
var bcrRemaining: Long = -1L,
var ttsRemaining: Long = -1L,
var foodsRemaining: Long = -1L,
var gvsRemaining: Long = -1L,
var tesRemaining: Long = -1L,
var dssRemaining: Long = -1L,
var tbrsRemaining: Long = -1L,
var ebsRemaining: Long = -1L,
var pssRemaining: Long = -1L,
var epssRemaining: Long = -1L,
var oesRemaining: Long = -1L
) {
fun size(): Long =
bolusesRemaining +
carbsRemaining +
bcrRemaining +
ttsRemaining +
foodsRemaining +
gvsRemaining +
tesRemaining +
dssRemaining +
tbrsRemaining +
ebsRemaining +
pssRemaining +
epssRemaining +
oesRemaining
}
private val queueCounter = QueueCounter()
private val isPaused get() = sp.getBoolean(R.string.key_ns_paused, false)
override fun queueSize(): Long = queueCounter.size()
private var running = false
private val sync = Any()
override suspend fun doUpload() {
synchronized(sync) {
if (running) {
rxBus.send(EventNSClientNewLog("● RUN", "Already running"))
return
}
running = true
}
rxBus.send(EventNSClientUpdateGuiStatus())
if (sp.getBoolean(R.string.key_ns_upload, true) && !isPaused) {
queueCounter.bolusesRemaining = (appRepository.getLastBolusId() ?: 0L) - sp.getLong(R.string.key_ns_bolus_last_synced_id, 0)
queueCounter.carbsRemaining = (appRepository.getLastCarbsId() ?: 0L) - sp.getLong(R.string.key_ns_carbs_last_synced_id, 0)
queueCounter.bcrRemaining = (appRepository.getLastBolusCalculatorResultId() ?: 0L) - sp.getLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)
queueCounter.ttsRemaining = (appRepository.getLastTempTargetId() ?: 0L) - sp.getLong(R.string.key_ns_temporary_target_last_synced_id, 0)
queueCounter.foodsRemaining = (appRepository.getLastFoodId() ?: 0L) - sp.getLong(R.string.key_ns_food_last_synced_id, 0)
queueCounter.gvsRemaining = (appRepository.getLastGlucoseValueId() ?: 0L) - sp.getLong(R.string.key_ns_glucose_value_last_synced_id, 0)
queueCounter.tesRemaining = (appRepository.getLastTherapyEventId() ?: 0L) - sp.getLong(R.string.key_ns_therapy_event_last_synced_id, 0)
queueCounter.dssRemaining = (appRepository.getLastDeviceStatusId() ?: 0L) - sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)
queueCounter.tbrsRemaining = (appRepository.getLastTemporaryBasalId() ?: 0L) - sp.getLong(R.string.key_ns_temporary_basal_last_synced_id, 0)
queueCounter.ebsRemaining = (appRepository.getLastExtendedBolusId() ?: 0L) - sp.getLong(R.string.key_ns_extended_bolus_last_synced_id, 0)
queueCounter.pssRemaining = (appRepository.getLastProfileSwitchId() ?: 0L) - sp.getLong(R.string.key_ns_profile_switch_last_synced_id, 0)
queueCounter.epssRemaining = (appRepository.getLastEffectiveProfileSwitchId() ?: 0L) - sp.getLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)
queueCounter.oesRemaining = (appRepository.getLastOfflineEventId() ?: 0L) - sp.getLong(R.string.key_ns_offline_event_last_synced_id, 0)
rxBus.send(EventNSClientUpdateGuiQueue())
val boluses = scope.async { processChangedBoluses() }
val carbs = scope.async { processChangedCarbs() }
val bcs = scope.async { processChangedBolusCalculatorResults() }
val tbs = scope.async { processChangedTemporaryBasals() }
val ebs = scope.async { processChangedExtendedBoluses() }
val pss = scope.async { processChangedProfileSwitches() }
val epss = scope.async { processChangedEffectiveProfileSwitches() }
val gvs = scope.async { processChangedGlucoseValues() }
val tts = scope.async { processChangedTempTargets() }
val foods = scope.async { processChangedFoods() }
val tes = scope.async { processChangedTherapyEvents() }
val dss = scope.async { processChangedDeviceStatuses() }
val oes = scope.async { processChangedOfflineEvents() }
val ps = scope.async { processChangedProfileStore() }
boluses.await()
carbs.await()
bcs.await()
tbs.await()
ebs.await()
pss.await()
epss.await()
gvs.await()
tts.await()
foods.await()
tes.await()
dss.await()
oes.await()
ps.await()
}
rxBus.send(EventNSClientUpdateGuiStatus())
running = false
}
override fun resetToNextFullSync() {
sp.remove(R.string.key_ns_glucose_value_last_synced_id)
sp.remove(R.string.key_ns_temporary_basal_last_synced_id)
sp.remove(R.string.key_ns_temporary_target_last_synced_id)
sp.remove(R.string.key_ns_extended_bolus_last_synced_id)
sp.remove(R.string.key_ns_food_last_synced_id)
sp.remove(R.string.key_ns_bolus_last_synced_id)
sp.remove(R.string.key_ns_carbs_last_synced_id)
sp.remove(R.string.key_ns_bolus_calculator_result_last_synced_id)
sp.remove(R.string.key_ns_therapy_event_last_synced_id)
sp.remove(R.string.key_ns_profile_switch_last_synced_id)
sp.remove(R.string.key_ns_effective_profile_switch_last_synced_id)
sp.remove(R.string.key_ns_offline_event_last_synced_id)
sp.remove(R.string.key_ns_profile_store_last_synced_timestamp)
val lastDeviceStatusDbId = appRepository.getLastDeviceStatusId()
if (lastDeviceStatusDbId != null) sp.putLong(R.string.key_ns_device_status_last_synced_id, lastDeviceStatusDbId)
else sp.remove(R.string.key_ns_device_status_last_synced_id)
}
private fun confirmLastBolusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_bolus_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Bolus data sync from $lastSynced")
sp.putLong(R.string.key_ns_bolus_last_synced_id, lastSynced)
}
}
private suspend fun processChangedBoluses() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastBolusId() ?: 0L
var startId = sp.getLong(R.string.key_ns_bolus_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_bolus_last_synced_id, 0)
startId = 0
}
queueCounter.bolusesRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementBolus(startId).blockingGet()?.let { bolus ->
aapsLogger.info(LTag.NSCLIENT, "Loading Bolus data Start: $startId ${bolus.first} forID: ${bolus.second.id} ")
val dataPair = DataSyncSelector.PairBolus(bolus.first, bolus.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
bolus.first.id == bolus.second.id && bolus.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring Bolus. Loaded from NS: ${bolus.second.id} ")
// only NsId changed, no need to upload
bolus.first.onlyNsIdAdded(bolus.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring Bolus. Only NS id changed: ${bolus.second.id} ")
// without nsId = create new
bolus.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, " $startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update if it's modified record
bolus.first.interfaceIDs.nightscoutId != null && bolus.first.id != bolus.second.id -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastBolusIdIfGreater(bolus.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastCarbsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_carbs_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Carbs data sync from $lastSynced")
sp.putLong(R.string.key_ns_carbs_last_synced_id, lastSynced)
}
}
private suspend fun processChangedCarbs() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastCarbsId() ?: 0L
var startId = sp.getLong(R.string.key_ns_carbs_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_carbs_last_synced_id, 0)
startId = 0
}
queueCounter.carbsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementCarbs(startId).blockingGet()?.let { carb ->
aapsLogger.info(LTag.NSCLIENT, "Loading Carbs data Start: $startId ${carb.first} forID: ${carb.second.id} ")
val dataPair = DataSyncSelector.PairCarbs(carb.first, carb.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
carb.first.id == carb.second.id && carb.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring Carbs. Loaded from NS: ${carb.second.id} ")
// only NsId changed, no need to upload
carb.first.onlyNsIdAdded(carb.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring Carbs. Only NS id changed ID: ${carb.second.id} ")
// without nsId = create new
carb.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update if it's modified record
carb.first.interfaceIDs.nightscoutId != null && carb.first.id != carb.second.id -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastCarbsIdIfGreater(carb.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastBolusCalculatorResultsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting BolusCalculatorResult data sync from $lastSynced")
sp.putLong(R.string.key_ns_bolus_calculator_result_last_synced_id, lastSynced)
}
}
private suspend fun processChangedBolusCalculatorResults() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastBolusCalculatorResultId() ?: 0L
var startId = sp.getLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)
startId = 0
}
queueCounter.bcrRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementBolusCalculatorResult(startId).blockingGet()?.let { bolusCalculatorResult ->
aapsLogger.info(LTag.NSCLIENT, "Loading BolusCalculatorResult data Start: $startId ${bolusCalculatorResult.first} forID: ${bolusCalculatorResult.second.id} ")
val dataPair = DataSyncSelector.PairBolusCalculatorResult(bolusCalculatorResult.first, bolusCalculatorResult.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
bolusCalculatorResult.first.id == bolusCalculatorResult.second.id && bolusCalculatorResult.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring BolusCalculatorResult. Loaded from NS: ${bolusCalculatorResult.second.id} ")
// only NsId changed, no need to upload
bolusCalculatorResult.first.onlyNsIdAdded(bolusCalculatorResult.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring BolusCalculatorResult. Only NS id changed ID: ${bolusCalculatorResult.second.id} ")
// without nsId = create new
bolusCalculatorResult.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update if it's modified record
bolusCalculatorResult.first.interfaceIDs.nightscoutId != null && bolusCalculatorResult.first.id != bolusCalculatorResult.second.id -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastBolusCalculatorResultsIdIfGreater(bolusCalculatorResult.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastTempTargetsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_temporary_target_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TemporaryTarget data sync from $lastSynced")
sp.putLong(R.string.key_ns_temporary_target_last_synced_id, lastSynced)
}
}
private suspend fun processChangedTempTargets() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastTempTargetId() ?: 0L
var startId = sp.getLong(R.string.key_ns_temporary_target_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_temporary_target_last_synced_id, 0)
startId = 0
}
queueCounter.ttsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementTemporaryTarget(startId).blockingGet()?.let { tt ->
aapsLogger.info(LTag.NSCLIENT, "Loading TemporaryTarget data Start: $startId ${tt.first} forID: ${tt.second.id} ")
val dataPair = DataSyncSelector.PairTemporaryTarget(tt.first, tt.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
tt.first.id == tt.second.id && tt.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryTarget. Loaded from NS: ${tt.second.id} ")
// only NsId changed, no need to upload
tt.first.onlyNsIdAdded(tt.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryTarget. Only NS id changed ID: ${tt.second.id} ")
// without nsId = create new
tt.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// existing with nsId = update
tt.first.interfaceIDs.nightscoutId != null -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastTempTargetsIdIfGreater(tt.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastFoodIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_food_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Food data sync from $lastSynced")
sp.putLong(R.string.key_ns_food_last_synced_id, lastSynced)
}
}
private suspend fun processChangedFoods() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastFoodId() ?: 0L
var startId = sp.getLong(R.string.key_ns_food_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_food_last_synced_id, 0)
startId = 0
}
queueCounter.foodsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementFood(startId).blockingGet()?.let { food ->
aapsLogger.info(LTag.NSCLIENT, "Loading Food data Start: $startId ${food.first} forID: ${food.second.id} ")
val dataPair = DataSyncSelector.PairFood(food.first, food.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
food.first.id == food.second.id && food.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring Food. Loaded from NS: ${food.second.id} ")
// only NsId changed, no need to upload
food.first.onlyNsIdAdded(food.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring Food. Only NS id changed ID: ${food.second.id} ")
// without nsId = create new
food.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("food", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update
food.first.interfaceIDs.nightscoutId != null -> {
activePlugin.activeNsClient?.nsUpdate("food", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastFoodIdIfGreater(food.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastGlucoseValueIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_glucose_value_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting GlucoseValue data sync from $lastSynced")
sp.putLong(R.string.key_ns_glucose_value_last_synced_id, lastSynced)
}
}
private suspend fun processChangedGlucoseValues() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastGlucoseValueId() ?: 0L
var startId = sp.getLong(R.string.key_ns_glucose_value_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_glucose_value_last_synced_id, 0)
startId = 0
}
queueCounter.gvsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementGlucoseValue(startId).blockingGet()?.let { gv ->
aapsLogger.info(LTag.NSCLIENT, "Loading GlucoseValue data Start: $startId ${gv.first} forID: ${gv.second.id} ")
val dataPair = DataSyncSelector.PairGlucoseValue(gv.first, gv.second.id)
if (activePlugin.activeBgSource.shouldUploadToNs(gv.first)) {
when {
// new record with existing NS id => must be coming from NS => ignore
gv.first.id == gv.second.id && gv.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring GlucoseValue. Loaded from NS: ${gv.second.id} ")
// only NsId changed, no need to upload
gv.first.onlyNsIdAdded(gv.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring GlucoseValue. Only NS id changed ID: ${gv.second.id} ")
// without nsId = create new
gv.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("entries", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update
else -> {// gv.first.interfaceIDs.nightscoutId != null
activePlugin.activeNsClient?.nsUpdate("entries", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
}
if (cont) confirmLastGlucoseValueIdIfGreater(gv.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastTherapyEventIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_therapy_event_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TherapyEvents data sync from $lastSynced")
sp.putLong(R.string.key_ns_therapy_event_last_synced_id, lastSynced)
}
}
private suspend fun processChangedTherapyEvents() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastTherapyEventId() ?: 0L
var startId = sp.getLong(R.string.key_ns_therapy_event_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_therapy_event_last_synced_id, 0)
startId = 0
}
queueCounter.tesRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementTherapyEvent(startId).blockingGet()?.let { te ->
aapsLogger.info(LTag.NSCLIENT, "Loading TherapyEvents data Start: $startId ${te.first} forID: ${te.second.id} ")
val dataPair = DataSyncSelector.PairTherapyEvent(te.first, te.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
te.first.id == te.second.id && te.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring TherapyEvent. Loaded from NS: ${te.second.id} ")
// only NsId changed, no need to upload
te.first.onlyNsIdAdded(te.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring TherapyEvent. Only NS id changed ID: ${te.second.id} ")
// without nsId = create new
te.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// nsId = update
te.first.interfaceIDs.nightscoutId != null -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastTherapyEventIdIfGreater(te.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastDeviceStatusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting DeviceStatus data sync from $lastSynced")
sp.putLong(R.string.key_ns_device_status_last_synced_id, lastSynced)
}
}
private suspend fun processChangedDeviceStatuses() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastDeviceStatusId() ?: 0L
var startId = sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_device_status_last_synced_id, 0)
startId = 0
}
queueCounter.dssRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementDeviceStatus(startId).blockingGet()?.let { deviceStatus ->
aapsLogger.info(LTag.NSCLIENT, "Loading DeviceStatus data Start: $startId $deviceStatus")
val dataPair = DataSyncSelector.PairDeviceStatus(deviceStatus, lastDbId)
activePlugin.activeNsClient?.nsAdd("devicestatus", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
if (cont) confirmLastDeviceStatusIdIfGreater(deviceStatus.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastTemporaryBasalIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_temporary_basal_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TemporaryBasal data sync from $lastSynced")
sp.putLong(R.string.key_ns_temporary_basal_last_synced_id, lastSynced)
}
}
private suspend fun processChangedTemporaryBasals() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastTemporaryBasalId() ?: 0L
var startId = sp.getLong(R.string.key_ns_temporary_basal_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_temporary_basal_last_synced_id, 0)
startId = 0
}
queueCounter.tbrsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementTemporaryBasal(startId).blockingGet()?.let { tb ->
aapsLogger.info(LTag.NSCLIENT, "Loading TemporaryBasal data Start: $startId ${tb.first} forID: ${tb.second.id} ")
val dataPair = DataSyncSelector.PairTemporaryBasal(tb.first, tb.second.id)
val profile = profileFunction.getProfile(tb.first.timestamp)
if (profile != null) {
when {
// new record with existing NS id => must be coming from NS => ignore
tb.first.id == tb.second.id && tb.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryBasal. Loaded from NS: ${tb.second.id} ")
// only NsId changed, no need to upload
tb.first.onlyNsIdAdded(tb.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryBasal. Only NS id changed ID: ${tb.second.id} ")
// without nsId = create new
tb.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId", profile)
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update
tb.first.interfaceIDs.nightscoutId != null -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId", profile)
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
} else aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryBasal. No profile: ${tb.second.id} ")
if (cont) confirmLastTemporaryBasalIdIfGreater(tb.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastExtendedBolusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_extended_bolus_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting ExtendedBolus data sync from $lastSynced")
sp.putLong(R.string.key_ns_extended_bolus_last_synced_id, lastSynced)
}
}
private suspend fun processChangedExtendedBoluses() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastExtendedBolusId() ?: 0L
var startId = sp.getLong(R.string.key_ns_extended_bolus_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_extended_bolus_last_synced_id, 0)
startId = 0
}
queueCounter.ebsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementExtendedBolus(startId).blockingGet()?.let { eb ->
aapsLogger.info(LTag.NSCLIENT, "Loading ExtendedBolus data Start: $startId ${eb.first} forID: ${eb.second.id} ")
val dataPair = DataSyncSelector.PairExtendedBolus(eb.first, eb.second.id)
val profile = profileFunction.getProfile(eb.first.timestamp)
if (profile != null) {
when {
// new record with existing NS id => must be coming from NS => ignore
eb.first.id == eb.second.id && eb.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring ExtendedBolus. Loaded from NS: ${eb.second.id} ")
// only NsId changed, no need to upload
eb.first.onlyNsIdAdded(eb.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring ExtendedBolus. Only NS id changed ID: ${eb.second.id} ")
// without nsId = create new
eb.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId", profile)
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update
eb.first.interfaceIDs.nightscoutId != null -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId", profile)
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
} else aapsLogger.info(LTag.NSCLIENT, "Ignoring ExtendedBolus. No profile: ${eb.second.id} ")
if (cont) confirmLastExtendedBolusIdIfGreater(eb.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastProfileSwitchIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_profile_switch_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting ProfileSwitch data sync from $lastSynced")
sp.putLong(R.string.key_ns_profile_switch_last_synced_id, lastSynced)
}
}
private suspend fun processChangedProfileSwitches() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastProfileSwitchId() ?: 0L
var startId = sp.getLong(R.string.key_ns_profile_switch_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_profile_switch_last_synced_id, 0)
startId = 0
}
queueCounter.pssRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementProfileSwitch(startId).blockingGet()?.let { ps ->
aapsLogger.info(LTag.NSCLIENT, "Loading ProfileSwitch data Start: $startId ${ps.first} forID: ${ps.second.id} ")
val dataPair = DataSyncSelector.PairProfileSwitch(ps.first, ps.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
ps.first.id == ps.second.id && ps.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring ProfileSwitch. Loaded from NS: ${ps.second.id} ")
// only NsId changed, no need to upload
ps.first.onlyNsIdAdded(ps.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring ProfileSwitch. Only NS id changed ID: ${ps.second.id} ")
// without nsId = create new
ps.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update
ps.first.interfaceIDs.nightscoutId != null -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastProfileSwitchIdIfGreater(ps.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastEffectiveProfileSwitchIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting EffectiveProfileSwitch data sync from $lastSynced")
sp.putLong(R.string.key_ns_effective_profile_switch_last_synced_id, lastSynced)
}
}
private suspend fun processChangedEffectiveProfileSwitches() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastEffectiveProfileSwitchId() ?: 0L
var startId = sp.getLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)
startId = 0
}
queueCounter.epssRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementEffectiveProfileSwitch(startId).blockingGet()?.let { ps ->
aapsLogger.info(LTag.NSCLIENT, "Loading EffectiveProfileSwitch data Start: $startId ${ps.first} forID: ${ps.second.id} ")
val dataPair = DataSyncSelector.PairEffectiveProfileSwitch(ps.first, ps.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
ps.first.id == ps.second.id && ps.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring EffectiveProfileSwitch. Loaded from NS: ${ps.second.id} ")
// only NsId changed, no need to upload
ps.first.onlyNsIdAdded(ps.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring EffectiveProfileSwitch. Only NS id changed ID: ${ps.second.id} ")
// without nsId = create new
ps.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// with nsId = update
ps.first.interfaceIDs.nightscoutId != null -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastEffectiveProfileSwitchIdIfGreater(ps.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastOfflineEventIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_offline_event_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting OfflineEvent data sync from $lastSynced")
sp.putLong(R.string.key_ns_offline_event_last_synced_id, lastSynced)
}
}
private suspend fun processChangedOfflineEvents() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastOfflineEventId() ?: 0L
var startId = sp.getLong(R.string.key_ns_offline_event_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_offline_event_last_synced_id, 0)
startId = 0
}
queueCounter.oesRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementOfflineEvent(startId).blockingGet()?.let { oe ->
aapsLogger.info(LTag.NSCLIENT, "Loading OfflineEvent data Start: $startId ${oe.first} forID: ${oe.second.id} ")
val dataPair = DataSyncSelector.PairOfflineEvent(oe.first, oe.second.id)
when {
// new record with existing NS id => must be coming from NS => ignore
oe.first.id == oe.second.id && oe.first.interfaceIDs.nightscoutId != null ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring OfflineEvent. Loaded from NS: ${oe.second.id} ")
// only NsId changed, no need to upload
oe.first.onlyNsIdAdded(oe.second) ->
aapsLogger.info(LTag.NSCLIENT, "Ignoring OfflineEvent. Only NS id changed ID: ${oe.second.id} ")
// without nsId = create new
oe.first.interfaceIDs.nightscoutId == null -> {
activePlugin.activeNsClient?.nsAdd("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
// existing with nsId = update
oe.first.interfaceIDs.nightscoutId != null -> {
activePlugin.activeNsClient?.nsUpdate("treatments", dataPair, "$startId/$lastDbId")
synchronized(dataPair) { dataPair.waitMillis(60000) }
cont = dataPair.confirmed
}
}
if (cont) confirmLastOfflineEventIdIfGreater(oe.second.id)
} ?: run {
cont = false
}
}
}
private fun confirmLastProfileStore(lastSynced: Long) {
sp.putLong(R.string.key_ns_profile_store_last_synced_timestamp, lastSynced)
}
private suspend fun processChangedProfileStore() {
if (isPaused) return
val lastSync = sp.getLong(R.string.key_ns_profile_store_last_synced_timestamp, 0)
val lastChange = sp.getLong(info.nightscout.core.utils.R.string.key_local_profile_last_change, 0)
if (lastChange == 0L) return
if (lastChange > lastSync) {
if (activePlugin.activeProfileSource.profile?.allProfilesValid != true) return
val profileStore = activePlugin.activeProfileSource.profile
val profileJson = profileStore?.data ?: return
// add for v3
if (JsonHelper.safeGetLongAllowNull(profileJson, "date") == null)
profileJson.put("date", profileStore.getStartDate())
val dataPair = DataSyncSelector.PairProfileStore(profileJson, dateUtil.now())
activePlugin.activeNsClient?.nsAdd("profile", dataPair, "")
synchronized(dataPair) { dataPair.waitMillis(60000) }
val now = dateUtil.now()
val cont = dataPair.confirmed
if (cont) confirmLastProfileStore(now)
}
}
}

View file

@ -1,737 +0,0 @@
package info.nightscout.plugins.sync.nsclient
import info.nightscout.database.impl.AppRepository
import info.nightscout.interfaces.plugin.ActivePlugin
import info.nightscout.interfaces.profile.ProfileFunction
import info.nightscout.interfaces.sync.DataSyncSelector
import info.nightscout.interfaces.sync.DataSyncSelectorV1
import info.nightscout.interfaces.utils.JsonHelper
import info.nightscout.plugins.sync.R
import info.nightscout.plugins.sync.nsShared.events.EventNSClientUpdateGuiQueue
import info.nightscout.plugins.sync.nsShared.events.EventNSClientUpdateGuiStatus
import info.nightscout.rx.bus.RxBus
import info.nightscout.rx.logging.AAPSLogger
import info.nightscout.rx.logging.LTag
import info.nightscout.shared.sharedPreferences.SP
import info.nightscout.shared.utils.DateUtil
import javax.inject.Inject
import javax.inject.Singleton
@Singleton
class DataSyncSelectorV1Impl @Inject constructor(
private val sp: SP,
private val aapsLogger: AAPSLogger,
private val dateUtil: DateUtil,
private val profileFunction: ProfileFunction,
private val activePlugin: ActivePlugin,
private val appRepository: AppRepository,
private val rxBus: RxBus
) : DataSyncSelectorV1 {
class QueueCounter(
var bolusesRemaining: Long = -1L,
var carbsRemaining: Long = -1L,
var bcrRemaining: Long = -1L,
var ttsRemaining: Long = -1L,
var foodsRemaining: Long = -1L,
var gvsRemaining: Long = -1L,
var tesRemaining: Long = -1L,
var dssRemaining: Long = -1L,
var tbrsRemaining: Long = -1L,
var ebsRemaining: Long = -1L,
var pssRemaining: Long = -1L,
var epssRemaining: Long = -1L,
var oesRemaining: Long = -1L
) {
fun size(): Long =
bolusesRemaining +
carbsRemaining +
bcrRemaining +
ttsRemaining +
foodsRemaining +
gvsRemaining +
tesRemaining +
dssRemaining +
tbrsRemaining +
ebsRemaining +
pssRemaining +
epssRemaining +
oesRemaining
}
private val queueCounter = QueueCounter()
private val isPaused get() = sp.getBoolean(R.string.key_ns_paused, false)
override fun queueSize(): Long = queueCounter.size()
override suspend fun doUpload() {
rxBus.send(EventNSClientUpdateGuiStatus())
if (sp.getBoolean(R.string.key_ns_upload, true) && !isPaused) {
queueCounter.bolusesRemaining = (appRepository.getLastBolusId() ?: 0L) - sp.getLong(R.string.key_ns_bolus_last_synced_id, 0)
queueCounter.carbsRemaining = (appRepository.getLastCarbsId() ?: 0L) - sp.getLong(R.string.key_ns_carbs_last_synced_id, 0)
queueCounter.bcrRemaining = (appRepository.getLastBolusCalculatorResultId() ?: 0L) - sp.getLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)
queueCounter.ttsRemaining = (appRepository.getLastTempTargetId() ?: 0L) - sp.getLong(R.string.key_ns_temporary_target_last_synced_id, 0)
queueCounter.foodsRemaining = (appRepository.getLastFoodId() ?: 0L) - sp.getLong(R.string.key_ns_food_last_synced_id, 0)
queueCounter.gvsRemaining = (appRepository.getLastGlucoseValueId() ?: 0L) - sp.getLong(R.string.key_ns_glucose_value_last_synced_id, 0)
queueCounter.tesRemaining = (appRepository.getLastTherapyEventId() ?: 0L) - sp.getLong(R.string.key_ns_therapy_event_last_synced_id, 0)
queueCounter.dssRemaining = (appRepository.getLastDeviceStatusId() ?: 0L) - sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)
queueCounter.tbrsRemaining = (appRepository.getLastTemporaryBasalId() ?: 0L) - sp.getLong(R.string.key_ns_temporary_basal_last_synced_id, 0)
queueCounter.ebsRemaining = (appRepository.getLastExtendedBolusId() ?: 0L) - sp.getLong(R.string.key_ns_extended_bolus_last_synced_id, 0)
queueCounter.pssRemaining = (appRepository.getLastProfileSwitchId() ?: 0L) - sp.getLong(R.string.key_ns_profile_switch_last_synced_id, 0)
queueCounter.epssRemaining = (appRepository.getLastEffectiveProfileSwitchId() ?: 0L) - sp.getLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)
queueCounter.oesRemaining = (appRepository.getLastOfflineEventId() ?: 0L) - sp.getLong(R.string.key_ns_offline_event_last_synced_id, 0)
rxBus.send(EventNSClientUpdateGuiQueue())
processChangedBoluses()
processChangedCarbs()
processChangedBolusCalculatorResults()
processChangedTemporaryBasals()
processChangedExtendedBoluses()
processChangedProfileSwitches()
processChangedEffectiveProfileSwitches()
processChangedGlucoseValues()
processChangedTempTargets()
processChangedFoods()
processChangedTherapyEvents()
processChangedDeviceStatuses()
processChangedOfflineEvents()
processChangedProfileStore()
}
rxBus.send(EventNSClientUpdateGuiStatus())
}
override fun resetToNextFullSync() {
sp.remove(R.string.key_ns_glucose_value_last_synced_id)
sp.remove(R.string.key_ns_temporary_basal_last_synced_id)
sp.remove(R.string.key_ns_temporary_target_last_synced_id)
sp.remove(R.string.key_ns_extended_bolus_last_synced_id)
sp.remove(R.string.key_ns_food_last_synced_id)
sp.remove(R.string.key_ns_bolus_last_synced_id)
sp.remove(R.string.key_ns_carbs_last_synced_id)
sp.remove(R.string.key_ns_bolus_calculator_result_last_synced_id)
sp.remove(R.string.key_ns_therapy_event_last_synced_id)
sp.remove(R.string.key_ns_profile_switch_last_synced_id)
sp.remove(R.string.key_ns_effective_profile_switch_last_synced_id)
sp.remove(R.string.key_ns_offline_event_last_synced_id)
sp.remove(R.string.key_ns_profile_store_last_synced_timestamp)
val lastDeviceStatusDbId = appRepository.getLastDeviceStatusId()
if (lastDeviceStatusDbId != null) sp.putLong(R.string.key_ns_device_status_last_synced_id, lastDeviceStatusDbId)
else sp.remove(R.string.key_ns_device_status_last_synced_id)
}
override fun confirmLastBolusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_bolus_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Bolus data sync from $lastSynced")
sp.putLong(R.string.key_ns_bolus_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedBoluses() {
if (isPaused) return
val lastDbId = appRepository.getLastBolusId() ?: 0L
var startId = sp.getLong(R.string.key_ns_bolus_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_bolus_last_synced_id, 0)
startId = 0
}
queueCounter.bolusesRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementBolus(startId).blockingGet()?.let { bolus ->
aapsLogger.info(LTag.NSCLIENT, "Loading Bolus data Start: $startId ${bolus.first} forID: ${bolus.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
bolus.first.id == bolus.second.id && bolus.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring Bolus. Loaded from NS: ${bolus.second.id} ")
confirmLastBolusIdIfGreater(bolus.second.id)
processChangedBoluses()
return
}
// only NsId changed, no need to upload
bolus.first.onlyNsIdAdded(bolus.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring Bolus. Only NS id changed: ${bolus.second.id} ")
confirmLastBolusIdIfGreater(bolus.second.id)
processChangedBoluses()
return
}
// without nsId = create new
bolus.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairBolus(bolus.first, bolus.second.id), " $startId/$lastDbId")
// with nsId = update if it's modified record
bolus.first.interfaceIDs.nightscoutId != null && bolus.first.id != bolus.second.id ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairBolus(bolus.first, bolus.second.id), "$startId/$lastDbId")
}
return
}
}
override fun confirmLastCarbsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_carbs_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Carbs data sync from $lastSynced")
sp.putLong(R.string.key_ns_carbs_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedCarbs() {
if (isPaused) return
val lastDbId = appRepository.getLastCarbsId() ?: 0L
var startId = sp.getLong(R.string.key_ns_carbs_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_carbs_last_synced_id, 0)
startId = 0
}
queueCounter.carbsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementCarbs(startId).blockingGet()?.let { carb ->
aapsLogger.info(LTag.NSCLIENT, "Loading Carbs data Start: $startId ${carb.first} forID: ${carb.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
carb.first.id == carb.second.id && carb.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring Carbs. Loaded from NS: ${carb.second.id} ")
confirmLastCarbsIdIfGreater(carb.second.id)
processChangedCarbs()
return
}
// only NsId changed, no need to upload
carb.first.onlyNsIdAdded(carb.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring Carbs. Only NS id changed ID: ${carb.second.id} ")
confirmLastCarbsIdIfGreater(carb.second.id)
processChangedCarbs()
return
}
// without nsId = create new
carb.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairCarbs(carb.first, carb.second.id), "$startId/$lastDbId")
// with nsId = update if it's modified record
carb.first.interfaceIDs.nightscoutId != null && carb.first.id != carb.second.id ->
activePlugin.activeNsClient?.nsUpdate(
"treatments",
DataSyncSelector.PairCarbs(carb.first, carb.second.id),
"$startId/$lastDbId"
)
}
return
}
}
override fun confirmLastBolusCalculatorResultsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting BolusCalculatorResult data sync from $lastSynced")
sp.putLong(R.string.key_ns_bolus_calculator_result_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedBolusCalculatorResults() {
if (isPaused) return
val lastDbId = appRepository.getLastBolusCalculatorResultId() ?: 0L
var startId = sp.getLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)
startId = 0
}
queueCounter.bcrRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementBolusCalculatorResult(startId).blockingGet()?.let { bolusCalculatorResult ->
aapsLogger.info(LTag.NSCLIENT, "Loading BolusCalculatorResult data Start: $startId ${bolusCalculatorResult.first} forID: ${bolusCalculatorResult.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
bolusCalculatorResult.first.id == bolusCalculatorResult.second.id && bolusCalculatorResult.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring BolusCalculatorResult. Loaded from NS: ${bolusCalculatorResult.second.id} ")
confirmLastBolusCalculatorResultsIdIfGreater(bolusCalculatorResult.second.id)
processChangedBolusCalculatorResults()
return
}
// only NsId changed, no need to upload
bolusCalculatorResult.first.onlyNsIdAdded(bolusCalculatorResult.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring BolusCalculatorResult. Only NS id changed ID: ${bolusCalculatorResult.second.id} ")
confirmLastBolusCalculatorResultsIdIfGreater(bolusCalculatorResult.second.id)
processChangedBolusCalculatorResults()
return
}
// without nsId = create new
bolusCalculatorResult.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairBolusCalculatorResult(bolusCalculatorResult.first, bolusCalculatorResult.second.id), "$startId/$lastDbId")
// with nsId = update if it's modified record
bolusCalculatorResult.first.interfaceIDs.nightscoutId != null && bolusCalculatorResult.first.id != bolusCalculatorResult.second.id ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairBolusCalculatorResult(bolusCalculatorResult.first, bolusCalculatorResult.second.id), "$startId/$lastDbId")
}
return
}
}
override fun confirmLastTempTargetsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_temporary_target_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TemporaryTarget data sync from $lastSynced")
sp.putLong(R.string.key_ns_temporary_target_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedTempTargets() {
if (isPaused) return
val lastDbId = appRepository.getLastTempTargetId() ?: 0L
var startId = sp.getLong(R.string.key_ns_temporary_target_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_temporary_target_last_synced_id, 0)
startId = 0
}
queueCounter.ttsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementTemporaryTarget(startId).blockingGet()?.let { tt ->
aapsLogger.info(LTag.NSCLIENT, "Loading TemporaryTarget data Start: $startId ${tt.first} forID: ${tt.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
tt.first.id == tt.second.id && tt.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryTarget. Loaded from NS: ${tt.second.id} ")
confirmLastTempTargetsIdIfGreater(tt.second.id)
processChangedTempTargets()
return
}
// only NsId changed, no need to upload
tt.first.onlyNsIdAdded(tt.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryTarget. Only NS id changed ID: ${tt.second.id} ")
confirmLastTempTargetsIdIfGreater(tt.second.id)
processChangedTempTargets()
return
}
// without nsId = create new
tt.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairTemporaryTarget(tt.first, tt.second.id), "$startId/$lastDbId")
// existing with nsId = update
tt.first.interfaceIDs.nightscoutId != null ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairTemporaryTarget(tt.first, tt.second.id), "$startId/$lastDbId")
}
return
}
}
override fun confirmLastFoodIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_food_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Food data sync from $lastSynced")
sp.putLong(R.string.key_ns_food_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedFoods() {
if (isPaused) return
val lastDbId = appRepository.getLastFoodId() ?: 0L
var startId = sp.getLong(R.string.key_ns_food_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_food_last_synced_id, 0)
startId = 0
}
queueCounter.foodsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementFood(startId).blockingGet()?.let { food ->
aapsLogger.info(LTag.NSCLIENT, "Loading Food data Start: $startId ${food.first} forID: ${food.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
food.first.id == food.second.id && food.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring Food. Loaded from NS: ${food.second.id} ")
confirmLastFoodIdIfGreater(food.second.id)
processChangedFoods()
return
}
// only NsId changed, no need to upload
food.first.onlyNsIdAdded(food.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring Food. Only NS id changed ID: ${food.second.id} ")
confirmLastFoodIdIfGreater(food.second.id)
processChangedFoods()
return
}
// without nsId = create new
food.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("food", DataSyncSelector.PairFood(food.first, food.second.id), "$startId/$lastDbId")
// with nsId = update
food.first.interfaceIDs.nightscoutId != null ->
activePlugin.activeNsClient?.nsUpdate("food", DataSyncSelector.PairFood(food.first, food.second.id), "$startId/$lastDbId")
}
return
}
}
override fun confirmLastGlucoseValueIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_glucose_value_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting GlucoseValue data sync from $lastSynced")
sp.putLong(R.string.key_ns_glucose_value_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedGlucoseValues() {
if (isPaused) return
val lastDbId = appRepository.getLastGlucoseValueId() ?: 0L
var startId = sp.getLong(R.string.key_ns_glucose_value_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_glucose_value_last_synced_id, 0)
startId = 0
}
queueCounter.gvsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementGlucoseValue(startId).blockingGet()?.let { gv ->
aapsLogger.info(LTag.NSCLIENT, "Loading GlucoseValue data Start: $startId ${gv.first} forID: ${gv.second.id} ")
if (activePlugin.activeBgSource.shouldUploadToNs(gv.first)) {
when {
// new record with existing NS id => must be coming from NS => ignore
gv.first.id == gv.second.id && gv.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring GlucoseValue. Loaded from NS: ${gv.second.id} ")
confirmLastGlucoseValueIdIfGreater(gv.second.id)
processChangedGlucoseValues()
return
}
// only NsId changed, no need to upload
gv.first.onlyNsIdAdded(gv.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring GlucoseValue. Only NS id changed ID: ${gv.second.id} ")
confirmLastGlucoseValueIdIfGreater(gv.second.id)
processChangedGlucoseValues()
return
}
// without nsId = create new
gv.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("entries", DataSyncSelector.PairGlucoseValue(gv.first, gv.second.id), "$startId/$lastDbId")
// with nsId = update
else -> // gv.first.interfaceIDs.nightscoutId != null
activePlugin.activeNsClient?.nsUpdate("entries", DataSyncSelector.PairGlucoseValue(gv.first, gv.second.id), "$startId/$lastDbId")
}
} else {
confirmLastGlucoseValueIdIfGreater(gv.second.id)
processChangedGlucoseValues()
return
}
}
}
override fun confirmLastTherapyEventIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_therapy_event_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TherapyEvents data sync from $lastSynced")
sp.putLong(R.string.key_ns_therapy_event_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedTherapyEvents() {
if (isPaused) return
val lastDbId = appRepository.getLastTherapyEventId() ?: 0L
var startId = sp.getLong(R.string.key_ns_therapy_event_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_therapy_event_last_synced_id, 0)
startId = 0
}
queueCounter.tesRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementTherapyEvent(startId).blockingGet()?.let { te ->
aapsLogger.info(LTag.NSCLIENT, "Loading TherapyEvents data Start: $startId ${te.first} forID: ${te.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
te.first.id == te.second.id && te.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring TherapyEvent. Loaded from NS: ${te.second.id} ")
confirmLastTherapyEventIdIfGreater(te.second.id)
processChangedTherapyEvents()
return
}
// only NsId changed, no need to upload
te.first.onlyNsIdAdded(te.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring TherapyEvent. Only NS id changed ID: ${te.second.id} ")
confirmLastTherapyEventIdIfGreater(te.second.id)
processChangedTherapyEvents()
return
}
// without nsId = create new
te.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairTherapyEvent(te.first, te.second.id), "$startId/$lastDbId")
// nsId = update
te.first.interfaceIDs.nightscoutId != null ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairTherapyEvent(te.first, te.second.id), "$startId/$lastDbId")
}
return
}
}
override fun confirmLastDeviceStatusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting DeviceStatus data sync from $lastSynced")
sp.putLong(R.string.key_ns_device_status_last_synced_id, lastSynced)
}
}
override suspend fun processChangedDeviceStatuses() {
if (isPaused) return
val lastDbId = appRepository.getLastDeviceStatusId() ?: 0L
var startId = sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_device_status_last_synced_id, 0)
startId = 0
}
queueCounter.dssRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementDeviceStatus(startId).blockingGet()?.let { deviceStatus ->
aapsLogger.info(LTag.NSCLIENT, "Loading DeviceStatus data Start: $startId $deviceStatus")
when {
// without nsId = create new
deviceStatus.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("devicestatus", DataSyncSelector.PairDeviceStatus(deviceStatus, lastDbId), "$startId/$lastDbId")
// with nsId = ignore
deviceStatus.interfaceIDs.nightscoutId != null -> Any()
}
return
}
}
override fun confirmLastTemporaryBasalIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_temporary_basal_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TemporaryBasal data sync from $lastSynced")
sp.putLong(R.string.key_ns_temporary_basal_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedTemporaryBasals() {
if (isPaused) return
val lastDbId = appRepository.getLastTemporaryBasalId() ?: 0L
var startId = sp.getLong(R.string.key_ns_temporary_basal_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_temporary_basal_last_synced_id, 0)
startId = 0
}
queueCounter.tbrsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementTemporaryBasal(startId).blockingGet()?.let { tb ->
aapsLogger.info(LTag.NSCLIENT, "Loading TemporaryBasal data Start: $startId ${tb.first} forID: ${tb.second.id} ")
val profile = profileFunction.getProfile(tb.first.timestamp)
if (profile != null) {
when {
// new record with existing NS id => must be coming from NS => ignore
tb.first.id == tb.second.id && tb.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryBasal. Loaded from NS: ${tb.second.id} ")
confirmLastTemporaryBasalIdIfGreater(tb.second.id)
processChangedTemporaryBasals()
return
}
// only NsId changed, no need to upload
tb.first.onlyNsIdAdded(tb.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryBasal. Only NS id changed ID: ${tb.second.id} ")
confirmLastTemporaryBasalIdIfGreater(tb.second.id)
processChangedTemporaryBasals()
return
}
// without nsId = create new
tb.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairTemporaryBasal(tb.first, tb.second.id), "$startId/$lastDbId", profile)
// with nsId = update
tb.first.interfaceIDs.nightscoutId != null ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairTemporaryBasal(tb.first, tb.second.id), "$startId/$lastDbId", profile)
}
return
} else {
aapsLogger.info(LTag.NSCLIENT, "Ignoring TemporaryBasal. No profile: ${tb.second.id} ")
confirmLastTemporaryBasalIdIfGreater(tb.second.id)
processChangedTemporaryBasals()
return
}
}
}
override fun confirmLastExtendedBolusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_extended_bolus_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting ExtendedBolus data sync from $lastSynced")
sp.putLong(R.string.key_ns_extended_bolus_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedExtendedBoluses() {
if (isPaused) return
val lastDbId = appRepository.getLastExtendedBolusId() ?: 0L
var startId = sp.getLong(R.string.key_ns_extended_bolus_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_extended_bolus_last_synced_id, 0)
startId = 0
}
queueCounter.ebsRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementExtendedBolus(startId).blockingGet()?.let { eb ->
aapsLogger.info(LTag.NSCLIENT, "Loading ExtendedBolus data Start: $startId ${eb.first} forID: ${eb.second.id} ")
val profile = profileFunction.getProfile(eb.first.timestamp)
if (profile != null) {
when {
// new record with existing NS id => must be coming from NS => ignore
eb.first.id == eb.second.id && eb.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring ExtendedBolus. Loaded from NS: ${eb.second.id} ")
confirmLastExtendedBolusIdIfGreater(eb.second.id)
processChangedExtendedBoluses()
return
}
// only NsId changed, no need to upload
eb.first.onlyNsIdAdded(eb.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring ExtendedBolus. Only NS id changed ID: ${eb.second.id} ")
confirmLastExtendedBolusIdIfGreater(eb.second.id)
processChangedExtendedBoluses()
return
}
// without nsId = create new
eb.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairExtendedBolus(eb.first, eb.second.id), "$startId/$lastDbId", profile)
// with nsId = update
eb.first.interfaceIDs.nightscoutId != null ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairExtendedBolus(eb.first, eb.second.id), "$startId/$lastDbId", profile)
}
return
} else {
aapsLogger.info(LTag.NSCLIENT, "Ignoring ExtendedBolus. No profile: ${eb.second.id} ")
confirmLastExtendedBolusIdIfGreater(eb.second.id)
processChangedExtendedBoluses()
return
}
}
}
override fun confirmLastProfileSwitchIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_profile_switch_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting ProfileSwitch data sync from $lastSynced")
sp.putLong(R.string.key_ns_profile_switch_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedProfileSwitches() {
if (isPaused) return
val lastDbId = appRepository.getLastProfileSwitchId() ?: 0L
var startId = sp.getLong(R.string.key_ns_profile_switch_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_profile_switch_last_synced_id, 0)
startId = 0
}
queueCounter.pssRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementProfileSwitch(startId).blockingGet()?.let { ps ->
aapsLogger.info(LTag.NSCLIENT, "Loading ProfileSwitch data Start: $startId ${ps.first} forID: ${ps.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
ps.first.id == ps.second.id && ps.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring ProfileSwitch. Loaded from NS: ${ps.second.id} ")
confirmLastProfileSwitchIdIfGreater(ps.second.id)
processChangedProfileSwitches()
return
}
// only NsId changed, no need to upload
ps.first.onlyNsIdAdded(ps.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring ProfileSwitch. Only NS id changed ID: ${ps.second.id} ")
confirmLastProfileSwitchIdIfGreater(ps.second.id)
processChangedProfileSwitches()
return
}
// without nsId = create new
ps.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairProfileSwitch(ps.first, ps.second.id), "$startId/$lastDbId")
// with nsId = update
ps.first.interfaceIDs.nightscoutId != null ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairProfileSwitch(ps.first, ps.second.id), "$startId/$lastDbId")
}
return
}
}
override fun confirmLastEffectiveProfileSwitchIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting EffectiveProfileSwitch data sync from $lastSynced")
sp.putLong(R.string.key_ns_effective_profile_switch_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedEffectiveProfileSwitches() {
if (isPaused) return
val lastDbId = appRepository.getLastEffectiveProfileSwitchId() ?: 0L
var startId = sp.getLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)
startId = 0
}
queueCounter.epssRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementEffectiveProfileSwitch(startId).blockingGet()?.let { ps ->
aapsLogger.info(LTag.NSCLIENT, "Loading EffectiveProfileSwitch data Start: $startId ${ps.first} forID: ${ps.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
ps.first.id == ps.second.id && ps.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring EffectiveProfileSwitch. Loaded from NS: ${ps.second.id} ")
confirmLastEffectiveProfileSwitchIdIfGreater(ps.second.id)
processChangedEffectiveProfileSwitches()
return
}
// only NsId changed, no need to upload
ps.first.onlyNsIdAdded(ps.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring EffectiveProfileSwitch. Only NS id changed ID: ${ps.second.id} ")
confirmLastEffectiveProfileSwitchIdIfGreater(ps.second.id)
processChangedEffectiveProfileSwitches()
return
}
// without nsId = create new
ps.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairEffectiveProfileSwitch(ps.first, ps.second.id), "$startId/$lastDbId")
// with nsId = update
ps.first.interfaceIDs.nightscoutId != null ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairEffectiveProfileSwitch(ps.first, ps.second.id), "$startId/$lastDbId")
}
return
}
}
override fun confirmLastOfflineEventIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_offline_event_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting OfflineEvent data sync from $lastSynced")
sp.putLong(R.string.key_ns_offline_event_last_synced_id, lastSynced)
}
}
override tailrec suspend fun processChangedOfflineEvents() {
if (isPaused) return
val lastDbId = appRepository.getLastOfflineEventId() ?: 0L
var startId = sp.getLong(R.string.key_ns_offline_event_last_synced_id, 0)
if (startId > lastDbId) {
sp.putLong(R.string.key_ns_offline_event_last_synced_id, 0)
startId = 0
}
queueCounter.oesRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementOfflineEvent(startId).blockingGet()?.let { oe ->
aapsLogger.info(LTag.NSCLIENT, "Loading OfflineEvent data Start: $startId ${oe.first} forID: ${oe.second.id} ")
when {
// new record with existing NS id => must be coming from NS => ignore
oe.first.id == oe.second.id && oe.first.interfaceIDs.nightscoutId != null -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring OfflineEvent. Loaded from NS: ${oe.second.id} ")
confirmLastOfflineEventIdIfGreater(oe.second.id)
processChangedOfflineEvents()
return
}
// only NsId changed, no need to upload
oe.first.onlyNsIdAdded(oe.second) -> {
aapsLogger.info(LTag.NSCLIENT, "Ignoring OfflineEvent. Only NS id changed ID: ${oe.second.id} ")
confirmLastOfflineEventIdIfGreater(oe.second.id)
processChangedOfflineEvents()
return
}
// without nsId = create new
oe.first.interfaceIDs.nightscoutId == null ->
activePlugin.activeNsClient?.nsAdd("treatments", DataSyncSelector.PairOfflineEvent(oe.first, oe.second.id), "$startId/$lastDbId")
// existing with nsId = update
oe.first.interfaceIDs.nightscoutId != null ->
activePlugin.activeNsClient?.nsUpdate("treatments", DataSyncSelector.PairOfflineEvent(oe.first, oe.second.id), "$startId/$lastDbId")
}
return
}
}
override fun confirmLastProfileStore(lastSynced: Long) {
sp.putLong(R.string.key_ns_profile_store_last_synced_timestamp, lastSynced)
}
override suspend fun processChangedProfileStore() {
if (isPaused) return
val lastSync = sp.getLong(R.string.key_ns_profile_store_last_synced_timestamp, 0)
val lastChange = sp.getLong(info.nightscout.core.utils.R.string.key_local_profile_last_change, 0)
if (lastChange == 0L) return
if (lastChange > lastSync) {
if (activePlugin.activeProfileSource.profile?.allProfilesValid != true) return
val profileStore = activePlugin.activeProfileSource.profile
val profileJson = profileStore?.data ?: return
// add for v3
if (JsonHelper.safeGetLongAllowNull(profileJson, "date") == null)
profileJson.put("date", profileStore.getStartDate())
activePlugin.activeNsClient?.nsAdd("profile", DataSyncSelector.PairProfileStore(profileJson, dateUtil.now()), "")
}
}
}

View file

@ -5,7 +5,6 @@ import android.content.Context
import android.content.Intent
import android.content.ServiceConnection
import android.os.IBinder
import android.provider.ContactsContract
import androidx.preference.PreferenceFragmentCompat
import androidx.preference.PreferenceScreen
import androidx.preference.SwitchPreference
@ -24,7 +23,6 @@ import info.nightscout.interfaces.profile.Profile
import info.nightscout.interfaces.profile.ProfileFunction
import info.nightscout.interfaces.source.DoingOwnUploadSource
import info.nightscout.interfaces.sync.DataSyncSelector
import info.nightscout.interfaces.sync.DataSyncSelectorV1
import info.nightscout.interfaces.sync.NsClient
import info.nightscout.interfaces.sync.Sync
import info.nightscout.plugins.sync.R

View file

@ -25,7 +25,6 @@ import info.nightscout.interfaces.notifications.Notification
import info.nightscout.interfaces.nsclient.NSAlarm
import info.nightscout.interfaces.nsclient.NSSettingsStatus
import info.nightscout.interfaces.nsclient.StoreDataForDb
import info.nightscout.interfaces.sync.DataSyncSelectorV1
import info.nightscout.interfaces.ui.UiInteraction
import info.nightscout.interfaces.utils.JsonHelper.safeGetString
import info.nightscout.interfaces.utils.JsonHelper.safeGetStringAllowNull
@ -34,6 +33,7 @@ import info.nightscout.plugins.sync.nsShared.NsIncomingDataProcessor
import info.nightscout.plugins.sync.nsShared.events.EventConnectivityOptionChanged
import info.nightscout.plugins.sync.nsShared.events.EventNSClientStatus
import info.nightscout.plugins.sync.nsShared.events.EventNSClientUpdateGuiStatus
import info.nightscout.plugins.sync.nsclient.DataSyncSelectorV1
import info.nightscout.plugins.sync.nsclient.NSClientPlugin
import info.nightscout.plugins.sync.nsclient.acks.NSAddAck
import info.nightscout.plugins.sync.nsclient.acks.NSAuthAck
@ -179,6 +179,18 @@ import javax.inject.Inject
.toObservable(EventNewHistoryData::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ resend("NEW_DATA") }, fabricPrivacy::logException)
disposable += rxBus
.toObservable(EventDeviceStatusChange::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ resend("EventDeviceStatusChange") }, fabricPrivacy::logException)
disposable += rxBus
.toObservable(EventTherapyEventChange::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ resend("EventTherapyEventChange") }, fabricPrivacy::logException)
disposable += rxBus
.toObservable(EventOfflineChange::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ resend("EventOfflineChange") }, fabricPrivacy::logException)
}
override fun onDestroy() {
@ -541,6 +553,7 @@ import javax.inject.Inject
}
}
rxBus.send(EventNSClientNewLog("◄ LAST", dateUtil.dateAndTimeString(latestDateInReceivedData)))
resend("LAST")
} catch (e: JSONException) {
aapsLogger.error("Unhandled exception", e)
}
@ -551,7 +564,7 @@ import javax.inject.Inject
}
}
fun dbUpdate(collection: String, _id: String?, data: JSONObject?, originalObject: Any, progress: String) {
fun dbUpdate(collection: String, @Suppress("LocalVariableName") _id: String?, data: JSONObject?, originalObject: Any, progress: String) {
try {
if (_id == null) return
if (!isConnected || !hasWriteAuth) return
@ -595,10 +608,10 @@ import javax.inject.Inject
if (!isConnected || !hasWriteAuth) return@runBlocking
scope.async {
if (socket?.connected() != true) return@async
if (lastAckTime > System.currentTimeMillis() - 10 * 1000L) {
aapsLogger.debug(LTag.NSCLIENT, "Skipping resend by lastAckTime: " + (System.currentTimeMillis() - lastAckTime) / 1000L + " sec")
return@async
}
// if (lastAckTime > System.currentTimeMillis() - 10 * 1000L) {
// aapsLogger.debug(LTag.NSCLIENT, "Skipping resend by lastAckTime: " + (System.currentTimeMillis() - lastAckTime) / 1000L + " sec")
// return@async
// }
rxBus.send(EventNSClientNewLog("● QUEUE", "Resend started: $reason"))
dataSyncSelectorV1.doUpload()
rxBus.send(EventNSClientNewLog("● QUEUE", "Resend ended: $reason"))

View file

@ -4,6 +4,7 @@ import android.content.Context
import android.os.SystemClock
import androidx.work.WorkerParameters
import androidx.work.workDataOf
import info.nightscout.core.utils.notify
import info.nightscout.core.utils.receivers.DataWorkerStorage
import info.nightscout.core.utils.worker.LoggingWorker
import info.nightscout.database.impl.AppRepository
@ -22,7 +23,6 @@ import info.nightscout.interfaces.sync.DataSyncSelector.PairProfileSwitch
import info.nightscout.interfaces.sync.DataSyncSelector.PairTemporaryBasal
import info.nightscout.interfaces.sync.DataSyncSelector.PairTemporaryTarget
import info.nightscout.interfaces.sync.DataSyncSelector.PairTherapyEvent
import info.nightscout.interfaces.sync.DataSyncSelectorV1
import info.nightscout.plugins.sync.R
import info.nightscout.plugins.sync.nsclient.acks.NSAddAck
import info.nightscout.rx.AapsSchedulers
@ -40,7 +40,6 @@ class NSClientAddAckWorker(
@Inject lateinit var dataWorkerStorage: DataWorkerStorage
@Inject lateinit var repository: AppRepository
@Inject lateinit var rxBus: RxBus
@Inject lateinit var dataSyncSelectorV1: DataSyncSelectorV1
@Inject lateinit var aapsSchedulers: AapsSchedulers
@Inject lateinit var sp: SP
@Inject lateinit var storeDataForDb: StoreDataForDb
@ -60,152 +59,128 @@ class NSClientAddAckWorker(
is PairTemporaryTarget -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdTemporaryTargets.add(pair.value)
dataSyncSelectorV1.confirmLastTempTargetsIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked TemporaryTarget " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedTempTargets()
}
is PairGlucoseValue -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdGlucoseValues.add(pair.value)
dataSyncSelectorV1.confirmLastGlucoseValueIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked GlucoseValue " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedGlucoseValues()
}
is PairFood -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdFoods.add(pair.value)
dataSyncSelectorV1.confirmLastFoodIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked Food " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedFoods()
}
is PairTherapyEvent -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdTherapyEvents.add(pair.value)
dataSyncSelectorV1.confirmLastTherapyEventIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked TherapyEvent " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedTherapyEvents()
}
is PairBolus -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdBoluses.add(pair.value)
dataSyncSelectorV1.confirmLastBolusIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked Bolus " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedBoluses()
}
is PairCarbs -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdCarbs.add(pair.value)
dataSyncSelectorV1.confirmLastCarbsIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked Carbs " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedCarbs()
}
is PairBolusCalculatorResult -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
storeDataForDb.nsIdBolusCalculatorResults.add(pair.value)
dataSyncSelectorV1.confirmLastBolusCalculatorResultsIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked BolusCalculatorResult " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedBolusCalculatorResults()
}
is PairTemporaryBasal -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdTemporaryBasals.add(pair.value)
dataSyncSelectorV1.confirmLastTemporaryBasalIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked TemporaryBasal " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedTemporaryBasals()
}
is PairExtendedBolus -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdExtendedBoluses.add(pair.value)
dataSyncSelectorV1.confirmLastExtendedBolusIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked ExtendedBolus " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedExtendedBoluses()
}
is PairProfileSwitch -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdProfileSwitches.add(pair.value)
dataSyncSelectorV1.confirmLastProfileSwitchIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked ProfileSwitch " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedProfileSwitches()
}
is PairEffectiveProfileSwitch -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdEffectiveProfileSwitches.add(pair.value)
dataSyncSelectorV1.confirmLastEffectiveProfileSwitchIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked EffectiveProfileSwitch " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedEffectiveProfileSwitches()
}
is DataSyncSelector.PairDeviceStatus -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdDeviceStatuses.add(pair.value)
dataSyncSelectorV1.confirmLastDeviceStatusIdIfGreater(pair.value.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked DeviceStatus " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedDeviceStatuses()
}
is PairProfileStore -> {
dataSyncSelectorV1.confirmLastProfileStore(ack.originalObject.id)
val pair = ack.originalObject
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked ProfileStore " + ack.id))
}
is PairOfflineEvent -> {
val pair = ack.originalObject
pair.value.interfaceIDs.nightscoutId = ack.id
pair.confirmed = true
storeDataForDb.nsIdOfflineEvents.add(pair.value)
dataSyncSelectorV1.confirmLastOfflineEventIdIfGreater(pair.id)
storeDataForDb.scheduleNsIdUpdate()
rxBus.send(EventNSClientNewLog("◄ DBADD", "Acked OfflineEvent " + pair.value.interfaceIDs.nightscoutId))
// Send new if waiting
dataSyncSelectorV1.processChangedOfflineEvents()
}
}
ack.originalObject?.let { synchronized(it) { it.notify() } }
return ret
}
}

View file

@ -3,6 +3,7 @@ package info.nightscout.plugins.sync.nsclient.workers
import android.content.Context
import androidx.work.WorkerParameters
import androidx.work.workDataOf
import info.nightscout.core.utils.notify
import info.nightscout.core.utils.receivers.DataWorkerStorage
import info.nightscout.core.utils.worker.LoggingWorker
import info.nightscout.database.impl.AppRepository
@ -18,7 +19,6 @@ import info.nightscout.interfaces.sync.DataSyncSelector.PairProfileSwitch
import info.nightscout.interfaces.sync.DataSyncSelector.PairTemporaryBasal
import info.nightscout.interfaces.sync.DataSyncSelector.PairTemporaryTarget
import info.nightscout.interfaces.sync.DataSyncSelector.PairTherapyEvent
import info.nightscout.interfaces.sync.DataSyncSelectorV1
import info.nightscout.plugins.sync.nsclient.acks.NSUpdateAck
import info.nightscout.rx.AapsSchedulers
import info.nightscout.rx.bus.RxBus
@ -34,7 +34,6 @@ class NSClientUpdateRemoveAckWorker(
@Inject lateinit var dataWorkerStorage: DataWorkerStorage
@Inject lateinit var repository: AppRepository
@Inject lateinit var rxBus: RxBus
@Inject lateinit var dataSyncSelectorV1: DataSyncSelectorV1
@Inject lateinit var aapsSchedulers: AapsSchedulers
override suspend fun doWorkAndLog(): Result {
@ -47,112 +46,89 @@ class NSClientUpdateRemoveAckWorker(
when (ack.originalObject) {
is PairTemporaryTarget -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastTempTargetsIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked TemporaryTarget" + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedTempTargets()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairGlucoseValue -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastGlucoseValueIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked GlucoseValue " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedGlucoseValues()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairFood -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastFoodIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked Food " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedFoods()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairTherapyEvent -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastTherapyEventIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked TherapyEvent " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedTherapyEvents()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairBolus -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastBolusIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked Bolus " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedBoluses()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairCarbs -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastCarbsIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked Carbs " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedCarbs()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairBolusCalculatorResult -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastBolusCalculatorResultsIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked BolusCalculatorResult " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedBolusCalculatorResults()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairTemporaryBasal -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastTemporaryBasalIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked TemporaryBasal " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedTemporaryBasals()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairExtendedBolus -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastExtendedBolusIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked ExtendedBolus " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedExtendedBoluses()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairProfileSwitch -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastProfileSwitchIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked ProfileSwitch " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedProfileSwitches()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairEffectiveProfileSwitch -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastEffectiveProfileSwitchIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked EffectiveProfileSwitch " + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedEffectiveProfileSwitches()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
is PairOfflineEvent -> {
val pair = ack.originalObject
dataSyncSelectorV1.confirmLastOfflineEventIdIfGreater(pair.id)
pair.confirmed = true
rxBus.send(EventNSClientNewLog("◄ DBUPDATE", "Acked OfflineEvent" + ack._id))
// Send new if waiting
dataSyncSelectorV1.processChangedOfflineEvents()
ret = Result.success(workDataOf("ProcessedData" to pair.toString()))
}
}
ack.originalObject?.let { synchronized(it) { it.notify() } }
return ret
}
}

View file

@ -7,7 +7,6 @@ import info.nightscout.interfaces.nsclient.StoreDataForDb
import info.nightscout.interfaces.plugin.ActivePlugin
import info.nightscout.interfaces.profile.ProfileFunction
import info.nightscout.interfaces.sync.DataSyncSelector
import info.nightscout.interfaces.sync.DataSyncSelectorV3
import info.nightscout.interfaces.utils.JsonHelper
import info.nightscout.plugins.sync.R
import info.nightscout.plugins.sync.nsShared.events.EventNSClientUpdateGuiQueue
@ -22,7 +21,7 @@ import javax.inject.Singleton
@OpenForTesting
@Singleton
class DataSyncSelectorV3Impl @Inject constructor(
class DataSyncSelectorV3 @Inject constructor(
private val sp: SP,
private val aapsLogger: AAPSLogger,
private val dateUtil: DateUtil,
@ -32,7 +31,7 @@ class DataSyncSelectorV3Impl @Inject constructor(
private val rxBus: RxBus,
private val storeDataForDb: StoreDataForDb,
private val config: Config
) : DataSyncSelectorV3 {
) : DataSyncSelector {
class QueueCounter(
var bolusesRemaining: Long = -1L,
@ -127,14 +126,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
else sp.remove(R.string.key_ns_device_status_last_synced_id)
}
fun confirmLastBolusIdIfGreater(lastSynced: Long) {
private fun confirmLastBolusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_bolus_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Bolus data sync from $lastSynced")
sp.putLong(R.string.key_ns_bolus_last_synced_id, lastSynced)
}
}
suspend fun processChangedBoluses() {
private suspend fun processChangedBoluses() {
var cont = true
while (cont) {
if (isPaused) return
@ -170,14 +169,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastCarbsIdIfGreater(lastSynced: Long) {
private fun confirmLastCarbsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_carbs_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Carbs data sync from $lastSynced")
sp.putLong(R.string.key_ns_carbs_last_synced_id, lastSynced)
}
}
suspend fun processChangedCarbs() {
private suspend fun processChangedCarbs() {
var cont = true
while (cont) {
if (isPaused) return
@ -213,14 +212,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastBolusCalculatorResultsIdIfGreater(lastSynced: Long) {
private fun confirmLastBolusCalculatorResultsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_bolus_calculator_result_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting BolusCalculatorResult data sync from $lastSynced")
sp.putLong(R.string.key_ns_bolus_calculator_result_last_synced_id, lastSynced)
}
}
suspend fun processChangedBolusCalculatorResults() {
private suspend fun processChangedBolusCalculatorResults() {
var cont = true
while (cont) {
if (isPaused) return
@ -264,14 +263,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastTempTargetsIdIfGreater(lastSynced: Long) {
private fun confirmLastTempTargetsIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_temporary_target_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TemporaryTarget data sync from $lastSynced")
sp.putLong(R.string.key_ns_temporary_target_last_synced_id, lastSynced)
}
}
suspend fun processChangedTempTargets() {
private suspend fun processChangedTempTargets() {
var cont = true
while (cont) {
if (isPaused) return
@ -307,14 +306,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastFoodIdIfGreater(lastSynced: Long) {
private fun confirmLastFoodIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_food_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting Food data sync from $lastSynced")
sp.putLong(R.string.key_ns_food_last_synced_id, lastSynced)
}
}
suspend fun processChangedFoods() {
private suspend fun processChangedFoods() {
var cont = true
while (cont) {
if (isPaused) return
@ -350,14 +349,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastGlucoseValueIdIfGreater(lastSynced: Long) {
private fun confirmLastGlucoseValueIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_glucose_value_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting GlucoseValue data sync from $lastSynced")
sp.putLong(R.string.key_ns_glucose_value_last_synced_id, lastSynced)
}
}
suspend fun processChangedGlucoseValues() {
private suspend fun processChangedGlucoseValues() {
var cont = true
while (cont) {
if (isPaused) return
@ -395,14 +394,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastTherapyEventIdIfGreater(lastSynced: Long) {
private fun confirmLastTherapyEventIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_therapy_event_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TherapyEvents data sync from $lastSynced")
sp.putLong(R.string.key_ns_therapy_event_last_synced_id, lastSynced)
}
}
suspend fun processChangedTherapyEvents() {
private suspend fun processChangedTherapyEvents() {
var cont = true
while (cont) {
if (isPaused) return
@ -438,44 +437,45 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastDeviceStatusIdIfGreater(lastSynced: Long) {
private fun confirmLastDeviceStatusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting DeviceStatus data sync from $lastSynced")
sp.putLong(R.string.key_ns_device_status_last_synced_id, lastSynced)
}
}
suspend fun processChangedDeviceStatuses() {
if (isPaused) return
val lastDbId = appRepository.getLastDeviceStatusId() ?: 0L
var startId = sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)
if (startId > lastDbId) {
aapsLogger.info(LTag.NSCLIENT, "Resetting startId: $startId lastDbId: $lastDbId")
sp.putLong(R.string.key_ns_device_status_last_synced_id, 0)
startId = 0
}
queueCounter.dssRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementDeviceStatus(startId).blockingGet()?.let { deviceStatus ->
//aapsLogger.info(LTag.NSCLIENT, "Loading DeviceStatus data Start: $startId $deviceStatus")
// without nsId = create new
if (deviceStatus.interfaceIDs.nightscoutId == null) {
if (activePlugin.activeNsClient?.nsAdd("devicestatus", DataSyncSelector.PairDeviceStatus(deviceStatus, lastDbId), "$startId/$lastDbId") == true)
confirmLastDeviceStatusIdIfGreater(lastDbId)
private suspend fun processChangedDeviceStatuses() {
var cont = true
while (cont) {
if (isPaused) return
val lastDbId = appRepository.getLastDeviceStatusId() ?: 0L
var startId = sp.getLong(R.string.key_ns_device_status_last_synced_id, 0)
if (startId > lastDbId) {
aapsLogger.info(LTag.NSCLIENT, "Resetting startId: $startId lastDbId: $lastDbId")
sp.putLong(R.string.key_ns_device_status_last_synced_id, 0)
startId = 0
}
queueCounter.dssRemaining = lastDbId - startId
rxBus.send(EventNSClientUpdateGuiQueue())
appRepository.getNextSyncElementDeviceStatus(startId).blockingGet()?.let { deviceStatus ->
//aapsLogger.info(LTag.NSCLIENT, "Loading DeviceStatus data Start: $startId $deviceStatus")
cont = activePlugin.activeNsClient?.nsAdd("devicestatus", DataSyncSelector.PairDeviceStatus(deviceStatus, lastDbId), "$startId/$lastDbId") ?: false
if (cont) confirmLastDeviceStatusIdIfGreater(deviceStatus.id)
// with nsId = ignore
} ?: run {
cont = false
}
// with nsId = ignore
}
queueCounter.dssRemaining = 0
}
fun confirmLastTemporaryBasalIdIfGreater(lastSynced: Long) {
private fun confirmLastTemporaryBasalIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_temporary_basal_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting TemporaryBasal data sync from $lastSynced")
sp.putLong(R.string.key_ns_temporary_basal_last_synced_id, lastSynced)
}
}
suspend fun processChangedTemporaryBasals() {
private suspend fun processChangedTemporaryBasals() {
var cont = true
while (cont) {
if (isPaused) return
@ -512,14 +512,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastExtendedBolusIdIfGreater(lastSynced: Long) {
private fun confirmLastExtendedBolusIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_extended_bolus_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting ExtendedBolus data sync from $lastSynced")
sp.putLong(R.string.key_ns_extended_bolus_last_synced_id, lastSynced)
}
}
suspend fun processChangedExtendedBoluses() {
private suspend fun processChangedExtendedBoluses() {
var cont = true
while (cont) {
if (isPaused) return
@ -558,14 +558,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastProfileSwitchIdIfGreater(lastSynced: Long) {
private fun confirmLastProfileSwitchIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_profile_switch_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting ProfileSwitch data sync from $lastSynced")
sp.putLong(R.string.key_ns_profile_switch_last_synced_id, lastSynced)
}
}
suspend fun processChangedProfileSwitches() {
private suspend fun processChangedProfileSwitches() {
var cont = true
while (cont) {
if (isPaused) return
@ -601,14 +601,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastEffectiveProfileSwitchIdIfGreater(lastSynced: Long) {
private fun confirmLastEffectiveProfileSwitchIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_effective_profile_switch_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting EffectiveProfileSwitch data sync from $lastSynced")
sp.putLong(R.string.key_ns_effective_profile_switch_last_synced_id, lastSynced)
}
}
suspend fun processChangedEffectiveProfileSwitches() {
private suspend fun processChangedEffectiveProfileSwitches() {
var cont = true
while (cont) {
if (isPaused) return
@ -644,14 +644,14 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastOfflineEventIdIfGreater(lastSynced: Long) {
private fun confirmLastOfflineEventIdIfGreater(lastSynced: Long) {
if (lastSynced > sp.getLong(R.string.key_ns_offline_event_last_synced_id, 0)) {
//aapsLogger.debug(LTag.NSCLIENT, "Setting OfflineEvent data sync from $lastSynced")
sp.putLong(R.string.key_ns_offline_event_last_synced_id, lastSynced)
}
}
suspend fun processChangedOfflineEvents() {
private suspend fun processChangedOfflineEvents() {
var cont = true
while (cont) {
if (isPaused) return
@ -687,11 +687,11 @@ class DataSyncSelectorV3Impl @Inject constructor(
}
}
fun confirmLastProfileStore(lastSynced: Long) {
private fun confirmLastProfileStore(lastSynced: Long) {
sp.putLong(R.string.key_ns_profile_store_last_synced_timestamp, lastSynced)
}
suspend fun processChangedProfileStore() {
private suspend fun processChangedProfileStore() {
if (isPaused) return
val lastSync = sp.getLong(R.string.key_ns_profile_store_last_synced_timestamp, 0)
val lastChange = sp.getLong(info.nightscout.core.utils.R.string.key_local_profile_last_change, 0)

View file

@ -30,7 +30,6 @@ import info.nightscout.interfaces.plugin.PluginType
import info.nightscout.interfaces.profile.Profile
import info.nightscout.interfaces.source.NSClientSource
import info.nightscout.interfaces.sync.DataSyncSelector
import info.nightscout.interfaces.sync.DataSyncSelectorV3
import info.nightscout.interfaces.sync.NsClient
import info.nightscout.interfaces.sync.Sync
import info.nightscout.interfaces.ui.UiInteraction
@ -66,11 +65,14 @@ import info.nightscout.plugins.sync.nsclientV3.workers.LoadTreatmentsWorker
import info.nightscout.rx.AapsSchedulers
import info.nightscout.rx.bus.RxBus
import info.nightscout.rx.events.EventAppExit
import info.nightscout.rx.events.EventDeviceStatusChange
import info.nightscout.rx.events.EventDismissNotification
import info.nightscout.rx.events.EventNSClientNewLog
import info.nightscout.rx.events.EventNewHistoryData
import info.nightscout.rx.events.EventOfflineChange
import info.nightscout.rx.events.EventPreferenceChange
import info.nightscout.rx.events.EventSWSyncStatus
import info.nightscout.rx.events.EventTherapyEventChange
import info.nightscout.rx.logging.AAPSLogger
import info.nightscout.rx.logging.LTag
import info.nightscout.sdk.NSAndroidClientImpl
@ -224,6 +226,18 @@ class NSClientV3Plugin @Inject constructor(
.toObservable(EventNewHistoryData::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ executeUpload("NEW_DATA", forceNew = false) }, fabricPrivacy::logException)
disposable += rxBus
.toObservable(EventDeviceStatusChange::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ executeUpload("EventDeviceStatusChange", forceNew = false) }, fabricPrivacy::logException)
disposable += rxBus
.toObservable(EventTherapyEventChange::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ executeUpload("EventTherapyEventChange", forceNew = false) }, fabricPrivacy::logException)
disposable += rxBus
.toObservable(EventOfflineChange::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ executeUpload("EventOfflineChange", forceNew = false) }, fabricPrivacy::logException)
runLoop = Runnable {
var refreshInterval = T.mins(5).msecs()

View file

@ -5,7 +5,7 @@ import androidx.work.WorkerParameters
import info.nightscout.androidaps.annotations.OpenForTesting
import info.nightscout.core.utils.worker.LoggingWorker
import info.nightscout.interfaces.plugin.ActivePlugin
import info.nightscout.interfaces.sync.DataSyncSelectorV3
import info.nightscout.plugins.sync.nsclientV3.DataSyncSelectorV3
import info.nightscout.plugins.sync.nsclientV3.NSClientV3Plugin
import info.nightscout.rx.bus.RxBus
import info.nightscout.rx.events.EventNSClientNewLog

View file

@ -45,7 +45,7 @@ internal class NSClientV3PluginTest : TestBaseWithProfile() {
@Mock lateinit var receiverDelegate: ReceiverDelegate
@Mock lateinit var uiInteraction: UiInteraction
@Mock lateinit var dataSyncSelectorV3: DataSyncSelectorV3Impl
@Mock lateinit var dataSyncSelectorV3: DataSyncSelectorV3
@Mock lateinit var nsAndroidClient: NSAndroidClient
@Mock lateinit var uel: UserEntryLogger
@Mock lateinit var nsClientSource: NSClientSource

View file

@ -8,7 +8,7 @@ import info.nightscout.androidaps.TestBase
import info.nightscout.core.utils.fabric.FabricPrivacy
import info.nightscout.interfaces.plugin.ActivePlugin
import info.nightscout.interfaces.sync.NsClient
import info.nightscout.plugins.sync.nsclientV3.DataSyncSelectorV3Impl
import info.nightscout.plugins.sync.nsclientV3.DataSyncSelectorV3
import info.nightscout.plugins.sync.nsclientV3.NSClientV3Plugin
import info.nightscout.rx.bus.RxBus
import kotlinx.coroutines.ExperimentalCoroutinesApi
@ -24,7 +24,7 @@ import org.mockito.Mockito.`when`
internal class DataSyncWorkerTest : TestBase() {
@Mock lateinit var fabricPrivacy: FabricPrivacy
@Mock lateinit var dataSyncSelectorV3: DataSyncSelectorV3Impl
@Mock lateinit var dataSyncSelectorV3: DataSyncSelectorV3
@Mock lateinit var activePlugin: ActivePlugin
@Mock lateinit var nsClient: NsClient
@Mock lateinit var rxBus: RxBus

View file

@ -17,11 +17,11 @@ import info.nightscout.interfaces.Config
import info.nightscout.interfaces.nsclient.StoreDataForDb
import info.nightscout.interfaces.receivers.ReceiverStatusStore
import info.nightscout.interfaces.source.NSClientSource
import info.nightscout.interfaces.sync.DataSyncSelectorV3
import info.nightscout.interfaces.ui.UiInteraction
import info.nightscout.plugins.sync.nsShared.NsIncomingDataProcessor
import info.nightscout.plugins.sync.nsclient.ReceiverDelegate
import info.nightscout.plugins.sync.nsclient.data.NSDeviceStatusHandler
import info.nightscout.plugins.sync.nsclientV3.DataSyncSelectorV3
import info.nightscout.plugins.sync.nsclientV3.NSClientV3Plugin
import info.nightscout.plugins.sync.nsclientV3.extensions.toNSSvgV3
import info.nightscout.rx.bus.RxBus