Sustainsys错误:"在读取Saml2SecurityToken的'[PII is hidden]'时抛出异常IDX13102。内部异常:'System.ArgumentException'。"

3

使用的Nuget包:

  1. Microsoft.AspNetCore.App - 2.1.1
  2. Microsoft.NETCore.App - 2.1.0
  3. Sustainsys.Saml2.AspNetCore2 - 2.2.0

Dotnet Core版本: 2.1.302

实现

以下代码添加在startup.cs文件的ConfigureServices(IServiceCollection services)方法中:

services.AddSaml2("saml2", options =>
{
    options.SPOptions.EntityId = new Sustainsys.Saml2.Metadata.EntityId(this.Configuration.Get<AppSetting>().SPEntityId);
    options.SPOptions.MinIncomingSigningAlgorithm = "http://www.w3.org/2000/09/xmldsig#rsa-sha1";
    options.SPOptions.NameIdPolicy = new Sustainsys.Saml2.Saml2P.Saml2NameIdPolicy(true, Sustainsys.Saml2.Saml2P.NameIdFormat.Unspecified);
    options.IdentityProviders.Add(
            new Sustainsys.Saml2.IdentityProvider(
                new Sustainsys.Saml2.Metadata.EntityId(this.Configuration.Get<AppSetting>().SPMetadata), options.SPOptions)
                {
                    LoadMetadata = true,
                    Binding = Sustainsys.Saml2.WebSso.Saml2BindingType.HttpPost
                });
})

身份验证由以下控制器操作触发:

[HttpGet]
public IActionResult Login(string returnUrl = null)
{
    var redirectUrl = Url.Content("~/Saml/Callback");
    return Challenge(
        new AuthenticationProperties { RedirectUri = redirectUrl }, "saml2");
}

与ID服务器的身份验证已成功完成,并根据本文末尾的XML作为POST请求接收到响应,位于https://SP-Server-xxxx/server/Saml2/Acs。但是,随后返回以下HTTP代码500的错误:

{
    error: "IDX13102: Exception thrown while reading '[PII is hidden]' for Saml2SecurityToken. Inner exception: 'System.ArgumentException'."
}

