Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

sms bolus from AAPSClient #3507

Open
wants to merge 11 commits into
base: dev
Choose a base branch
from
1 change: 1 addition & 0 deletions core/keys/src/main/kotlin/app/aaps/core/keys/StringKey.kt
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ enum class StringKey(
AutomationLocation("location", "PASSIVE", hideParentScreenIfHidden = true),

SmsAllowedNumbers("smscommunicator_allowednumbers", ""),
SmsReceiverNumber("sms_communicator_receiver_number", "", showInApsMode = false, showInPumpControlMode = false, dependency = BooleanKey.SmsAllowRemoteCommands),
SmsOtpPassword("smscommunicator_otp_password", "", dependency = BooleanKey.SmsAllowRemoteCommands),

VirtualPumpType("virtualpump_type", "Generic AAPS"),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,12 +37,15 @@ import app.aaps.core.interfaces.resources.ResourceHelper
import app.aaps.core.interfaces.rx.bus.RxBus
import app.aaps.core.interfaces.rx.events.EventRefreshOverview
import app.aaps.core.interfaces.sharedPreferences.SP
import app.aaps.core.interfaces.smsCommunicator.Sms
import app.aaps.core.interfaces.smsCommunicator.SmsCommunicator
import app.aaps.core.interfaces.ui.UiInteraction
import app.aaps.core.interfaces.utils.DateUtil
import app.aaps.core.interfaces.utils.DecimalFormatter
import app.aaps.core.interfaces.utils.Round
import app.aaps.core.keys.BooleanKey
import app.aaps.core.keys.Preferences
import app.aaps.core.keys.StringKey
import app.aaps.core.objects.constraints.ConstraintObject
import app.aaps.core.objects.extensions.formatColor
import app.aaps.core.objects.extensions.highValueToUnitsToString
Expand All @@ -63,6 +66,7 @@ class BolusWizard @Inject constructor(
val injector: HasAndroidInjector
) {

@Inject lateinit var smsCommunicator: SmsCommunicator
@Inject lateinit var aapsLogger: AAPSLogger
@Inject lateinit var rh: ResourceHelper
@Inject lateinit var rxBus: RxBus
Expand All @@ -86,9 +90,12 @@ class BolusWizard @Inject constructor(
@Inject lateinit var processedDeviceStatusData: ProcessedDeviceStatusData

var timeStamp: Long
// var phoneNumber: String

init {
injector.androidInjector().inject(this)
// why [email protected] not visible in scoped DetailedBolusInfo().apply
// phoneNumber = preferences.get(StringKey.SmsReceiverNumber)
timeStamp = dateUtil.now()
}

Expand Down Expand Up @@ -330,7 +337,7 @@ class BolusWizard @Inject constructor(
}

private fun confirmMessageAfterConstraints(context: Context, advisor: Boolean, quickWizardEntry: QuickWizardEntry? = null): Spanned {

var phoneNumber = preferences.get(StringKey.SmsReceiverNumber)
val actions: LinkedList<String> = LinkedList()
if (insulinAfterConstraints > 0) {
val pct = if (percentageCorrection != 100) " ($percentageCorrection%)" else ""
Expand Down Expand Up @@ -371,7 +378,10 @@ class BolusWizard @Inject constructor(
.formatColor(context, rh, app.aaps.core.ui.R.attr.warningColor)
)
if (config.NSCLIENT && insulinAfterConstraints > 0)
actions.add(rh.gs(app.aaps.core.ui.R.string.bolus_recorded_only).formatColor(context, rh, app.aaps.core.ui.R.attr.warningColor))
if (preferences.get(BooleanKey.SmsAllowRemoteCommands) && !phoneNumber.isNullOrBlank())
actions.add(rh.gs(app.aaps.core.ui.R.string.sms_bolus_notification).formatColor(context, rh, app.aaps.core.ui.R.attr.warningColor))
else
actions.add(rh.gs(app.aaps.core.ui.R.string.bolus_recorded_only).formatColor(context, rh, app.aaps.core.ui.R.attr.warningColor))
if (useAlarm && !advisor && carbs > 0 && carbTime > 0)
actions.add(rh.gs(app.aaps.core.ui.R.string.alarminxmin, carbTime).formatColor(context, rh, app.aaps.core.ui.R.attr.infoColor))
if (advisor)
Expand Down Expand Up @@ -538,6 +548,13 @@ class BolusWizard @Inject constructor(
ValueWithUnit.Minute(carbTime).takeIf { carbTime != 0 }
).filterNotNull()
)
var phoneNumber = preferences.get(StringKey.SmsReceiverNumber)
if (preferences.get(BooleanKey.SmsAllowRemoteCommands) && !phoneNumber.isNullOrBlank()) {
mushroom-dev marked this conversation as resolved.
Show resolved Hide resolved
rh.gs(app.aaps.core.ui.R.string.sms_bolus_notification).formatColor(context, rh, app.aaps.core.ui.R.attr.warningColor)
smsCommunicator.sendSMS(Sms(phoneNumber, rh.gs(app.aaps.core.ui.R.string.bolus) + " " + insulin))
insulin = 0.0 // commandQueue will process carbs
}

commandQueue.bolus(this, object : Callback() {
override fun run() {
if (!result.success) {
Expand Down
2 changes: 2 additions & 0 deletions core/ui/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -452,9 +452,11 @@
<string name="cobvsiob">COB vs IOB</string>
<string name="slowabsorptiondetected"><![CDATA[<font color=\'%1$s\'>!!!!! Slow carbs absorption detected: %2$d%% of time. Double check your calculation. COB can be overestimated thus more insulin could be given !!!!!</font>]]></string>
<string name="partialboluswizard">Deliver this part of bolus wizard result [%]</string>
<string name="sms_receiver_number">Receiver phone number for sms commands sent from AAPSClient phone</string>
<string name="partialboluswizard_reset_time">Old glycemia time threshold [min]</string>
<string name="bolus_constraint_applied_warn">Bolus constraint applied: %1$.2f U to %2$.2f U</string>
<string name="bolus_recorded_only">Bolus will be recorded only (not delivered by pump)</string>
<string name="sms_bolus_notification">Send sms with insulin request</string>
<string name="advisoralarm">Run alarm when is time to eat</string>
<string name="no_action_selected">No action selected, nothing will happen</string>
<string name="carb_equal_zero_no_action">Carbs = 0. No action taken!</string>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,10 +41,13 @@ import app.aaps.core.objects.extensions.putString
import app.aaps.core.objects.extensions.store
import app.aaps.core.objects.extensions.storeBoolean
import app.aaps.core.objects.extensions.storeString
import app.aaps.core.validators.DefaultEditTextValidator
import app.aaps.core.validators.EditTextValidator
import app.aaps.core.validators.preferences.AdaptiveClickPreference
import app.aaps.core.validators.preferences.AdaptiveDoublePreference
import app.aaps.core.validators.preferences.AdaptiveIntPreference
import app.aaps.core.validators.preferences.AdaptiveIntentPreference
import app.aaps.core.validators.preferences.AdaptiveStringPreference
import app.aaps.core.validators.preferences.AdaptiveSwitchPreference
import app.aaps.core.validators.preferences.AdaptiveUnitPreference
import app.aaps.plugins.main.R
Expand Down Expand Up @@ -219,6 +222,13 @@ class OverviewPlugin @Inject constructor(
addPreference(AdaptiveSwitchPreference(ctx = context, booleanKey = BooleanKey.OverviewShowTreatmentButton, title = R.string.treatments))
addPreference(AdaptiveSwitchPreference(ctx = context, booleanKey = BooleanKey.OverviewShowWizardButton, title = R.string.calculator_label))
addPreference(AdaptiveSwitchPreference(ctx = context, booleanKey = BooleanKey.OverviewShowInsulinButton, title = app.aaps.core.ui.R.string.configbuilder_insulin))
addPreference(AdaptiveSwitchPreference(ctx = context, booleanKey = BooleanKey.SmsAllowRemoteCommands, summary = R.string.client_allow_sms_warning, title = R.string.client_allow_sms))
addPreference(
AdaptiveStringPreference(
ctx = context, stringKey = StringKey.SmsReceiverNumber, dialogMessage = R.string.sms_receiver_number_dialog, title = app.aaps.core.ui.R.string.sms_receiver_number,
validatorParams = DefaultEditTextValidator.Parameters(testType = EditTextValidator.TEST_PHONE)
)
)
addPreference(AdaptiveDoublePreference(ctx = context, doubleKey = DoubleKey.OverviewInsulinButtonIncrement1, dialogMessage = R.string.insulin_increment_button_message, title = R.string.firstinsulinincrement))
addPreference(AdaptiveDoublePreference(ctx = context, doubleKey = DoubleKey.OverviewInsulinButtonIncrement2, dialogMessage = R.string.insulin_increment_button_message, title = R.string.secondinsulinincrement))
addPreference(AdaptiveDoublePreference(ctx = context, doubleKey = DoubleKey.OverviewInsulinButtonIncrement3, dialogMessage = R.string.insulin_increment_button_message, title = R.string.thirdinsulinincrement))
Expand Down Expand Up @@ -279,13 +289,17 @@ class OverviewPlugin @Inject constructor(
addPreference(AdaptiveIntPreference(ctx = context, intKey = IntKey.OverviewResCritical, title = R.string.statuslights_res_critical))
addPreference(AdaptiveIntPreference(ctx = context, intKey = IntKey.OverviewBattWarning, title = R.string.statuslights_bat_warning))
addPreference(AdaptiveIntPreference(ctx = context, intKey = IntKey.OverviewBattCritical, title = R.string.statuslights_bat_critical))
addPreference(AdaptiveClickPreference(ctx = context, stringKey = StringKey.OverviewCopySettingsFromNs, title = R.string.statuslights_copy_ns,
onPreferenceClickListener = {
nsSettingStatus.copyStatusLightsNsSettings(context)
true
}))
addPreference(
AdaptiveClickPreference(ctx = context, stringKey = StringKey.OverviewCopySettingsFromNs, title = R.string.statuslights_copy_ns,
onPreferenceClickListener = {
nsSettingStatus.copyStatusLightsNsSettings(context)
true
})
)
})
addPreference(AdaptiveIntPreference(ctx = context, intKey = IntKey.OverviewBolusPercentage, dialogMessage = R.string.deliverpartofboluswizard, title = app.aaps.core.ui.R.string.partialboluswizard))


addPreference(AdaptiveIntPreference(ctx = context, intKey = IntKey.OverviewResetBolusPercentageTime, dialogMessage = R.string.deliver_part_of_boluswizard_reset_time, title = app.aaps.core.ui.R.string.partialboluswizard_reset_time))
addPreference(AdaptiveSwitchPreference(ctx = context, booleanKey = BooleanKey.OverviewUseBolusAdvisor, summary = R.string.enable_bolus_advisor_summary, title = R.string.enable_bolus_advisor))
addPreference(AdaptiveSwitchPreference(ctx = context, booleanKey = BooleanKey.OverviewUseBolusReminder, summary = R.string.enablebolusreminder_summary, title = R.string.enablebolusreminder))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -933,11 +933,12 @@ class SmsCommunicatorPlugin @Inject constructor(
if (divided.size == 3 && !isMeal) {
sendSMS(Sms(receivedSms.phoneNumber, rh.gs(R.string.wrong_format)))
} else if (bolus > 0.0) {
val iob = iobCobCalculator.calculateIobFromBolus().round().iob + iobCobCalculator.calculateIobFromTempBasalsIncludingConvertedExtended().round().basaliob
val passCode = generatePassCode()
val reply = if (isMeal)
rh.gs(R.string.smscommunicator_meal_bolus_reply_with_code, bolus, passCode)
rh.gs(R.string.smscommunicator_meal_bolus_reply_with_code, bolus, passCode, iob)
else
rh.gs(R.string.smscommunicator_bolus_reply_with_code, bolus, passCode)
rh.gs(R.string.smscommunicator_bolus_reply_with_code, bolus, passCode, iob)
receivedSms.processed = true
messageToConfirm = AuthRequest(injector, receivedSms, reply, passCode, object : SmsAction(pumpCommand = true, bolus) {
override fun run() {
Expand Down
13 changes: 8 additions & 5 deletions plugins/main/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
<resources>

<!-- SMS Communicator & OTP Authenticator -->

<string name="smscommunicator">SMS Communicator</string>
<string name="smscommunicator_shortname">SMS</string>
<string name="description_sms_communicator">Remote control AAPS using SMS commands.</string>
Expand Down Expand Up @@ -34,8 +33,8 @@
<string name="sms_timeout_while_waiting">Timeout while waiting for finish of previous pump communication</string>
<string name="smscommunicator_allowednumbers">Allowed phone numbers</string>
<string name="smscommunicator_allowednumbers_summary">+XXXXXXXXXX;+YYYYYYYYYY</string>
<string name="smscommunicator_bolus_reply_with_code">To deliver bolus %1$.2fU reply with code %2$s</string>
<string name="smscommunicator_meal_bolus_reply_with_code">To deliver meal bolus %1$.2fU reply with code %2$s</string>
<string name="smscommunicator_bolus_reply_with_code">To deliver bolus %1$.2fU reply with code %2$s. Current IOB is %3$.2fU</string>
<string name="smscommunicator_meal_bolus_reply_with_code">To deliver meal bolus %1$.2fU reply with code %2$s. Current IOB is %3$.2fU</string>
<string name="smscommunicator_temptarget_with_code">To set the Temp Target %1$s reply with code %2$s</string>
<string name="smscommunicator_temptarget_cancel">To cancel Temp Target reply with code %1$s</string>
<string name="smscommunicator_stops_ns_with_code">To disable the SMS Remote Service reply with code %1$s.\n\nKeep in mind that you\'ll able to reactivate it directly from the AAPS master smartphone only.</string>
Expand Down Expand Up @@ -186,7 +185,7 @@
<string name="statuslights_patch_pump_age">patch pump age</string>
<string name="patch_pump">Patch pump</string>

<!-- Overview -->
<!-- Overview Preferences -->
<string name="show_statuslights">Show status lights on home screen</string>
<string name="statuslights_cage_warning">Threshold warning cannula age [h]</string>
<string name="statuslights_cage_critical">Threshold critical cannula age [h]</string>
Expand Down Expand Up @@ -276,8 +275,12 @@
<string name="enablebolusreminder">Enable bolus reminder</string>
<string name="enablebolusreminder_summary">Use reminder to bolus later with wizard ("post-bolus")</string>
<string name="run_question">Run %s?</string>
<!-- AAPSClient sms related settings-->
<string name="sms_receiver_number_dialog">If number is provided, insulin and calculator buttons will be able to send SMS command to inject bolus. Note that you still need to confirm it and reply with security token/code. Note that you need to enabled SMS control of AAPS phone to use this function.</string>
<string name="client_allow_sms">Allow AAPSClient to send SMS with bolus command</string>
<string name="client_allow_sms_warning">"Use this functionality with caution. Before enabling make sure that IOB and BG is synchronized between AAPS and AAPSClient. Some users reported issue with that. Use it at your own risk, every time you shall check IOB and BG before issuing a bolus. You can do that by sending 'BG' command."</string>

<!-- OverviewMenu-->
<!-- OverviewMenu-->
<string name="key_graph_config" translatable="false">graphconfig</string>
<string name="overview_show_predictions">Predictions</string>
<string name="overview_show_treatments">Treatments</string>
Expand Down
24 changes: 22 additions & 2 deletions ui/src/main/kotlin/app/aaps/ui/dialogs/InsulinDialog.kt
Original file line number Diff line number Diff line change
Expand Up @@ -30,11 +30,15 @@ import app.aaps.core.interfaces.pump.defs.determineCorrectBolusStepSize
import app.aaps.core.interfaces.queue.Callback
import app.aaps.core.interfaces.queue.CommandQueue
import app.aaps.core.interfaces.resources.ResourceHelper
import app.aaps.core.interfaces.smsCommunicator.Sms
import app.aaps.core.interfaces.smsCommunicator.SmsCommunicator
import app.aaps.core.interfaces.ui.UiInteraction
import app.aaps.core.interfaces.utils.DecimalFormatter
import app.aaps.core.interfaces.utils.SafeParse
import app.aaps.core.keys.BooleanKey
import app.aaps.core.keys.DoubleKey
import app.aaps.core.keys.IntKey
import app.aaps.core.keys.StringKey
import app.aaps.core.keys.UnitDoubleKey
import app.aaps.core.objects.constraints.ConstraintObject
import app.aaps.core.objects.extensions.formatColor
Expand All @@ -58,6 +62,7 @@ import kotlin.math.max

class InsulinDialog : DialogFragmentWithDate() {

@Inject lateinit var smsCommunicator: SmsCommunicator
@Inject lateinit var constraintChecker: ConstraintsChecker
@Inject lateinit var rh: ResourceHelper
@Inject lateinit var profileFunction: ProfileFunction
Expand Down Expand Up @@ -125,8 +130,16 @@ class InsulinDialog : DialogFragmentWithDate() {

val pump = activePlugin.activePump
if (config.NSCLIENT) {
binding.recordOnly.isChecked = true
binding.recordOnly.isEnabled = false
// If SmsAllowRemoteCommands is True and valid phone number is provided. then user might use either SMS command or record only.
// Hardcode record_only option otherwise
val allowSms = preferences.get(BooleanKey.SmsAllowRemoteCommands)
if(allowSms) {
binding.recordOnly.isEnabled = !preferences.get(StringKey.SmsReceiverNumber).isNullOrBlank()
binding.recordOnly.isChecked = preferences.get(StringKey.SmsReceiverNumber).isNullOrBlank()
} else {
binding.recordOnly.isEnabled = false
binding.recordOnly.isChecked = true
}
}
val maxInsulin = constraintChecker.getMaxBolusAllowed().value()

Expand Down Expand Up @@ -197,8 +210,10 @@ class InsulinDialog : DialogFragmentWithDate() {
val actions: LinkedList<String?> = LinkedList()
val units = profileFunction.getUnits()
val unitLabel = if (units == GlucoseUnit.MMOL) rh.gs(app.aaps.core.ui.R.string.mmol) else rh.gs(app.aaps.core.ui.R.string.mgdl)
val phoneNumber = preferences.get(StringKey.SmsReceiverNumber)
val recordOnlyChecked = binding.recordOnly.isChecked
val eatingSoonChecked = binding.startEatingSoonTt.isChecked
val sendSMS = preferences.get(BooleanKey.SmsAllowRemoteCommands) && !phoneNumber.isNullOrBlank()

if (insulinAfterConstraints > 0) {
actions.add(
Expand All @@ -207,6 +222,9 @@ class InsulinDialog : DialogFragmentWithDate() {
)
if (recordOnlyChecked)
actions.add(rh.gs(app.aaps.core.ui.R.string.bolus_recorded_only).formatColor(context, rh, app.aaps.core.ui.R.attr.warningColor))
else if (sendSMS)
actions.add(rh.gs(app.aaps.core.ui.R.string.sms_bolus_notification).formatColor(context, rh, app.aaps.core.ui.R.attr.warningColor))

if (abs(insulinAfterConstraints - insulin) > pumpDescription.pumpType.determineCorrectBolusStepSize(insulinAfterConstraints))
actions.add(
rh.gs(app.aaps.core.ui.R.string.bolus_constraint_applied_warn, insulin, insulinAfterConstraints).formatColor(context, rh, app.aaps.core.ui.R.attr.warningColor)
Expand Down Expand Up @@ -269,6 +287,8 @@ class InsulinDialog : DialogFragmentWithDate() {
).subscribe()
if (timeOffset == 0)
automation.removeAutomationEventBolusReminder()
} else if (sendSMS) {
smsCommunicator.sendSMS(Sms(phoneNumber, rh.gs(app.aaps.core.ui.R.string.bolus) + " " + detailedBolusInfo.insulin))
} else {
uel.log(
Action.BOLUS, Sources.InsulinDialog,
Expand Down
Loading