Azure上的SignalR 2.2的CORS问题

时间:2017-03-23 14:03:27

标签: cors signalr signalr-hub

我正在尝试从我的Angular2连接SignalR进行消息传递。

我在chrome中遇到错误:

  

XMLHttpRequest cannot load https://ls-dev-signalr.azurewebsites.net/signalr/negotiate?clientProtocol=1…onData=%5B%7B%22name%22%3A%22realtimemessaginghub%22%7D%5D&_=1490197517724. No 'Access-Control-Allow-Origin' header is present on the requested resource. Origin 'null' is therefore not allowed access.

我的SignalR配置位于OWIN Startup文件中,如下所示:

public void Configuration(IAppBuilder app)
{
    var config = new HttpConfiguration();

    var corsOption = new CorsOptions
        {
            PolicyProvider = new CorsPolicyProvider
            {
                PolicyResolver = context =>
                {
                    var policy = new CorsPolicy { AllowAnyOrigin = true, AllowAnyHeader = true, AllowAnyMethod = true };

                    return Task.FromResult(policy);
                }
            }
        };

    app.Map("/signalr", map =>
    {
        var hubConfiguration = new HubConfiguration
            {
                EnableDetailedErrors = false,
                //EnableJSONP = true,
                EnableJavaScriptProxies = true,
            };
       map.UseCors(corsOption).RunSignalR(hubConfiguration);
    });

    app.UseCors(corsOption);
    WebApiConfig.Register(config);
    app.UseWebApi(config);

}

我研究过很多SO帖子,但没有取得任何成功。

如何为SignalR启用CORS?

来自@ShaulBehr的更新,他正在就此问题与OP合作:

我们已将问题缩小到以下事实:浏览器客户端在发出SignalR连接请求时未发送Origin标头。我们可以在Postman中重现这种行为:如果发送Origin标头,SignalR端点会以Access-Control-Allow-Origin标头响应。如果不是,不是。

问题(对于赏金)现在是:

  • 我们如何让客户端发送Origin标头?
  • 即使请求中省略了Access-Control-Allow-Origin标头,我们如何让Azure网站使用Origin标头进行响应?

3 个答案:

答案 0 :(得分:2)

我一直发现将此部分添加到web.config文件效果最佳:

 <system.webServer>
   <httpProtocol>
     <customHeaders>
       <add name="Access-Control-Allow-Origin" value="*" />
       <add name="Access-Control-Allow-Methods" value="GET,PUT,POST,DELETE,OPTIONS" />
     </customHeaders>
   </httpProtocol>
 </system.webServer>

注意:这些设置是“全开”的,接受任何来电者。您的用例可能需要更严格。

希望这有帮助!

答案 1 :(得分:2)

根据HTTP规范(以下网址):

  

在遵循跨站点访问请求的要求时,用户   代理商必须确保每个请求(包括重定向等)   cetera)设置Origin HTTP请求头,值设置为   访问控制来源。

https://www.w3.org/TR/2008/WD-access-control-20080912/#cross-site0

IIS在这方面遵守规范,只有在设置了Origin请求标头时才发送Access-Control-Allow-Origin标头。

话虽如此,即使不推荐,也可以强制服务器始终为每个请求设置Access-Control-Allow-Origin标头,方法是将其添加为web.config文件中的自定义标头。 您还必须删除Azure门户中Cors刀片中的所有条目。

要实现此目的,您可以将以下部分添加到web.config文件中:

<configuration>
  <system.webServer>
    <httpProtocol>
         <customHeaders>
            <add name="Access-Control-Allowed-Origin" value="*" />
         </customHeaders>
    </httpProtocol>
  </system.webServer>
</configuration>

答案 2 :(得分:1)

我使用SignalR跨域,我也在v2.2上。我虽然使用Angular 1.5。但如果问题确实存在于SignalR方面,那么这应该可行。

  app.Map("/signalr", map =>
     {
        // Setup the CORS middleware to run before SignalR.
        // By default this will allow all origins. You can 
        // configure the set of origins and/or http verbs by
        // providing a cors options with a different policy.
        map.UseCors(CorsOptions.AllowAll);
        var hubConfiguration = new HubConfiguration
        {
           EnableDetailedErrors = true
        };
        map.RunSignalR(hubConfiguration);
     });