请指出设置或实现方面存在的问题。
响应XML:
<samlp:Response xmlns:samlp="urn:oasis:names:tc:SAML:2.0:protocol" xmlns:saml="urn:oasis:names:tc:SAML:2.0:assertion" Consent="urn:oasis:names:tc:SAML:2.0:consent:obtained" Destination="https://SP-Server-xxxx/server/Saml2/Acs" ID="XXXXX" InResponseTo="XXXXX" IssueInstant="2018-11-28T06:26:12Z" Version="2.0">
    <saml:Issuer>https://ID-Server-yyyy/zzzz/saml2/metadata</saml:Issuer>
    <samlp:Status>
        <samlp:StatusCode Value="urn:oasis:names:tc:SAML:2.0:status:Success"/>
    </samlp:Status>
    <saml:Assertion ID="XXXXX" IssueInstant="2018-11-28T06:26:12Z" Version="2.0">
        <saml:Issuer>https://ID-Server-yyyy/zzzz/saml2/metadata</saml:Issuer>
        <ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
            <ds:SignedInfo>
                <CanonicalizationMethod xmlns="http://www.w3.org/2000/09/xmldsig#" Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
                <ds:SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1"/>
                <ds:Reference URI="#yyyyy">
                    <ds:Transforms>
                        <ds:Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature"/>
                        <ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
                    </ds:Transforms>
                    <ds:DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1"/>
                    <DigestValue xmlns="http://www.w3.org/2000/09/xmldsig#">zzzzz</DigestValue>
                </ds:Reference>
            </ds:SignedInfo>
            <SignatureValue xmlns="http://www.w3.org/2000/09/xmldsig#"> 'removed the signature value' </SignatureValue>
            <ds:KeyInfo>
                <ds:X509Data>
                    <ds:X509Certificate> 'removed the certificate' </ds:X509Certificate>
                </ds:X509Data>
            </ds:KeyInfo>
        </ds:Signature>
        <saml:Subject>
            <saml:NameID Format="urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress" NameQualifier="https://ID-Server-yyyy/zzzz/saml2/metadata" SPNameQualifier="https://SP-Server-xxxx">
                abc@xyz.com
            </saml:NameID>
            <saml:SubjectConfirmation Method="urn:oasis:names:tc:SAML:2.0:cm:bearer">
                <saml:SubjectConfirmationData InResponseTo="XXXXX" NotOnOrAfter="2018-11-28T06:31:12Z" Recipient="https://SP-Server-xxxx/server/Saml2/Acs"/>
            </saml:SubjectConfirmation>
        </saml:Subject>
        <saml:Conditions NotBefore="2018-11-28T06:21:12Z" NotOnOrAfter="2018-11-28T06:31:12Z">
            <saml:AudienceRestriction>
                <saml:Audience>https://SP-Server-xxxx</saml:Audience>
            </saml:AudienceRestriction>
        </saml:Conditions>
        <saml:AuthnStatement AuthnInstant="2018-11-28T06:26:09Z" SessionIndex="XXXXX">
            <saml:AuthnContext>
                <saml:AuthnContextClassRef>urn:oasis:names:tc:SAML:2.0:ac:classes:Password</saml:AuthnContextClassRef>
                <saml:AuthnContextDeclRef>name/password/uri</saml:AuthnContextDeclRef>
            </saml:AuthnContext>
        </saml:AuthnStatement>
        <saml:AttributeStatement>
            <saml:Attribute xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" Name="LastName" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:unspecified">
                <saml:AttributeValue xsi:type="xs:string">Last Name</saml:AttributeValue>
            </saml:Attribute>
            <saml:Attribute xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" Name="mail" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:unspecified">
                <saml:AttributeValue xsi:type="xs:string">abc@xyz.com</saml:AttributeValue>
            </saml:Attribute>
            <saml:Attribute xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" Name="MiddleName" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:unspecified">
                <saml:AttributeValue xsi:type="xs:string">Middle Name</saml:AttributeValue>
            </saml:Attribute>
            <saml:Attribute xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" Name="FirstName" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:unspecified">
                <saml:AttributeValue xsi:type="xs:string">First Name</saml:AttributeValue>
            </saml:Attribute>
            <saml:Attribute xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" Name="Id" NameFormat="urn:oasis:names:tc:SAML:2.0:attrname-format:unspecified">
                <saml:AttributeValue xsi:type="xs:string">Id Value</saml:AttributeValue>
            </saml:Attribute>
        </saml:AttributeStatement>
    </saml:Assertion>
</samlp:Response>

更新:IdentityModelEventSource.ShowPII设置为true后,错误响应将更改如下:

{
    error: "IDX13102: Exception thrown while reading 'AuthnContext' for Saml2SecurityToken. Inner exception: 'System.ArgumentException: IDX13300: 'value' must be an absolute Uri, was: 'name/password/uri' at Microsoft.IdentityModel.Tokens.Saml2.Saml2AuthenticationContext.set_DeclarationReference(Uri value) at Microsoft.IdentityModel.Tokens.Saml2.Saml2AuthenticationContext..ctor(Uri classReference, Uri declarationReference) at Microsoft.IdentityModel.Tokens.Saml2.Saml2Serializer.ReadAuthenticationContext(XmlDictionaryReader reader)'."
}

根据错误信息,我认为ID服务器需要使用有效的URI设置AuthnContext。请确认。

以下是堆栈跟踪:

