NSClient -> kt

This commit is contained in:
Milos Kozak 2021-05-03 14:15:19 +02:00
parent c75d4e8e4e
commit 840de7b3b9
8 changed files with 391 additions and 472 deletions

View file

@ -28,7 +28,7 @@ class Objective3 @Inject constructor(injector: HasAndroidInjector) : Objective(i
}
override fun specialActionEnabled(): Boolean =
NSClientService.isConnected && NSClientService.hasWriteAuth
nsClientPlugin.nsClientService?.isConnected == true && nsClientPlugin.nsClientService?.hasWriteAuth == true
override fun specialAction(activity: FragmentActivity, input: String) {
objectivesPlugin.completeObjectives(activity, input)

View file

@ -1,320 +0,0 @@
package info.nightscout.androidaps.plugins.general.nsclient;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.os.Handler;
import android.os.HandlerThread;
import android.os.IBinder;
import android.text.Spanned;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.preference.PreferenceFragmentCompat;
import androidx.preference.SwitchPreference;
import java.util.ArrayList;
import java.util.List;
import javax.inject.Inject;
import javax.inject.Singleton;
import dagger.android.HasAndroidInjector;
import info.nightscout.androidaps.interfaces.Config;
import info.nightscout.androidaps.Constants;
import info.nightscout.androidaps.R;
import info.nightscout.androidaps.events.EventAppExit;
import info.nightscout.androidaps.events.EventChargingState;
import info.nightscout.androidaps.events.EventNetworkChange;
import info.nightscout.androidaps.events.EventPreferenceChange;
import info.nightscout.androidaps.interfaces.PluginBase;
import info.nightscout.androidaps.interfaces.PluginDescription;
import info.nightscout.androidaps.interfaces.PluginType;
import info.nightscout.androidaps.logging.AAPSLogger;
import info.nightscout.androidaps.logging.LTag;
import info.nightscout.androidaps.plugins.bus.RxBusWrapper;
import info.nightscout.androidaps.plugins.general.nsclient.data.AlarmAck;
import info.nightscout.androidaps.plugins.general.nsclient.data.NSAlarm;
import info.nightscout.androidaps.plugins.general.nsclient.events.EventNSClientNewLog;
import info.nightscout.androidaps.plugins.general.nsclient.events.EventNSClientResend;
import info.nightscout.androidaps.plugins.general.nsclient.events.EventNSClientStatus;
import info.nightscout.androidaps.plugins.general.nsclient.events.EventNSClientUpdateGUI;
import info.nightscout.androidaps.plugins.general.nsclient.services.NSClientService;
import info.nightscout.androidaps.utils.FabricPrivacy;
import info.nightscout.androidaps.utils.HtmlHelper;
import info.nightscout.androidaps.utils.ToastUtils;
import info.nightscout.androidaps.utils.buildHelper.BuildHelper;
import info.nightscout.androidaps.utils.resources.ResourceHelper;
import info.nightscout.androidaps.utils.rx.AapsSchedulers;
import info.nightscout.androidaps.utils.sharedPreferences.SP;
import io.reactivex.disposables.CompositeDisposable;
@Singleton
public class NSClientPlugin extends PluginBase {
private final CompositeDisposable disposable = new CompositeDisposable();
private final AAPSLogger aapsLogger;
private final RxBusWrapper rxBus;
private final ResourceHelper resourceHelper;
private final Context context;
private final AapsSchedulers aapsSchedulers;
private final FabricPrivacy fabricPrivacy;
private final SP sp;
private final NsClientReceiverDelegate nsClientReceiverDelegate;
private final Config config;
private final BuildHelper buildHelper;
public Handler handler;
private final List<EventNSClientNewLog> listLog = new ArrayList<>();
Spanned textLog = HtmlHelper.INSTANCE.fromHtml("");
public boolean paused;
boolean autoscroll;
public String status = "";
public @Nullable NSClientService nsClientService = null;
@Inject
public NSClientPlugin(
HasAndroidInjector injector,
AAPSLogger aapsLogger,
AapsSchedulers aapsSchedulers,
RxBusWrapper rxBus,
ResourceHelper resourceHelper,
Context context,
FabricPrivacy fabricPrivacy,
SP sp,
NsClientReceiverDelegate nsClientReceiverDelegate,
Config config,
BuildHelper buildHelper
) {
super(new PluginDescription()
.mainType(PluginType.GENERAL)
.fragmentClass(NSClientFragment.class.getName())
.pluginIcon(R.drawable.ic_nightscout_syncs)
.pluginName(R.string.nsclientinternal)
.shortName(R.string.nsclientinternal_shortname)
.preferencesId(R.xml.pref_nsclientinternal)
.description(R.string.description_ns_client),
aapsLogger, resourceHelper, injector
);
this.aapsLogger = aapsLogger;
this.aapsSchedulers = aapsSchedulers;
this.rxBus = rxBus;
this.resourceHelper = resourceHelper;
this.context = context;
this.fabricPrivacy = fabricPrivacy;
this.sp = sp;
this.nsClientReceiverDelegate = nsClientReceiverDelegate;
this.config = config;
this.buildHelper = buildHelper;
if (config.getNSCLIENT()) {
getPluginDescription().alwaysEnabled(true).visibleByDefault(true);
}
if (handler == null) {
HandlerThread handlerThread = new HandlerThread(NSClientPlugin.class.getSimpleName() + "Handler");
handlerThread.start();
handler = new Handler(handlerThread.getLooper());
}
}
public boolean isAllowed() {
return nsClientReceiverDelegate.allowed;
}
@Override
protected void onStart() {
paused = sp.getBoolean(R.string.key_nsclientinternal_paused, false);
autoscroll = sp.getBoolean(R.string.key_nsclientinternal_autoscroll, true);
Intent intent = new Intent(context, NSClientService.class);
context.bindService(intent, mConnection, Context.BIND_AUTO_CREATE);
super.onStart();
nsClientReceiverDelegate.grabReceiversState();
disposable.add(rxBus
.toObservable(EventNSClientStatus.class)
.observeOn(aapsSchedulers.getIo())
.subscribe(event -> {
status = event.getStatus(resourceHelper);
rxBus.send(new EventNSClientUpdateGUI());
}, fabricPrivacy::logException)
);
disposable.add(rxBus
.toObservable(EventNetworkChange.class)
.observeOn(aapsSchedulers.getIo())
.subscribe(nsClientReceiverDelegate::onStatusEvent, fabricPrivacy::logException)
);
disposable.add(rxBus
.toObservable(EventPreferenceChange.class)
.observeOn(aapsSchedulers.getIo())
.subscribe(nsClientReceiverDelegate::onStatusEvent, fabricPrivacy::logException)
);
disposable.add(rxBus
.toObservable(EventAppExit.class)
.observeOn(aapsSchedulers.getIo())
.subscribe(event -> {
if (nsClientService != null) {
context.unbindService(mConnection);
}
}, fabricPrivacy::logException)
);
disposable.add(rxBus
.toObservable(EventNSClientNewLog.class)
.observeOn(aapsSchedulers.getIo())
.subscribe(event -> {
addToLog(event);
aapsLogger.debug(LTag.NSCLIENT, event.getAction() + " " + event.getLogText());
}, fabricPrivacy::logException)
);
disposable.add(rxBus
.toObservable(EventChargingState.class)
.observeOn(aapsSchedulers.getIo())
.subscribe(nsClientReceiverDelegate::onStatusEvent, fabricPrivacy::logException)
);
disposable.add(rxBus
.toObservable(EventNSClientResend.class)
.observeOn(aapsSchedulers.getIo())
.subscribe(event -> resend(event.getReason()), fabricPrivacy::logException)
);
}
@Override
protected void onStop() {
context.getApplicationContext().unbindService(mConnection);
disposable.clear();
super.onStop();
}
@Override
public void preprocessPreferences(@NonNull PreferenceFragmentCompat preferenceFragment) {
super.preprocessPreferences(preferenceFragment);
if (config.getNSCLIENT()) {
SwitchPreference key_ns_uploadlocalprofile = preferenceFragment.findPreference(resourceHelper.gs(R.string.key_ns_uploadlocalprofile));
if (key_ns_uploadlocalprofile != null) key_ns_uploadlocalprofile.setVisible(false);
SwitchPreference key_ns_autobackfill = preferenceFragment.findPreference(resourceHelper.gs(R.string.key_ns_autobackfill));
if (key_ns_autobackfill != null) key_ns_autobackfill.setVisible(false);
SwitchPreference key_ns_create_announcements_from_errors = preferenceFragment.findPreference(resourceHelper.gs(R.string.key_ns_create_announcements_from_errors));
if (key_ns_create_announcements_from_errors != null)
key_ns_create_announcements_from_errors.setVisible(false);
SwitchPreference key_ns_create_announcements_from_carbs_req = preferenceFragment.findPreference(resourceHelper.gs(R.string.key_ns_create_announcements_from_carbs_req));
if (key_ns_create_announcements_from_carbs_req != null)
key_ns_create_announcements_from_carbs_req.setVisible(false);
SwitchPreference key_ns_upload_only = preferenceFragment.findPreference(resourceHelper.gs(R.string.key_ns_upload_only));
if (key_ns_upload_only != null) {
key_ns_upload_only.setVisible(false);
key_ns_upload_only.setEnabled(false);
}
SwitchPreference key_ns_sync_use_absolute = preferenceFragment.findPreference(resourceHelper.gs(R.string.key_ns_sync_use_absolute));
if (key_ns_sync_use_absolute != null) key_ns_sync_use_absolute.setVisible(false);
} else {
// APS or pumpControl mode
SwitchPreference key_ns_upload_only = preferenceFragment.findPreference(resourceHelper.gs(R.string.key_ns_upload_only));
if (key_ns_upload_only != null)
key_ns_upload_only.setVisible(buildHelper.isEngineeringMode());
}
}
private final ServiceConnection mConnection = new ServiceConnection() {
public void onServiceDisconnected(ComponentName name) {
aapsLogger.debug(LTag.NSCLIENT, "Service is disconnected");
nsClientService = null;
}
public void onServiceConnected(ComponentName name, IBinder service) {
aapsLogger.debug(LTag.NSCLIENT, "Service is connected");
NSClientService.LocalBinder mLocalBinder = (NSClientService.LocalBinder) service;
if (mLocalBinder != null) // is null when running in roboelectric
nsClientService = mLocalBinder.getServiceInstance();
}
};
synchronized void clearLog() {
handler.post(() -> {
synchronized (listLog) {
listLog.clear();
}
rxBus.send(new EventNSClientUpdateGUI());
});
}
private synchronized void addToLog(final EventNSClientNewLog ev) {
handler.post(() -> {
synchronized (listLog) {
listLog.add(ev);
// remove the first line if log is too large
if (listLog.size() >= Constants.MAX_LOG_LINES) {
listLog.remove(0);
}
}
rxBus.send(new EventNSClientUpdateGUI());
});
}
synchronized void updateLog() {
try {
StringBuilder newTextLog = new StringBuilder();
synchronized (listLog) {
for (EventNSClientNewLog log : listLog) {
newTextLog.append(log.toPreparedHtml());
}
}
textLog = HtmlHelper.INSTANCE.fromHtml(newTextLog.toString());
} catch (OutOfMemoryError e) {
ToastUtils.showToastInUiThread(context, rxBus, "Out of memory!\nStop using this phone !!!", R.raw.error);
}
}
void resend(String reason) {
if (nsClientService != null)
nsClientService.resend(reason);
}
public void pause(boolean newState) {
sp.putBoolean(R.string.key_nsclientinternal_paused, newState);
paused = newState;
rxBus.send(new EventPreferenceChange(resourceHelper, R.string.key_nsclientinternal_paused));
}
public String url() {
return NSClientService.nsURL;
}
public boolean hasWritePermission() {
return NSClientService.hasWriteAuth;
}
public void handleClearAlarm(NSAlarm originalAlarm, long silenceTimeInMsec) {
if (!isEnabled(PluginType.GENERAL)) {
return;
}
if (sp.getBoolean(R.string.key_ns_noupload, false)) {
aapsLogger.debug(LTag.NSCLIENT, "Upload disabled. Message dropped");
return;
}
AlarmAck ack = new AlarmAck();
ack.level = originalAlarm.level();
ack.group = originalAlarm.group();
ack.silenceTime = silenceTimeInMsec;
if (nsClientService != null)
nsClientService.sendAlarmAck(ack);
}
public void updateLatestDateReceivedIfNewer(long latestReceived) {
if (nsClientService != null && latestReceived > nsClientService.latestDateInReceivedData)
nsClientService.latestDateInReceivedData = latestReceived;
}
}

View file

@ -0,0 +1,250 @@
package info.nightscout.androidaps.plugins.general.nsclient
import android.content.ComponentName
import android.content.Context
import android.content.Intent
import android.content.ServiceConnection
import android.os.Handler
import android.os.HandlerThread
import android.os.IBinder
import androidx.preference.PreferenceFragmentCompat
import androidx.preference.SwitchPreference
import dagger.android.HasAndroidInjector
import info.nightscout.androidaps.Constants
import info.nightscout.androidaps.R
import info.nightscout.androidaps.events.EventAppExit
import info.nightscout.androidaps.events.EventChargingState
import info.nightscout.androidaps.events.EventNetworkChange
import info.nightscout.androidaps.events.EventPreferenceChange
import info.nightscout.androidaps.interfaces.Config
import info.nightscout.androidaps.interfaces.PluginBase
import info.nightscout.androidaps.interfaces.PluginDescription
import info.nightscout.androidaps.interfaces.PluginType
import info.nightscout.androidaps.logging.AAPSLogger
import info.nightscout.androidaps.logging.LTag
import info.nightscout.androidaps.plugins.bus.RxBusWrapper
import info.nightscout.androidaps.plugins.general.nsclient.data.AlarmAck
import info.nightscout.androidaps.plugins.general.nsclient.data.NSAlarm
import info.nightscout.androidaps.plugins.general.nsclient.events.EventNSClientNewLog
import info.nightscout.androidaps.plugins.general.nsclient.events.EventNSClientResend
import info.nightscout.androidaps.plugins.general.nsclient.events.EventNSClientStatus
import info.nightscout.androidaps.plugins.general.nsclient.events.EventNSClientUpdateGUI
import info.nightscout.androidaps.plugins.general.nsclient.services.NSClientService
import info.nightscout.androidaps.utils.FabricPrivacy
import info.nightscout.androidaps.utils.HtmlHelper.fromHtml
import info.nightscout.androidaps.utils.ToastUtils
import info.nightscout.androidaps.utils.buildHelper.BuildHelper
import info.nightscout.androidaps.utils.resources.ResourceHelper
import info.nightscout.androidaps.utils.rx.AapsSchedulers
import info.nightscout.androidaps.utils.sharedPreferences.SP
import io.reactivex.disposables.CompositeDisposable
import java.util.*
import javax.inject.Inject
import javax.inject.Singleton
@Singleton
class NSClientPlugin @Inject constructor(
injector: HasAndroidInjector,
aapsLogger: AAPSLogger,
private val aapsSchedulers: AapsSchedulers,
private val rxBus: RxBusWrapper,
resourceHelper: ResourceHelper,
private val context: Context,
private val fabricPrivacy: FabricPrivacy,
private val sp: SP,
private val nsClientReceiverDelegate: NsClientReceiverDelegate,
private val config: Config,
private val buildHelper: BuildHelper
) : PluginBase(PluginDescription()
.mainType(PluginType.GENERAL)
.fragmentClass(NSClientFragment::class.java.name)
.pluginIcon(R.drawable.ic_nightscout_syncs)
.pluginName(R.string.nsclientinternal)
.shortName(R.string.nsclientinternal_shortname)
.preferencesId(R.xml.pref_nsclientinternal)
.description(R.string.description_ns_client),
aapsLogger, resourceHelper, injector
) {
private val disposable = CompositeDisposable()
var handler: Handler? = null
private val listLog: MutableList<EventNSClientNewLog> = ArrayList()
var textLog = fromHtml("")
var paused = false
var autoscroll = false
var status = ""
var nsClientService: NSClientService? = null
val isAllowed: Boolean
get() = nsClientReceiverDelegate.allowed
init {
if (config.NSCLIENT) {
pluginDescription.alwaysEnabled(true).visibleByDefault(true)
}
if (handler == null) {
val handlerThread = HandlerThread(NSClientPlugin::class.java.simpleName + "Handler")
handlerThread.start()
handler = Handler(handlerThread.looper)
}
}
override fun onStart() {
paused = sp.getBoolean(R.string.key_nsclientinternal_paused, false)
autoscroll = sp.getBoolean(R.string.key_nsclientinternal_autoscroll, true)
val intent = Intent(context, NSClientService::class.java)
context.bindService(intent, mConnection, Context.BIND_AUTO_CREATE)
super.onStart()
nsClientReceiverDelegate.grabReceiversState()
disposable.add(rxBus
.toObservable(EventNSClientStatus::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ event: EventNSClientStatus ->
status = event.getStatus(resourceHelper)
rxBus.send(EventNSClientUpdateGUI())
}, fabricPrivacy::logException)
)
disposable.add(rxBus
.toObservable(EventNetworkChange::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ ev -> nsClientReceiverDelegate.onStatusEvent(ev) }, fabricPrivacy::logException)
)
disposable.add(rxBus
.toObservable(EventPreferenceChange::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ ev -> nsClientReceiverDelegate.onStatusEvent(ev) }, fabricPrivacy::logException)
)
disposable.add(rxBus
.toObservable(EventAppExit::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ if (nsClientService != null) context.unbindService(mConnection) }, fabricPrivacy::logException)
)
disposable.add(rxBus
.toObservable(EventNSClientNewLog::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ event: EventNSClientNewLog ->
addToLog(event)
aapsLogger.debug(LTag.NSCLIENT, event.action + " " + event.logText)
}, fabricPrivacy::logException)
)
disposable.add(rxBus
.toObservable(EventChargingState::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ ev -> nsClientReceiverDelegate.onStatusEvent(ev) }, fabricPrivacy::logException)
)
disposable.add(rxBus
.toObservable(EventNSClientResend::class.java)
.observeOn(aapsSchedulers.io)
.subscribe({ event -> resend(event.reason) }, fabricPrivacy::logException)
)
}
override fun onStop() {
context.applicationContext.unbindService(mConnection)
disposable.clear()
super.onStop()
}
override fun preprocessPreferences(preferenceFragment: PreferenceFragmentCompat) {
super.preprocessPreferences(preferenceFragment)
if (config.NSCLIENT) {
val key_ns_uploadlocalprofile = preferenceFragment.findPreference<SwitchPreference>(resourceHelper.gs(R.string.key_ns_uploadlocalprofile))
if (key_ns_uploadlocalprofile != null) key_ns_uploadlocalprofile.isVisible = false
val key_ns_autobackfill = preferenceFragment.findPreference<SwitchPreference>(resourceHelper.gs(R.string.key_ns_autobackfill))
if (key_ns_autobackfill != null) key_ns_autobackfill.isVisible = false
val key_ns_create_announcements_from_errors = preferenceFragment.findPreference<SwitchPreference>(resourceHelper.gs(R.string.key_ns_create_announcements_from_errors))
if (key_ns_create_announcements_from_errors != null) key_ns_create_announcements_from_errors.isVisible = false
val key_ns_create_announcements_from_carbs_req = preferenceFragment.findPreference<SwitchPreference>(resourceHelper.gs(R.string.key_ns_create_announcements_from_carbs_req))
if (key_ns_create_announcements_from_carbs_req != null) key_ns_create_announcements_from_carbs_req.isVisible = false
val key_ns_upload_only = preferenceFragment.findPreference<SwitchPreference>(resourceHelper.gs(R.string.key_ns_upload_only))
if (key_ns_upload_only != null) {
key_ns_upload_only.isVisible = false
key_ns_upload_only.isEnabled = false
}
val key_ns_sync_use_absolute = preferenceFragment.findPreference<SwitchPreference>(resourceHelper.gs(R.string.key_ns_sync_use_absolute))
if (key_ns_sync_use_absolute != null) key_ns_sync_use_absolute.isVisible = false
} else {
// APS or pumpControl mode
val key_ns_upload_only = preferenceFragment.findPreference<SwitchPreference>(resourceHelper.gs(R.string.key_ns_upload_only))
if (key_ns_upload_only != null) key_ns_upload_only.isVisible = buildHelper.isEngineeringMode()
}
}
private val mConnection: ServiceConnection = object : ServiceConnection {
override fun onServiceDisconnected(name: ComponentName) {
aapsLogger.debug(LTag.NSCLIENT, "Service is disconnected")
nsClientService = null
}
override fun onServiceConnected(name: ComponentName, service: IBinder) {
aapsLogger.debug(LTag.NSCLIENT, "Service is connected")
val mLocalBinder = service as NSClientService.LocalBinder
@Suppress("UNNECESSARY_SAFE_CALL")
nsClientService = mLocalBinder?.serviceInstance // is null when running in roboelectric
}
}
@Synchronized fun clearLog() {
handler?.post {
synchronized(listLog) { listLog.clear() }
rxBus.send(EventNSClientUpdateGUI())
}
}
@Synchronized private fun addToLog(ev: EventNSClientNewLog) {
handler?.post {
synchronized(listLog) {
listLog.add(ev)
// remove the first line if log is too large
if (listLog.size >= Constants.MAX_LOG_LINES) {
listLog.removeAt(0)
}
}
rxBus.send(EventNSClientUpdateGUI())
}
}
@Synchronized fun updateLog() {
try {
val newTextLog = StringBuilder()
synchronized(listLog) {
for (log in listLog) {
newTextLog.append(log.toPreparedHtml())
}
}
textLog = fromHtml(newTextLog.toString())
} catch (e: OutOfMemoryError) {
ToastUtils.showToastInUiThread(context, rxBus, "Out of memory!\nStop using this phone !!!", R.raw.error)
}
}
fun resend(reason: String) {
nsClientService?.resend(reason)
}
fun pause(newState: Boolean) {
sp.putBoolean(R.string.key_nsclientinternal_paused, newState)
paused = newState
rxBus.send(EventPreferenceChange(resourceHelper, R.string.key_nsclientinternal_paused))
}
fun url(): String = nsClientService?.nsURL ?: ""
fun hasWritePermission(): Boolean = nsClientService?.hasWriteAuth ?: false
fun handleClearAlarm(originalAlarm: NSAlarm, silenceTimeInMilliseconds: Long) {
if (!isEnabled(PluginType.GENERAL)) return
if (sp.getBoolean(R.string.key_ns_noupload, false)) {
aapsLogger.debug(LTag.NSCLIENT, "Upload disabled. Message dropped")
return
}
nsClientService?.sendAlarmAck(
AlarmAck().also { ack ->
ack.level = originalAlarm.level()
ack.group = originalAlarm.group()
ack.silenceTime = silenceTimeInMilliseconds
})
}
fun updateLatestDateReceivedIfNewer(latestReceived: Long) {
nsClientService?.let { if (latestReceived > it.latestDateInReceivedData) it.latestDateInReceivedData = latestReceived }
}
}

