而后,这拳头突然胀大,竟然形成了一个直径达到三丈的巨拳,狠狠的向着鲁修拍了下去。

.NET下使用socket.io随笔记录


一、问题背景

目前公司在互联网产品上需要程序与前端部分要进行一个实时交互,在进行一定程度上的选型后,决定使用socket.io框架进行一个实践,算是公司的一个新的 尝试,也算是给自己增加增长见闻,由于我是做后端以及桌面程序开发,所以前端部分就不细聊,主要是针对桌面程序如何连接socket.io进行一个尝试

二、基本逻辑图

  本地应用程序:部署在局域网内(可以联通外网),主要负责相关数据获取

  Web浏览器端:跟本地应用程序不是处于同一个网络,请求发起方

  中转服务(重点):中转服务集成认证功能,必须经过认证的客户端才允许进行连接,并且对于客户端要有唯一指定的ID进行连接操作

  整体思路如以上的流程图,由Web浏览器端开始发起请求,Web浏览器端通过连接中转服务,将信息发送给指定的本地应用程序,应用程序处理完成后,将结果通过原路径进行一个反馈

二、客户端程序开发

  客户端SDK采用SocketIoClientDotNet,这是一个github上开源的,可以连接socket.io的客户端,支持.net 3.5及以上,可以方便的帮助我们进行连接socket.io的开发

 Socket  socket = IO.Socket("ws://192.168.7.4:3000", new IO.Options()
            {
                Reconnection = true,
                Cookies = new Dictionary<string, string>() { { "companyId", GlobalStatic.COMPANY.COMPANY_ID }, { "userId", GlobalStatic.UserDomain.user.USER_ID } },
                Timeout = 60000,
                ReconnectionDelay = 1000,

                Transports = new List<string>() { "websocket" },
                Path ="heart"
            });

            socket.On(Socket.EVENT_CONNECT, () =>
            {

                JObject jObject = JObject.Parse(Newtonsoft.Json.JsonConvert.SerializeObject(new
                {
                    companyId = GlobalStatic.COMPANY.COMPANY_ID,
                    token = GlobalStatic.TOKEN,
                    hostId = GlobalStatic.HOST_ID,
                    hostName = GlobalStatic.HOST_NAME,
                    printerNames = GlobalStatic.HOSTINFO.PrinterName,
                    source = "assistant",
                    userId = GlobalStatic.UserDomain.user.USER_ID
                }));
                socket.Emit("authentication", jObject);
                Debug.WriteLine("authentication");
            });
            socket.On(Socket.EVENT_DISCONNECT, (data) =>
            {
                Debug.WriteLine("心跳断开连接" + data);
                flag = false;
                OnConnectionStatus?.Invoke(flag);
                socket.Disconnect();
            });
            socket.On("authenticated", (obj) =>
            {
                flag = true;
                OnConnectionStatus?.Invoke(flag);
                Debug.WriteLine("心跳认证成功:" + obj);
            });
            socket.On("unauthorized", (obj) =>
            {
                Debug.WriteLine("心跳认证失败" + obj);
                socket.Disconnect();
            });

SocketIoClientDotNet注意点:

  1. emit的数据必须为字符串或者JObject(Newtonsoft.Json中的)
  2. 从实际情况来看,内部每个On的监听都是维护了一个线程,所有如果是不想要阻塞的话,那在on的方法中还需要自己起线程去完成
  3. 如果不在options中设置AutoConnect=false的话,那实例化socket成功之后就会进行connect动作

三、关于SocketIoClientDotNet坑的问题

  在实际的使用过程中,偶然发现在程序开了很久 之后,线程数会一直增多,尝试调节各种参数都毫无作用,最后只能无奈的跟踪源码部分,在Thread文件夹下找到Heartbeat_net35.cs文件中,发现run方法里的while一直无法跳出去,并且注册DoWork越来越多,如下所示,导致线程越来越多,目前解决办法是将该代码注释掉,还没发现什么问题,如果有哪位知道这段代码作用的话,望告知,谢谢

using System;
using System.ComponentModel;
using System.Threading;

namespace Quobject.EngineIoClientDotNet.Thread
{
    public class Heartbeat
    {
        private volatile bool gotHeartbeat = false;
        private BackgroundWorker heartBeatTimer= new BackgroundWorker();
        private CancellationTokenSource ts;

        private Heartbeat()
        {
            ts = new CancellationTokenSource();
        }

        public static Heartbeat Start(Action onTimeout, int timeout)
        {
            Heartbeat heartbeat = new Heartbeat();
            heartbeat.Run(onTimeout, timeout);
            return heartbeat;            
        }

        public void OnHeartbeat()
        {
            gotHeartbeat = true;
        }

        private void Run(Action onTimeout, int timeout)
        {
            heartBeatTimer = new BackgroundWorker();

            heartBeatTimer.DoWork += (s, e) =>
            {
               while (!ts.IsCancellationRequested)
               {
                    System.Threading.Thread.Sleep(timeout);
                    if (!gotHeartbeat && !ts.IsCancellationRequested)
                    {
                        onTimeout();
                        break;
                    }
                }
            };

            heartBeatTimer.RunWorkerAsync();
        }

        public void Stop()
        {
            ts.Cancel();
        }
    }
}

  

作者: Mango

出处: http://www.cnblogs.com/OMango/

关于自己:专注.Net桌面开发以及Web后台开发,开始接触微服务、docker等互联网相关

本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出, 原文链接 如有问题, 可邮件(hongjb@yizit.com)咨询.

 

 

 

当前文章:http://hnhdqp.com/content/2018-10/13/content_27180.html

发布时间:2019-02-22 02:56:32

广州粤富网络科技 棋牌转让宁波 联众游戏手机版 怎么下载联众大厅 血战到底麻将单机版下载 牛总管官方下载31.97m 扑克牌玩游戏喝酒 德州扑克世界排名 德州扑克王online 扎金花可以强行开牌吗

编辑:建开戏

相关新闻

长安千万打造秦岭北麓绿色长廊

2019-02-22 04:21:17

吉安云抵商贸有限公司

长期用电脑应多吃哪些食物

2019-02-22 12:02:58

海南械酌有限责任公司

【魅力测试】你的异性魅力指数,这样算才准!

2019-02-22 08:34:16

长春秸济网络科技

就是好的手工艺品是需要时间的积累和沉淀的

2019-02-22 01:21:16

盐城温油科技股份有限公司

热门推荐

  • 【css3】旋转倒计时
  • ES6中let和闭包
  • 英特尔展示首块原型独立显卡
  • 首都互联网行业年度对话--技术创新
  • 荣耀京东自营新年特惠:爆品手机最高直降1000元
  • 死神来临之际,人体会发生怎样的变化?
  • 奢华运动风 宾利全新欧陆GT国内首发
  • 9999元新高度:联想Moto Z 2018正式开售
  • 新疆且末县发生3.8级地震 震源深度25千米
  • 连董建华也开始套现!李嘉诚王健林潘石屹这些大佬到底怎么了?
  • 河北新闻网版权所有 本站点信息未经允许不得复制或镜像 法律顾问:手机网站app制作 掌心诈金花
  • 途途真金炸金花 copyright ? 2000 - 2016
  • 新闻热线:0311-67563366 广告热线:0311-67562966 新闻投诉:0311-67562994
  • 冀ICP备 09047539号-1 | 互联网新闻信息服务许可证编号:1312006002
  • 广播电视节目制作经营许可证(冀)字第101号|信息网络传播视听节目许可证0311618号
  • 网狐荣耀棋牌app 棋牌游戏送10元 乐逗游戏官网 wpp麻将助手是真的吗