我想在运行时在asp.net应用程序中配置ADFS终结点。 有一个问题:如果我为多个端点声明了单个回调方法,那么我会出现异常:
Microsoft.IdentityModel.Tokens.SecurityTokenSignatureKeyNotFoundException: IDX10501: Signature validation failed. Unable to match keys:
kid: '[PII is hidden]',
token: '[PII is hidden]'.
如果我要对每个端点的回调进行硬编码,那么所有方法都可以工作,但这不是我的情况。
Startup.cs
public class Startup
{
public void Configuration(IAppBuilder app)
{
var federationEndpoints = Service.ListActiveFederationEndpoints();
if (federationEndpoints.Any())
{
app.SetDefaultSignInAsAuthenticationType(CookieAuthenticationDefaults.AuthenticationType);
app.UseCookieAuthentication(new CookieAuthenticationOptions());
var endpointOptions = new List<WsFederationAuthenticationOptions>();
foreach (var endpoint in federationEndpoints)
{
string metadata = endpoint.ServerUri;
string wtrealm = endpoint.RelyingPartyIdentifier;
endpointOptions.Add(new WsFederationAuthenticationOptions
{
Wtrealm = wtrealm,
MetadataAddress = metadata,
AuthenticationType = endpoint.Name
});
}
app.Map("/FederationAuth", configuration =>
{
endpointOptions.ForEach(o => app.UseWsFederationAuthentication(o));
});
}
AntiForgeryConfig.UniqueClaimTypeIdentifier = ClaimTypes.Name;
}
}
FederationAuthController中的登录和常见回调
[AllowAnonymous]
public void ExternalLogin(string endpointName)
{
var ctx = Request.GetOwinContext();
ctx.Authentication.Challenge(
new AuthenticationProperties { RedirectUri = Url.Action("LoginCallbackAdfs", "FederationAuth") },
endpointName);
}
public ActionResult LoginCallbackAdfs()
{
var ctx = System.Web.HttpContext.Current;
var claimsIdentity = User.Identity as ClaimsIdentity;
var sessionIdentity = Service.LoginByClaims(claimsIdentity);
return this.RedirectToAction("Index", "SinglePage");
}
我已经阅读了许多有关在Web.config中配置硬编码的多个ADFS终结点的答案,但是是否有可能在运行时配置points?
谢谢!
答案 0 :(得分:0)
Wreply应该是唯一的,并且在管道构建期间为每个联合中间件设置。我做了唯一的Wreply,其中包括端点名称作为回调参数。 Startup.cs
public void Configuration(IAppBuilder app)
{
var federationChannels = Service.GetFederationChannels();
app.UseCookieAuthentication(new CookieAuthenticationOptions());
app.SetDefaultSignInAsAuthenticationType(CookieAuth.AuthenticationType);
foreach (var channel in federationChannels)
{
var metadata = channel.Metadata;
var wtrealm = channel.Wtrealm ;
var host = GetServerAddress();
var wreply = $"{host}FederationLogin/channel={channel.Id}";
app.UseWsFederationAuthentication(new WsFederationAuthenticationOptions
{
Wtrealm = wtrealm,
MetadataAddress = metadata,
AuthenticationType = channel.Id,
Wreply = wreply,
SignOutWreply = host
});
}
AntiForgeryConfig.UniqueClaimTypeIdentifier = ClaimTypes.Name;
}
控制器
public ActionResult FederationLogin(string channel)
{
....
HttpContext.GetOwinContext().Authentication.Challenge(new AuthenticationProperties(), channel);
....
}