java - 将现有 SAML 断言添加到 WS 安全 header

标签 java xml soap saml spring-ws

我使用 spring-ws (2.1.4) WebServiceTemplate 和自定义 WebServiceMessageCallback 来插入带有 SAML 的安全 header ,我将作为 org.w3c.dom.Element 接收该 header ,并且仅创建自己用于测试。

我使用 webServiceTemplate.marshalSendAndReceive(request, new HeaderCallback(ctx, uri)) 来编码并发送我的请求。

我的问题是服务器端签名验证失败,摘要不匹配。比较发送之前和接收之后的 SAML 输出,我发现在接收端,我在发送之前没有的元素上有命名空间声明。

我当前在回调中执行的操作:

@Override
public void doWithMessage(WebServiceMessage message) throws IOException, TransformerException {
    super.doWithMessage(message);

    Assert.isInstanceOf(SoapMessage.class, message);
    SoapMessage soapMessage = (SoapMessage) message;
    SoapHeaderElement securityHeader = soapMessage.getSoapHeader().addHeaderElement(WS_SECURITY_NAME);

    try {
        Transformer t = TransformerFactory.newInstance().newTransformer();
        t.transform(new DOMSource(assertion), securityHeader.getResult());
    } catch (org.springframework.oxm.MarshallingException ex) {
        throw new IOException(ex);
    }

有谁知道如何将元素插入 SOAP XML 中以确保该元素不会被修改?或者是否有其他方法可以使用 Spring WebServiceTemplate 来实现此目的?

我遇到了 org.apache.ws.security.saml.ext.SAMLCallback,它有一个 setAssertionElement 方法,但是我没有找到如何让它与 WebServiceTemplate(分别为 Wss4jSecurityInterceptor)一起使用,特别是考虑到我需要将现有的 SAML 断言作为参数传递。

发送前的 SAML XML:

<saml2:Assertion xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" IssueInstant="2015-09-23T09:46:14.357Z" Version="2.0">
<saml2:Issuer>iTEST</saml2:Issuer>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod 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="">
<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"/>
<ds:DigestValue>rVbvzGr4LI/Kd0c+kuhqkupSY44=</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
<ds:SignatureValue>TIbtFHnqURfko94eqANDX8UEhw0HSI3xL0sAQ5GbhjVn2DicckzxpoJL3RVPF6KhLOkUPm5IgnF5At6Es69D48DLE+QvWvP0F7VmcdNJHRSnzIWYaJsXfNfDt2AXXM1kanp5Gq8nj1EsT6C8SlkO1x77C3vKkn1nLSNszEkukuhEzA8V7G+l6L65bIveA36IyYqjiVDKIMOIzHMF9qK03Um7qJHWoxvxSig1UPBINlBtDqyhbGW01OnoHP8qXK7bzuP6p3zbBDhhEYMyNV2P8GT8zX1+cv+JE6ghde4K9hyf6V+x6L218L1AOjACEJUkBrxw0q1uJAVGA1UNJPJbJQ==</ds:SignatureValue>
<ds:KeyInfo>
<ds:X509Data>
<ds:X509Certificate>MIIC1TCCAb2gAwIBAgIENFWkEzANBgkqhkiG9w0BAQsFADAbMRkwFwYDVQQDExBpVEVTVDpjb21tdW5pdHlBMB4XDTE1MDkxMDE0NDcyMFoXDTI1MDkwNzE0NDcyMFowGzEZMBcGA1UEAxMQaVRFU1Q6Y29tbXVuaXR5QTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMX9f6af8s8bqZSlSl7nZVmVz9sQuaxK/fYHwKcBCmeQGfx67K6Lrmg4ZkVlMxFPFAZta8i0UHVbFXD6hY4nD8skA+P1RjnHvk4KboBM2krtx7tSC8IzXmtb8sxXsfLKfu1Blqq0lX0kjPyvCIo4FLOSRE//AuKy8zeTSrKAX8tcZYo23mX8TWkp22Hd6O/x4IxuakWRB6fq8DxYWFsu9f1cnt2n3R+d/myrZ6XRVdpZhptWlZjzy90L2VOuHFC3kY8DvgSCdI3UgL+PzD7R3cKUytHlz04LO5cJue4kRaGbNOdgJoRdj4D24BsjpIZ9PCbzSw689N/hRftsUtO5PRECAwEAAaMhMB8wHQYDVR0OBBYEFBL153jJBGRArnJ5dSyHZGKC3vGcMA0GCSqGSIb3DQEBCwUAA4IBAQCWa0KtdISsQecjA3i4Kyr50oynOnas6YK9Jgb3LzJEU911JW4vX4rHmXEe64OkbIO/fpdCE30saTiBoLEFxrUx0xn+0wGvPMIBJZYncaZUUN9412XPEjYoj5DnFjFvdYqNsdNZ9cOs3sa5hRWufea+QFhSJKSG0nouwW1/5WT3/GYtKJZystL2N2q6pUqhwfP5x1JDELTcoiZZzbTkHOxFiz5iLMrZyDL8Bmb856pF7SzmD6NzLXpqiOwMjTeDWyJ3I9mZqDwoTwxC/e8wG42d486GKu3O/BbDkxEv5UDClMY2722oZKKhu3TdQLOIOLJChKgghjuEWOXb+mDdj/Qq</ds:X509Certificate>
</ds:X509Data>
</ds:KeyInfo>
</ds:Signature>
<saml2:Subject>
<saml2:NameID>authSigner</saml2:NameID>
</saml2:Subject>
</saml2:Assertion>

收到后的 SAML XML:

<saml2:Assertion xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" IssueInstant="2015-09-23T09:46:14.357Z" Version="2.0">
<saml2:Issuer xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion">iTEST</saml2:Issuer>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" xmlns:ds="http://www.w3.org/2000/09/xmldsig#"/>
<ds:SignatureMethod Algorithm="http://www.w3.org/2000/09/xmldsig#rsa-sha1" xmlns:ds="http://www.w3.org/2000/09/xmldsig#"/>
<ds:Reference URI="" xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:Transforms xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:Transform Algorithm="http://www.w3.org/2000/09/xmldsig#enveloped-signature" xmlns:ds="http://www.w3.org/2000/09/xmldsig#"/>
<ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#" xmlns:ds="http://www.w3.org/2000/09/xmldsig#"/>
</ds:Transforms>
<ds:DigestMethod Algorithm="http://www.w3.org/2000/09/xmldsig#sha1" xmlns:ds="http://www.w3.org/2000/09/xmldsig#"/>
<ds:DigestValue xmlns:ds="http://www.w3.org/2000/09/xmldsig#">rVbvzGr4LI/Kd0c+kuhqkupSY44=</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
<ds:SignatureValue xmlns:ds="http://www.w3.org/2000/09/xmldsig#">TIbtFHnqURfko94eqANDX8UEhw0HSI3xL0sAQ5GbhjVn2DicckzxpoJL3RVPF6KhLOkUPm5IgnF5At6Es69D48DLE+QvWvP0F7VmcdNJHRSnzIWYaJsXfNfDt2AXXM1kanp5Gq8nj1EsT6C8SlkO1x77C3vKkn1nLSNszEkukuhEzA8V7G+l6L65bIveA36IyYqjiVDKIMOIzHMF9qK03Um7qJHWoxvxSig1UPBINlBtDqyhbGW01OnoHP8qXK7bzuP6p3zbBDhhEYMyNV2P8GT8zX1+cv+JE6ghde4K9hyf6V+x6L218L1AOjACEJUkBrxw0q1uJAVGA1UNJPJbJQ==</ds:SignatureValue>
<ds:KeyInfo xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:X509Data xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:X509Certificate xmlns:ds="http://www.w3.org/2000/09/xmldsig#">MIIC1TCCAb2gAwIBAgIENFWkEzANBgkqhkiG9w0BAQsFADAbMRkwFwYDVQQDExBpVEVTVDpjb21tdW5pdHlBMB4XDTE1MDkxMDE0NDcyMFoXDTI1MDkwNzE0NDcyMFowGzEZMBcGA1UEAxMQaVRFU1Q6Y29tbXVuaXR5QTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMX9f6af8s8bqZSlSl7nZVmVz9sQuaxK/fYHwKcBCmeQGfx67K6Lrmg4ZkVlMxFPFAZta8i0UHVbFXD6hY4nD8skA+P1RjnHvk4KboBM2krtx7tSC8IzXmtb8sxXsfLKfu1Blqq0lX0kjPyvCIo4FLOSRE//AuKy8zeTSrKAX8tcZYo23mX8TWkp22Hd6O/x4IxuakWRB6fq8DxYWFsu9f1cnt2n3R+d/myrZ6XRVdpZhptWlZjzy90L2VOuHFC3kY8DvgSCdI3UgL+PzD7R3cKUytHlz04LO5cJue4kRaGbNOdgJoRdj4D24BsjpIZ9PCbzSw689N/hRftsUtO5PRECAwEAAaMhMB8wHQYDVR0OBBYEFBL153jJBGRArnJ5dSyHZGKC3vGcMA0GCSqGSIb3DQEBCwUAA4IBAQCWa0KtdISsQecjA3i4Kyr50oynOnas6YK9Jgb3LzJEU911JW4vX4rHmXEe64OkbIO/fpdCE30saTiBoLEFxrUx0xn+0wGvPMIBJZYncaZUUN9412XPEjYoj5DnFjFvdYqNsdNZ9cOs3sa5hRWufea+QFhSJKSG0nouwW1/5WT3/GYtKJZystL2N2q6pUqhwfP5x1JDELTcoiZZzbTkHOxFiz5iLMrZyDL8Bmb856pF7SzmD6NzLXpqiOwMjTeDWyJ3I9mZqDwoTwxC/e8wG42d486GKu3O/BbDkxEv5UDClMY2722oZKKhu3TdQLOIOLJChKgghjuEWOXb+mDdj/Qq</ds:X509Certificate>
</ds:X509Data>
</ds:KeyInfo>
</ds:Signature>
<saml2:Subject xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion">
<saml2:NameID xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion">authSigner</saml2:NameID>
</saml2:Subject>
</saml2:Assertion>
</wsse:Security>
<小时/>

编辑:我找到了一种不添加额外命名空间的方法。我现在正在做的是使用 javax.xml.soap.SOAPMessage 并导入节点:

@Override
public void doWithMessage(WebServiceMessage message) throws IOException, TransformerException {
    super.doWithMessage(message);

    Assert.isInstanceOf(SaajSoapMessage.class, message);

    try {
        SOAPMessage soapMessage = ((SaajSoapMessage) message).getSaajMessage();
        SOAPPart soapPart = soapMessage.getSOAPPart();
        SOAPEnvelope soapEnvelope = soapPart.getEnvelope();

        if (soapEnvelope.getHeader() == null) {
            soapEnvelope.addHeader();
        }

        SOAPHeaderElement securityElement = soapEnvelope.getHeader().addHeaderElement(WS_SECURITY_NAME);
        securityElement.appendChild(soapPart.importNode(assertion, true));

    } catch (SOAPException ex) {
        throw new IOException(ex);
    }

}

但是,即使差异显示输出之间没有差异验证仍然失败。此时,我不确定我是否可以信任输出,并且这样做确实不会改变 SAML...

还有什么想法可能导致摘要不匹配吗?

最佳答案

以下方法(我已经将其作为编辑记录在我的问题中)阻止添加其他 namespace 。

@Override
public void doWithMessage(WebServiceMessage message) throws IOException, TransformerException {
    super.doWithMessage(message);

    Assert.isInstanceOf(SaajSoapMessage.class, message);

    try {
        SOAPMessage soapMessage = ((SaajSoapMessage) message).getSaajMessage();
        SOAPPart soapPart = soapMessage.getSOAPPart();
        SOAPEnvelope soapEnvelope = soapPart.getEnvelope();

        if (soapEnvelope.getHeader() == null) {
            soapEnvelope.addHeader();
        }

        SOAPHeaderElement securityElement = soapEnvelope.getHeader().addHeaderElement(WS_SECURITY_NAME);
        securityElement.appendChild(soapPart.importNode(assertion, true));

    } catch (SOAPException ex) {
        throw new IOException(ex);
    }

}

我还让 SAML 验证正常工作。它与将 SAML 添加到 SOAP 消息的方式无关(也是我使用 Transformer 的原始方法 - 尽管它添加了额外的命名空间 - 现在已验证)。断言中缺少 ID。

这是我的 SAML 现在的样子:

<saml2:Assertion xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion" ID="_63ecd7ce7163507e56270edcd644494b" IssueInstant="2015-09-24T18:23:15.118Z" Version="2.0">
<saml2:Issuer>iTEST</saml2:Issuer>
<ds:Signature xmlns:ds="http://www.w3.org/2000/09/xmldsig#">
<ds:SignedInfo>
<ds:CanonicalizationMethod 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="#_63ecd7ce7163507e56270edcd644494b">
<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"/>
<ds:DigestValue>yjlkSOIJC3qNYzEYfipGIwoAD9A=</ds:DigestValue>
</ds:Reference>
</ds:SignedInfo>
<ds:SignatureValue>fIEp5aYFVesexZWAfMM+e8kcwe52nl54xMr92wtz2BZ3TIVkY6u5vfh8hA0q6hkzEEaHV5vM0cEXholekn4og41jhMn7XwmScggrbr/neYBMdE95GRz6Nv2Sc6PzqPTYeFp+Dylho7sy1yZtWAb3jiGm8zdHJIQuk6NNUZhnMPkZqjXpM68U9cRGojAmnczbRVl2couxDp5fErivKJgJuffN3FVBfCFrFOjGpVf00ukZxqJJ3RP+n7wXWl251W0i0KvWCZPCD5gzl69EzNFc78o8khzd26aLIeDFLBQr0BPnrC454dZZ/SSNeH52HtDstNJ6SBrWFAA8c8vnLSJ0fg==</ds:SignatureValue>
<ds:KeyInfo>
<ds:X509Data>
<ds:X509Certificate>MIIC1TCCAb2gAwIBAgIENFWkEzANBgkqhkiG9w0BAQsFADAbMRkwFwYDVQQDExBpVEVTVDpjb21tdW5pdHlBMB4XDTE1MDkxMDE0NDcyMFoXDTI1MDkwNzE0NDcyMFowGzEZMBcGA1UEAxMQaVRFU1Q6Y29tbXVuaXR5QTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAMX9f6af8s8bqZSlSl7nZVmVz9sQuaxK/fYHwKcBCmeQGfx67K6Lrmg4ZkVlMxFPFAZta8i0UHVbFXD6hY4nD8skA+P1RjnHvk4KboBM2krtx7tSC8IzXmtb8sxXsfLKfu1Blqq0lX0kjPyvCIo4FLOSRE//AuKy8zeTSrKAX8tcZYo23mX8TWkp22Hd6O/x4IxuakWRB6fq8DxYWFsu9f1cnt2n3R+d/myrZ6XRVdpZhptWlZjzy90L2VOuHFC3kY8DvgSCdI3UgL+PzD7R3cKUytHlz04LO5cJue4kRaGbNOdgJoRdj4D24BsjpIZ9PCbzSw689N/hRftsUtO5PRECAwEAAaMhMB8wHQYDVR0OBBYEFBL153jJBGRArnJ5dSyHZGKC3vGcMA0GCSqGSIb3DQEBCwUAA4IBAQCWa0KtdISsQecjA3i4Kyr50oynOnas6YK9Jgb3LzJEU911JW4vX4rHmXEe64OkbIO/fpdCE30saTiBoLEFxrUx0xn+0wGvPMIBJZYncaZUUN9412XPEjYoj5DnFjFvdYqNsdNZ9cOs3sa5hRWufea+QFhSJKSG0nouwW1/5WT3/GYtKJZystL2N2q6pUqhwfP5x1JDELTcoiZZzbTkHOxFiz5iLMrZyDL8Bmb856pF7SzmD6NzLXpqiOwMjTeDWyJ3I9mZqDwoTwxC/e8wG42d486GKu3O/BbDkxEv5UDClMY2722oZKKhu3TdQLOIOLJChKgghjuEWOXb+mDdj/Qq</ds:X509Certificate>
</ds:X509Data>
</ds:KeyInfo>
</ds:Signature>
<saml2:Subject>
<saml2:NameID>authSigner</saml2:NameID>
</saml2:Subject>
</saml2:Assertion>

关于java - 将现有 SAML 断言添加到 WS 安全 header ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32721118/

相关文章:

android - Titanium Studio - 合金|标签的字体大小

android - 编辑位于另一个 XML 文件中的 CheckBox 和 EditText

java - 使用 Spring-WS 和 JAXB 的 AbstractMethodEndpointMapping 中的 AbstractMethodError

java - WSIT/Metro 不理解安全 SOAP header

ruby-on-rails - 在 Ruby on Rails 中使用 Savon 的 SOAP 调用在信封和主要操作周围变得奇怪

java - 如何在同一个 `groupingBy` 中处理 `stream()` 的结果 List<T> 值?

Java技术冲突

java - 为什么在我的 LinkedBinaryTree 实现中只添加了根

java - 如何在 Android 上从 JWT 收集签名、 header 和正文

JavaScript 可以在 FF/IE 中运行,但不能在 Chrome/Safari 中运行