View file

@ -1,117 +0,0 @@
package info.nightscout.androidaps.plugins.general.nsclient;
import java.util.Arrays;
import javax.inject.Inject;
import javax.inject.Singleton;
import info.nightscout.androidaps.R;
import info.nightscout.androidaps.events.EventChargingState;
import info.nightscout.androidaps.events.EventNetworkChange;
import info.nightscout.androidaps.events.EventPreferenceChange;
import info.nightscout.androidaps.plugins.bus.RxBusWrapper;
import info.nightscout.androidaps.receivers.ReceiverStatusStore;
import info.nightscout.androidaps.utils.resources.ResourceHelper;
import info.nightscout.androidaps.utils.sharedPreferences.SP;
@Singleton
class NsClientReceiverDelegate {
private boolean allowedChargingState = true;
private boolean allowedNetworkState = true;
boolean allowed = true;
private RxBusWrapper rxBus;
private ResourceHelper resourceHelper;
private SP sp;
private ReceiverStatusStore receiverStatusStore;
@Inject
public NsClientReceiverDelegate(
RxBusWrapper rxBus,
ResourceHelper resourceHelper,
SP sp,
ReceiverStatusStore receiverStatusStore
) {
this.rxBus = rxBus;
this.resourceHelper = resourceHelper;
this.sp = sp;
this.receiverStatusStore = receiverStatusStore;
}
void grabReceiversState() {
receiverStatusStore.updateNetworkStatus();
}
void onStatusEvent(EventPreferenceChange ev) {
if (ev.isChanged(resourceHelper, R.string.key_ns_wifionly) ||
ev.isChanged(resourceHelper, R.string.key_ns_wifi_ssids) ||
ev.isChanged(resourceHelper, R.string.key_ns_allowroaming)
) {
receiverStatusStore.updateNetworkStatus();
onStatusEvent(receiverStatusStore.getLastNetworkEvent());
} else if (ev.isChanged(resourceHelper, R.string.key_ns_chargingonly)) {
receiverStatusStore.broadcastChargingState();
}
}
void onStatusEvent(final EventChargingState ev) {
boolean newChargingState = calculateStatus(ev);
if (newChargingState != allowedChargingState) {
allowedChargingState = newChargingState;
processStateChange();
}
}
void onStatusEvent(final EventNetworkChange ev) {
boolean newNetworkState = calculateStatus(ev);
if (newNetworkState != allowedNetworkState) {
allowedNetworkState = newNetworkState;
processStateChange();
}
}
private void processStateChange() {
boolean newAllowedState = allowedChargingState && allowedNetworkState;
if (newAllowedState != allowed) {
allowed = newAllowedState;
rxBus.send(new EventPreferenceChange(resourceHelper.gs(R.string.key_nsclientinternal_paused)));
}
}
boolean calculateStatus(final EventChargingState ev) {
boolean chargingOnly = sp.getBoolean(R.string.key_ns_chargingonly, false);
boolean newAllowedState = true;
if (!ev.isCharging() && chargingOnly) {
newAllowedState = false;
}
return newAllowedState;
}
boolean calculateStatus(final EventNetworkChange ev) {
boolean wifiOnly = sp.getBoolean(R.string.key_ns_wifionly, false);
String allowedSSIDstring = sp.getString(R.string.key_ns_wifi_ssids, "");
String[] allowedSSIDs = allowedSSIDstring.split(";");
if (allowedSSIDstring.isEmpty()) allowedSSIDs = new String[0];
boolean allowRoaming = sp.getBoolean(R.string.key_ns_allowroaming, true);
boolean newAllowedState = true;
if (ev.getWifiConnected()) {
if (allowedSSIDs.length != 0 && !Arrays.asList(allowedSSIDs).contains(ev.getSsid())) {
newAllowedState = false;
}
} else {
if ((!allowRoaming && ev.getRoaming()) || wifiOnly) {
newAllowedState = false;
}
}
return newAllowedState;
}
}

