【求教】高手讲下C#Socket的长连接和短连接的问题
这个和C#无关,而是和SOCKET你如何用有比较大的关系,和具体场景无关。
现在有服务器A,客户端B、C
长连接:顾名思义,就是连接一旦连上就保持连接状态不关闭,举个例子,B现在要跟C聊天,然后通过服务器A中转后和C连接上了,B完成和C聊天后,这个用于发送消息的SOCKET不关闭而仍然维持连接状态就是长连接(只是举个例子,比如软件考虑到B和C可能过一阵还会聊天)了。
短连接:顾名思义,就是维持时间比较短的连接,在实际中就是该SOCKET当前任务一旦结束就关闭连接。用到上面的例子就是B和C聊完后,SOCKET就关闭了,下次需要聊天的时候重新连接。
关于长连接和短连接以前讨论的人很多,一般认为长连接效率高,因为不需要反复去连接,但是容易堵塞,那就麻烦了,到底丢了多少包都不清楚。而短连接恰好相反。
一般在用的时候,尽可能的SOCKET专用,即发送消息的SOCKET专门发送消息,传文件的SOCKET专门传文件。如果要用长连接,最好在自己的协议上考虑到心跳包,即过一阵发一个心跳包看对方是否有响应来确定是否SOCKET阻塞了,是否掉线了等等。
这个就不需要代码了吧,几句话就通了
没有信令服务器,各个WebRTC之间是没办法通信的。
传递媒体数据有两个信息,必须经过信令服务器进行交换
通过SDP来表示,如编解码器是什么?是否支持音频视频?编码方式是什么?等
这些信息是通过SDP协议描述出来,通过信令服务器中转的
两个WebRTC客户端会尽可能选择P2P进行连接,那么进行连接前是如何发现对方的?就是通过信令服务器。
首先将你所有网络相关信息传到信令服务器,服务器帮你交换到对端,对端拿到你的信息后,
若在同一局域网内,直接通过P2P传输;若不在,首先进行P2P穿越,看是否能打通,打通则传输,打不通则中转等。
还有一点也需要信令服务器进行传输,比如加入房间,离开房间,禁言等功能
在传输时,一般有两种协议 TCP和 UDP
底层协议使用 UDP主要用于流媒体传输(音频视频)还有文本,文字聊天等,但 UDP是不可靠传输,是可以丢包的,当然音频视频是可以丢包的,丢失一帧只会卡顿下,还可以继续工作。
但信令服务器不能丢失数据,所有的包必须保证到达,否则断开连接,所以信令服务器一般使用TCP可靠性传输。
websocket底层使用的就是 TCP协议, socketio 使用的也是TCP
在websocket官方中,是有三个服务器的,ROOM服务器(提供用户进出房间服务)、信令服务器、流媒体(中转)服务器
选用socketio 即不用单独写ROOM服务器,这里ROOM和信令是同一个服务器
socketio是一个基于Nodejs的库,在现有的Node Server上增加个socketio即可
在任何终端都可以引入socketio客户端的库,通过客户端的库就可以连接到 Nodejs中 socketio服务器上
这样就可以建立连接,然后就可以创建,加入房间,这样房间内的人就可以通信了
多个 sockeio可以串行通信。
手机之间互相socket如果是内网之间是没问题的,如果是广域网存在很多问题,涉及到网络穿透,直接连接是万万不行的。必须通过中间服务器,实现了网络穿透连接,然后手机和手机才能直连。具体你可以查查百度 tcp 穿透。
socket
服务器给指定的客户端发消息该怎么处理(tcp)(c语言)
多个客户端之间进行通讯,通过服务器转发的形式,现在客户端1请求向客户端2发送消息,先把消息发送到服务器,服务器怎么才能把消息转发到客户端2而不是转发给客户端3或者他自己。
WebRTC ,名称源自 网页即时通信 (英语:Web Real-Time Communication)的缩写,是一个支持网页浏览器进行实时语音对话或视频对话的 API。它于 2011 年 6 月 1 日开源并在 Google、Mozilla、Opera 支持下被纳入万维网联盟的 W3C 推荐标准。
首先,他即是 API 也是协议。
其次,他是浏览器进行音频与视频通话的 API,其实还有屏幕共享的功能。
最后,它现在已经处于 W3C 标准,各大浏览器厂商已经对他进行兼容了。
但是如果我们想使用好 webrtc,就得先了解 websocket。而对于 websocket,大家应该都比较熟悉了,比如社交聊天、多人 游戏 、协同编辑、视频会议、基于位置的应用(地图)、等等需要高实时的场景。我们比较常用的微信、QQ、某些直播软件等等也都是基于 websocket 实现消息与信令的转发。大家看到这里可能在信令这里迟疑了,接着看。
webrtc 是 P2P 的一种技术,什么是 P2P?其实就是 端对端,就说是你的音频、视频流不经过服务器中转,直接由一端发送到另一端。
不经过服务器中转,也就说时候,如果通过过程中服务器突然崩溃,是不是通话还能继续?
是的!但是发送音频视频流前,一定是需要建立 P2P 连接的,建立连接前一定需要服务器进行信令转发,这个信令就是通话两端的标识。
而如果想用 webrtc 实现通话,就得先中转信令、建立连接。而建立连接的话最好是要用 websocket 进行信令转发的。大家都知道,websocket 是个通道,在这个通道的所有端,都可以收到任意一端的消息流,包括发消息的本人。
为什么不经过服务器就可以直接获取到对方的视频音频流呢?是因为建立了 P2P 通道,这个 P2P 在中转信令的时候就已经通了,传输视频音频流的时候还要啥服务器啊。这个时候,肯定有小伙伴表示怀疑,音频视频流可以不通过服务器?是的,我骗了大家,确实要经过服务器,但是只是线上需要服务器转发,如果我们是本地两台或者多台同一局域网的端 进行 webrtc 音频视频流的转发,确实不需要中转服务器,但是线上有可能需要,也有可能不需要,这里又涉及到了一个 打洞 的概念。
我们平常可能会听到比较牛 x 的词汇,什么打洞、内网穿透、NAT 穿越,各种高大上的东西,其实也是蛮好理解的。大家都知道,两个不同网络下的两台主机不可以直接进行通信,而是需要走公网或者说各自的网关。打洞、内网穿透、NAT 穿越其实就是一个意思,就是使用 udp 让我们两台非同一网络的主机互联,不走公网,直接实现连接。有玩过花生壳的同学一定能理解内网穿透这个概念。
本地开发的话,两台主机连同一局域网,根本不需要内网穿透,就可以直接通信。
线上开发的话,如果能够 STUN 打洞成功,也不需要中转服务器。但是,有打洞不成功的概率,为什么呢,因为没有走公网,没有给运营商带来收益却带来通信成本,肯定要限制。国外打洞成功的概率在 70%,但是国内 50%都不到。
所以,为了防止打洞不成功的情况,我们使用 TURN 中转服务器 转发流媒体数据进行一个最后保障。此外还有一种方式为 逆向连接 ,也可以帮助我们实现 P2P 建立,他的原理是必须是一方走公网,也是有局限性的。
coturn 中继服务器由两部分组成 STUN 与 TURN,STUN 帮助我们打洞,TURN 帮助我们转发流媒体数据。
##连接过程
以下所有 API 截止到 20211206 为最新
##我有疑问
给大家看看 sdp 的本质,就是自身的媒体信息和编解码信息
一个 offer,一个 answer,我们彼此都知道对方的媒体信息与编解码信息,这样我们才能好好协商,我这边该用什么方式对你的视频音频流进行解码、渲染。
过程有些繁杂,具体流程小伙伴们可以看这篇文章 WebRTC TURN 协议初识及 turnserver 实践。
了解 webrtc 的音视频采集、桌面采集;
了解 websocket 和 webrtc 的整个链路建立过程;
实现 1V1 文字传输、视频通话、语音通话、屏幕共享;
实现视频通话、语音通话、屏幕共享过程中的截图、录音、录屏及 截图、录音、录屏的在线播放与下载;
将以上功能部署上线;
在这里,我们要对音视频建立过程画一个基本的流程图。
基本流程图
对于这些信令,我们使用 websocket 进行转发,这里大家会问,为什么不使用 http?
首先,我们的要实现的 demo 本来就含有发送普通文本消息的功能,就是使用 websocket。(长短轮询太老了,性能太差)
其次,第一点可以忽略,http 的请求会打回原路,A 向服务器请求,绝对不会传向 B。
但是如果我们要使用 websocket 转发信令,就要清楚的了解,在同一管道的所有端都会收到这条消息。所以,对于上面流程图来说,其实所有的小箭头都是双向的。
这时候,我们可以在 node 服务中来控制推送消息的方向,也可以在客户端来控制,这里我选择在 AB 端来控制。
其次,我们在本地开发,如果使用一台电脑,两个浏览器的形式,websocket 文字消息是可以的。但是音视频通话不行,因为不管是传输通道还是音视频设备(麦克、扬声器等)都是冲突的。所以,我们可以通过同一局域网,使用两台电脑解决这个问题。并且,因为 webrtc 的安全限制,必须使用 https(不管是线上还是本地)与域名,我们可以通过线上配置 https 与域名,本地设置浏览器忽略 https 与配置 host 文件映射来解决这个问题。
接下来,我们使用 vue 和 nodejs,可以最快最简单的实现 demo。
废话少说,我们开撕!
展示部分代码
这里我使用 socketio 这个第三方包,快速的首发消息,转发信令。(建议大家使用 vue-socketio)可以在组件中收发消息与信令。
将 socket-io 的 websocket 建立连接与接收消息,接收信令放到 vuex 中。
同样,我们在 node 服务中,也是使用 socket-io 这个包
对于视频、音频、及屏幕共享来说,代码都是类似的。所以,举例视频采集。
通过使用 getUserMedia,我们可以采集到音视频双轨的媒体流,我们传入一个参数 constraints,这个参数可以配置(控制采集音频还是视频)
将采集到的动态媒体流赋值给 video 标签,我们自己的画面就显示在网页上了。
同样,如果是音频采集,只需要配置参数 constraints 中的 audio 为 false 即可。
电脑屏幕采集,只需要将 getUserMedia 这个 API 替换为 getDisplayMedia 即可。
此时视频端发起端,采集到了媒体流后,需要发送 apply 信令给接收端。这个信令是询问接收端是否接起视频通话。
如果接起,接收端会采集自己的音视频双轨的媒体流,并且初始化 peerconnection,将媒体流放入此管道,监听 ICE 候选信息 如果收集到,就发送给对方,并将自己的同意信令 reply,回复给视频发起端。
如果拒绝接起,接收端会回复一个拒绝的信令给视频发起端。
接收端此时收到拒绝,会关闭视频音频流的采集。
接收端此时收到接起,会初始化 peerconnection,并将自己的媒体流放入此管道,监听 ICE 候选信息 如果收集到,就发送给对方。并且创建一个 offer(此 offer 包含 sdp),将 offer 放到本地后,发送 offer 给视频接收端。
视频接收端接收到 offer,放到自己的远端,并且创建一个 answer,将 answer 放到本地后,发送给视频发起方。
视频发起方接收到 answer,将 answer 放到远端。
此时,接收和发起端都在监听 ICE 候选信息 如果收集到,就发送给对方。一但监听到了就将对方的动态媒体流赋值给 B,播放出来。
截图:我们可以使用 canvas 利用相关方法 getContext("2d")drawImage , 实现 web 层面的截取。
录音/录像/录屏:使用 MediaRecorder 将我们的媒体流或者对方的媒体流保存到数组中。
只需要将保存的静态媒体流赋值给 video 标签
同理,我们可以将音视频流下载下来。
部署 webrtc 重要的两个条件:域名 与 https,我们需要配置这两块。
我们的 node 服务不仅是 https+域名,websocket 也需要更为安全的 wss 协议,我们需要给我们的 websocket 配置 wss。
在前面我们也提过,本地开发之所以能够成功,并且有效果,是因为内网是直接通信的,并没有走公网,也就没有实现内网穿透。
如果我们想要在线上实现这个功能,我们必须配置 coturn 中转服务器。centos 内核的配置文章可以参考 这篇,ubuntu 内核的配置参考 这篇。
在开发和上线后能够发现以下几个问题。
环境、设备、信号溢出、算法不兼容产生的噪音、声学与线路产生的回音、网络拥塞及数据包传输速率不稳定产生的延迟。
我们可以通过接入一些算法及提高硬件设备质量,来减少噪音回音,降低延迟。
对于噪音,采集音频时可以设置 noiseSuppression: true ,可以降低 一些环境及设备的噪音。
对于回声,采集音频时可以设置 echoCancellation: true ,可以去除回声。
剩下的交给算法、设备和网络来处理了。
在这方面的 探索 ,我就到此为止了,大家可以接着研究 WebRTC 传输是如何保证音视频服务质量 ,研究一下成熟应用是如何解决这三大难点的。
大家在视频通话过程中,可以使用多种特效。美颜、贴纸等等。
然而在 webrtc 的 web 端领域,视频特效领域是非常潜的。造成这种情况的原因是 js 的性能问题。
比较简单的方法就是使用 canvas 画布,对我们的视频图象加一层滤镜,但是在本质上并没有改变媒体流。传输到远端仍然是没有特效的。当然,我们可以通过 websocket 控制远端的视频特效,但是由于视频流没有改变,对方如果下载视频流的话,播放出来仍然是没有特效的。
另一种方案如下,这里我就不做赘述,大家可以思考一下是如何实现的(以下为简单特效与贴纸)。
需要创建 n-1 个 PeerConnection 连接,因为我们要与 n-1 个人进行视频共享,每个人都是这样。但是这里会涉及谁主动发 offer 的问题。我们可以让新加入的成员向其他 n-1 个成员发送 offer,也可以使 n-1 个成员向新加入的成员发送 offer。这里我们可以用遍历的方式生成 PeerConnection 和 offer。当然多人通话就看你服务器顶不顶的住了。
这里我们就不知情的使用了多端通信的知名通信方案——Mesh,Mesh 就是两两通信从而形成网状结构。除了 Mesh 这种通信方案,还有 MCU,MCU 方案主要是将同一房间的所有终端的音视频流进行混合然后发向各个终端,这样服务器的压力其实是非常巨大的。另外还有 SFU 通信方案,中转服务器收到某终端音视频流后,单一转发到其他终端。
经过上面一系列的理解、思考、构建、开发、部署等等,我们对 webrtc 有了一些初步的了解及认识。对于这方面的研究与 探索 我们都要继续继续深入下去。因为满足我们的好奇心与求知欲,提升我们的这一领域的技术,丰富我们整体的知识体系,何乐而不为呢。
最后,以上所有的内容都来源于资料、个人实验及个人总结,文中有错的地方希望大家及时指正。
两种方法:
方法一:使用代理服务器
使用代理服务器的第一步是要获取代理服务器的IP 地址和端口信息,我们可以使用搜索引擎到网上搜索,而使用"QQ代理公布器"可以很快速地找到合适的代理服务器,将"QQ代理公布器" 下载地址:点击这里进入下载页面下载并安装到系统中并运行,然后在主窗口中选择代理类型,例如Socks5,再单击"读数据"按钮即可获取一批不同地区的代理服务器。
提示:
1为了获得工作状态正常的服务器IP地址,在搜索之前选择"是否测试代理"选项,这样搜索到的服务器使用成功率将更高。
2QQ程序目前支持两种代理服务器,一个是Socks5,另一个是HTTP11,其中的Socks和HTTP都是通讯协议,也就是这个代理服务器提供服务的通讯协议。
得到了代理服务器的IP地址后,单击QQ主窗口中的"QQ菜单系统参数",在打开的窗口中选择"网络设置"标签,选择代理服务器类型,然后将代理服务器的IP和端口号输入,单击"测试"按钮测试一下该服务器是否工作正常;得到了工作正常的信息后,单击"确定"按钮并重新登录QQ即可生效。
方法二:让QQ2自免疫
如果你使用的是最新版的QQ程序,单击"QQ菜单系统参数",在打开的窗口中选择"安全设置",然后将右侧窗口中的"通讯模式选择"设置为"通过服务器模式与好友交换信息"。
最后单击"确定"退出并重新登录QQ即可,这样设置之后,对方QQ聊天窗口中得到的将是"无法取得对方IP,消息将通过服务器中转"这将令对方大失所望。
隐藏IP
使用代理服务器是一种简单有效的隐藏IP法,具体操作是:打开QQ的“系统参数”,单击“网络设置”,选中“使用SOCKET5代理服务器”。在“代理服务器地址”、“端口号”、处输入你寻找的免费代理地址,端口号为:1080;校验用户名和密码一般不用填。点击“测试”按钮,如果你填入的代理地址有效,则会弹出“代理服务器工作正常”提示框,否则就会弹出“无法连接到代理服务器”的提示。上述步骤做完之后,最后点击“确定”完成。代理服务器的地址很多网站有提供,自己用工具(如“代理猎手”)也可以找到很多。要特别注意的一点是:按照上述方法找到确实可用的代理服务器后,要先退出QQ,再启动QQ重新登录,这样才会改变QQ的IP,否则QQ的IP不会改变的。代理服务器有时候会失效,需要换一个新的服务器。用此方法只能隐藏QQ的IP,即别人通过一般的QQ工具查不到你的真实IP地址,但高手还是有办法查出你的真实IP的
0条评论