Asp.Net Core WebAPI CORS 不工作

Posted

技术标签:

【中文标题】Asp.Net Core WebAPI CORS 不工作【英文标题】:Asp.Net Core WebAPI CORS Not working 【发布时间】:2017-07-14 02:52:37 【问题描述】:

我正在尝试使用 .Net Core 实现 WebAPI 服务,但我无法设置 CORS 正常工作。

我得到了主应用程序“MainApp”,它将即时生成发票,我想将其作为服务进行推广。这不是一个纯粹的 WebAPI 应用程序。我只想将此 InvoiceController 添加为 WebAPI,并且还有其他控制器,例如 HomeController、ProductsController 等......带有视图和 cshtml

我有单独的 Classic WebForm .Net 应用程序,它将通过 Ajax 调用该 InvoiceGeneration 服务并在网站上显示值。

当我运行我的 ajax 脚本时,我遇到了这个著名的 CORS 错误。

这是我的 ajax Get 方法。我是否输入xhrFields 都没有关系。我什至更改了dataType: 'jsonp',它仍然给我同样的错误。

$.ajax(
                type: "GET",
                url: 'http://localhost:57012/invoice/test/123',
                dataType: 'json',                
                contentType: 'application/json',
                success: function (data)                     
                    console.log(data);
                ,
                xhrFields: 
                    withCredentials: true
                
            );

InvoiceController.cs

我的发票服务非常简单...只有一种方法返回一些 JSON 值。

由于我使用 Policy 和 Claims 来确定安全性,因此我放置了AllowAnonymous 属性。即使我取消了该限制,它仍然不起作用。

public class InvoiceController : Controller
            
        [HttpGet]
        [AllowAnonymous]        
        [EnableCors("AllowAll")]
        public async Task<IActionResult> Test(string id)
        

            return new JsonResult(id);
        
    

Startup.cs

我添加了 AllowAll Policy 以允许所有类型的请求。

    public void ConfigureServices(IServiceCollection services)
            
                services.AddDbContext<DbContexts.PJDbContext>(options => options.UseSqlServer(Configuration.GetConnectionString("PJConnection")));

                services.AddSingleton<IHttpContextAccessor, HttpContextAccessor>();

                services.AddMvc()
                    .AddJsonOptions(o => o.SerializerSettings.NullValueHandling = Newtonsoft.Json.NullValueHandling.Ignore)
                    .AddJsonOptions(o => o.SerializerSettings.ContractResolver = new Newtonsoft.Json.Serialization.DefaultContractResolver());

                services.AddCors(options => options.AddPolicy("AllowAll", p => p.AllowAnyOrigin()
                                                                .AllowAnyMethod()
                                                                 .AllowAnyHeader()
                                                                 .AllowCredentials()));    


                services.AddAuthorization(options =>
                
                    options.AddPolicy(Constants.CONST_POLICY_SUPERADMIN, policy => policy.RequireRole(Constants.CONST_ROLE_SUPERADMIN));
                    options.AddPolicy(Constants.CONST_POLICY_STUDENT, policy => policy.RequireRole(Constants.CONST_ROLE_STUDENT, Constants.CONST_ROLE_ADMIN, Constants.CONST_ROLE_SUPERADMIN));
                );
            

public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory, IOptions<AppSettings> AppSettings)
            
                loggerFactory.AddConsole(Configuration.GetSection("Logging"));
                loggerFactory.AddDebug();

                if (env.IsDevelopment())
                
                    app.UseDeveloperExceptionPage();
                
                else
                
                    app.UseExceptionHandler("/Home/Error");
                

                app.UseStaticFiles();

                if (env.IsProduction())
                
                    app.UseStaticFiles(new StaticFileOptions()
                    
                        FileProvider = new PhysicalFileProvider(AppSettings.Value.FilePathToUpload),
                        RequestPath = new PathString("/Files"),
                    );
                

                app.UseCookieAuthentication(new CookieAuthenticationOptions
                
                    AuthenticationScheme = "Cookie",
                    LoginPath = new PathString("/Account/Login/"),
                    AccessDeniedPath = new PathString("/Account/Forbidden/"),
                    AutomaticAuthenticate = true,
                    AutomaticChallenge = true
                );

                app.UseCors("AllowAll");
                app.UseMvc(routes =>
                
                    routes.MapRoute(
                        name: "default",
                        template: "controller=Home/action=Index/id?");
                );
            

这是有趣的部分。

我创建了另一个新的 .Net Core WebAPI 项目并将这个 CORS 设置复制到 Startup.cs 和 InvoiceController 到新项目。 CORS 工作正常,我的 AJAX 可以从新项目中调用该方法。

但我不想制作多个项目,我不能将那个 WebAPI 嵌入到现有的 MVC WebApp 项目中吗?

我看过一些教程,它们在同一个项目中同时运行 WebAPI 和 MVC 控制器(显然它们在同一个域中。所以,CORS 对他们来说不是问题)。非常混乱。

你们能帮我解决一下吗?

附言。这个 Html5Rocks 教程 js 脚本也不起作用。

在我看来,我认为 JqueryAJAX 脚本没有任何问题。 我得到了另一个纯 WebAPI .Net Core 服务,并且我设法使用相同的“AllowAll Policy”代码正确设置了 CORS。我可以使用这个简单的 Jquery 脚本从任何跨域网站调用该服务。

$.ajax(
                type: "GET",
                url: 'http://oakapi/staff/byid/2618',
                dataType: 'json',                
                contentType: 'application/json',
                success: function (data) 
                    console.log(data);
                             
            );

【问题讨论】:

我很好奇,您的 [EnableCors] 您使用的是什么依赖项?是 Microsoft.AspNet.Cors 吗? 它来自 Microsoft.AspNetCore.Cors。理论上,我们不需要使用它,因为我们在 Startup.cs 中全局设置了它。我只放了一个,因为我的解决方案都没有奏效,并且尝试了所有镜头。 【参考方案1】:

像这样设置ajax:

$.ajax(
            type: "GET",
            url: 'http://oakapi/staff/byid/2618',
            dataType: 'jsonp',                
            contentType: 'application/javascript',
            success: function (data) 
                console.log(data);
                         
        );

【讨论】:

【参考方案2】:

我认为 service.AddCors() 应该放在 service.AddMvc() 之前。

【讨论】:

以上是关于Asp.Net Core WebAPI CORS 不工作的主要内容,如果未能解决你的问题,请参考以下文章

Blazor 无法连接到 ASP.NET Core WebApi (CORS)

在 ASP.Net Core 5 WebAPI 中启用 CORS

如何在 ASP.net Core WebAPI 中启用 CORS

仅在 IIS 中发布时,在 ASP.net Core 3.1 WebAPI 中启用 CORS 时出错

在 ASP .NET Core 2.1 Web Api 中启用 CORS

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