View file

@ -0,0 +1,90 @@
package info.nightscout.androidaps.plugins.general.nsclient
import info.nightscout.androidaps.R
import info.nightscout.androidaps.events.EventChargingState
import info.nightscout.androidaps.events.EventNetworkChange
import info.nightscout.androidaps.events.EventPreferenceChange
import info.nightscout.androidaps.plugins.bus.RxBusWrapper
import info.nightscout.androidaps.receivers.ReceiverStatusStore
import info.nightscout.androidaps.utils.resources.ResourceHelper
import info.nightscout.androidaps.utils.sharedPreferences.SP
import javax.inject.Inject
import javax.inject.Singleton
@Singleton
class NsClientReceiverDelegate @Inject constructor(
private val rxBus: RxBusWrapper,
private val resourceHelper: ResourceHelper,
private val sp: SP,
private val receiverStatusStore: ReceiverStatusStore
) {
private var allowedChargingState = true
private var allowedNetworkState = true
var allowed = true
fun grabReceiversState() {
receiverStatusStore.updateNetworkStatus()
}
fun onStatusEvent(ev: EventPreferenceChange) {
if (ev.isChanged(resourceHelper, R.string.key_ns_wifionly) ||
ev.isChanged(resourceHelper, R.string.key_ns_wifi_ssids) ||
ev.isChanged(resourceHelper, R.string.key_ns_allowroaming)) {
receiverStatusStore.updateNetworkStatus()
onStatusEvent(receiverStatusStore.lastNetworkEvent)
} else if (ev.isChanged(resourceHelper, R.string.key_ns_chargingonly)) {
receiverStatusStore.broadcastChargingState()
}
}
fun onStatusEvent(ev: EventChargingState) {
val newChargingState = calculateStatus(ev)
if (newChargingState != allowedChargingState) {
allowedChargingState = newChargingState
processStateChange()
}
}
fun onStatusEvent(ev: EventNetworkChange?) {
val newNetworkState = calculateStatus(ev)
if (newNetworkState != allowedNetworkState) {
allowedNetworkState = newNetworkState
processStateChange()
}
}
private fun processStateChange() {
val newAllowedState = allowedChargingState && allowedNetworkState
if (newAllowedState != allowed) {
allowed = newAllowedState
rxBus.send(EventPreferenceChange(resourceHelper.gs(R.string.key_nsclientinternal_paused)))
}
}
fun calculateStatus(ev: EventChargingState): Boolean {
val chargingOnly = sp.getBoolean(R.string.key_ns_chargingonly, false)
var newAllowedState = true
if (!ev.isCharging && chargingOnly) {
newAllowedState = false
}
return newAllowedState
}
fun calculateStatus(ev: EventNetworkChange?): Boolean {
val wifiOnly = sp.getBoolean(R.string.key_ns_wifionly, false)
val allowedSsidString = sp.getString(R.string.key_ns_wifi_ssids, "")
val allowedSSIDs: List<String> = if (allowedSsidString.isEmpty()) List(0) { "" } else allowedSsidString.split(";")
val allowRoaming = sp.getBoolean(R.string.key_ns_allowroaming, true)
var newAllowedState = true
if (ev?.wifiConnected == true) {
if (allowedSSIDs.isNotEmpty() && !allowedSSIDs.contains(ev.ssid)) {
newAllowedState = false
}
} else {
if (!allowRoaming && ev?.roaming == true || wifiOnly) {
newAllowedState = false
}
}
return newAllowedState
}
}

