add loadEvents(), small improvements
This commit is contained in:
parent
e568ab399f
commit
8caeb4a3e0
|
@ -0,0 +1,9 @@
|
||||||
|
package info.nightscout.interfaces.pump
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Functionality supported by Medtrum* pumps only
|
||||||
|
*/
|
||||||
|
interface Medtrum {
|
||||||
|
|
||||||
|
fun loadEvents(): PumpEnactResult // events history to build treatments from
|
||||||
|
}
|
|
@ -4,6 +4,7 @@ import dagger.android.HasAndroidInjector
|
||||||
import info.nightscout.interfaces.plugin.ActivePlugin
|
import info.nightscout.interfaces.plugin.ActivePlugin
|
||||||
import info.nightscout.interfaces.pump.Dana
|
import info.nightscout.interfaces.pump.Dana
|
||||||
import info.nightscout.interfaces.pump.Diaconn
|
import info.nightscout.interfaces.pump.Diaconn
|
||||||
|
import info.nightscout.interfaces.pump.Medtrum
|
||||||
import info.nightscout.interfaces.pump.PumpEnactResult
|
import info.nightscout.interfaces.pump.PumpEnactResult
|
||||||
import info.nightscout.interfaces.queue.Callback
|
import info.nightscout.interfaces.queue.Callback
|
||||||
import info.nightscout.interfaces.queue.Command
|
import info.nightscout.interfaces.queue.Command
|
||||||
|
@ -32,6 +33,13 @@ class CommandLoadEvents(
|
||||||
aapsLogger.debug(LTag.PUMPQUEUE, "Result success: ${r.success} enacted: ${r.enacted}")
|
aapsLogger.debug(LTag.PUMPQUEUE, "Result success: ${r.success} enacted: ${r.enacted}")
|
||||||
callback?.result(r)?.run()
|
callback?.result(r)?.run()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (pump is Medtrum) {
|
||||||
|
val medtrumPump = pump as Medtrum
|
||||||
|
val r = medtrumPump.loadEvents()
|
||||||
|
aapsLogger.debug(LTag.PUMPQUEUE, "Result success: ${r.success} enacted: ${r.enacted}")
|
||||||
|
callback?.result(r)?.run()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
override fun status(): String = rh.gs(info.nightscout.core.ui.R.string.load_events)
|
override fun status(): String = rh.gs(info.nightscout.core.ui.R.string.load_events)
|
||||||
|
|
|
@ -17,6 +17,7 @@ import info.nightscout.interfaces.profile.Profile
|
||||||
import info.nightscout.interfaces.profile.ProfileFunction
|
import info.nightscout.interfaces.profile.ProfileFunction
|
||||||
import info.nightscout.interfaces.pump.DetailedBolusInfo
|
import info.nightscout.interfaces.pump.DetailedBolusInfo
|
||||||
import info.nightscout.interfaces.pump.DetailedBolusInfoStorage
|
import info.nightscout.interfaces.pump.DetailedBolusInfoStorage
|
||||||
|
import info.nightscout.interfaces.pump.Medtrum
|
||||||
import info.nightscout.interfaces.pump.Pump
|
import info.nightscout.interfaces.pump.Pump
|
||||||
import info.nightscout.interfaces.pump.PumpEnactResult
|
import info.nightscout.interfaces.pump.PumpEnactResult
|
||||||
import info.nightscout.interfaces.pump.PumpPluginBase
|
import info.nightscout.interfaces.pump.PumpPluginBase
|
||||||
|
@ -85,7 +86,7 @@ import kotlin.math.round
|
||||||
.shortName(R.string.medtrum_pump_shortname)
|
.shortName(R.string.medtrum_pump_shortname)
|
||||||
.preferencesId(R.xml.pref_medtrum_pump)
|
.preferencesId(R.xml.pref_medtrum_pump)
|
||||||
.description(R.string.medtrum_pump_description), injector, aapsLogger, rh, commandQueue
|
.description(R.string.medtrum_pump_description), injector, aapsLogger, rh, commandQueue
|
||||||
), Pump {
|
), Pump, Medtrum {
|
||||||
|
|
||||||
private val disposable = CompositeDisposable()
|
private val disposable = CompositeDisposable()
|
||||||
private var medtrumService: MedtrumService? = null
|
private var medtrumService: MedtrumService? = null
|
||||||
|
@ -270,16 +271,20 @@ import kotlin.math.round
|
||||||
// round rate to pump rate
|
// round rate to pump rate
|
||||||
val pumpRate = constraintChecker.applyBasalConstraints(Constraint(absoluteRate), profile).value()
|
val pumpRate = constraintChecker.applyBasalConstraints(Constraint(absoluteRate), profile).value()
|
||||||
temporaryBasalStorage.add(PumpSync.PumpState.TemporaryBasal(dateUtil.now(), T.mins(durationInMinutes.toLong()).msecs(), pumpRate, true, tbrType, 0L, 0L))
|
temporaryBasalStorage.add(PumpSync.PumpState.TemporaryBasal(dateUtil.now(), T.mins(durationInMinutes.toLong()).msecs(), pumpRate, true, tbrType, 0L, 0L))
|
||||||
val connectionOk = medtrumService?.setTempBasal(pumpRate, durationInMinutes) ?: false
|
val connectionOK = medtrumService?.setTempBasal(pumpRate, durationInMinutes) ?: false
|
||||||
if (connectionOk
|
if (connectionOK
|
||||||
&& medtrumPump.tempBasalInProgress
|
&& medtrumPump.tempBasalInProgress
|
||||||
&& Math.abs(medtrumPump.tempBasalAbsoluteRate - pumpRate) <= 0.05
|
&& Math.abs(medtrumPump.tempBasalAbsoluteRate - pumpRate) <= 0.05
|
||||||
/*&& Math.abs(medtrumPump.tempBasalRemainingMinutes - durationInMinutes) <= 5*/) {
|
/*&& Math.abs(medtrumPump.tempBasalRemainingMinutes - durationInMinutes) <= 5*/) {
|
||||||
|
|
||||||
return PumpEnactResult(injector).success(true).enacted(true).duration(/*medtrumPump.tempBasalRemainingMinutes*/durationInMinutes).absolute(medtrumPump.tempBasalAbsoluteRate).isPercent(false)
|
return PumpEnactResult(injector).success(true).enacted(true).duration(/*medtrumPump.tempBasalRemainingMinutes*/durationInMinutes).absolute(medtrumPump.tempBasalAbsoluteRate)
|
||||||
|
.isPercent(false)
|
||||||
.isTempCancel(false)
|
.isTempCancel(false)
|
||||||
} else {
|
} else {
|
||||||
aapsLogger.error(LTag.PUMP, "setTempBasalAbsolute failed, connectionOk: $connectionOk, tempBasalInProgress: ${medtrumPump.tempBasalInProgress}, tempBasalAbsoluteRate: ${medtrumPump.tempBasalAbsoluteRate}") //, tempBasalRemainingMinutes: ${medtrumPump.tempBasalRemainingMinutes}")
|
aapsLogger.error(
|
||||||
|
LTag.PUMP,
|
||||||
|
"setTempBasalAbsolute failed, connectionOK: $connectionOK, tempBasalInProgress: ${medtrumPump.tempBasalInProgress}, tempBasalAbsoluteRate: ${medtrumPump.tempBasalAbsoluteRate}"
|
||||||
|
) //, tempBasalRemainingMinutes: ${medtrumPump.tempBasalRemainingMinutes}")
|
||||||
return PumpEnactResult(injector).success(false).enacted(false).comment("Medtrum setTempBasalAbsolute failed")
|
return PumpEnactResult(injector).success(false).enacted(false).comment("Medtrum setTempBasalAbsolute failed")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -298,11 +303,11 @@ import kotlin.math.round
|
||||||
if (!isInitialized()) return PumpEnactResult(injector).success(false).enacted(false)
|
if (!isInitialized()) return PumpEnactResult(injector).success(false).enacted(false)
|
||||||
|
|
||||||
aapsLogger.info(LTag.PUMP, "cancelTempBasal - enforceNew: $enforceNew")
|
aapsLogger.info(LTag.PUMP, "cancelTempBasal - enforceNew: $enforceNew")
|
||||||
val connectionOk = medtrumService?.cancelTempBasal() ?: false
|
val connectionOK = medtrumService?.cancelTempBasal() ?: false
|
||||||
if (connectionOk && !medtrumPump.tempBasalInProgress) {
|
if (connectionOK && !medtrumPump.tempBasalInProgress) {
|
||||||
return PumpEnactResult(injector).success(true).enacted(true).isTempCancel(true)
|
return PumpEnactResult(injector).success(true).enacted(true).isTempCancel(true)
|
||||||
} else {
|
} else {
|
||||||
aapsLogger.error(LTag.PUMP, "cancelTempBasal failed, connectionOk: $connectionOk, tempBasalInProgress: ${medtrumPump.tempBasalInProgress}")
|
aapsLogger.error(LTag.PUMP, "cancelTempBasal failed, connectionOK: $connectionOK, tempBasalInProgress: ${medtrumPump.tempBasalInProgress}")
|
||||||
return PumpEnactResult(injector).success(false).enacted(false).comment("Medtrum cancelTempBasal failed")
|
return PumpEnactResult(injector).success(false).enacted(false).comment("Medtrum cancelTempBasal failed")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -357,4 +362,15 @@ import kotlin.math.round
|
||||||
|
|
||||||
override fun timezoneOrDSTChanged(timeChangeType: TimeChangeType) {
|
override fun timezoneOrDSTChanged(timeChangeType: TimeChangeType) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Medtrum interface
|
||||||
|
override fun loadEvents(): PumpEnactResult {
|
||||||
|
if (!isInitialized()) {
|
||||||
|
val result = PumpEnactResult(injector).success(false)
|
||||||
|
result.comment = "pump not initialized"
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
val connectionOK = medtrumService?.loadEvents() ?: false
|
||||||
|
return PumpEnactResult(injector).success(connectionOK)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -48,17 +48,20 @@ class CancelTempBasalPacket(injector: HasAndroidInjector) : MedtrumPacket(inject
|
||||||
|
|
||||||
medtrumPump.handleBasalStatusUpdate(basalType, basalRate, basalSequence, basalPatchId, basalStartTime)
|
medtrumPump.handleBasalStatusUpdate(basalType, basalRate, basalSequence, basalPatchId, basalStartTime)
|
||||||
|
|
||||||
|
if (basalType == BasalType.STANDARD) {
|
||||||
|
// If we have standard here, means TBR is cancelled successfully
|
||||||
pumpSync.syncStopTemporaryBasalWithPumpId(
|
pumpSync.syncStopTemporaryBasalWithPumpId(
|
||||||
timestamp = basalStartTime, // Time of normal basal start = time of tbr end
|
timestamp = basalStartTime, // Time of normal basal start = time of tbr end
|
||||||
endPumpId = basalStartTime,
|
endPumpId = basalStartTime,
|
||||||
pumpType = medtrumPump.pumpType,
|
pumpType = medtrumPump.pumpType,
|
||||||
pumpSerial = medtrumPump.pumpSN.toString(radix = 16)
|
pumpSerial = medtrumPump.pumpSN.toString(radix = 16)
|
||||||
)
|
)
|
||||||
aapsLogger.warn(
|
aapsLogger.debug(
|
||||||
LTag.PUMPCOMM,
|
LTag.PUMPCOMM,
|
||||||
"CancelTempBasalPacket: EVENT TEMP_END ($basalType) ${dateUtil.dateAndTimeString(basalStartTime)} ($basalStartTime) "
|
"CancelTempBasalPacket: EVENT TEMP_END ${dateUtil.dateAndTimeString(basalStartTime)} ($basalStartTime) "
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
}
|
||||||
return success
|
return success
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -55,12 +55,12 @@ class SynchronizePacket(injector: HasAndroidInjector) : MedtrumPacket(injector)
|
||||||
offset += 4 // If field is present, skip 4 bytes
|
offset += 4 // If field is present, skip 4 bytes
|
||||||
}
|
}
|
||||||
if (fieldMask and MASK_NORMAL_BOLUS != 0) {
|
if (fieldMask and MASK_NORMAL_BOLUS != 0) {
|
||||||
aapsLogger.warn(LTag.PUMPCOMM, "SynchronizePacket: Normal bolus present removing from fieldMask")
|
aapsLogger.debug(LTag.PUMPCOMM, "SynchronizePacket: Normal bolus present removing from fieldMask")
|
||||||
fieldMask = fieldMask and MASK_NORMAL_BOLUS.inv()
|
fieldMask = fieldMask and MASK_NORMAL_BOLUS.inv()
|
||||||
syncData = syncData.copyOfRange(0, offset) + syncData.copyOfRange(offset + 3, syncData.size)
|
syncData = syncData.copyOfRange(0, offset) + syncData.copyOfRange(offset + 3, syncData.size)
|
||||||
}
|
}
|
||||||
if (fieldMask and MASK_EXTENDED_BOLUS != 0) {
|
if (fieldMask and MASK_EXTENDED_BOLUS != 0) {
|
||||||
aapsLogger.warn(LTag.PUMPCOMM, "SynchronizePacket: Extended bolus present removing from fieldMask")
|
aapsLogger.debug(LTag.PUMPCOMM, "SynchronizePacket: Extended bolus present removing from fieldMask")
|
||||||
fieldMask = fieldMask and MASK_EXTENDED_BOLUS.inv()
|
fieldMask = fieldMask and MASK_EXTENDED_BOLUS.inv()
|
||||||
syncData = syncData.copyOfRange(0, offset) + syncData.copyOfRange(offset + 3, syncData.size)
|
syncData = syncData.copyOfRange(0, offset) + syncData.copyOfRange(offset + 3, syncData.size)
|
||||||
}
|
}
|
||||||
|
|
|
@ -72,7 +72,7 @@ class BLEComm @Inject internal constructor(
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
|
|
||||||
private const val WRITE_DELAY_MILLIS: Long = 50
|
private const val WRITE_DELAY_MILLIS: Long = 100
|
||||||
private const val SERVICE_UUID = "669A9001-0008-968F-E311-6050405558B3"
|
private const val SERVICE_UUID = "669A9001-0008-968F-E311-6050405558B3"
|
||||||
private const val READ_UUID = "669a9120-0008-968f-e311-6050405558b3"
|
private const val READ_UUID = "669a9120-0008-968f-e311-6050405558b3"
|
||||||
private const val WRITE_UUID = "669a9101-0008-968f-e311-6050405558b3"
|
private const val WRITE_UUID = "669a9101-0008-968f-e311-6050405558b3"
|
||||||
|
|
|
@ -72,7 +72,6 @@ class MedtrumService : DaggerService(), BLECommCallback {
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
|
|
||||||
// TODO: Test and further increase?
|
|
||||||
private const val COMMAND_DEFAULT_TIMEOUT_SEC: Long = 60
|
private const val COMMAND_DEFAULT_TIMEOUT_SEC: Long = 60
|
||||||
private const val COMMAND_SYNC_TIMEOUT_SEC: Long = 120
|
private const val COMMAND_SYNC_TIMEOUT_SEC: Long = 120
|
||||||
private const val COMMAND_CONNECTING_TIMEOUT_SEC: Long = 30
|
private const val COMMAND_CONNECTING_TIMEOUT_SEC: Long = 30
|
||||||
|
@ -199,8 +198,11 @@ class MedtrumService : DaggerService(), BLECommCallback {
|
||||||
}
|
}
|
||||||
|
|
||||||
fun readPumpStatus() {
|
fun readPumpStatus() {
|
||||||
// Most of these things are already done when a connection is setup, but wo dont know how long the pump was connected for?
|
// Update pump events
|
||||||
|
loadEvents()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun loadEvents(): Boolean {
|
||||||
// Send a poll patch, to workaround connection losses?
|
// Send a poll patch, to workaround connection losses?
|
||||||
var result = sendPacketAndGetResponse(PollPatchPacket(injector))
|
var result = sendPacketAndGetResponse(PollPatchPacket(injector))
|
||||||
// So just do a syncronize to make sure we have the latest data
|
// So just do a syncronize to make sure we have the latest data
|
||||||
|
@ -210,9 +212,11 @@ class MedtrumService : DaggerService(), BLECommCallback {
|
||||||
if (result) result = syncRecords()
|
if (result) result = syncRecords()
|
||||||
if (!result) {
|
if (!result) {
|
||||||
aapsLogger.error(LTag.PUMPCOMM, "Failed to sync records")
|
aapsLogger.error(LTag.PUMPCOMM, "Failed to sync records")
|
||||||
return
|
|
||||||
}
|
}
|
||||||
if (result) medtrumPump.lastConnection = System.currentTimeMillis()
|
if (result) medtrumPump.lastConnection = System.currentTimeMillis()
|
||||||
|
aapsLogger.debug(LTag.PUMPCOMM, "Events loaded")
|
||||||
|
rxBus.send(EventPumpStatusChanged(rh.gs(info.nightscout.pump.medtrum.R.string.gettingpumpstatus)))
|
||||||
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
fun setBolus(insulin: Double, t: EventOverviewBolusProgress.Treatment): Boolean {
|
fun setBolus(insulin: Double, t: EventOverviewBolusProgress.Treatment): Boolean {
|
||||||
|
@ -250,13 +254,19 @@ class MedtrumService : DaggerService(), BLECommCallback {
|
||||||
|
|
||||||
val bolusDurationInMSec = (insulin * 60 * 1000)
|
val bolusDurationInMSec = (insulin * 60 * 1000)
|
||||||
val expectedEnd = bolusStart + bolusDurationInMSec + 2000
|
val expectedEnd = bolusStart + bolusDurationInMSec + 2000
|
||||||
while (System.currentTimeMillis() < expectedEnd && result == true) {
|
while (System.currentTimeMillis() < expectedEnd && result == true && medtrumPump.bolusDone == false) {
|
||||||
SystemClock.sleep(1000)
|
SystemClock.sleep(1000)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Do not call update status directly, reconnection may be needed
|
// Do not call update status directly, reconnection may be needed
|
||||||
commandQueue.readStatus(rh.gs(info.nightscout.pump.medtrum.R.string.gettingbolusstatus), object : Callback() {
|
commandQueue.loadEvents(object : Callback() {
|
||||||
override fun run() {
|
override fun run() {
|
||||||
|
if (this.result.success == false && isConnected == false) {
|
||||||
|
// Reschedule loadEvents when we lost connection during the command
|
||||||
|
aapsLogger.warn(LTag.PUMP, "loadEvents failed due to connection loss, rescheduling")
|
||||||
|
commandQueue.loadEvents(this)
|
||||||
|
return
|
||||||
|
}
|
||||||
rxBus.send(EventPumpStatusChanged(rh.gs(info.nightscout.pump.medtrum.R.string.gettingbolusstatus)))
|
rxBus.send(EventPumpStatusChanged(rh.gs(info.nightscout.pump.medtrum.R.string.gettingbolusstatus)))
|
||||||
bolusingEvent.percent = 100
|
bolusingEvent.percent = 100
|
||||||
}
|
}
|
||||||
|
@ -278,7 +288,7 @@ class MedtrumService : DaggerService(), BLECommCallback {
|
||||||
|
|
||||||
// Get history records, this will update the prevoius basals
|
// Get history records, this will update the prevoius basals
|
||||||
// Do not call update status directly, reconnection may be needed
|
// Do not call update status directly, reconnection may be needed
|
||||||
commandQueue.readStatus(rh.gs(info.nightscout.pump.medtrum.R.string.gettingtempbasalstatus), object : Callback() {
|
commandQueue.loadEvents(object : Callback() {
|
||||||
override fun run() {
|
override fun run() {
|
||||||
rxBus.send(EventPumpStatusChanged(rh.gs(info.nightscout.pump.medtrum.R.string.gettingtempbasalstatus)))
|
rxBus.send(EventPumpStatusChanged(rh.gs(info.nightscout.pump.medtrum.R.string.gettingtempbasalstatus)))
|
||||||
}
|
}
|
||||||
|
@ -292,7 +302,7 @@ class MedtrumService : DaggerService(), BLECommCallback {
|
||||||
|
|
||||||
// Get history records, this will update the prevoius basals
|
// Get history records, this will update the prevoius basals
|
||||||
// Do not call update status directly, reconnection may be needed
|
// Do not call update status directly, reconnection may be needed
|
||||||
commandQueue.readStatus(rh.gs(info.nightscout.pump.medtrum.R.string.gettingtempbasalstatus), object : Callback() {
|
commandQueue.loadEvents(object : Callback() {
|
||||||
override fun run() {
|
override fun run() {
|
||||||
rxBus.send(EventPumpStatusChanged(rh.gs(info.nightscout.pump.medtrum.R.string.gettingtempbasalstatus)))
|
rxBus.send(EventPumpStatusChanged(rh.gs(info.nightscout.pump.medtrum.R.string.gettingtempbasalstatus)))
|
||||||
}
|
}
|
||||||
|
@ -312,7 +322,7 @@ class MedtrumService : DaggerService(), BLECommCallback {
|
||||||
if (result) result = packet?.let { sendPacketAndGetResponse(it) } == true
|
if (result) result = packet?.let { sendPacketAndGetResponse(it) } == true
|
||||||
|
|
||||||
// Get history records, this will update the pump state and add changes in TBR to AAPS history
|
// Get history records, this will update the pump state and add changes in TBR to AAPS history
|
||||||
if (result) result = syncRecords()
|
commandQueue.loadEvents(null)
|
||||||
|
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
@ -690,12 +700,14 @@ class MedtrumService : DaggerService(), BLECommCallback {
|
||||||
override fun onEnter() {
|
override fun onEnter() {
|
||||||
aapsLogger.debug(LTag.PUMPCOMM, "Medtrum Service reached ReadyState!")
|
aapsLogger.debug(LTag.PUMPCOMM, "Medtrum Service reached ReadyState!")
|
||||||
// Now we are fully connected and authenticated and we can start sending commands. Let AAPS know
|
// Now we are fully connected and authenticated and we can start sending commands. Let AAPS know
|
||||||
|
if (isConnected == false) {
|
||||||
medtrumPump.connectionState = ConnectionState.CONNECTED
|
medtrumPump.connectionState = ConnectionState.CONNECTED
|
||||||
if (medtrumPlugin.isInitialized()) {
|
if (medtrumPlugin.isInitialized()) {
|
||||||
rxBus.send(EventPumpStatusChanged(EventPumpStatusChanged.Status.CONNECTED))
|
rxBus.send(EventPumpStatusChanged(EventPumpStatusChanged.Status.CONNECTED))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// This state is when a command is send and we wait for a response for that command
|
// This state is when a command is send and we wait for a response for that command
|
||||||
private inner class CommandState : State() {
|
private inner class CommandState : State() {
|
||||||
|
|
|
@ -46,7 +46,9 @@
|
||||||
<string name="snInput_title">SN</string>
|
<string name="snInput_title">SN</string>
|
||||||
<string name="snInput_summary">Serial number pump base</string>
|
<string name="snInput_summary">Serial number pump base</string>
|
||||||
|
|
||||||
|
<!-- treatment state-->
|
||||||
<string name="waitingforestimatedbolusend">Waiting for bolus end. Remaining %1$d sec.</string>
|
<string name="waitingforestimatedbolusend">Waiting for bolus end. Remaining %1$d sec.</string>
|
||||||
|
<string name="gettingpumpstatus">Getting pump status</string>
|
||||||
<string name="gettingbolusstatus">Getting bolus status</string>
|
<string name="gettingbolusstatus">Getting bolus status</string>
|
||||||
<string name="gettingtempbasalstatus">Getting temporary basal status</string>
|
<string name="gettingtempbasalstatus">Getting temporary basal status</string>
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue