hub类的生命周期
SignalR每次需要处理集线器操作(例如客户端连接,断开连接或向服务器发起方法调用)时,都会创建Hub类的新实例。不要实例化Hub类或从服务器上的代码中调用其方法;所有这一切都是由SignalR Hubs管道为您完成的。
因为Hub类的实例是暂时的,所以不能使用它们来维护从一个方法调用到下一个方法的状态。每次服务器接收到来自客户端的方法调用时,Hub类的新实例都会处理该消息。要通过多个连接和方法调用来维护状态,请在Hub类上使用其他方法(如数据库或静态变量),或使用不能从Hub派生的其他类。如果将数据保存在内存中,则使用Hub类中的静态变量等方法,数据将在应用程序域回收时丢失。
如果你想通过在Hub类之外运行的代码发送消息给客户端,你不能通过实例化一个Hub类实例来完成,但是你可以通过获取对Hub类的SignalR上下文对象的引用, 参见How to call client methods and manage groups from outside the Hub class.。
构建hub处理程序
public class ContosoChatHub : Hub { public void NewContosoChatMessage(string name, string message) { Clients.All.addNewMessageToPage(name, message); } }
如上所示,只需继承hub类,默认情况下,JavaScript客户端通过使用类名称的【驼峰版】(注意:小驼峰,第一个字母小写)来引用集线器。 SignalR自动进行此更改,以便JavaScript代码可以符合JavaScript约定。 前面的例子在JavaScript代码中被称为contosoChatHub。例如在这个例子中,js客户端连接为:
var contosoChatHubProxy = $.connection.contosoChatHub;
如果想指定连接名,不使用类名,则声明时使用HubName如下:
[HubName("PascalCaseContosoChatHub")] public class ContosoChatHub : Hub此时客户端写法为
var contosoChatHubProxy = $.connection.PascalCaseContosoChatHub;
多个集线器
您可以在应用程序中定义多个Hub类。当你这样做,连接是共享的,但组是分开的:所有的客户端将使用相同的URL与服务建立SignalR连接(如果您指定了一个,则为“/ signalr”或您的自定义URL),并且该连接用于服务定义的所有集线器。与在单个类中定义所有集线器功能相比,多个集线器没有性能差异。
所有集线器都获得相同的HTTP请求信息。由于所有集线器共享相同的连接,因此服务器获取的唯一HTTP请求信息是建立SignalR连接的原始HTTP请求中的内容。如果使用连接请求通过指定查询字符串将信息从客户端传递到服务器,则不能向不同的集线器提供不同的查询字符串。所有集线器都将收到相同的信息。生成的JavaScript代理文件将在一个文件中包含所有Hub的代理。有关JavaScript代理的信息,SignalR Hubs API Guide - JavaScript Client - The generated proxy and what it does for you.
在SignalR中,您可以定义命名组以广播到已连接客户端的子集。每个Hub都分别维护组。例如,一个名为“Administrators”的组将为您的ContosoChatHub类包含一组客户端,并且相同的组名将引用您的StockTickerHub类的一组不同的客户端。