View file

@ -99,20 +99,20 @@ public class NSClientService extends DaggerService {
private final CompositeDisposable disposable = new CompositeDisposable();
static public PowerManager.WakeLock mWakeLock;
// public PowerManager.WakeLock mWakeLock;
private final IBinder mBinder = new NSClientService.LocalBinder();
static public Handler handler;
private Handler handler;
public static Socket mSocket;
public static boolean isConnected = false;
public static boolean hasWriteAuth = false;
private static Integer dataCounter = 0;
private static Integer connectCounter = 0;
public Socket mSocket;
public boolean isConnected = false;
public boolean hasWriteAuth = false;
private Integer dataCounter = 0;
private Integer connectCounter = 0;
private boolean nsEnabled = false;
static public String nsURL = "";
public String nsURL = "";
private String nsAPISecret = "";
private String nsDevice = "";
private final Integer nsHours = 48;
@ -140,9 +140,9 @@ public class NSClientService extends DaggerService {
@Override
public void onCreate() {
super.onCreate();
PowerManager powerManager = (PowerManager) getSystemService(Context.POWER_SERVICE);
mWakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "AndroidAPS:NSClientService");
mWakeLock.acquire();
// PowerManager powerManager = (PowerManager) getSystemService(Context.POWER_SERVICE);
// mWakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "AndroidAPS:NSClientService");
// mWakeLock.acquire();
initialize();
@ -209,7 +209,7 @@ public class NSClientService extends DaggerService {
public void onDestroy() {
super.onDestroy();
disposable.clear();
if (mWakeLock.isHeld()) mWakeLock.release();
// if (mWakeLock.isHeld()) mWakeLock.release();
}
public void processAddAck(NSAddAck ack) {
@ -277,13 +277,14 @@ public class NSClientService extends DaggerService {
readPreferences();
if (!nsAPISecret.equals(""))
//noinspection UnstableApiUsage
nsAPIhashCode = Hashing.sha1().hashString(nsAPISecret, Charsets.UTF_8).toString();
rxBus.send(new EventNSClientStatus("Initializing"));
if (!nsClientPlugin.isAllowed()) {
rxBus.send(new EventNSClientNewLog("NSCLIENT", "not allowed"));
rxBus.send(new EventNSClientStatus("Not allowed"));
} else if (nsClientPlugin.paused) {
} else if (nsClientPlugin.getPaused()) {
rxBus.send(new EventNSClientNewLog("NSCLIENT", "paused"));
rxBus.send(new EventNSClientStatus("Paused"));
} else if (!nsEnabled) {
@ -519,11 +520,11 @@ public class NSClientService extends DaggerService {
private final Emitter.Listener onDataUpdate = new Emitter.Listener() {
@Override
public void call(final Object... args) {
NSClientService.handler.post(() -> {
handler.post(() -> {
PowerManager powerManager = (PowerManager) getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,
"AndroidAPS:NSClientService_onDataUpdate");
wakeLock.acquire();
wakeLock.acquire(3000);
try {
JSONObject data = (JSONObject) args[0];
@ -733,27 +734,35 @@ public class NSClientService extends DaggerService {
handler.post(() -> {
if (mSocket == null || !mSocket.connected()) return;
rxBus.send(new EventNSClientNewLog("QUEUE", "Resend started: " + reason));
if (lastAckTime > System.currentTimeMillis() - 10 * 1000L) {
aapsLogger.debug(LTag.NSCLIENT, "Skipping resend by lastAckTime: " + ((System.currentTimeMillis() - lastAckTime) / 1000L) + " sec");
return;
}
PowerManager powerManager = (PowerManager) getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,
"AndroidAPS:NSClientService_onDataUpdate");
wakeLock.acquire(T.mins(10).msecs());
try {
dataSyncSelector.processChangedBolusesCompat();
dataSyncSelector.processChangedCarbsCompat();
dataSyncSelector.processChangedBolusCalculatorResultsCompat();
dataSyncSelector.processChangedTemporaryBasalsCompat();
dataSyncSelector.processChangedExtendedBolusesCompat();
dataSyncSelector.processChangedProfileSwitchesCompat();
dataSyncSelector.processChangedGlucoseValuesCompat();
dataSyncSelector.processChangedTempTargetsCompat();
dataSyncSelector.processChangedFoodsCompat();
dataSyncSelector.processChangedTherapyEventsCompat();
dataSyncSelector.processChangedDeviceStatusesCompat();
dataSyncSelector.processChangedProfileStore();
rxBus.send(new EventNSClientNewLog("QUEUE", "Resend started: " + reason));
rxBus.send(new EventNSClientNewLog("QUEUE", "Resend ended: " + reason));
dataSyncSelector.processChangedBolusesCompat();
dataSyncSelector.processChangedCarbsCompat();
dataSyncSelector.processChangedBolusCalculatorResultsCompat();
dataSyncSelector.processChangedTemporaryBasalsCompat();
dataSyncSelector.processChangedExtendedBolusesCompat();
dataSyncSelector.processChangedProfileSwitchesCompat();
dataSyncSelector.processChangedGlucoseValuesCompat();
dataSyncSelector.processChangedTempTargetsCompat();
dataSyncSelector.processChangedFoodsCompat();
dataSyncSelector.processChangedTherapyEventsCompat();
dataSyncSelector.processChangedDeviceStatusesCompat();
dataSyncSelector.processChangedProfileStore();
rxBus.send(new EventNSClientNewLog("QUEUE", "Resend ended: " + reason));
} finally {
if (wakeLock.isHeld()) wakeLock.release();
}
});
}

View file

@ -189,8 +189,8 @@ class SWDefinition @Inject constructor(
.label(R.string.status)
.initialStatus(nsClientPlugin.status)
)
.validator { nsClientPlugin.nsClientService != null && NSClientService.isConnected && NSClientService.hasWriteAuth }
.visibility { !(nsClientPlugin.nsClientService != null && NSClientService.isConnected && NSClientService.hasWriteAuth) }
.validator { nsClientPlugin.nsClientService?.isConnected == true && nsClientPlugin.nsClientService?.hasWriteAuth == true }
.visibility { !(nsClientPlugin.nsClientService?.isConnected == true && nsClientPlugin.nsClientService?.hasWriteAuth == true) }
private val screenPatientName = SWScreen(injector, R.string.patient_name)
.skippable(true)
.add(SWInfoText(injector)
@ -268,13 +268,19 @@ class SWDefinition @Inject constructor(
.label(R.string.adjustprofileinns))
.add(SWFragment(injector, this)
.add(NSProfileFragment()))
.validator { nsProfilePlugin.profile?.getDefaultProfile()?.let { ProfileSealed.Pure(it).isValid("StartupWizard", activePlugin.activePump, config, resourceHelper, rxBus) } ?: false }
.validator {
nsProfilePlugin.profile?.getDefaultProfile()?.let { ProfileSealed.Pure(it).isValid("StartupWizard", activePlugin.activePump, config, resourceHelper, rxBus) }
?: false
}
.visibility { nsProfilePlugin.isEnabled() }
private val screenLocalProfile = SWScreen(injector, R.string.localprofile)
.skippable(false)
.add(SWFragment(injector, this)
.add(LocalProfileFragment()))
.validator { localProfilePlugin.profile?.getDefaultProfile()?.let { ProfileSealed.Pure(it).isValid("StartupWizard", activePlugin.activePump, config, resourceHelper, rxBus) } ?: false }
.validator {
localProfilePlugin.profile?.getDefaultProfile()?.let { ProfileSealed.Pure(it).isValid("StartupWizard", activePlugin.activePump, config, resourceHelper, rxBus) }
?: false
}
.visibility { localProfilePlugin.isEnabled() }
private val screenProfileSwitch = SWScreen(injector, R.string.careportal_profileswitch)
.skippable(false)

View file

@ -85,6 +85,7 @@ fun extendedBolusFromNsIdForInvalidating(nsId: String): ExtendedBolus =
JSONObject()
.put("mills", 1)
.put("amount", -1.0)
.put("enteredinsulin", -1.0)
.put("duration", -1.0)
.put("splitNow", 0)
.put("splitExt", 100)