cleanup, hook to preferences change

This commit is contained in:
Milos Kozak 2019-06-07 11:07:08 +02:00
parent 01006b32ce
commit 643ddfae52
8 changed files with 111 additions and 79 deletions

View file

@ -30,7 +30,7 @@ public class TidepoolJavaFragment extends SubscriberFragment {
Button login = view.findViewById(R.id.tidepool_login); Button login = view.findViewById(R.id.tidepool_login);
login.setOnClickListener(v1 -> { login.setOnClickListener(v1 -> {
TidepoolUploader.INSTANCE.doLogin(); TidepoolUploader.INSTANCE.doLogin(false);
}); });
Button uploadnow = view.findViewById(R.id.tidepool_uploadnow); Button uploadnow = view.findViewById(R.id.tidepool_uploadnow);
uploadnow.setOnClickListener(v2 -> MainApp.bus().post(new EventTidepoolDoUpload())); uploadnow.setOnClickListener(v2 -> MainApp.bus().post(new EventTidepoolDoUpload()));

View file

@ -6,6 +6,8 @@ import info.nightscout.androidaps.Constants
import info.nightscout.androidaps.MainApp import info.nightscout.androidaps.MainApp
import info.nightscout.androidaps.R import info.nightscout.androidaps.R
import info.nightscout.androidaps.events.EventNetworkChange import info.nightscout.androidaps.events.EventNetworkChange
import info.nightscout.androidaps.events.EventNewBG
import info.nightscout.androidaps.events.EventPreferenceChange
import info.nightscout.androidaps.interfaces.PluginBase import info.nightscout.androidaps.interfaces.PluginBase
import info.nightscout.androidaps.interfaces.PluginDescription import info.nightscout.androidaps.interfaces.PluginDescription
import info.nightscout.androidaps.interfaces.PluginType import info.nightscout.androidaps.interfaces.PluginType
@ -16,8 +18,8 @@ import info.nightscout.androidaps.plugins.general.tidepool.events.EventTidepoolR
import info.nightscout.androidaps.plugins.general.tidepool.events.EventTidepoolStatus import info.nightscout.androidaps.plugins.general.tidepool.events.EventTidepoolStatus
import info.nightscout.androidaps.plugins.general.tidepool.events.EventTidepoolUpdateGUI import info.nightscout.androidaps.plugins.general.tidepool.events.EventTidepoolUpdateGUI
import info.nightscout.androidaps.plugins.general.tidepool.utils.RateLimit import info.nightscout.androidaps.plugins.general.tidepool.utils.RateLimit
import info.nightscout.androidaps.plugins.iob.iobCobCalculator.events.EventAutosensCalculationFinished
import info.nightscout.androidaps.receivers.ChargingStateReceiver import info.nightscout.androidaps.receivers.ChargingStateReceiver
import info.nightscout.androidaps.receivers.NetworkChangeReceiver
import info.nightscout.androidaps.utils.SP import info.nightscout.androidaps.utils.SP
import info.nightscout.androidaps.utils.T import info.nightscout.androidaps.utils.T
import info.nightscout.androidaps.utils.ToastUtils import info.nightscout.androidaps.utils.ToastUtils
@ -33,13 +35,11 @@ object TidepoolPlugin : PluginBase(PluginDescription()
.description(R.string.description_tidepool) .description(R.string.description_tidepool)
) { ) {
private val log = LoggerFactory.getLogger(L.TIDEPOOL) private val log = LoggerFactory.getLogger(L.TIDEPOOL)
private var wifiConnected = false
private val listLog = ArrayList<EventTidepoolStatus>() private val listLog = ArrayList<EventTidepoolStatus>()
@Suppress("DEPRECATION") // API level 24 to replace call
var textLog = Html.fromHtml("") var textLog = Html.fromHtml("")
var paused: Boolean = false
override fun onStart() { override fun onStart() {
MainApp.bus().register(this) MainApp.bus().register(this)
super.onStart() super.onStart()
@ -52,17 +52,19 @@ object TidepoolPlugin : PluginBase(PluginDescription()
fun doUpload() { fun doUpload() {
if (TidepoolUploader.connectionStatus == TidepoolUploader.ConnectionStatus.DISCONNECTED) if (TidepoolUploader.connectionStatus == TidepoolUploader.ConnectionStatus.DISCONNECTED)
TidepoolUploader.doLogin() TidepoolUploader.doLogin(true)
else else
TidepoolUploader.doUpload() TidepoolUploader.doUpload()
} }
@Suppress("UNUSED_PARAMETER") @Suppress("UNUSED_PARAMETER")
@Subscribe @Subscribe
fun onStatusEvent(ev: EventAutosensCalculationFinished) { fun onStatusEvent(ev: EventNewBG) {
if (ev.bgReading!!.date!! < TidepoolUploader.getLastEnd())
TidepoolUploader.setLastEnd(ev.bgReading!!.date!!)
if (isEnabled(PluginType.GENERAL) if (isEnabled(PluginType.GENERAL)
&& (!SP.getBoolean(R.string.key_tidepool_only_while_charging, false) || ChargingStateReceiver.isCharging()) && (!SP.getBoolean(R.string.key_tidepool_only_while_charging, false) || ChargingStateReceiver.isCharging())
&& (!SP.getBoolean(R.string.key_tidepool_only_while_unmetered, false) || wifiConnected) && (!SP.getBoolean(R.string.key_tidepool_only_while_unmetered, false) || NetworkChangeReceiver.isWifiConnected())
&& RateLimit.ratelimit("tidepool-new-data-upload", T.mins(4).secs().toInt())) && RateLimit.ratelimit("tidepool-new-data-upload", T.mins(4).secs().toInt()))
doUpload() doUpload()
} }
@ -73,6 +75,15 @@ object TidepoolPlugin : PluginBase(PluginDescription()
doUpload() doUpload()
} }
@Subscribe
fun onEventPreferenceChange(ev: EventPreferenceChange) {
if (ev.isChanged(R.string.key_tidepool_dev_servers)
|| ev.isChanged(R.string.key_tidepool_username)
|| ev.isChanged(R.string.key_tidepool_password)
)
TidepoolUploader.resetInstance()
}
@Suppress("UNUSED_PARAMETER") @Suppress("UNUSED_PARAMETER")
@Subscribe @Subscribe
fun onEventTidepoolResetData(ev: EventTidepoolResetData) { fun onEventTidepoolResetData(ev: EventTidepoolResetData) {
@ -87,7 +98,7 @@ object TidepoolPlugin : PluginBase(PluginDescription()
@Subscribe @Subscribe
fun onEventNetworkChange(ev: EventNetworkChange) { fun onEventNetworkChange(ev: EventNetworkChange) {
wifiConnected = ev.wifiConnected // TODO start upload on wifi connect
} }
@Subscribe @Subscribe
@ -116,6 +127,7 @@ object TidepoolPlugin : PluginBase(PluginDescription()
newTextLog.append(log.toPreparedHtml()) newTextLog.append(log.toPreparedHtml())
} }
} }
@Suppress("DEPRECATION") // API level 24 to replace call
textLog = Html.fromHtml(newTextLog.toString()) textLog = Html.fromHtml(newTextLog.toString())
} catch (e: OutOfMemoryError) { } catch (e: OutOfMemoryError) {
ToastUtils.showToastInUiThread(MainApp.instance().applicationContext, "Out of memory!\nStop using this phone !!!", R.raw.error) ToastUtils.showToastInUiThread(MainApp.instance().applicationContext, "Out of memory!\nStop using this phone !!!", R.raw.error)

View file

@ -6,11 +6,12 @@ import info.nightscout.androidaps.BuildConfig
import info.nightscout.androidaps.MainApp import info.nightscout.androidaps.MainApp
import info.nightscout.androidaps.R import info.nightscout.androidaps.R
import info.nightscout.androidaps.logging.L import info.nightscout.androidaps.logging.L
import info.nightscout.androidaps.plugins.general.tidepool.TidepoolPlugin
import info.nightscout.androidaps.plugins.general.tidepool.events.EventTidepoolStatus import info.nightscout.androidaps.plugins.general.tidepool.events.EventTidepoolStatus
import info.nightscout.androidaps.plugins.general.tidepool.messages.* import info.nightscout.androidaps.plugins.general.tidepool.messages.*
import info.nightscout.androidaps.utils.DateUtil
import info.nightscout.androidaps.utils.OKDialog import info.nightscout.androidaps.utils.OKDialog
import info.nightscout.androidaps.utils.SP import info.nightscout.androidaps.utils.SP
import info.nightscout.androidaps.utils.T
import okhttp3.MediaType import okhttp3.MediaType
import okhttp3.OkHttpClient import okhttp3.OkHttpClient
import okhttp3.RequestBody import okhttp3.RequestBody
@ -64,10 +65,11 @@ object TidepoolUploader {
retrofit = null retrofit = null
if (L.isEnabled(L.TIDEPOOL)) if (L.isEnabled(L.TIDEPOOL))
log.debug("Instance reset") log.debug("Instance reset")
connectionStatus = TidepoolUploader.ConnectionStatus.DISCONNECTED
} }
@Synchronized @Synchronized
fun doLogin() { fun doLogin(doUpload: Boolean = false) {
if (connectionStatus == TidepoolUploader.ConnectionStatus.CONNECTED || connectionStatus == TidepoolUploader.ConnectionStatus.CONNECTING) { if (connectionStatus == TidepoolUploader.ConnectionStatus.CONNECTED || connectionStatus == TidepoolUploader.ConnectionStatus.CONNECTING) {
if (L.isEnabled(L.TIDEPOOL)) if (L.isEnabled(L.TIDEPOOL))
log.debug("Already connected") log.debug("Already connected")
@ -78,11 +80,11 @@ object TidepoolUploader {
session = Session(AuthRequestMessage.getAuthRequestHeader(), SESSION_TOKEN_HEADER) session = Session(AuthRequestMessage.getAuthRequestHeader(), SESSION_TOKEN_HEADER)
if (session?.authHeader != null) { if (session?.authHeader != null) {
connectionStatus = TidepoolUploader.ConnectionStatus.CONNECTING connectionStatus = TidepoolUploader.ConnectionStatus.CONNECTING
status("Connecting") MainApp.bus().post(EventTidepoolStatus(("Connecting")))
val call = session!!.service?.getLogin(session?.authHeader!!) val call = session!!.service?.getLogin(session?.authHeader!!)
call?.enqueue(TidepoolCallback<AuthReplyMessage>(session!!, "Login", { call?.enqueue(TidepoolCallback<AuthReplyMessage>(session!!, "Login", {
startSession(session!!) startSession(session!!, doUpload)
}, { }, {
connectionStatus = TidepoolUploader.ConnectionStatus.FAILED; connectionStatus = TidepoolUploader.ConnectionStatus.FAILED;
loginFailed() loginFailed()
@ -91,7 +93,7 @@ object TidepoolUploader {
} else { } else {
if (L.isEnabled(L.TIDEPOOL)) log.debug("Cannot do login as user credentials have not been set correctly") if (L.isEnabled(L.TIDEPOOL)) log.debug("Cannot do login as user credentials have not been set correctly")
connectionStatus = TidepoolUploader.ConnectionStatus.FAILED; connectionStatus = TidepoolUploader.ConnectionStatus.FAILED;
status("Invalid credentials") MainApp.bus().post(EventTidepoolStatus(("Invalid credentials")))
releaseWakeLock() releaseWakeLock()
return return
} }
@ -119,7 +121,7 @@ object TidepoolUploader {
releaseWakeLock() releaseWakeLock()
} }
fun startSession(session: Session) { fun startSession(session: Session, doUpload: Boolean = false) {
extendWakeLock(30000) extendWakeLock(30000)
if (session.authReply?.userid != null) { if (session.authReply?.userid != null) {
// See if we already have an open data set to write to // See if we already have an open data set to write to
@ -128,14 +130,15 @@ object TidepoolUploader {
datasetCall.enqueue(TidepoolCallback<List<DatasetReplyMessage>>(session, "Get Open Datasets", { datasetCall.enqueue(TidepoolCallback<List<DatasetReplyMessage>>(session, "Get Open Datasets", {
if (session.datasetReply == null) { if (session.datasetReply == null) {
status("Creating new dataset") MainApp.bus().post(EventTidepoolStatus(("Creating new dataset")))
val call = session.service.openDataSet(session.token!!, session.authReply!!.userid!!, OpenDatasetRequestMessage().getBody()) val call = session.service.openDataSet(session.token!!, session.authReply!!.userid!!, OpenDatasetRequestMessage().getBody())
call.enqueue(TidepoolCallback<DatasetReplyMessage>(session, "Open New Dataset", { call.enqueue(TidepoolCallback<DatasetReplyMessage>(session, "Open New Dataset", {
connectionStatus = TidepoolUploader.ConnectionStatus.CONNECTED; connectionStatus = TidepoolUploader.ConnectionStatus.CONNECTED;
status("New dataset OK") MainApp.bus().post(EventTidepoolStatus(("New dataset OK")))
if (doUpload) doUpload()
releaseWakeLock() releaseWakeLock()
}, { }, {
status("New dataset FAILED") MainApp.bus().post(EventTidepoolStatus(("New dataset FAILED")))
connectionStatus = TidepoolUploader.ConnectionStatus.FAILED; connectionStatus = TidepoolUploader.ConnectionStatus.FAILED;
releaseWakeLock() releaseWakeLock()
})) }))
@ -145,18 +148,19 @@ object TidepoolUploader {
// TODO: Wouldn't need to do this if we could block on the above `call.enqueue`. // TODO: Wouldn't need to do this if we could block on the above `call.enqueue`.
// ie, do the openDataSet conditionally, and then do `doUpload` either way. // ie, do the openDataSet conditionally, and then do `doUpload` either way.
connectionStatus = TidepoolUploader.ConnectionStatus.CONNECTED; connectionStatus = TidepoolUploader.ConnectionStatus.CONNECTED;
status("Appending to existing dataset") MainApp.bus().post(EventTidepoolStatus(("Appending to existing dataset")))
if (doUpload) doUpload()
releaseWakeLock() releaseWakeLock()
} }
}, { }, {
connectionStatus = TidepoolUploader.ConnectionStatus.FAILED; connectionStatus = TidepoolUploader.ConnectionStatus.FAILED;
status("Open dataset FAILED") MainApp.bus().post(EventTidepoolStatus(("Open dataset FAILED")))
releaseWakeLock() releaseWakeLock()
})) }))
} else { } else {
log.error("Got login response but cannot determine userid - cannot proceed") log.error("Got login response but cannot determine userid - cannot proceed")
connectionStatus = TidepoolUploader.ConnectionStatus.FAILED; connectionStatus = TidepoolUploader.ConnectionStatus.FAILED;
status("Error userid") MainApp.bus().post(EventTidepoolStatus(("Error userid")))
releaseWakeLock() releaseWakeLock()
} }
} }
@ -175,43 +179,36 @@ object TidepoolUploader {
releaseWakeLock() releaseWakeLock()
} else if (chunk.length == 2) { } else if (chunk.length == 2) {
if (L.isEnabled(L.TIDEPOOL)) log.debug("Empty dataset - marking as succeeded") if (L.isEnabled(L.TIDEPOOL)) log.debug("Empty dataset - marking as succeeded")
status("No data to upload") MainApp.bus().post(EventTidepoolStatus(("No data to upload")))
releaseWakeLock() releaseWakeLock()
} else { } else {
val body = RequestBody.create(MediaType.parse("application/json"), chunk) val body = RequestBody.create(MediaType.parse("application/json"), chunk)
status("Uploading") MainApp.bus().post(EventTidepoolStatus(("Uploading")))
val call = session!!.service!!.doUpload(session!!.token!!, session!!.datasetReply!!.getUploadId()!!, body) val call = session!!.service!!.doUpload(session!!.token!!, session!!.datasetReply!!.getUploadId()!!, body)
call.enqueue(TidepoolCallback<UploadReplyMessage>(session!!, "Data Upload", { call.enqueue(TidepoolCallback<UploadReplyMessage>(session!!, "Data Upload", {
UploadChunk.setLastEnd(session!!.end) setLastEnd(session!!.end)
status("Upload completed OK") MainApp.bus().post(EventTidepoolStatus(("Upload completed OK")))
releaseWakeLock() releaseWakeLock()
}, { }, {
status("Upload FAILED") MainApp.bus().post(EventTidepoolStatus(("Upload FAILED")))
releaseWakeLock() releaseWakeLock()
})) }))
} }
} }
fun status(status: String) {
if (L.isEnabled(L.TIDEPOOL))
log.debug("New status: $status")
MainApp.bus().post(EventTidepoolStatus(status))
}
fun deleteDataSet() { fun deleteDataSet() {
if (session?.datasetReply?.id != null) { if (session?.datasetReply?.id != null) {
extendWakeLock(60000) extendWakeLock(60000)
val call = session!!.service?.deleteDataSet(session!!.token!!, session!!.datasetReply!!.id!!) val call = session!!.service?.deleteDataSet(session!!.token!!, session!!.datasetReply!!.id!!)
call?.enqueue(TidepoolCallback(session!!, "Delete Dataset", { call?.enqueue(TidepoolCallback(session!!, "Delete Dataset", {
connectionStatus = TidepoolUploader.ConnectionStatus.DISCONNECTED connectionStatus = TidepoolUploader.ConnectionStatus.DISCONNECTED
status("Dataset removed OK") MainApp.bus().post(EventTidepoolStatus(("Dataset removed OK")))
releaseWakeLock() releaseWakeLock()
}, { }, {
connectionStatus = TidepoolUploader.ConnectionStatus.DISCONNECTED connectionStatus = TidepoolUploader.ConnectionStatus.DISCONNECTED
status("Dataset remove FAILED") MainApp.bus().post(EventTidepoolStatus(("Dataset remove FAILED")))
releaseWakeLock() releaseWakeLock()
})) }))
} else { } else {
@ -219,6 +216,23 @@ object TidepoolUploader {
} }
} }
fun getLastEnd(): Long {
val result = SP.getLong(R.string.key_tidepool_last_end, 0)
return Math.max(result, DateUtil.now() - T.months(2).msecs())
}
fun setLastEnd(time: Long) {
if (time > getLastEnd()) {
SP.putLong(R.string.key_tidepool_last_end, time)
val friendlyEnd = DateUtil.dateAndTimeString(time)
MainApp.bus().post(EventTidepoolStatus(("Marking uploaded data up to $friendlyEnd")))
if (L.isEnabled(L.TIDEPOOL)) log.debug("Updating last end to: " + DateUtil.dateAndTimeString(time))
} else {
if (L.isEnabled(L.TIDEPOOL)) log.debug("Cannot set last end to: " + DateUtil.dateAndTimeString(time) + " vs " + DateUtil.dateAndTimeString(getLastEnd()))
}
}
@Synchronized @Synchronized
private fun extendWakeLock(ms: Long) { private fun extendWakeLock(ms: Long) {
if (wl == null) { if (wl == null) {

View file

@ -1,13 +1,12 @@
package info.nightscout.androidaps.plugins.general.tidepool.comm package info.nightscout.androidaps.plugins.general.tidepool.comm
import info.nightscout.androidaps.MainApp import info.nightscout.androidaps.MainApp
import info.nightscout.androidaps.R
import info.nightscout.androidaps.logging.L import info.nightscout.androidaps.logging.L
import info.nightscout.androidaps.plugins.general.tidepool.elements.* import info.nightscout.androidaps.plugins.general.tidepool.elements.*
import info.nightscout.androidaps.plugins.general.tidepool.events.EventTidepoolStatus
import info.nightscout.androidaps.plugins.general.tidepool.utils.GsonInstance import info.nightscout.androidaps.plugins.general.tidepool.utils.GsonInstance
import info.nightscout.androidaps.plugins.treatments.TreatmentsPlugin import info.nightscout.androidaps.plugins.treatments.TreatmentsPlugin
import info.nightscout.androidaps.utils.DateUtil import info.nightscout.androidaps.utils.DateUtil
import info.nightscout.androidaps.utils.SP
import info.nightscout.androidaps.utils.T import info.nightscout.androidaps.utils.T
import org.slf4j.LoggerFactory import org.slf4j.LoggerFactory
import java.util.* import java.util.*
@ -22,13 +21,13 @@ object UploadChunk {
if (session == null) if (session == null)
return null return null
session.start = getLastEnd() session.start = TidepoolUploader.getLastEnd()
session.end = Math.min(session.start + MAX_UPLOAD_SIZE, DateUtil.now()) session.end = Math.min(session.start + MAX_UPLOAD_SIZE, DateUtil.now())
val result = get(session.start, session.end) val result = get(session.start, session.end)
if (result.length < 3) { if (result.length < 3) {
if (L.isEnabled(L.TIDEPOOL)) log.debug("No records in this time period, setting start to best end time") if (L.isEnabled(L.TIDEPOOL)) log.debug("No records in this time period, setting start to best end time")
setLastEnd(Math.max(session.end, getOldestRecordTimeStamp())) TidepoolUploader.setLastEnd(Math.max(session.end, getOldestRecordTimeStamp()))
} }
return result return result
} }
@ -56,22 +55,6 @@ object UploadChunk {
return GsonInstance.defaultGsonInstance().toJson(records) return GsonInstance.defaultGsonInstance().toJson(records)
} }
fun getLastEnd(): Long {
val result = SP.getLong(R.string.key_tidepool_last_end, 0)
return Math.max(result, DateUtil.now() - T.months(2).msecs())
}
fun setLastEnd(time: Long) {
if (time > getLastEnd()) {
SP.putLong(R.string.key_tidepool_last_end, time)
val friendlyEnd = DateUtil.dateAndTimeString(time)
TidepoolUploader.status("Marking uploaded data up to $friendlyEnd")
if (L.isEnabled(L.TIDEPOOL)) log.debug("Updating last end to: " + DateUtil.dateAndTimeString(time))
} else {
if (L.isEnabled(L.TIDEPOOL)) log.debug("Cannot set last end to: " + DateUtil.dateAndTimeString(time) + " vs " + DateUtil.dateAndTimeString(getLastEnd()))
}
}
// numeric limits must match max time windows // numeric limits must match max time windows
private fun getOldestRecordTimeStamp(): Long { private fun getOldestRecordTimeStamp(): Long {
@ -99,39 +82,41 @@ object UploadChunk {
return result return result
} }
internal fun getBloodTests(start: Long, end: Long): List<BloodGlucoseElement> { internal fun getBloodTests(start: Long, end: Long): List<BloodGlucoseElement> {
val readings = MainApp.getDbHelper().getCareportalEvents(start, end, true) val readings = MainApp.getDbHelper().getCareportalEvents(start, end, true)
if (L.isEnabled(L.TIDEPOOL)) val selection = BloodGlucoseElement.fromCareportalEvents(readings)
log.debug("${readings.size} CPs selected for upload") if (selection.isNotEmpty())
return BloodGlucoseElement.fromCareportalEvents(readings) MainApp.bus().post(EventTidepoolStatus("${selection.size} BGs selected for upload"))
return selection
} }
internal fun getBgReadings(start: Long, end: Long): List<SensorGlucoseElement> { internal fun getBgReadings(start: Long, end: Long): List<SensorGlucoseElement> {
val readings = MainApp.getDbHelper().getBgreadingsDataFromTime(start, end, true) val readings = MainApp.getDbHelper().getBgreadingsDataFromTime(start, end, true)
if (L.isEnabled(L.TIDEPOOL)) val selection = SensorGlucoseElement.fromBgReadings(readings)
log.debug("${readings.size} BGs selected for upload") if (selection.isNotEmpty())
return SensorGlucoseElement.fromBgReadings(readings) MainApp.bus().post(EventTidepoolStatus("${selection.size} CGMs selected for upload"))
return selection
} }
internal fun getBasals(start: Long, end: Long): List<BasalElement> { internal fun getBasals(start: Long, end: Long): List<BasalElement> {
val tbrs = MainApp.getDbHelper().getTemporaryBasalsDataFromTime(start, end, true) val tbrs = MainApp.getDbHelper().getTemporaryBasalsDataFromTime(start, end, true)
if (L.isEnabled(L.TIDEPOOL)) val selection = BasalElement.fromTemporaryBasals(tbrs)
log.debug("${tbrs.size} TBRs selected for upload") if (selection.isNotEmpty())
return BasalElement.fromTemporaryBasals(tbrs) MainApp.bus().post(EventTidepoolStatus("${selection.size} TBRs selected for upload"))
return selection
} }
internal fun getProfiles(start: Long, end: Long): List<ProfileElement> { internal fun getProfiles(start: Long, end: Long): List<ProfileElement> {
val pss = MainApp.getDbHelper().getProfileSwitchEventsFromTime(start, end, true) val pss = MainApp.getDbHelper().getProfileSwitchEventsFromTime(start, end, true)
if (L.isEnabled(L.TIDEPOOL)) val selection = LinkedList<ProfileElement>()
log.debug("${pss.size} ProfileSwitches selected for upload")
val results = LinkedList<ProfileElement>()
for (ps in pss) { for (ps in pss) {
val pe = ProfileElement(ps) val pe = ProfileElement(ps)
results.add(pe) selection.add(pe)
} }
return results if (selection.size > 0)
MainApp.bus().post(EventTidepoolStatus("${selection.size} ProfileSwitches selected for upload"))
return selection
} }
} }

View file

@ -1,13 +1,23 @@
package info.nightscout.androidaps.plugins.general.tidepool.events package info.nightscout.androidaps.plugins.general.tidepool.events
import info.nightscout.androidaps.events.Event import info.nightscout.androidaps.events.Event
import info.nightscout.androidaps.logging.L
import info.nightscout.androidaps.utils.DateUtil import info.nightscout.androidaps.utils.DateUtil
import info.nightscout.androidaps.utils.LocaleHelper
import org.slf4j.LoggerFactory
import java.text.SimpleDateFormat import java.text.SimpleDateFormat
class EventTidepoolStatus(val status: String) : Event() { class EventTidepoolStatus(val status: String) : Event() {
private val log = LoggerFactory.getLogger(L.TIDEPOOL)
var date: Long = DateUtil.now() var date: Long = DateUtil.now()
internal var timeFormat = SimpleDateFormat("HH:mm:ss") init {
if (L.isEnabled(L.TIDEPOOL))
log.debug("New status: $status")
}
internal var timeFormat = SimpleDateFormat("HH:mm:ss", LocaleHelper.getLocale())
fun toPreparedHtml(): StringBuilder { fun toPreparedHtml(): StringBuilder {
val stringBuilder = StringBuilder() val stringBuilder = StringBuilder()

View file

@ -21,6 +21,8 @@ public class NetworkChangeReceiver extends BroadcastReceiver {
private static Logger log = LoggerFactory.getLogger(L.CORE); private static Logger log = LoggerFactory.getLogger(L.CORE);
private static EventNetworkChange lastEvent = null;
@Override @Override
public void onReceive(final Context context, final Intent intent) { public void onReceive(final Context context, final Intent intent) {
EventNetworkChange event = grabNetworkStatus(context); EventNetworkChange event = grabNetworkStatus(context);
@ -61,6 +63,11 @@ public class NetworkChangeReceiver extends BroadcastReceiver {
log.debug("NETCHANGE: Disconnected."); log.debug("NETCHANGE: Disconnected.");
} }
lastEvent = event;
return event; return event;
} }
public static boolean isWifiConnected() {
return lastEvent != null && lastEvent.wifiConnected;
}
} }

View file

@ -121,7 +121,7 @@ public class FabricPrivacy {
.replace(".net/", ":"); .replace(".net/", ":");
MainApp.getFirebaseAnalytics().setUserProperty("Mode", BuildConfig.APPLICATION_ID + "-" + closedLoopEnabled); MainApp.getFirebaseAnalytics().setUserProperty("Mode", BuildConfig.APPLICATION_ID + "-" + closedLoopEnabled);
MainApp.getFirebaseAnalytics().setUserProperty("Language", LocaleHelper.getLanguage(MainApp.instance())); MainApp.getFirebaseAnalytics().setUserProperty("Language", LocaleHelper.getLanguage());
MainApp.getFirebaseAnalytics().setUserProperty("Version", BuildConfig.VERSION); MainApp.getFirebaseAnalytics().setUserProperty("Version", BuildConfig.VERSION);
MainApp.getFirebaseAnalytics().setUserProperty("HEAD", BuildConfig.HEAD); MainApp.getFirebaseAnalytics().setUserProperty("HEAD", BuildConfig.HEAD);
MainApp.getFirebaseAnalytics().setUserProperty("Remote", remote); MainApp.getFirebaseAnalytics().setUserProperty("Remote", remote);

View file

@ -21,17 +21,17 @@ public class LocaleHelper {
private static final String SELECTED_LANGUAGE = "Locale.Helper.Selected.Language"; private static final String SELECTED_LANGUAGE = "Locale.Helper.Selected.Language";
public static void onCreate(Context context) { public static void onCreate(Context context) {
String lang = getPersistedData(context, Locale.getDefault().getLanguage()); String lang = getPersistedData(Locale.getDefault().getLanguage());
setLocale(context, lang); setLocale(context, lang);
} }
public static void onCreate(Context context, String defaultLanguage) { public static void onCreate(Context context, String defaultLanguage) {
String lang = getPersistedData(context, defaultLanguage); String lang = getPersistedData(defaultLanguage);
setLocale(context, lang); setLocale(context, lang);
} }
public static String getLanguage(Context context) { public static String getLanguage() {
return getPersistedData(context, Locale.getDefault().getLanguage()); return getPersistedData(Locale.getDefault().getLanguage());
} }
public static void setLocale(Context context, String language) { public static void setLocale(Context context, String language) {
@ -39,7 +39,7 @@ public class LocaleHelper {
updateResources(context, language); updateResources(context, language);
} }
private static String getPersistedData(Context context, String defaultLanguage) { private static String getPersistedData(String defaultLanguage) {
return SP.getString(SELECTED_LANGUAGE, defaultLanguage); return SP.getString(SELECTED_LANGUAGE, defaultLanguage);
} }
@ -62,4 +62,8 @@ public class LocaleHelper {
resources.updateConfiguration(configuration, resources.getDisplayMetrics()); resources.updateConfiguration(configuration, resources.getDisplayMetrics());
} }
public static Locale getLocale() {
return new Locale(getPersistedData("en"));
}
} }