【发布时间】:2016-03-17 09:15:41
【问题描述】:
我已将 SignalR 添加到我现有的 MVC 项目中,并尝试使用 MVC 中的相同 ApplicationUserManager 将用户加载到集线器上下文中。
连接完成后,我像这样调用一些服务器方法:
var alertsHub = $.connection.monitoringHub;
$(function() {
alertsHub.client.processAlertChange = function (name, alert) {
console.log(alert);
};
//start the connection
$.connection.hub.start().done(function () {
console.log("Connected, transport = " + $.connection.hub.transport.name);
alertsHub.server.subscribeToMonitor();
});
});
在我的 Hub 方法中有一个调用
CurrentUser = ConnectedUsers.GetOrAdd(this.Context.ConnectionId, UserManager.FindByName(this.Context.User.Identity.Name));
UserManager 就是这样的属性
protected static ConcurrentDictionary<string, ApplicationUser> ConnectedUsers = new ConcurrentDictionary<string, ApplicationUser>();
private ApplicationUserManager _userManager;
public ApplicationUserManager UserManager
{
get
{
if (_userManager == null)
{
_userManager = Context.Request.GetHttpContext().GetOwinContext().GetUserManager<ApplicationUserManager>();
}
return _userManager;
}
}
protected ApplicationUser CurrentUser { get; set; }
问题是,当使用 webSockets 传输时,我收到错误“无法访问已处置的对象”
SignalR: webSockets transport connected. Initiating start request.
SignalR: The start request succeeded. Transitioning to the connected state.
SignalR: Now monitoring keep alive with a warning timeout of 13333.333333333332, keep alive timeout of 20000 and disconnecting timeout of 300000
Connected to monitoringHub, transport = webSockets
SignalR: Invoking monitoringhub.SubscribeToMonitor
SignalR: monitoringhub.SubscribeToMonitor failed to execute. Error: Cannot access a disposed object.
Object name: 'ApplicationUserManager'.
但是!当我强制 serverSentEvents 传输时 - 没有错误,一切正常。为什么?以及如何修复它...
我的 Startup.cs
ConfigureAuth(app);
// Any connection or hub wire up and configuration should go here
var hubConfiguration = new HubConfiguration();
hubConfiguration.EnableDetailedErrors = true;
app.MapSignalR("/sr", hubConfiguration);
GlobalHost.HubPipeline.RequireAuthentication();
GlobalHost.Configuration.ConnectionTimeout = TimeSpan.FromSeconds(120);
GlobalHost.Configuration.DisconnectTimeout = TimeSpan.FromSeconds(300);
GlobalHost.Configuration.KeepAlive = TimeSpan.FromSeconds(10);
【问题讨论】:
-
你试过在像 Fiddler 这样的代理中查看它吗?
-
由于已处置 Identity 对象,服务器上发生此错误。 Fiddler、Postman 等只会看到服务器响应的内容。在这种情况下,Postman 可能会收到 500 服务器错误。该响应将归因于特定的实施。 Fiddler 可能没有帮助。
-
ApplicationUserManager 是范围服务吗?正如您从 Context.Request 中获得的那样,我相信如此。因此,当您尝试获取它已经被处置的对象时。尝试更改此行
CurrentUser = ConnectedUsers.GetOrAdd(this.Context.ConnectionId, UserManager.FindByName(this.Context.User.Identity.Name));以实际获取 UserManager 执行而不是使用属性。
标签: c# asp.net-mvc websocket signalr asp.net-identity