[英]How to use SignalR 2 with WEB API, calling SignalR methods from API and from Clients
[英]how SignalR works in Web API
我正在像这个例子一样在SignalR聊天项目中工作
但是它运行良好,我想在Web API项目中创建chat hub.cs并从其他客户端项目中调用它。
我已经搜索了解决方案,但没有找到任何解决方案。 我该如何实现。
我的chatHub
public class ChatHub : Hub
{
dbcontext db = new dbcontext();
ChatManager chatManager = new ChatManager();
public static string ConnectionId = null;
public void Send(string name, string message)
{
ConnectedUsers cu = chatManager.getCurrentUserRow(Context.ConnectionId);
if (cu != null)
{
string L_ConnectionId = cu.Other_ConnectionId;
Clients.Client(L_ConnectionId)
.addNewMessageToPage(name, message);
}
}
public override Task OnConnected()
{
Console.WriteLine("Connected user: " + Context.User.Identity.Name);
ConnectionId = Context.ConnectionId;
chatManager.AddAndRemoveUser(true, Context.ConnectionId); // to add user in connectedUser Table
chatManager.OpenRandomChat(Context.ConnectionId);
return base.OnConnected();
}
public override Task OnDisconnected(bool stopCalled)
{
chatManager.RemoveLeftUser(Context.ConnectionId);
chatManager.AddAndRemoveUser(false, Context.ConnectionId);
return base.OnDisconnected(stopCalled);
}
public override Task OnReconnected()
{
Console.WriteLine("ReConnected user: " + Context.User.Identity.Name);
return base.OnReconnected();
}
public void NewConnection()
{
int retVal = -1;
chatManager.RemoveLeftUser(Context.ConnectionId); // to remove left user from 2 users
chatManager.OpenRandomChat(Context.ConnectionId); // to chosse random user for me
// to get me and my if i have partner ..
ConnectedUsers cu = chatManager.getCurrentUserRow(Context.ConnectionId);
if (cu != null)
{
retVal = 0;
//string groupId = cu.ConnectionId + cu.Other_ConnectionId;
//string R_ConnectionId = cu.ConnectionId;
string L_ConnectionId = cu.Other_ConnectionId;
}
Clients.Client(Context.ConnectionId)
.sendGroupData(retVal);
}
public void SendQuestion(string question)
{
ConnectedUsers cu = chatManager.getCurrentUserRow(Context.ConnectionId);
if (cu != null)
{
string L_ConnectionId = cu.Other_ConnectionId;
Clients.Client(L_ConnectionId)
.sendQuestion(question);
}
}
public void AnswerQuestion(string answer)
{
ConnectedUsers cu = chatManager.getCurrentUserRow(Context.ConnectionId);
if (cu != null)
{
string L_ConnectionId = cu.Other_ConnectionId;
Clients.Client(L_ConnectionId)
.answerQuestion(answer);
}
}
}
我创建了一个单独的类库,该类库在我的任何其他项目中都包含和使用,效果很好,并且可以访问单个可重用的Hub。 我使用我的订单通知。
namespace MyProjects.SignalR.Hubs
{
public class OrdersHub : Hub
{
public void OrderDeleted(int manufacturerId, int orderId)
{
Clients.Group(OrdersGroup(manufacturerId)).BroadcastOrder(orderId);
}
public Task JoinOrders(int manufacturerId)
{
return Groups.Add(Context.ConnectionId, OrdersGroup(manufacturerId));
}
private string OrdersGroup(int manufacturerId)
{
return "orders" + manufacturerId;
}
}
}
然后,在其他任何使用此功能的项目中,我只需调用:
var ordersHubContext = GlobalHost.ConnectionManager.GetHubContext<OrdersHub>();
ordersHubContext.Clients.All.OrderDeleted(order.ManufacturerID, order.OrderID);
ChatManager chatManager = new ChatManager();
您无法在集线器中执行此操作。 集线器实例不是持久性的,它们是在每个单个请求上都重新创建的,您的ChatManager
也是如此。
为此,请将您的ChatManager
转换为Lazy
单例。 在这种情况下使用Lazy的目的是使其线程安全(对于SignalR而言,它非常简洁):
public sealed class ChatManager
{
private static readonly Lazy< ChatManager > lazy =
new Lazy< ChatManager >(() => new ChatManager());
public static ChatManager Instance { get { return lazy.Value; } }
private ChatManager()
{
}
// TODO add your methods here
}
然后,从您的中心:
ChatManager.Instance.AddAndRemoveUser(true, Context.ConnectionId);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.