SignalR介绍简单示例教程入门版

ASP .NET SignalR 是一个ASP .NET 下的类库,可以在ASP .NET 的Web项目中实现实时通信。什么是实时通信的Web呢?就是让客户端(Web页面)和服务器端可以互相通知消息及调用方法,当然这是实时操作的。

WebSockets是HTML5提供的新的API,可以在Web网页与服务器端间建立Socket连接,当WebSockets可用时(即浏览器支持Html5)SignalR使用WebSockets,当不支持时SignalR将使用其它技术来保证达到相同效果。

SignalR当然也提供了非常简单易用的高阶API,使服务器端可以单个或批量调用客户端上的JavaScript函数,并且非常 方便地进行连接管理,例如客户端连接到服务器端,或断开连接,客户端分组,以及客户端授权,使用SignalR都非常 容易实现。

SignalR 将与客户端进行实时通信带给了ASP .NET 。当然这样既好用,而且也有足够的扩展性。以前用户需要刷新页面或使用Ajax轮询才能实现的实时显示数据,现在只要使用SignalR,就可以简单实现了。

最重要的是您无需重新建立项目,使用现有ASP .NET项目即可无缝使用SignalR。

最近因为项目中涉及到了实时数据的传输,特地去了解了一下当前Web应用中常见的实时交互手段,当然一开始也不仅限于Web客户端。从c#自带的Socket类,到Html5中的WebSocket,再到Asp .Net利器SignalR,总算将这块知识点及应用入门了,当然今天的主要内容还是Web端的消息交互技术(Ajax,Comet,WebSocket等),这些技术难度有中有低,应用场所也有不同,最后我们要根据项目情况来选择恰当的技术。接下来便简单介绍一下

Web消息交互技术

常见技术

应用技术

说明

优缺点

轮询(polling)

这应该是最常见的一种实现数据交互的方式,开发人员控制客户端以一定时间间隔中向服务器发送Ajax查询请求大,但是也因此,当服务器端内容并没有显著变化时,这种连接方式将带来很多无效的请求,造成服务器资源损耗。适合并发量小,实时性要求低的应用模型,更像是定时任务。

优点:实现最为简单,配置简单,出错几率小 缺点:每次都是一次完整的http请求,易延迟,有效请求命中率少,并发较大时,服务器资源损耗大

长轮询(long polling)

长轮询是对轮询的改进,客户端通过请求连接到服务器,并保持一段时间的连接状态,直到消息更新或超时才返回Response并中止连接,可以有效减少无效请求的次数。属于Comet实现

优点:有效减少无效连接,实时性较高 缺点:客户端和服务器端保持连接造成资源浪费,服务器端信息更新频繁时,long polling并不比polling高效,并且当数据量很大时,会造成连续的polls不断产生,性能上反而更糟糕

iframe流

iframe流方式是在页面中插入一个隐藏的iframe,利用其src属性在服务器和客户端之间创建一条长链接,服务器向iframe传输数据(通常是HTML,内有负责插入信息的javascript),来实时更新页面。属于Comet实现

优点:实时性高,浏览器兼容度好 缺点:客户端和服务器端保持长连接造成资源浪费

WebSocket

WebSocket是HTML5提供的一种在单个 TCP 连接上进行全双工通讯的协议,目前chrome、Firefox、Opera、Safari等主流版本均支持,Internet Explorer从10开始支持。另外因为WebSocket 提供浏览器一个原生的 socket实现,所以直接解決了 Comet 架构很容易出错的问题,而在整個架构的复杂度上也比传统的实现简单得多。

优点:服务器与客户端之间交换的数据包档头很小,节约带宽。全双工通信,服务器可以主动传送数据给客户端。 缺点:旧版浏览器不支持

Comet 简介

浏览器作为 Web 应用的前台,自身的处理功能比较有限。浏览器的发展需要客户端升级软件,同时由于客户端浏览器软件的多样性,在某种意义上,也影响了浏览器新技术的推广。在 Web 应用中,浏览器的主要工作是发送请求、解析服务器返回的信息以不同的风格显示。AJAX 是浏览器技术发展的成果,通过在浏览器端发送异步请求,提高了单用户操作的响应性。但 Web 本质上是一个多用户的系统,对任何用户来说,可以认为服务器是另外一个用户。现有 AJAX 技术的发展并不能解决在一个多用户的 Web 应用中,将更新的信息实时传送给客户端,从而用户可能在“过时”的信息下进行操作。而 AJAX 的应用又使后台数据更新更加频繁成为可能。

WebSocket介绍

