繁体   English   中英

如何配置.net核心以将身份验证Cookie发送到其他域

[英]How to configure .net core to send authentication cookies to different domain

我正在尝试使用前端与域不同的cookie。 后端是使用.net核心实现的,而前端是Angular。 我研究过,我需要设置withCredentials:进行http调用时设置为true。 但是,当我将其设置为true时,会出现此错误:

对预检请求的响应未通过访问控制检查:当请求的凭据模式为“包括”时,响应中“ Access-Control-Allow-Origin”标头的值不得为通配符“ *”。 我一直在尝试设置CORS和Cookie设置以适应这种情况。 这是我来自StartUp.cs的相关代码。 Cors设置:

services.AddCors(options =>
        {
            options.AddPolicy("AllowDomainOrigin",
                builder =>
                {
                    builder
                        .WithOrigins("http://some.domain.net")
                        .AllowAnyHeader()
                        .AllowAnyMethod();
                });
            options.AddPolicy("AllowForLocalhost",
                builder =>
                {
                    builder
                        .WithOrigins("http://localhost:4200")
                        .AllowAnyHeader()
                        .AllowAnyMethod()
                        .AllowCredentials();
                });
        });
services.AddSession(options =>
        {
            options.Cookie.SameSite = SameSiteMode.None;
        });
...
        app.UseCors("AllowDomainOrigin");
        app.UseCors("AllowForLocalhost");

Cookie设置:

services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme)
            .AddCookie(CookieAuthenticationDefaults.AuthenticationScheme, options => 
            {
                options.Cookie.Domain = "some.domain.net";
                options.Cookie.Name = "access_token";
                options.Cookie.SameSite = SameSiteMode.None;
                options.LoginPath = "/login";
                options.LogoutPath = "/login";
            })
            .AddCookie("localhost", options => 
            {
                options.Cookie.Domain = "localhost";
                options.Cookie.Name = "localhost_access_token";
                options.Cookie.SameSite = SameSiteMode.None;
                options.LoginPath = "/login";
                options.LogoutPath = "/login";
            })
            .AddCookie("othercloud", options => 
            {
                options.Cookie.Domain = "domain.com";
                options.Cookie.Name = "musiple_access_token";
                options.Cookie.SameSite = SameSiteMode.None;
                options.LoginPath = "/login";
                options.LogoutPath = "/login";
            })
            .AddJwtBearer(options => 
            {
                options.TokenValidationParameters = tokenValidationParameters;
            });

这是我在登录控制器中登录HttpContext的方式:

await HttpContext.SignOutAsync(CookieAuthenticationDefaults.AuthenticationScheme);
await HttpContext.SignOutAsync("localhost");
await HttpContext.SignOutAsync("othercloud");
await HttpContext.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme,
            new ClaimsPrincipal(identity),
            authProperties);
await HttpContext.SignInAsync("localhost",
            new ClaimsPrincipal(identity),
            authProperties);
await HttpContext.SignInAsync("othercloud",
            new ClaimsPrincipal(identity),
            authProperties);

这是我的音频文件端点:

[HttpGet("{id}")]
[Authorize(AuthenticationSchemes= CookieAuthenticationDefaults.AuthenticationScheme +", localhost, othercloud")]
public async Task<FileStreamResult> Get(int id)

如您所见,我还将JWT令牌与身份验证一起使用。 我需要Cookie,因为我使用音频元素从REST API下载了mp3文件,并且将音频元素src直接设置为我的REST API地址。 因此,在使用音频元素时,无法将JWT设置为标头。 在这种情况下,当我的前端与后端位于同一域时,Cookie可以很好地工作,但是现在我正尝试将前端也移至其他服务器和域。

我需要如何配置后端以从其他域获取Cookie?

我的后端在Azure上。 还有一些CORS设置,我可以删除*并将其替换为特殊地址。 这与此有关吗?

编辑:

找到Azure CORS设置后,异常更改为:

对预检请求的响应未通过访问控制检查:响应中的“ Access-Control-Allow-Credentials”标头的值为“”,当请求的凭据模式为“ include”时,该值必须为“ true”

编辑2:

您需要从Azure删除所有CORS设置,以获取.net核心cors设置以进行cors控制。 仍然没有成功,但解决方案可能略微不足。

终于我开始工作了。 正如我在编辑评论中所说的,主要原因是azures CORS设置。 删除它们后,即可进入.net核心设置。这是我的最终解决方案:Cookie设置:

services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme)
            .AddCookie(CookieAuthenticationDefaults.AuthenticationScheme, options => 
            {
                options.Cookie.Name = "access_token";
                options.Cookie.SameSite = SameSiteMode.None;
            })
            .AddJwtBearer(options => 
            {
                options.TokenValidationParameters = tokenValidationParameters;
            });

CORS设置:

services.AddCors(options =>
        {
            options.AddPolicy("AllowAllOrigins",
                builder =>
                {
                    builder
                        .AllowAnyOrigin()
                        .AllowAnyHeader()
                        .AllowAnyMethod()
                        .AllowCredentials();
                });
        });
...

app.UseCors("AllowAllOrigins");

这是后端登录中的相关代码:

await HttpContext.SignOutAsync(CookieAuthenticationDefaults.AuthenticationScheme);

await HttpContext.SignInAsync(CookieAuthenticationDefaults.AuthenticationScheme,
            new ClaimsPrincipal(identity),
            authProperties);

这在我的音频控制器端点中就足够了

[HttpGet("{id}")]
[Authorize()]
public async Task<FileStreamResult> Get(int id)

在前端,我设置了withCredentials:当我进行登录呼叫时设置为true。

现在,当我使用AllowAnyOrigin而不是WithOrigin时,这是非常不安全的,但是由于某种原因,我没有让它与WithOrigin一起使用。

对于那些正在阅读此书并在天蓝色中使用.net Core并想要使用CORS的用户,请从Azure中删除您的CORS设置,然后在.net Core中处理它们,因为在.net Core中,比天蓝色的CORS中的配置要多得多。 这是我从互联网上找到的一些信息:

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM