1、介紹javascript
SignalR對websocket、SSE、長鏈接、forever frame進行封裝。html
websocket(html5):ws協議,這個協議基於tcp的。也就是說和http沒有關係(兼容性很差)前端
SSE:客戶端訂閱服務器的一個事件,而後方便經過這個事件推送到客戶端。 server => client html5
長連接:保持一次連接的時間,例如保持一個連接5sjava
forever frame:在body中藏一個iframe,那麼這個iframe和server是一個永久連接,若是server來數據,經過這個連接推送到clientjquery
2、PersistentConnectionweb
1,參數redis
《1》 request: 獲取一些連接中的附加信息,request.querystring
request.cookie後端
request是一個katana的包裝類。跨域
singlaR 的request 實際上是asp.net 中的 Request的子集。
《2》 connectionId 這個參數就是 客戶端鏈接到服務器的惟一標識。。。也就說這個標識標識了客戶端。本質上來講,和SessionID是一個性質。 【GUID】
2,demo
using System; using System.Threading.Tasks; using Microsoft.Owin; using Owin; [assembly: OwinStartup(typeof(WebApplication1.Startup1))] namespace WebApplication1 { public class Startup1 { public void Configuration(IAppBuilder app) { // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=316888 app.MapSignalR<MyConnection1>("/connection"); } } }
using System; using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; using System.Web; using Microsoft.AspNet.SignalR; namespace WebApplication1 { public class MyConnection1 : PersistentConnection { //js調用 start 觸發 protected override Task OnConnected(IRequest request, string connectionId) { return Connection.Send(connectionId, "Welcome!"); } //js 調用send觸發 protected override Task OnReceived(IRequest request, string connectionId, string data) { return Connection.Broadcast(data); } //關閉鏈接(或者瀏覽器窗口)觸發 protected override Task OnDisconnected(IRequest request, string connectionId, bool stopCalled) { return base.OnDisconnected(request, connectionId, stopCalled); } } }
<!DOCTYPE html> <html> <head> <meta charset="utf-8" /> <title></title> <script src="Scripts/jquery-1.6.4.js"></script> <script src="Scripts/jquery.signalR-2.2.3.js"></script> <script type="text/javascript"> var con = $.connection("/connection"); //啓動 con.start(function (data) { con.send("asdasd") }) con.received(function (data) { console.log("receive:"+data) }) </script> </head> <body> </body> </html>
2、group(建簡易聊天室)
using System; using System.Threading.Tasks; using Microsoft.Owin; using Owin; [assembly: OwinStartup(typeof(WebApplication1.Startup1))] namespace WebApplication1 { public class Startup1 { public void Configuration(IAppBuilder app) { // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=316888 app.MapSignalR<MyConnection1>("/connection"); } } }
using System; using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; using System.Web; using Microsoft.AspNet.SignalR; namespace WebApplication1 { public class MyConnection1 : PersistentConnection { private const string DEFAULT = "default"; //js調用 start 觸發 protected override Task OnConnected(IRequest request, string connectionId) { this.Groups.Add(connectionId, DEFAULT); //excludeConnectionIds:排除通知的connectionId。在default組中,除了本身,其餘人都能收到信息 return this.Groups.Send(DEFAULT, connectionId + "進入房間", connectionId); } //js 調用send觸發 protected override Task OnReceived(IRequest request, string connectionId, string data) { //excludeConnectionIds:排除通知的connectionId。在default組中,除了本身,其餘人都能收到信息 return this.Groups.Send(DEFAULT, connectionId + ":" + data, connectionId); } //關閉鏈接(或者瀏覽器窗口)觸發 protected override Task OnDisconnected(IRequest request, string connectionId, bool stopCalled) { return base.OnDisconnected(request, connectionId, stopCalled); } } }
<!DOCTYPE html> <html> <head> <meta charset="utf-8" /> <title></title> <script src="Scripts/jquery-1.6.4.js"></script> <script src="Scripts/jquery.signalR-2.2.3.js"></script> <script type="text/javascript"> $(function () { var con = $.connection("/connection"); //啓動 con.start(function (data) { }) con.received(function (data) { $("#context").append("<br/>"+data) console.log(data) }) $("#send").click(function () { con.send($("#txt").val()) }) }) </script> </head> <body> <input type="text" id="txt" /> <input type="button" id="send" value="發送"/> <div id="context"> </div> </body> </html>
案例下載:https://pan.baidu.com/s/1YJN-bwertKNQc2O5JHlQgg
3、Hub
1,js調用直接後端方法、後端直接調用js方法
using System; using System.Threading.Tasks; using Microsoft.Owin; using Owin; [assembly: OwinStartup(typeof(WebApplication1.Startup1))] namespace WebApplication1 { public class Startup1 { public void Configuration(IAppBuilder app) { // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=316888 app.MapSignalR(); } } }
using System; using System.Collections.Generic; using System.Linq; using System.Web; using Microsoft.AspNet.SignalR; namespace WebApplication1 { public class MyHub : Hub { public void Hello() { //直接調用前端js方法 Clients.All.aa("abc"); } } }
<!DOCTYPE html> <html> <head> <meta charset="utf-8" /> <title></title> <script src="Scripts/jquery-1.6.4.js"></script> <script src="Scripts/jquery.signalR-2.2.3.js"></script> <!--引用js--> <script src="/signalr/js"></script> <script type="text/javascript"> $(function () { //啓動hub $.connection.hub.start() var conne = $.connection.myHub; //申明客戶端js方法 conne.client.aa = function (msg) { $("#context").append("<br/>" + msg) } $("#send").click(function () { //直接調用後端方法 conne.server.hello(); }) }) </script> </head> <body> <input type="text" id="txt" /> <input type="button" id="send" value="發送"/> <div id="context"> </div> </body> </html>
2,HubName/HubMethodName
using Microsoft.AspNet.SignalR.Hubs;
using System; using System.Collections.Generic; using System.Linq; using System.Web; using Microsoft.AspNet.SignalR; using Microsoft.AspNet.SignalR.Hubs; namespace WebApplication1 { [HubName("MyHub")] public class MyHub : Hub { [HubMethodName("Hello")] public void Hello() { //直接調用前端js方法 Clients.All.aa("abc"); } } }
3,ConnectionId
this.Context.ConnectionId;
4、Hub中的clients 和 groups屬性
1,Clients
①T All { get; }
至關於持久鏈接中的 Broadcast。
②T AllExcept(params string[] excludeConnectionIds);
給排除本人全部人發送消息。(excludeConnectionIds排除的鏈接id)
③T Client(string connectionId);
跟Send操做就是同樣的了。
④T Clients(IList<string> connectionIds);
和Send操做的重載方法同樣,能夠給一批指定的人發送。
⑤T Group(string groupName, params string[] excludeConnectionIds);
給房間中的指定人發送消息: Clients.Group("room1", "asdfasdfads");
⑥T Groups(IList<string> groupNames, params string[] excludeConnectionIds);
給房間列表中的指定人發送消息; 【自然的聊天室功能】
⑦T User(string userId);
這個和Client是有區別的。 這個userId => this.Context.Request.User.Identity.Name 【form驗證】
cookie中間件來作到singlar的身份驗證。
userId 是你本身定義的一個標識。
T Users(IList<string> userIds);
2,Groups
①Task Add(string connectionId, string groupName);
向組內添加連接
②Task Remove(string connectionId, string groupName);
刪除組內的鏈接
5、GlobalHost
1,獲取Hub的上下文
var hub = GlobalHost.ConnectionManager.GetHubContext<MyHub>();
2,對singlar的全局設置
GlobalHost.Configuration.MaxIncomingWebSocketMessageSize:
websocket模式下,消息的傳輸大小,若是大於默認的64k,那麼就會出問題。
GlobalHost.Configuration.DisconnectTimeout:
websocket強制關閉的時間。 30 seconds
GlobalHost.Configuration.TransportConnectTimeout:
傳輸的超時時間。 5s
6、生成代理js
下載安裝nuget: Microsoft.AspNet.SignalR.Utils
1,模板:signalr.exe ghp /path:《..\bin》 /o:《..\hub.js》
2,案例:
C:\Users\Hunter\Desktop\ConsoleApp3\packages\Microsoft.AspNet.SignalR.Utils.2.2.3\tools>signalr.exe ghp /path:C:\Users\Hunter\Desktop\ConsoleApp3\WebApplication2\bin /o:C:\Users\Hunter\Desktop\ConsoleApp3\WebApplication2\Scripts\hub.js
3,編譯命令:
$(SolutionDir)packages\Microsoft.AspNet.SignalR.Utils.2.2.3\tools\signalr.exe ghp /path:$(SolutionDir)$(ProjectName)\$(OutDir) /o:$(SolutionDir)$(ProjectName)\Scripts\hub.js
4,替換代理js
7、支持跨域
①下載安裝nuget: Microsoft.Owin.Cors
②配置項
using System; using System.Threading.Tasks; using Microsoft.Owin; using Owin; using Microsoft.AspNet.SignalR; using Microsoft.Owin.Cors; [assembly: OwinStartup(typeof(WebApplication2.Startup))] namespace WebApplication2 { public class Startup { public void Configuration(IAppBuilder app) { // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=316888 app.UseCors(CorsOptions.AllowAll); app.MapSignalR(); } } }
③生成代理js
④修改代理js
⑤html
<!DOCTYPE html> <html> <head> <meta charset="utf-8" /> <title></title> <script src="Scripts/jquery-1.6.4.js"></script> <script src="Scripts/jquery.signalR-2.2.3.js"></script> <!--引用js--> <!--<script src="/signalr/js"></script>--> <script src="Scripts/hub.js"></script> <script type="text/javascript"> $(function () { //啓動hub $.connection.hub.start() var conne = $.connection.myHub; //申明客戶端js方法 conne.client.aa = function (msg) { $("#context").append("<br/>" + msg) } $("#send").click(function () { //直接調用後端方法 conne.server.hello(); }) }) </script> </head> <body> <input type="text" id="txt" /> <input type="button" id="send" value="發送"/> <div id="context"> </div> </body> </html>
案例下載:https://pan.baidu.com/s/1GY_Io63qZeECbGbEH589fg
8、集羣部署
使用redis:
nuget: Microsoft.AspNet.SignalR.Redis
using System; using System.Threading.Tasks; using Microsoft.Owin; using Owin; using Microsoft.AspNet.SignalR; using Microsoft.Owin.Cors; [assembly: OwinStartup(typeof(WebApplication2.Startup))] namespace WebApplication2 { public class Startup { public void Configuration(IAppBuilder app) { // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=316888 //使用redis作底板 GlobalHost.DependencyResolver.UseRedis("localhost", 6379,string.Empty, "mykey"); app.UseCors(CorsOptions.AllowAll); app.MapSignalR(); } } }
9、將singlar.exe 裝入到 性能監視器
signlar.exe ipc 命令來安裝性能監視器 [install performance counters]
signlar.exe upc 來卸載性能監視器 [uninstall performance counters]
10、HubPipeLine管道
實現:IHubPipelineModule
①入流: BuildIncoming 監控
②出流: BuildOutgoing 監控