CORS 在 ASP.NET Web API 2 应用程序中不起作用

Posted

技术标签:

【中文标题】CORS 在 ASP.NET Web API 2 应用程序中不起作用【英文标题】:CORS not working in ASP.NET Web API 2 app 【发布时间】:2017-04-28 20:28:48 【问题描述】:

你知道,通常情况下:CORS 不起作用。 Chrome 为我提供了这个:

Fetch API 无法加载 https://url-to-my-api-thing。不 'Access-Control-Allow-Origin' 标头出现在请求的 资源。原点 'https://url-to-the-origin-thing' 因此不是 允许访问。如果不透明的响应满足您的需求,请将 请求模式为“no-cors”以获取禁用 CORS 的资源。

我有一个使用 OWIN 管道并托管在 IIS 中的 ASP.NET Web API 2 应用程序。

这是我(尝试)在 Configuration 方法中设置 CORS 的方法:

// ... container setup above, CORS is the first middleware ...

var corsPolicyProvider = new CorsPolicyProvider(_corsOrigins, container.GetInstance<ILogger>);
app.UseCors(new CorsOptions

    PolicyProvider = corsPolicyProvider
);

app.UseStageMarker(PipelineStage.Authenticate);

configuration.Services.Replace(typeof(IExceptionHandler), new PassThroughExceptionHandler());
configuration.MapHttpAttributeRoutes();
app.UseWebApi(configuration);

这就是我的CorsPolicyProvider 类的样子:

public class CorsPolicyProvider : ICorsPolicyProvider

    private readonly Regex _corsOriginsRegex;
    private readonly string _defaultCorsOrigin;
    private readonly Func<ILogger> _scopedLoggerCreator;

    public CorsPolicyProvider(string corsOrigins, Func<ILogger> scopedLoggerCreator)
    
        _corsOriginsRegex = new Regex($"(corsOrigins)", RegexOptions.IgnoreCase);
        _defaultCorsOrigin = corsOrigins?.Split('|').FirstOrDefault();
        _scopedLoggerCreator = scopedLoggerCreator;
    

    public Task<CorsPolicy> GetCorsPolicyAsync(IOwinRequest request)
    
        var logger = _scopedLoggerCreator();

        var allowedOrigin = _defaultCorsOrigin;
        string[] origins;
        request.Headers.TryGetValue("Origin", out origins);
        var origin = origins?.FirstOrDefault();
        if (origin != null && Uri.IsWellFormedUriString(origin, UriKind.Absolute) && _corsOriginsRegex.IsMatch(new Uri(origin).Host))
            allowedOrigin = origins.FirstOrDefault();

        var policy = new CorsPolicy
        
            Origins =  allowedOrigin ,
            Methods =  HttpMethod.Get.Method, HttpMethod.Post.Method, HttpMethod.Put.Method, HttpMethod.Delete.Method ,
            Headers =  "accept", "content-type" ,
            SupportsCredentials = true,
            PreflightMaxAge = 1728000
        ;

        logger?.Verbose("Resolving CORS policy: @CorsPolicy", policy);

        return Task.FromResult(policy);
    

为什么此政策从未触发,或者充其量是出现故障?如果我在本地测试时设置断点并显式发送OPTIONS 请求,它会进入GetCorsPolicyAsync 方法,并且还会按预期记录请求。但是,当 API 在服务器上并且我尝试从 Chrome 中的网站调用它时,它从不记录请求,它只是告诉我没有 CORS 标头。

【问题讨论】:

请不要停在那里!什么是配置问题?我正面临一个听起来很像这样的问题。 就我而言,配置已被来自不同环境的配置覆盖。因此,我们系统测试环境中的应用程序试图与我们的验收测试环境中的 API 通信,这将无法正常工作,因为验收测试 API(正确地如此)仅接受验收测试应用程序作为其来源。 【参考方案1】:

...就像发条一样,当我在上面发布一些内容时,我就找到了答案。 一个 CORS 标头,并且请求 正在被记录,但是环境的配置错误,所以来源(然后由于它是不同的环境而无效)被正确阻止,日志最终出现在错误的服务器上。修正了配置,它再次按预期工作。

【讨论】:

您正在体验 Rubber Duck 调试。 en.wikipedia.org/wiki/Rubber_duck_debugging 将其纳入故障排除可能会对您有所帮助。 你是绝对正确的。我在 Stack Overflow 上做了很多 - 写一个很长的问题,尝试填空,然后偶然发现一个解决方案并再次删除我的帖子。我通常会在发布之前找到答案......但在这种情况下不会:( @MartinWedvich 当我这样做时,我只是继续为自己提供一个答案,希望它可以帮助其他有类似问题的人。我最成功的例子就是这对question and answer。

以上是关于CORS 在 ASP.NET Web API 2 应用程序中不起作用的主要内容,如果未能解决你的问题,请参考以下文章

asp.net web api 2 CORS 和身份验证授权配置

CORS 在 ASP.NET Web API 2 应用程序中不起作用

本地 Javascript Fetch Post 请求失败,调用 ASP.NET Core 2.2 Web API。 CORS 已启用

如何在 ASP.NET Web API SelfHost 应用程序中使用 CORS?

我正在将我的 asp.net web api 迁移到 asp.net core。 Cors 迁移

如何让 CORS 与 ASP.Net Core Web API 服务器 Angular 2 客户端一起工作