2016-11-17 13:06:17 -05:00
|
|
|
|
using System;
|
|
|
|
|
using System.Collections.Generic;
|
2016-11-17 13:37:57 -05:00
|
|
|
|
using System.Diagnostics;
|
2016-11-17 13:06:17 -05:00
|
|
|
|
using System.Linq;
|
|
|
|
|
using System.Text;
|
|
|
|
|
using System.Threading.Tasks;
|
|
|
|
|
using System.Windows;
|
2016-11-18 01:23:45 -05:00
|
|
|
|
using System.Windows.Input;
|
2016-11-18 23:29:27 -05:00
|
|
|
|
using System.ServiceProcess;
|
2016-11-19 01:32:23 -05:00
|
|
|
|
using System.Net.NetworkInformation;
|
|
|
|
|
|
2016-11-17 13:37:57 -05:00
|
|
|
|
using WifiSitter;
|
|
|
|
|
using WifiSitter.Model;
|
2016-11-17 13:06:17 -05:00
|
|
|
|
using WifiSitterGui.Helpers;
|
2016-11-19 01:32:23 -05:00
|
|
|
|
|
2016-11-17 13:37:57 -05:00
|
|
|
|
using XDMessaging;
|
2016-11-17 13:06:17 -05:00
|
|
|
|
|
|
|
|
|
namespace WifiSitterGui.ViewModel
|
|
|
|
|
{
|
|
|
|
|
public class WifiSitterAgentViewModel : MvvmObservable
|
|
|
|
|
{
|
|
|
|
|
#region fields
|
|
|
|
|
|
|
|
|
|
private static MainWindowViewModel _windowVM;
|
|
|
|
|
private RelayCommand _launchWindowCommand;
|
2016-11-18 01:23:45 -05:00
|
|
|
|
private RelayCommand _takeFiveCommand; // Asks service to pause for 5 minutes
|
2016-11-17 13:06:17 -05:00
|
|
|
|
private static MainWindow _statusGui;
|
2016-11-17 13:37:57 -05:00
|
|
|
|
private static WifiSitterIpc _wsIpc;
|
|
|
|
|
private Action<object, XDMessageEventArgs> _handleMsgRcv;
|
|
|
|
|
private static string _serviceChannel;
|
2016-11-18 01:23:45 -05:00
|
|
|
|
private System.Timers.Timer _netstateCheckTimer;
|
|
|
|
|
|
2016-11-17 13:06:17 -05:00
|
|
|
|
#endregion // fields
|
|
|
|
|
|
|
|
|
|
#region constructor
|
|
|
|
|
|
|
|
|
|
public WifiSitterAgentViewModel() {
|
2016-11-17 13:37:57 -05:00
|
|
|
|
Intitialize();
|
2016-11-17 13:06:17 -05:00
|
|
|
|
}
|
|
|
|
|
|
2016-11-19 01:34:12 -05:00
|
|
|
|
|
2016-11-17 13:06:17 -05:00
|
|
|
|
public WifiSitterAgentViewModel(MainWindowViewModel WindowVM) {
|
|
|
|
|
_windowVM = WindowVM;
|
2016-11-17 13:37:57 -05:00
|
|
|
|
Intitialize();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
private void Intitialize() {
|
2016-11-19 01:32:23 -05:00
|
|
|
|
// Get NetState
|
|
|
|
|
RequestNetworkState();
|
|
|
|
|
|
2016-11-18 01:23:45 -05:00
|
|
|
|
// Intermittent network state polling
|
|
|
|
|
_netstateCheckTimer = new System.Timers.Timer();
|
|
|
|
|
_netstateCheckTimer.AutoReset = true;
|
|
|
|
|
_netstateCheckTimer.Interval = 30 * 1000; // 30 seconds
|
|
|
|
|
_netstateCheckTimer.Elapsed += (o, e) => { RequestNetworkState(); };
|
|
|
|
|
_netstateCheckTimer.Start();
|
2016-11-17 13:37:57 -05:00
|
|
|
|
|
2016-11-19 01:32:23 -05:00
|
|
|
|
// Connection state changed event handler setup
|
|
|
|
|
NetworkChange.NetworkAvailabilityChanged += (o, e) => { RequestNetworkState(3 * 1000); };
|
|
|
|
|
NetworkChange.NetworkAddressChanged += (o, e) => { RequestNetworkState(3 * 1000); };
|
|
|
|
|
|
2016-11-18 01:23:45 -05:00
|
|
|
|
Trace.WriteLine(String.Format("WifiSitter service msg channel: {0}", ServiceChannelName));
|
2016-11-17 13:06:17 -05:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
#endregion // constructor
|
|
|
|
|
|
|
|
|
|
#region properties
|
|
|
|
|
|
2016-11-18 23:29:27 -05:00
|
|
|
|
internal WifiSitterIpc WsIpc {
|
|
|
|
|
get {
|
|
|
|
|
if (_wsIpc == null) {
|
|
|
|
|
// Setup IPC message listener
|
|
|
|
|
_handleMsgRcv = new Action<object, XDMessageEventArgs>(wsIpc_MessageReceived);
|
|
|
|
|
_wsIpc = new WifiSitterIpc(_handleMsgRcv);
|
|
|
|
|
}
|
|
|
|
|
return _wsIpc;
|
|
|
|
|
}
|
|
|
|
|
}
|
2016-11-19 01:32:23 -05:00
|
|
|
|
|
2016-11-18 23:29:27 -05:00
|
|
|
|
|
2016-11-17 13:06:17 -05:00
|
|
|
|
public MainWindowViewModel WindowVM {
|
|
|
|
|
get { if (_windowVM == null) {
|
|
|
|
|
_windowVM = new MainWindowViewModel();
|
|
|
|
|
}
|
|
|
|
|
return _windowVM;
|
|
|
|
|
}
|
|
|
|
|
private set { _windowVM = value; OnPropertyChanged("WindowVM"); }
|
|
|
|
|
}
|
|
|
|
|
|
2016-11-19 01:34:12 -05:00
|
|
|
|
|
2016-11-17 13:37:57 -05:00
|
|
|
|
internal string ServiceChannelName {
|
|
|
|
|
get {
|
2016-11-21 17:28:17 -05:00
|
|
|
|
var serviceProc = Process.GetProcesses().Where(x => x.ProcessName.ToLower().StartsWith("wifisitter"))
|
|
|
|
|
.Where(x => !x.ProcessName.ToLower().Contains("gui")).ToArray();
|
|
|
|
|
if (serviceProc != null &&
|
|
|
|
|
serviceProc.Length > 0) {
|
|
|
|
|
_serviceChannel = String.Format("{0}-{1}", serviceProc[0].Id, serviceProc[0].ProcessName);
|
2016-11-17 13:37:57 -05:00
|
|
|
|
}
|
2016-11-21 17:28:17 -05:00
|
|
|
|
|
2016-11-17 13:37:57 -05:00
|
|
|
|
return _serviceChannel;
|
|
|
|
|
}
|
|
|
|
|
}
|
2016-11-18 23:29:27 -05:00
|
|
|
|
|
2016-11-17 13:06:17 -05:00
|
|
|
|
#endregion // properties
|
|
|
|
|
|
|
|
|
|
#region methods
|
2016-11-18 01:23:45 -05:00
|
|
|
|
|
2016-11-19 01:32:23 -05:00
|
|
|
|
public void RequestNetworkState(int Delay) {
|
|
|
|
|
Task.Delay(Delay).ContinueWith((task) => { RequestNetworkState(); }, TaskScheduler.FromCurrentSynchronizationContext());
|
|
|
|
|
}
|
|
|
|
|
|
2016-11-21 19:16:01 -05:00
|
|
|
|
|
2016-11-19 01:32:23 -05:00
|
|
|
|
public void RequestNetworkState () {
|
2016-11-18 01:23:45 -05:00
|
|
|
|
if (!String.IsNullOrEmpty(ServiceChannelName)) {
|
|
|
|
|
try {
|
|
|
|
|
Trace.WriteLine("Checking for network state.");
|
2016-11-18 23:29:27 -05:00
|
|
|
|
WsIpc.MsgBroadcaster.SendToChannel(ServiceChannelName, new WifiSitterIpcMessage("get_netstate", _wsIpc.MyChannelName, _wsIpc.MyChannelName).IpcMessageJsonString());
|
2016-11-18 01:23:45 -05:00
|
|
|
|
}
|
|
|
|
|
catch (Exception e) {
|
|
|
|
|
Trace.WriteLine(e.Message);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-11-17 13:06:17 -05:00
|
|
|
|
#endregion // methods
|
|
|
|
|
|
|
|
|
|
#region commands
|
|
|
|
|
|
2016-11-18 01:23:45 -05:00
|
|
|
|
public ICommand LaunchSettingsWindow {
|
2016-11-17 13:06:17 -05:00
|
|
|
|
get {
|
|
|
|
|
if (_launchWindowCommand == null) {
|
|
|
|
|
_launchWindowCommand = new RelayCommand(() => {
|
|
|
|
|
if (_statusGui == null) {
|
|
|
|
|
_statusGui = new MainWindow();
|
|
|
|
|
_statusGui.DataContext = WindowVM;
|
|
|
|
|
_statusGui.Closed += (s, e) => { _statusGui = null; };
|
|
|
|
|
_statusGui.Show();
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
_statusGui.WindowState = WindowState.Normal;
|
|
|
|
|
_statusGui.Activate();
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
return _launchWindowCommand;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-11-18 01:23:45 -05:00
|
|
|
|
|
|
|
|
|
public ICommand SendTakeFiveRequest {
|
|
|
|
|
get {
|
|
|
|
|
if (_takeFiveCommand == null) {
|
|
|
|
|
_takeFiveCommand = new RelayCommand(() => {
|
|
|
|
|
var request = new WifiSitterIpcMessage("take_five", _wsIpc.MyChannelName, _wsIpc.MyChannelName);
|
2016-11-21 17:28:17 -05:00
|
|
|
|
WsIpc.MsgBroadcaster.SendToChannel(ServiceChannelName, request.IpcMessageJsonString());
|
2016-11-18 01:23:45 -05:00
|
|
|
|
// TODO need response validation mechanism
|
|
|
|
|
});
|
|
|
|
|
}
|
|
|
|
|
return _takeFiveCommand;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-11-17 13:06:17 -05:00
|
|
|
|
#endregion // commands
|
|
|
|
|
|
|
|
|
|
#region events
|
2016-11-17 13:37:57 -05:00
|
|
|
|
|
|
|
|
|
internal void wsIpc_MessageReceived(object sender, XDMessageEventArgs e) {
|
|
|
|
|
if (!e.DataGram.IsValid) {
|
|
|
|
|
Trace.WriteLine("Invalid datagram received.");
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
WifiSitterIpcMessage _sr = null;
|
|
|
|
|
try { _sr = Newtonsoft.Json.JsonConvert.DeserializeObject<WifiSitterIpcMessage>(e.DataGram.Message); }
|
|
|
|
|
catch { Trace.WriteLine("Deserialize to ServiceRequest failed."); }
|
|
|
|
|
|
|
|
|
|
if (_sr != null) {
|
2016-11-18 01:23:45 -05:00
|
|
|
|
switch (_sr.Request) {
|
|
|
|
|
case "give_netstate":
|
2016-11-21 17:28:17 -05:00
|
|
|
|
try { WindowVM.NetState = Newtonsoft.Json.JsonConvert.DeserializeObject<SimpleNetworkState>(Encoding.UTF8.GetString(_sr.Payload)); }
|
2016-11-18 01:23:45 -05:00
|
|
|
|
catch { WifiSitter.WifiSitter.LogLine("Failed to deserialize netstate, payload."); }
|
|
|
|
|
break;
|
|
|
|
|
case "taking_five":
|
2016-11-21 19:16:01 -05:00
|
|
|
|
Trace.WriteLine(String.Format("Responded 'taking_five' : {0}", Encoding.UTF8.GetString(_sr.Payload)));
|
2016-11-18 01:23:45 -05:00
|
|
|
|
break;
|
|
|
|
|
case "service_status":
|
|
|
|
|
// TODO issue service status update
|
|
|
|
|
break;
|
|
|
|
|
default:
|
|
|
|
|
Trace.WriteLine(String.Format("Unknown request type: {0} from {1}", _sr?.Request, _sr?.Requestor));
|
|
|
|
|
break;
|
2016-11-17 13:37:57 -05:00
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
else {
|
|
|
|
|
Trace.WriteLine(e.DataGram.Message);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-11-17 13:06:17 -05:00
|
|
|
|
#endregion // events
|
|
|
|
|
}
|
|
|
|
|
}
|