Asp.NET标识-在运行时设置CookieDomain

ve7v8dk2  于 2023-08-08  发布在  .NET
关注(0)|答案(4)|浏览(127)

如果我想从Request.Url或存储在数据库中的一些设置中提取这个值,如何在运行时在CookieAuthenticationOptions中设置CookieDOmain?
我想支持子域,但也支持多租户太其中每个有不同的域。
目前,这是配置我没有访问这些。
保禄

bbmckpt7

bbmckpt71#

您可以指定自己的Cookie提供程序:

CookieAuthProvider myProvider = new CookieAuthProvider();
app.UseCookieAuthentication(new CookieAuthenticationOptions
{
   AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
   LoginPath = new PathString("/Account/Login"),
   Provider = myProvider
});

字符串
实现您自己的提供程序,或者简单地从现有提供程序继承:

public class CookieAuthProvider : CookieAuthenticationProvider
{
    public override void ResponseSignIn(CookieResponseSignInContext context)
    {
      //Alter you cookie options
      //context.CookieOptions.Domain  =  "www...";      
      base.ResponseSignIn(context);
    }
 }


并实现ResponseSignIn,当端点在将其转换为cookie之前提供登录信息时,将调用它。通过实施该方法,可以改变进入票据的声明和额外信息。
您将获得一个CookieResponseSignInContext,它公开了CookieOptions属性,可以在ResponseSignIn调用期间替换或更改这些属性。
Katana项目的代码参考:

  • ICookieAuthenticationProvider
  • CookieResponseSignInContext
  • CookieAuthenticationHandler
njthzxwz

njthzxwz2#

你已经尝试过了吗:

app.UseCookieAuthentication(new CookieAuthenticationOptions
{
  AuthenticationType = "Application",
  LoginPath = "/Account/Login",
  CookieDomain = ".myDomain.com"
});

字符串

yebdmbv4

yebdmbv43#

使用SlidingExpiration选项时,MK. answer似乎不允许正确处理令牌续订。
作为一种解决方法,您可以提供自定义cookie管理器,并定义自己的添加/删除cookie的方法,而不是提供自定义cookie提供程序。
在我的例子中,为了保持简单,我在后台重用了默认的cookie管理器。(我不能扩展它,它的方法是不可重写的。
下面是我最终得到的代码:

using Microsoft.AspNet.Identity;
using Microsoft.Owin;
using Microsoft.Owin.Infrastructure;
using Microsoft.Owin.Security.Cookies;
using Microsoft.Owin.Security.DataProtection;
using Owin;

public class Startup
{
    public void Configuration(IAppBuilder app)
    {
        var options = new CookieAuthenticationOptions
        {
            AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
            SlidingExpiration = true,
            CookieManager = new CustomCookieManager()
        };

        app.UseCookieAuthentication(options);
    }
}

public class CustomCookieManager : ICookieManager
{
    private readonly ICookieManager ConcreteManager;

    public CustomCookieManager()
    {
        ConcreteManager = new ChunkingCookieManager();
    }

    string ICookieManager.GetRequestCookie(IOwinContext context, string key)
    {
        return ConcreteManager.GetRequestCookie(context, key);
    }

    void ICookieManager.AppendResponseCookie(IOwinContext context, string key, string value, CookieOptions options)
    {
        SetupDomain(context, options);
        ConcreteManager.AppendResponseCookie(context, key, value, options);
    }

    void ICookieManager.DeleteCookie(IOwinContext context, string key, CookieOptions options)
    {
        SetupDomain(context, options);
        ConcreteManager.DeleteCookie(context, key, options);
    }

    private void SetupDomain(IOwinContext context, CookieOptions options)
    {
        // custom logic for assigning something to options.Domain
    }
}

字符串

r7xajy2e

r7xajy2e4#

为了在NET7中工作,我们需要更新Frédéric代码。我也没有删除我的自定义逻辑,为共享cookie之间的子域,也许这将有助于中小企业。而且在我的自定义逻辑实现了Duende Identity Server的共享cookie(Identity Server 4也必须工作)。

using Duende.IdentityServer.Configuration;
using Microsoft.AspNetCore.Authentication.Cookies;

namespace IdentityServerForEt
{
    public class CustomCookieManager : ICookieManager
    {
        private readonly ICookieManager ConcreteManager;

        public CustomCookieManager()
        {
            ConcreteManager = new ChunkingCookieManager();
        }

        public string? GetRequestCookie(HttpContext context, string key)
        {
            return ConcreteManager.GetRequestCookie(context, key);
        }

        public void AppendResponseCookie(HttpContext context, string key, string? value, CookieOptions options)
        {
            SetupDomain(context, options);
            ConcreteManager.AppendResponseCookie(context, key, value, options);
        }

        public void DeleteCookie(HttpContext context, string key, CookieOptions options)
        {
            SetupDomain(context, options);
            ConcreteManager.DeleteCookie(context, key, options);
        }

        private static void SetupDomain(HttpContext context, CookieOptions options)
        {
            var hostParts = context.Request.Host.Value.Split('.');
            string? domain = null;
            if (hostParts.Length > 2)
                domain = string.Join('.', hostParts.TakeLast(2));
            options.Domain = domain;
            if (domain != null)
            {
                var identityServerOption = context.RequestServices.GetService<IdentityServerOptions>();
                if (identityServerOption != null)
                    identityServerOption.Authentication.CheckSessionCookieDomain = domain;
            }
        }
    }
}

字符串

相关问题