You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

使用OpenSAML为SOAP Body生成分离式签名的问题求助

使用OpenSAML为SOAP Body生成分离式签名的问题求助

需求描述

我需要为SOAP Body生成分离式签名(detached signing),目标XML格式如下:

<soap:Envelope
xmlns:soap="http://www.w3.org/2003/05/soap-envelope">
<env:Header
    xmlns:env="http://www.w3.org/2003/05/soap-envelope">
    <wsse:Security
        xmlns:wsse="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd"
        xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" soap:mustUnderstand="true">
        <ds:Signature
            xmlns:ds="http://www.w3.org/2000/09/xmldsig#" Id="SIG-B9561BC9E482A7482717165370736895">
            <ds:SignedInfo>
                <ds:CanonicalizationMethod Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#"/>
                <ds:SignatureMethod Algorithm="http://www.w3.org/2001/04/xmldsig-more#rsa-sha512"/>
                <ds:Reference URI="#id-B9561BC9E482A7482717165370736684">
                    <ds:Transforms>
                        <ds:Transform Algorithm="http://www.w3.org/2001/10/xml-exc-c14n#">
                        </ds:Transform>
                    </ds:Transforms>
                    <ds:DigestMethod Algorithm="http://www.w3.org/2001/04/xmlenc#sha512"/>
                    <ds:DigestValue>some value</ds:DigestValue>
                </ds:Reference>
            </ds:SignedInfo>
            <ds:SignatureValue>some value </ds:SignatureValue>
        </ds:Signature>
    </wsse:Security>
</env:Header>
<soap:Body
    xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" wsu:Id="id-B9561BC9E482A7482717165370736684">
    <Test/>
</soap:Body>
</soap:Envelope>

当前实现代码

我基于OpenSAML做了部分实现,先配置签名的基础参数:

signature.setSigningCredential(credential);
signature.setSignatureAlgorithm(SignatureConstants.ALGO_ID_SIGNATURE_RSA_SHA1);
signature.setCanonicalizationAlgorithm(SignatureConstants.ALGO_ID_C14N_EXCL_OMIT_COMMENTS);

接着添加指向SOAP Body的内容引用:

Element bodyElement = (Element) doc.getDocumentElement().getElementsByTagName("SOAP-Body").item(0);
        String bodyId = "body123"; // Unique reference ID
        bodyElement.setAttribute("Id", bodyId);
        bodyElement.setIdAttribute("Id", true);

        DocumentInternalIDContentReference uriContentReference = new DocumentInternalIDContentReference( bodyId);
        uriContentReference.setDigestAlgorithm(SignatureConstants.ALGO_ID_DIGEST_SHA256);
        uriContentReference.getTransforms().add(SignatureConstants.TRANSFORM_C14N_EXCL_OMIT_COMMENTS);

        signature.getContentReferences().add(uriContentReference);

最后执行签名操作:

Signer.signObject(signature);

遇到的错误

执行过程中抛出了如下异常:

Exception in thread "main" org.opensaml.xmlsec.signature.support.SignatureException: Signature computation error
    at org.opensaml.xmlsec.signature.support.impl.provider.ApacheSantuarioSignerProviderImpl.signObject(ApacheSantuarioSignerProviderImpl.java:62)
    at org.opensaml.xmlsec.signature.support.Signer.signObject(Signer.java:73)
    at com.amazon.bancomatpayremittancelambda.service.OpenSAMLDetachedSignature.main(OpenSAMLDetachedSignature.java:98)
Caused by: org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID body123
Original Exception was org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID body123
Original Exception was org.apache.xml.security.signature.ReferenceNotInitializedException: Cannot resolve element with ID body123
Original Exception was org.apache.xml.security.utils.resolver.ResourceResolverException: Cannot resolve element with ID body123
    at org.apache.xml.security.signature.Reference.calculateDigest(Reference.java:744)
    at org.apache.xml.security.signature.Reference.generateDigestValue(Reference.java:405)
    at org.apache.xml.security.signature.Manifest.generateDigestValues(Manifest.java:205)
    at org.apache.xml.security.signature.XMLSignature.sign(XMLSignature.java:631)
    at org.opensaml.xmlsec.signature.support.impl.provider.ApacheSantuarioSignerProviderImpl.signObject(ApacheSantuarioSignerProviderImpl.java:59)
    ... 2 more

问题总结

tl;dr
我该如何用OpenSAML生成符合上述示例的XML请求?

备注:内容来源于stack exchange,提问作者SynAck

火山引擎 最新活动