2018-11-29 08:45:10.700 +01:00 [Debug] Signature validation passed for Saml Response Microsoft.IdentityModel.Tokens.Saml2.Saml2Id
2018-11-29 08:45:10.759 +01:00 [Error] Exception is occurred
Microsoft.IdentityModel.Tokens.Saml2.Saml2SecurityTokenReadException: IDX13102: Exception thrown while reading 'AuthnContext' for Saml2SecurityToken. Inner exception: 'System.ArgumentException: IDX13300: 'value' must be an absolute Uri, was: 'name/password/uri'
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2AuthenticationContext.set_DeclarationReference(Uri value)
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2AuthenticationContext..ctor(Uri classReference, Uri declarationReference)
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2Serializer.ReadAuthenticationContext(XmlDictionaryReader reader)'. ---> System.ArgumentException: IDX13300: 'value' must be an absolute Uri, was: 'name/password/uri'
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2AuthenticationContext.set_DeclarationReference(Uri value)
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2AuthenticationContext..ctor(Uri classReference, Uri declarationReference)
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2Serializer.ReadAuthenticationContext(XmlDictionaryReader reader)
   --- End of inner exception stack trace ---
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2Serializer.ReadAuthenticationContext(XmlDictionaryReader reader)
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2Serializer.ReadAuthenticationStatement(XmlDictionaryReader reader)
   at Sustainsys.Saml2.Saml2P.Saml2PSerializer.ReadAssertion(XmlReader reader)
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2SecurityTokenHandler.ReadSaml2Token(String token)
   at Microsoft.IdentityModel.Tokens.Saml2.Saml2SecurityTokenHandler.ValidateToken(String token, TokenValidationParameters validationParameters, SecurityToken& validatedToken)
   at Sustainsys.Saml2.Saml2P.Saml2Response.CreateClaims(IOptions options, IdentityProvider idp)+MoveNext()
   at System.Collections.Generic.List`1.AddEnumerable(IEnumerable`1 enumerable)
   at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source)
   at Sustainsys.Saml2.Saml2P.Saml2Response.GetClaims(IOptions options, IDictionary`2 relayData)
   at Sustainsys.Saml2.WebSso.AcsCommand.ProcessResponse(IOptions options, Saml2Response samlResponse, StoredRequestState storedRequestState)
   at Sustainsys.Saml2.WebSso.AcsCommand.Run(HttpRequestData request, IOptions options)
   at Sustainsys.Saml2.AspNetCore2.Saml2Handler.HandleRequestAsync()
   at Microsoft.AspNetCore.Authentication.AuthenticationMiddleware.Invoke(HttpContext context)
   at Service.Provider.Middleware.LanguageHandlingMiddleware.Invoke(HttpContext context) in X:\Projects\Service-Provider\Middleware\LanguageHandlingMiddleware.cs:line 21
   at Service.Provider.Middleware.ErrorHandlingMiddleware.Invoke(HttpContext context, ILogger`1 logger) in X:\Projects\Service-Provider\Middleware\ErrorHandlingMiddleware.cs:line 22

更新2

感谢@Anders的回复。由于我们无法控制ipd,我已要求idp开发人员考虑上述更改。但与此同时,我们尝试深入了解选项。我参考了这里托管的一个文档:https://media.readthedocs.org/pdf/saml2/latest/saml2.pdf。第2.18.1节列出了元素的属性。它提到了 IgnoreAuthenticationContextInResponse 属性。根据该属性的描述,将其设置为 true 似乎可以解决上述错误。但是,在配置SPOtions( options.SPOptions.Compatibility.IgnoreAuthenticationContextInResponse ?)的兼容性元素时,我找不到这个属性。

我们正在使用Sustainsys.Saml2.AspNetCore2包版本2.2.0。

是否说明在版本2.2.0中尚未提供Compatibility.IgnoreAuthenticationContextInResponse属性?


请提供异常的堆栈跟踪,并将IdentityModelEventSource.ShowPII标志设置为true,以在日志消息中显示实际值。 - undefined
我已经编辑了问题,添加了堆栈跟踪。 - undefined
是的,在升级到2.0版本时可能会忘记 IgnoreAuthenticationContextInResponse 兼容标志。请在代码库中提交一个错误报告。 - undefined
感谢澄清。我已在此处报告错误:https://github.com/Sustainsys/Saml2/issues/1045 - undefined
看起来项目中添加了SPOptions.Compatibility.IgnoreAuthenticationContextInResponse属性,并且这解决了我的问题。应该将此作为答案添加进去。 - undefined
1个回答

3
问题在于idp为提供了一个值name/password/uri。这不是一个有效的值,根据SAML2规范,它必须是绝对URI。
但在这种情况下,我认为Idp应该完全省略该元素。它已经在上一行引用了一个众所周知的身份验证方法:urn:oasis:names:tc:SAML:2.0:ac:classes:Password

谢谢你的回答。我在问题中又做了一个更新,因为评论框里没有足够的空间。如果你能看一下,我会很感激。 - undefined

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接