WebSocket本质上是一个基于TCP的持久化协议,相对于HTTP这种非持久的协议来说,它能够更好的节省服务器资源和带宽,并且真正实现实时通信。以下是它与传统技术的性能对比图(Websocket.org提供)

我们可以看到相比于传统技术,在流量和负载逐渐增大时,WebSocket的性能表现是远远超过它们的。

SignalR是什么

SignalR是一个.Net开源库,用于构建需要实时进行用户交互和数据更新的Web应用,如在线聊天,游戏,天气或者股票信息更新等实时应用程序。SignalR简化了构建实时应用的过程,它包括了一个Asp .Net服务器端库和一个Js端库,集成了数种常见的消息传输方式,如long pollingWebSocket,并提供相应的Api供开发人员选择如何调用,帮助其可以简单快速地实现客户端与服务器端相互间的实时通信。当环境条件合适时,SignalR将WebSocket作为底层传输方式的优先实现,当然,它也能很高效地回退到其他技术。同时,SignalR提供了非常良好的Api以供远程调用(RPC) 浏览器中的js代码。接下来,看看SignalR的传输方式和通信模型,这是SignalR的核心所在。

SignalR基本适用于任何可以用上述技术实现的场合,但是对寄宿平台版本有要求。如.Net Framework 平台,SignalR库需要4.5及以上版本的支持,而Mono上也实现了SignalR。如果是最新的.Net Core 1.0,建议大家直接使用SelfHost方式寄宿。

默认传输方式

传输方式

选择条件

long polling

1.IE8或更早版本 2.连接启动时JSONP参数设置为TRUE 3.Forever Frame不可用

WebSocket

1.正在使用跨域连接,并且符合以下条件(以下不满足任一条则使用长轮询) (1).客户端支持CORS (2).客户端支持WebSocket (3).服务器端支持WebSocket 2.不配置使用JSONP,连接不跨域并且客户端和服务器端都支持WebSocket (1).客户端支持CORS (2).客户端支持WebSocket (3).服务器端支持WebSocket

ServerSendEvent

客户端或服务器端不支持Websocket

Forever Frame

EventSource不可用(基本上除了IE外都支持)

自动管理传输方式

不指定传输方式时,SignalR会以Http方式发起请求,比对客户端和服务器端后,假如WebSocket可用,则自动升级到WebSocket模式,WebSocket是最理想的传输方式,除了能高效使用服务器内存,低延迟,还能实现客户端和服务器端的全双工通信。开发人员可以通过SignalR中js库的$.connection.chatHub.logging = true;来启用hub事件的日志记录

通信模型

SignalR包括两种客户端和服务器端之间进行通信的模型,Persistent ConnectionsHubs

通信模型

说明

Persistent Connections

Persistent Connections表示一个发送单个,编组,广播信息的简单终结点。开发人员通过使用持久性连接Api,直接访问SignalR公开的底层通信协议。

Hubs

Hubs是基于连接Api的更高级别的通信管道,它允许客户端和服务器上彼此直接调用方法,SignalR能够很神奇地处理跨机器的调度,使得客户端和服务器端能够轻松调用在对方端上的方法。使用Hub还允许开发人员将强类型的参数传递给方法并且绑定模型

SignalR具体开发步骤

Hubs的示例网上已经很多了(文章末尾附上链接),这边先来快速开始一个SignalR使用永久连接的Demo.

关于永久连接和Hubs的区别,这里有些很棒的解释.

(1)安装Nuget包

创建一个默认的Asp .Net Mvc项目使用Install-Package Microsoft.AspNet.SignalR安装SignalR包

(2)增加SignalR服务

新增Connections文件夹,添加SignalR永久连接类ChatConnections

using System.Threading.Tasks;using Microsoft.AspNet.SignalR;namespace SignalRUsingPersistentConnectionsDemo.Connections{    public class ChatConnection : PersistentConnection
    {        protected override Task OnConnected(IRequest request, string connectionId)        {            return Connection.Send(connectionId, "Welcome!");
        }        protected override Task OnReceived(IRequest request, string connectionId, string data)        {            return Connection.Broadcast(data);
        }
    }
}

(3)增加Startup启动类

using Microsoft.Owin;using Owin;using SignalRUsingPersistentConnectionsDemo;using SignalRUsingPersistentConnectionsDemo.Connections;

[assembly: OwinStartup(typeof (Startup))]namespace SignalRUsingPersistentConnectionsDemo{    public class Startup
    {        public void Configuration(IAppBuilder app)        {            // 有关如何配置应用程序的详细信息,请访问 http://go.microsoft.com/fwlink/?LinkID=316888
            // 配置上文实现的ChatConnections
            app.MapSignalR<ChatConnection>("/Connections/ChatConnection");
        }
    }
}

