经过前面几篇文章javascript
史上最全面的SignalR系列教程-一、认识SignalRcss
史上最全面的SignalR系列教程-二、SignalR 实现推送功能-永久链接类实现方式html
史上最全面的SignalR系列教程-三、SignalR 实现推送功能-集线器类实现方式java
RDIFramework.NET敏捷开发框架经过SignalR技术整合即时通信(IM)jquery
咱们对SignalR的概念以及SignalR的最主要的两类通讯模型(Persistent Connections与Hubs)进行了详细的对比讲解,也作了案例展现。本篇将为你们介绍.NET特有的Self-Host自托管的应用,即以Self-Host自托管为宿主加载SignalR服务。git
宿主一词咱们不会陌生,它能够看做是一个基础设施,它为一些服务和功能提供最底层的支持,如你的web应用程序能够运行在iis或者apache上,而这两个东西就是web应用程序的宿主,而今天说的自主宿主SelfHost它能够本身去监听本身的服务,如你能够把一个web应用程序宿主到一个console控制台程序上,或者把一个webApi宿主到一个console或者windowService上,这都是能够的。github
Self-Host的介绍咱们能够参考msdn官方事例https://docs.microsoft.com/en-us/dotnet/framework/wcf/samples/self-host 这是一个wcf的事例。web
SignalR经常依托于ASP.NET应用程序运行于IIS中,但它还能够自我托管(好比做为console winform、Windows service),只要咱们使用self-host库就能够了。该库向全部的SignalR 2库同样,构建于OWIN (Open Web Interface for .NET)。OWIN定义了一个在.NET web 服务端和web 应用程序的抽象。OWIN解耦了从服务端来的web 应用程序,这使得OWIN对于子托管web应用程序于本身的进程中得以表现得很完美。apache
有的小伙伴可能就要问了,为何必定要使用这种方式来托管呢?基于IIS的方式不是更简单吗?不托管于IIS的缘由主要有如下方面的考虑:跨域
本篇主要讲解如下内容:
为了更简单的说明self-host托管的方式,咱们用控制台应用程序来作演示。固然咱们也能够自托管到Windows服务中去,若是你更但愿托管到Windows服务,能够参考Self-Hosting SignalR in a Windows Service
在上一项目的基础上,咱们新建一个名为:SignalRSelfHost的控制台应用程序,以下所所示:
要使用Selft-Host宿主SignalR,必须引用Microsoft.AspNet.SignalR.SelfHost包。咱们在程序包管理控制台输入如下命令安装SelfHost包。
Install-Package Microsoft.AspNet.SignalR.SelfHost
要想支持跨域访问,还须要安装
Install-Package Microsoft.Owin.Cors
若是用命令的方式安装失败,咱们能够用NuGet的方式安装,以下图所示。
编写代码以下:
using Microsoft.AspNet.SignalR; using Microsoft.Owin.Cors; using Microsoft.Owin.Hosting; using Owin; using System; namespace SignalRSelfHost { class Program { static void Main(string[] args) { // This will *ONLY* bind to localhost, if you want to bind to all addresses // use http://*:8080 to bind to all addresses. // See http://msdn.microsoft.com/en-us/library/system.net.httplistener.aspx // for more information. string url = "http://localhost:8077"; using (WebApp.Start(url)) { Console.WriteLine("SignalR Server running on {0}", url); Console.ReadLine(); } } } /// <summary> /// 该类含有SignalR服务端的配置(该教程使用的惟一的配置是用来调用UseCors), /// MapSignalR为全部形式的Hub对象建立了路由规则 /// </summary> class Startup { public void Configuration(IAppBuilder app) { app.UseCors(CorsOptions.AllowAll); app.MapSignalR(); } } /// <summary> /// SignalR的Hub 类是程序要提供给客户端的 /// 该类就一个方法,Send:客户端能够用来发送消息给其余客户端 /// </summary> public class MyHub : Hub { //服务端的方法,客户端能够去调用 public void Send(string name, string message) { //调用客户端的方法addMessage(string s1,string s2); Clients.All.addMessage(name, message); } } }
代码说明:
Program:包含程序的主方法。在这个方法中,类型为Startup的web应用程序启动于指定的URL (http://localhost:8077)。 若是须要更加安全一点,能够支持SSL,请去这里看看How to: Configure a Port with an SSL Certificate
Startup: 该类含有SignalR服务端的配置(该教程使用的惟一的配置是用来调用UseCors), MapSignalR为全部形式的Hub对象建立了路由规则。
MyHub:SignalR的Hub 类是程序要提供给客户端的。 该类就一个方法:Send, 客户端能够用来发送消息给其余客户端。
编译运行SignalR控制台服务端以下。
能够看到咱们的控制台服务端已经成功启动起来了。
代码以下:
<!DOCTYPE html> <html> <head> <title>SignalRSelfHostJSClient Chat</title> <style type="text/css"> .container { background-color: #a1c6ec; border: thick solid #e62fc7; padding: 20px; margin: 20px; } </style> </head> <body> <div class="container"> <input type="text" id="message" style="width:350px;" placeholder="请输入消息内容..."/> <input type="button" id="sendmessage" value="发送" /> <input type="hidden" id="displayname" /> <ul id="discussion"></ul> </div> <!--Script references. --> <!--Reference the jQuery library. --> <script src="Scripts/jquery-1.6.4.min.js"></script> <!--Reference the SignalR library. --> <script src="Scripts/jquery.signalR-2.4.1.min.js"></script> <!--Reference the autogenerated SignalR hub script. --> <script src="http://localhost:8077/signalr/hubs"></script> <!--Add script to update the page and send messages.--> <script type="text/javascript"> $(function () { //Set the hubs URL for the connection $.connection.hub.url = "http://localhost:8077/signalr"; // Declare a proxy to reference the hub. var chat = $.connection.myHub; // Create a function that the hub can call to broadcast messages. chat.client.addMessage = function (name, message) { // Html encode display name and message. var encodedName = $('<div />').text(name).html(); var encodedMsg = $('<div />').text(message).html(); // Add the message to the page. $('#discussion').prepend('<li><strong>' + encodedName + '</strong>: ' + encodedMsg + '</li>'); }; // Get the user name and store it to prepend to messages. $('#displayname').val(prompt('Enter your name:', '')); // Set initial focus to message input box. $('#message').focus(); // Start the connection. $.connection.hub.start().done(function () { $('#sendmessage').click(function () { // Call the Send method on the hub. chat.server.send($('#displayname').val(), $('#message').val()); // Clear text box and reset focus for next comment. $('#message').val('').focus(); }); }); }); </script> </body> </html>
先运行SignalRSelfHost控制台服务端后,再运行两个咱们的测试客户端,分别输入不一样的用户名,试试聊天的效果,以下图所示。
编写界面代码以下:
using Microsoft.AspNet.SignalR.Client; using System; using System.Configuration; using System.Windows.Forms; namespace SignalRSelfHostWinFormClient { /// <summary> /// SignalRSelfHost WinForm测试客户端 /// 用于接收消息(需配合SignalRSelfHostJSClient项目使用) /// </summary> public partial class SignalRSelfHostWinFormClientTest : Form { //定义代理,广播服务链接相关 private static IHubProxy HubProxy { get; set; } private static readonly string ServerUrl = ConfigurationManager.AppSettings["SignalRServer"]; //定义一个链接对象 public static HubConnection Connection { get; set; } public SignalRSelfHostWinFormClientTest() { CheckForIllegalCrossThreadCalls = false; InitializeComponent(); } private void SignalRSelfHostWinFormClientTest_Load(object sender, EventArgs e) { Connection = new HubConnection(ServerUrl); Connection.Closed += Connection_Closed; HubProxy = Connection.CreateHubProxy("MyHub"); HubProxy.On<string, string>("addMessage", RecvMsg);//接收实时信息 Connection.Start().ContinueWith(task => { if (!task.IsFaulted) { msgContent.AppendText(string.Format("与Signal服务器链接成功,服务器地址:{0}\r\n",ServerUrl)); } else { msgContent.AppendText("与服务器链接失败,请确认服务器是否开启。\r\n"); } }).Wait(); } private void Connection_Closed() { msgContent.AppendText("链接关闭...\r\n"); } private void RecvMsg(string name, string message) { msgContent.AppendText(string.Format("接收时间:{0},发送人:{1},消息内容:{2},\r\n", DateTime.Now, name, message)); } } }
经过以上的详细讲解,咱们已经很是清楚的了解了如何经过SignalR打通各终端以实现相互沟通的通讯。例子虽然比较简洁,但彻底能够以此为基础,扩展更复杂的业务应用。
实例源码能够移步github下载,地址:https://github.com/yonghu86/SignalRTestProj
一路走来数个年头,感谢RDIFramework.NET框架的支持者与使用者,你们能够经过下面的地址了解详情。
RDIFramework.NET官方网站:http://www.rdiframework.net/
RDIFramework.NET官方博客:http://blog.rdiframework.net/
同时须要说明的,之后的全部技术文章以官方网站为准,欢迎你们收藏!
RDIFramework.NET框架由海南国思软件科技有限公司专业团队长期打造、一直在更新、一直在升级,请放心使用!
欢迎关注RDIFramework.net框架官方公众微信(微信号:guosisoft),及时了解最新动态。
扫描二维码当即关注