我的移动应用程序通过azure使用Facebook Auth。对于带有[MobileApiController]
标志的ApiControllers,auth运行良好。
我似乎找不到如何使SignalR Hub授权——authorize属性阻止用户访问。我发现的所有文章似乎都很旧,都使用了不推荐使用的Azure移动服务,这是不同的,也不兼容。
我已经将SignalR客户端配置为使用x-zumo-auth头集连接长轮询。
我最终制作了一个自定义SignalR身份验证属性。下面的代码供其他感兴趣的人使用。
public class HubAuthorizeAttribute : AuthorizeAttribute
{
public HubAuthorizeAttribute()
{
}
public override bool AuthorizeHubConnection(HubDescriptor hubDescriptor, IRequest request)
{
var owinContext = request.GetHttpContext().GetOwinContext();
ClaimsPrincipal claimsPrincipalFromToken;
var options = Startup.AuthenticationOptions;
string tokenFromHeader = request.Headers[AppServiceAuthenticationHandler.AuthenticationHeaderName];
if (!string.IsNullOrEmpty(tokenFromHeader))
{
bool claimsAreValid = options.TokenHandler.TryValidateLoginToken(tokenFromHeader, options.SigningKey, options.ValidAudiences, options.ValidIssuers, out claimsPrincipalFromToken);
if (claimsAreValid)
{
var identity = claimsPrincipalFromToken.Identity as ClaimsIdentity;
request.Environment["server.User"] = new ClaimsPrincipal(identity);
return true;
}
}
return false;
}
public override bool AuthorizeHubMethodInvocation(IHubIncomingInvokerContext hubIncomingInvokerContext, bool appliesToMethod)
{
var connectionId = hubIncomingInvokerContext.Hub.Context.ConnectionId;
// check the authenticated user principal from environment
var environment = hubIncomingInvokerContext.Hub.Context.Request.Environment;
var principal = environment["server.User"] as ClaimsPrincipal;
if (principal != null && principal.Identity != null && principal.Identity.IsAuthenticated)
{
// create a new HubCallerContext instance with the principal generated from token
// and replace the current context so that in hubs we can retrieve current user identity
hubIncomingInvokerContext.Hub.Context = new HubCallerContext(new ServerRequest(environment), connectionId);
return true;
}
else
{
return false;
}
}
}