(4)前端js配置

前端js实现消息广播,并实时记录

@{
    Layout = null;
}<script src="~/Scripts/jquery-1.10.2.min.js"></script><script src="~/Scripts/jquery.signalR-2.2.0.min.js"></script><script type="text/javascript">
    $(function () {        var connection = $.connection("/Connections/ChatConnection");

        $('#displayname').val(prompt('Enter your name:', ''));
        $("msg").focus();

        connection.received(function (data) {
            $('#messages').append('<li>' + data + '</li>');
        });

        connection.start().done(function() {
            $("#broadcast").click(function () {
                connection.send($('#displayname').val()+':'+$('#msg').val());
            });
        });

    });</script><input type="text" id="msg" /><input type="button" id="broadcast" value="broadcast"/><input type="hidden" id="displayname" /><ul id="messages"></ul>

(5)实际效果

(6).Net Client实现

除了Web实时应用之外,你也可以用其他应用程序实现实时交互,如控制台。只需要Install-Package Microsoft.AspNet.SignalR.Client命令,示例编码如下

using Microsoft.AspNet.SignalR.Client;using static System.Console;namespace DotnetClientWithSignalRDemo{    internal class Program
    {        private static void Main(string[] args)        {            var connection = new Connection("http://localhost:1508/Connections/ChatConnection");

            connection.Received += WriteLine;
            connection.Start().Wait();            string line;            while ((line = ReadLine()) != null)
            {
                connection.Send(line).Wait();
            }
        }
    }
}

效果如图,同样实现了双向通信

简单示例教程入门版

SignalR的简单教程制作一个在线的聊天

  • 前端用了国产的一个MVVM框架 avalon 的早期版本和 layer 插件
  • MVC项目里面新增一个Hub 的继承类 ChatHub , 标签HubName 类似于一个重命名的效果
  • OnlineCache 类的作用是定义了一个KEY和VALUE主要用于记录用户名称和Signalr自动生成的KEY关系
  • Startup.cs 里记得注册下 app.MapSignalR();

原文发布于微信公众号 - 程序你好(codinghello)

原文发表时间:2018-04-27

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏张善友的专栏

ADO.NET的弹性连接控制[ADO.NET idle connection resiliency]

ADO.NET连接SQL Server有时候联机会无故的中断 (例如闲置过久或是交易时间太长等因素),这时又要重新连接,在.NET Framework 4.5之...

2019
来自专栏非著名程序员

强烈推荐 | 程序员七大生产力工具

简评:GitHub 是一个面向开源及私有软件项目的托管平台,同时它也为程序员提供了生产力工具,旨在帮助开发者更高效地构建软件。本文给大家推荐七种高效生产力工具。...

2725
来自专栏.NET后端开发

ADO.NET入门教程(二)了解.NET数据提供程序

摘要       在上一篇文章《你必须知道的ADO.NET(一) 初识ADO.NET》中,我们知道ADO.NET的两大核心组件分别是Data Provider和...

41311
来自专栏从零开始学自动化测试

Appium+python自动化9-SDK Manager

前言 SDK Manager到有哪些东西是必须安装的呢? 一、SDK Manager 1.双击打开SDK Manager界面 ? 2.Tools里面前三个是必须...

2986
来自专栏林德熙的博客

cant found Microsoft.VSSDK.BuildTools.15.0.26201

可以打开 EncodingNormalior\packages 文件夹,删除所有的文件,然后重新编译。

711
来自专栏张善友的专栏

MSDN Magazine 4月份asp.net文章

执行 Web 标准以便更加易于访问:       本文讨论了 Web 标准如此重要的原因,并给出了一些可用于创建符合标准的网站的技术。采用这些标准可能会有一定...

1939
来自专栏伪君子的梦呓

小白教程——安装和使用PyCharm

0.0 前言 上一个推送,我教大家怎么安装Python 3.X,安装完了,那我们肯定就是要用IDE (Integrated Development Envi...

6318
来自专栏晓晨的专栏

.NET Core 从 Github到 Nuget 持续集成、部署

1413
来自专栏小狼的世界

几款Linux下的日志书写工具

最近将工作环境切换到了Ubuntu 10.04 下,非常怀念原来的 Liver Writer,于是Google了一下,找找看Linux下是否有同样出色的离线博客...

832
来自专栏图像识别与深度学习

Android Studio

2718

扫码关注云+社区