在 ASP.NET 5 跨子域共享身份验证 Cookie

Sharing Authentication Cookie in ASP.NET 5 across subdomains

我有两个 ASP.NET 5 MVC 6 应用程序。

一个 运行 在 www.mydomain.tld,一个在 world1.mydomain.tld

如果用户登录 www 子域的应用程序,我希望她也登录 world1 子域的应用程序。使用ASP.NET身份实现登录 3.

我在 Startup.cs 中设置了两个应用程序,如下所示:

public void ConfigureServices (IServiceCollection services) {
    // [...]

    services.AddCaching();
    services.AddSession(
        options => {
            options.CookieDomain = ".mydomain.tld";
            options.IdleTimeout = TimeSpan.FromMinutes(30);
        }
    );

    // [...]
}

public void Configure (IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerfactory) {
    // [...]

    app.UseCookieAuthentication(null, IdentityOptions.ExternalCookieAuthenticationScheme);
    app.UseCookieAuthentication(null, IdentityOptions.TwoFactorRememberMeCookieAuthenticationScheme);
    app.UseCookieAuthentication(null, IdentityOptions.TwoFactorUserIdCookieAuthenticationScheme);
    app.UseCookieAuthentication(
        config => {
            config.CookieDomain = ".mydomain.tld";
        },
        IdentityOptions.ApplicationCookieAuthenticationScheme
    );

    // [...]
}

我还通过 web.config 设置了两个应用程序的机器密钥,如下所示:

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <system.web>
    <machineKey decryption="AES"
                decryptionKey="SOME DECRYPTION KEY"
                validation="HMACSHA256"
                validationKey="SOME ENCRYPTION KEY" />
  </system.web>
</configuration>

登录 www 子域有效,但访问 world1 子域上的站点无效,因为身份验证 cookie 未被识别为有效的登录 cookie。

我做错了什么?

应用程序彼此 automatically isolated。您需要确保三件事;

  1. 他们使用相同的密钥库
  2. 他们使用相同的应用程序 ID。
  3. 它们在同一个应用程序池中,或者每个池中的标识相同。

Apps 运行在同一台主机上,在相同的托管机制下将使用相同的密钥库。如果它们在不同的机器上,您将需要使用网络驱动器上的密钥存储,或其他共享位置,例如 azure blob 存储。

为了设置两个应用程序通用的应用程序 ID,您需要 configure 数据保护堆栈。

例如,

public void ConfigureServices(IServiceCollection services)
{
    services.AddDataProtection();
    services.ConfigureDataProtection(configure =>
    {
        configure.SetApplicationName("my application");
    });
}

如果您需要 运行 应用程序作为不同的用户,那么您需要更改密钥的保护方式以使用机器级 DPAPI 或 X509 证书。

您不需要在您的 web.config 中输入机器密钥,机器密钥不再是用户。