我试图将OpenId Connect集成到长期存在的Webforms应用程序中。我能够迁移应用程序以使用OWIN,并且我正在使用OpenIdConnectAuthenticationMiddleware对我的IdP提供程序进行身份验证。一切都很顺利,直到我需要从IdP获得新身份并设置cookie - 我认为哪一部分没有发生。我Startup.Configure方法OpenId Connect中间件未在WebForms应用程序中设置身份验证Cookie
重要部分:
app.SetDefaultSignInAsAuthenticationType(CookieAuthenticationDefaults.AuthenticationType);
app.UseCookieAuthentication(new CookieAuthenticationOptions
{
AuthenticationType = DefaultAuthenticationTypes.ApplicationCookie,
LoginPath = new PathString("/login.aspx"),
CookieManager = new SystemWebCookieManager() //custom cookie manager
});
app.UseOpenIdConnectAuthentication(new OpenIdConnectAuthenticationOptions
{
Authority = "https://[development_domain]/core",
ClientId = "VDWeb",
ResponseType = "code id_token token",
Scope = "openid profile",
UseTokenLifetime = true,
SignInAsAuthenticationType = "Cookies",
Notifications = new OpenIdConnectAuthenticationNotifications
{
SecurityTokenValidated = async n =>
{
var userInfo = await EndpointAndTokenHelper.CallUserInfoEndpoint(n.ProtocolMessage.AccessToken);
//now store Preferred name :
var prefNameClaim = new Claim(
Thinktecture.IdentityModel.Client.JwtClaimTypes.PreferredUserName,
userInfo.Value<string>("preferred_username"));
var myIdentity = new ClaimsIdentity(
n.AuthenticationTicket.Identity.AuthenticationType,
Thinktecture.IdentityModel.Client.JwtClaimTypes.PreferredUserName,
Thinktecture.IdentityModel.Client.JwtClaimTypes.Role);
myIdentity.AddClaim(prefNameClaim);
//add unique_user_key claim
var subjectClaim = n.AuthenticationTicket.Identity.FindFirst(Thinktecture.IdentityModel.Client.JwtClaimTypes.Subject);
myIdentity.AddClaim(new Claim("unique_user_key", subjectClaim.Value));
myIdentity.AddClaim(new Claim("id_token", n.ProtocolMessage.IdToken));
var ticket = new AuthenticationTicket(myIdentity, n.AuthenticationTicket.Properties);
var currentUtc = new SystemClock().UtcNow;
ticket.Properties.IssuedUtc = currentUtc;
ticket.Properties.ExpiresUtc = currentUtc.Add(TimeSpan.FromHours(12));
n.AuthenticationTicket = ticket;
},
}
});
我可以证实AuthentocationTicket填充正确,但身份验证cookie不会设置。我确实知道这个问题https://katanaproject.codeplex.com/workitem/197,并且我已经尝试了针对此问题提供的所有解决方法,但没有任何帮助。有趣的是,当我尝试在SecurityTokenValidated事件 - n.Response.Cookies.Append("Test", "Test");
中放置我自己的cookie时,我可以看到cookie已正确设置。
其中一种解决方法建议实施您自己的CookieManager。让我感到好奇的是,当我在这个自定义管理器中将一个断点放入Cookie设置器中时,它并未被击中,即中间件似乎甚至不尝试设置cookie。所以我的主要问题 - 中间件到底会在什么时候尝试设置cookie?是否当我设置我的AuthenticationTicket?
编辑1:添加更多信息。我试图与另一个网络应用程序进行比较,这次是MVC,我配置为使用相同的IdP并按预期工作。两款应用的启动代码都是相同的。当通过SecurityTokenValidated事件调试时,我可以看到MVC应用程序(工作)创建了System.Security.Principal.WindowsPrincipal
身份,而webforms应用程序(非工作)创建了System.Security.Principal.GenericIdentity
身份。
我也加入了这个小文档片断
app.UseStageMarker(PipelineStage.Authenticate);
app.Use((context, next) =>
{
var identity = context.Request.User.Identity;
return next.Invoke();
});
只是为了看看有什么身份获取填充这个流水线阶段。对于MVC应用程序(工作),我通过设置AuthenticationTicket来看到我添加的身份,对于webforms应用程序,我仍然可以看到未经身份验证的GenericIdentity。
您是否使用了特定的解决方案来实施?我正在尝试做类似的事情,但我很难弄清楚在OpenID Connect上的代码示例是如何开始的。 –