Azure存储CORS返回原始通配符并在浏览器中失败

时间:2014-05-05 14:36:28

标签: azure cors azure-storage

在Azure blob存储上启用CORS时,几乎所有内容都可以设置,但是" ... Allow-Credentials"标题,总是如此。

因此,当使用通配符作为origin-header时,飞行前请求正常工作并将通配符转换为实际原点。

但后续的GET请求不会转换通配符并返回以下组合:

Access-Control-Allow-Origin: *
Access-Control-Allow-Credentials: true

这在Chrome中是非法的(也可能是其他浏览器)。错误是

XMLHttpRequest cannot load ...
A wildcard '*' cannot be used in the 'Access-Control-Allow-Origin' header when the credentials flag is true.
Origin 'http://localhost' is therefore not allowed access. 

在新的WebAPI v2 CORS包中,通配符将替换为实际原点。 另外,为什么在对blob存储的请求中需要cookie等凭据?最好把它关掉。

当我想使用原始通配符时,如何解决这个问题?

更新

这是我在App_Start上运行的初始化代码

public static void Initialize()
{
    // Azure blob storage settings
    var storageAccount = CloudStorageAccount.Parse(ConfigurationManager.ConnectionStrings["AzureStorage"].ConnectionString);
    var client = storageAccount.CreateCloudBlobClient();
    var serviceProperties = client.GetServiceProperties();
    serviceProperties.Cors = new CorsProperties();

    serviceProperties.Cors.CorsRules.Add(new CorsRule()
    {
        AllowedHeaders = new List<string>() { "*" },
        AllowedOrigins = new List<string>() { "*" },
        AllowedMethods = CorsHttpMethods.Get,
        ExposedHeaders = new List<string>() { "*" },
        MaxAgeInSeconds = 3600
    });

    client.SetServiceProperties(serviceProperties);
}

2 个答案:

答案 0 :(得分:3)

您遇到的错误是由于将xmlhttpreqeust上的withCredentials属性设置为true,在这种情况下,浏览器将拒绝通配符Access-Control-Allow-Origin。

  

在新的WebAPI v2 CORS包中,通配符被替换为   实际来源。

返回通配符是启用缓存的正确方法,请查看以下方案:

  • 用户A向MAS(Microsoft Azure存储)上的公共Blob发送GET请求。
  • 如果您使用CDN /代理缓存公共资源,这是最佳做法,那么CDN将缓存blob,并将Access-Control-Allow-Origin设置为'*'。
  • 现在用户B向MAS发送相同的请求并从缓存中获取响应,在这种情况下,因为缓存的blob具有通配符Access-Control-Allow-Origin,浏览器将允许该请求,而您不需要点击MAS服务器。

现在在另一种情况下,您始终返回实际原点,您无法为多个客户端缓存该资源,因为如果Access-Control-Allow-Origin的实际来源与实际原点不同,则浏览器将失败CORS请求请求原始标题。

  

另外,为什么我需要一个诸如cookie之类的凭证   请求blob存储?最好把它关掉。

您需要凭据,因为发送经过身份验证的请求的一种方法是使用Authorization标头,如果预检请求不允许,那么浏览器应该使用Authorization标头失败实际请求。

答案 1 :(得分:1)

时确实有效
withCredentials == false
<{1>}对象上的

。在我的情况下,这个设置搞砸了我使用的js框架。