using Common.system; using Newtonsoft.Json.Linq; using SuperSocket.ClientEngine; using System; using System.Collections.Generic; using System.Threading; using System.Threading.Tasks; using WebSocket4Net; using XHZB.Model; namespace XHZB.Desktop.WebSocket { public class WSocketClient : IDisposable { // 打开的窗口列表 private static readonly Dictionary WinDic = new Dictionary(); private static WSocketClient instance; public static WSocketClient getInstance() { if (instance == null) { instance = new WSocketClient(); } return instance; } public static NLog.Logger _Logger = NLog.LogManager.GetCurrentClassLogger(); #region 向外传递数据事件 public event Action MessageReceived; #endregion WebSocket4Net.WebSocket _webSocket; /// /// 检查重连线程 /// Thread _thread; /// /// 心跳 /// Thread thread; bool _isRunning = true; /// /// WebSocket连接地址 /// public string ServerPath { get; set; } //public WSocketClient() //{ // string url = "ws://schoolwstest.xhkjedu.com/ws"; // ServerPath = url; // this._webSocket = new WebSocket4Net.WebSocket(url); // this._webSocket.Opened += WebSocket_Opened; // this._webSocket.Error += WebSocket_Error; // this._webSocket.Closed += WebSocket_Closed; // this._webSocket.MessageReceived += WebSocket_MessageReceived; // //注册消息接收事件,接收服务端发送的数据 // MessageReceived += (data) => { // Console.WriteLine(data); // }; // //开始链接 // Start(); // SendMessage(SocketMsgManger.offlineMsg()); //} public void StartWsClient() { string url = "ws://schoolwstest.xhkjedu.com/ws"; ServerPath = url; this._webSocket = new WebSocket4Net.WebSocket(url); this._webSocket.Opened += WebSocket_Opened; this._webSocket.Error += WebSocket_Error; this._webSocket.Closed += WebSocket_Closed; this._webSocket.MessageReceived += WebSocket_MessageReceived; //注册消息接收事件,接收服务端发送的数据 MessageReceived += (data) => { Console.WriteLine(data); }; //开始链接 Start(); SendMessage(SocketMsgManger.offlineMsg()); } #region "web socket " /// /// 连接方法 /// public bool Start() { bool result = true; try { this._webSocket.Open(); this._isRunning = true; this._thread = new Thread(new ThreadStart(CheckConnection)); this._thread.Start(); thread = new Thread(new ThreadStart(Heartbeat)); thread.Start(); } catch (Exception ex) { _Logger.Error(ex.ToString()); result = false; } return result; } /// /// 消息收到事件 /// /// /// void WebSocket_MessageReceived(object sender, MessageReceivedEventArgs e) { _Logger.Info(" Received:" + e.Message); MessageReceived?.Invoke(e.Message); Console.WriteLine("WS:消息收到:" + e.Message); //string str = e.Message; // JObject.Parse(str); //string str = jo["c"].ToString(); SocketModel msgBean = JsonHelper.JsonToObj(e.Message); //if(isMsg) // { // GetOnlineStudentsModel msgBean = JsonHelper.JsonToObj(e.Message); // if (msgBean.c == 1040) // { // } // } if (msgBean != null && msgBean.b != null) { if (msgBean.c == 1040) { GetOnlineStudentsModel msgOnline = JsonHelper.JsonToObj(e.Message); foreach (StudentModel getOnline in msgOnline.b.stulst) { OnlineUserModel item = new OnlineUserModel(); if (getUserByIds(getOnline.userid) == null) { item.usertype = 2001; item.userid = getOnline.userid; item.username = getOnline.username; item.userpic = getOnline.headportrait; APP.OnlineUserList.Add(item); } } return; } //GetOnlineStudentsModel get = new GetOnlineStudentsModel(); //get.b = new StulstModel(); //Console.WriteLine("WS:消息收到1111:" + get); } if (msgBean.c != 0 && msgBean.u == 2) { if (msgBean.c == 2001)//上线 { if(getUserByIds(msgBean.b.stid) == null) { OnlineUserModel item = new OnlineUserModel { usertype = msgBean.c, userid = msgBean.b.stid, username = msgBean.b.stname, userpic = msgBean.b.stpic }; APP.OnlineUserList.Add(item); sendUserChangeToWin(); } } else if (msgBean.c == 2002)//下线 { try { for (int i = 0; i < APP.OnlineUserList.Count; i++) { if (msgBean.b.stid == APP.OnlineUserList[i].userid) { APP.OnlineUserList.RemoveAt(i); break; } } } catch (Exception ex) { LogHelper.WriteErrLog("(移除)" + ex.Message, ex); } sendUserChangeToWin(); } sendMsgToWin(msgBean); } } /// /// 是否存在用户 /// /// /// public OnlineUserModel getUserByIds(int userid) { if (APP.OnlineUserList.Count > 0) { OnlineUserModel[] userList = APP.OnlineUserList.ToArray(); foreach (OnlineUserModel user in userList) { if (user != null) { if (user.userid == userid) { return user; } } } } return null; } private static void sendMsgToWin(SocketModel msg) { foreach (KeyValuePair kvp in WinDic) { if (kvp.Value is SocketCallback callback) { callback.receiveWsMsg(msg); } } } /// /// 添加要推送消息的窗口 /// /// public void addWin(object win) { if (WinDic.ContainsKey(win.GetType())) { WinDic[win.GetType()] = win; } else { WinDic.Add(win.GetType(), win); } } /// /// 发送给需要接收的窗口 /// private static void sendUserChangeToWin() { foreach (KeyValuePair kvp in WinDic) { if (kvp.Value is SocketCallback callback) { callback.userListChange(); } } } /// /// 移除窗口 /// /// public void removedWin(object win) { if (WinDic.ContainsKey(win.GetType())) { WinDic.Remove(win.GetType()); } } /// /// Socket关闭事件 /// /// /// void WebSocket_Closed(object sender, EventArgs e) { _Logger.Info("websocket_Closed"); } /// /// Socket报错事件 /// /// /// void WebSocket_Error(object sender, ErrorEventArgs e) { _Logger.Info("websocket_Error:" + e.Exception.ToString()); } /// /// Socket打开事件 /// /// /// void WebSocket_Opened(object sender, EventArgs e) { SendMessage(SocketMsgManger.AddMsg()); _Logger.Info(" websocket_Opened"); SendMessage(SocketMsgManger.offlineMsg()); } /// /// 检查重连线程 /// private void CheckConnection() { do { try { if (this._webSocket.State != WebSocket4Net.WebSocketState.Open && this._webSocket.State != WebSocket4Net.WebSocketState.Connecting) { _Logger.Info(" Reconnect websocket WebSocketState:" + this._webSocket.State); this._webSocket.Close(); this._webSocket.Open(); Console.WriteLine("正在重连"); } } catch (Exception ex) { _Logger.Error(ex.ToString()); } System.Threading.Thread.Sleep(5000); } while (this._isRunning); } /// /// 心跳 /// private void Heartbeat() { do { try { if(_webSocket != null && _webSocket.State == WebSocket4Net.WebSocketState.Open) { byte[] bt = new byte[] { 01 }; _webSocket.Send(bt, 0, 1); Console.WriteLine("心跳:" + DateTime.Now.ToString()); } } catch (Exception ex) { _Logger.Error(ex.ToString()); } Thread.Sleep(10000); } while (true); } #endregion /// /// 发送消息 /// /// public void SendMessage(string Message) { Task.Factory.StartNew(() => { if (_webSocket != null && _webSocket.State == WebSocket4Net.WebSocketState.Open) { this._webSocket.Send(Message); Console.WriteLine("WS:发送消息:" + Message); } }); } public void Dispose() { this._isRunning = false; try { _thread.Abort(); } catch { } this._webSocket.Close(); this._webSocket.Dispose(); this._webSocket = null; } } }