这些cxf / ws-security属性设置正确吗? (得到TPE1122错误," WS安全标题无效")

时间:2016-05-13 23:24:17

标签: encryption soap cxf ws-security irs

我们正在尝试使用CXF向IRS发送已签名的,部分加密的SOAP消息。我们认为我们遵循他们的所有指示,但存在歧义。一些签名和加密属性可以通过多种方式设置,但我尝试过的排列都没有让我们超越可怕的" TPE1122"错误(WS安全标头无效)。如果有人成功完成了这项工作,是否有一些我们未能设置的财产?我特别不确定加密算法设置以及整个元素是否应加密或仅加密其中的3个标题元素。感谢。

    BulkRequestTransmitterService ss = new BulkRequestTransmitterService(wsdlURL, SERVICE_NAME);
    BulkRequestTransmitterPortType port = ss.getBulkRequestTransmitterPort();

    org.apache.cxf.endpoint.Client client = ClientProxy.getClient(port);

    // set up MTOM
    Binding binding = ((BindingProvider)port).getBinding();
    ((SOAPBinding)binding).setMTOMEnabled(true);

    // set output properties
    Map<String, Object> outProps = new HashMap<String, Object>();
    outProps.put("action", "Timestamp Signature Encrypt");
    outProps.put("passwordType", "PasswordDigest");
    outProps.put("signatureUser", "[REDACTED]";
    outProps.put(WSHandlerConstants.SIG_KEY_ID, "X509KeyIdentifier"); 
    outProps.put("passwordCallbackClass", "UTPasswordCallback"); 
    outProps.put("encryptionUser", "irs"); 
    outProps.put("encryptionPropFile", "encryption.properties");
    outProps.put("encryptionKeyIdentifier", "DirectReference"); 
    outProps.put("encryptionKeyTransportAlgorithm", "http://www.w3.org/2001/04/xmlenc#rsa-oaep-mgf1p");

    // ENC_SYM_ALGO: what is the default?  what should correct value be?  and are these two lines equivalent?
    outProps.put(WSHandlerConstants.ENC_SYM_ALGO, WSConstants.TRIPLE_DES);  
    outProps.put("encryptionSymAlgorithm", "http://www.w3.org/2001/04/xmlenc#tripledes-cbc");

    // do we encrypt each of the three signed headers, or entire Signature element?  have tried it both ways
    outProps.put("encryptionParts",
        //"{Element}{" + WSU_NS + "}Timestamp;"
        //+"{Element}{urn:us:gov:treasury:irs:ext:aca:air:7.0}ACATransmitterManifestReqDtl;"
        //+"{Element}{urn:us:gov:treasury:irs:ext:aca:air:7.0}ACABusinessHeader;");
        "{Element}{http://www.w3.org/2000/09/xmldsig#}Signature;");

    outProps.put("signaturePropFile", "signature.properties");
    outProps.put("signatureAlgorithm", "http://www.w3.org/2000/09/xmldsig#rsa-sha1");
    outProps.put("signatureParts",
            "{Element}{" + WSU_NS + "}Timestamp;"
            + "{Element}{urn:us:gov:treasury:irs:ext:aca:air:7.0}ACATransmitterManifestReqDtl;"
            + "{Element}{urn:us:gov:treasury:irs:ext:aca:air:7.0}ACABusinessHeader;");  
    outProps.put(WSHandlerConstants.SIG_C14N_ALGO, "http://www.w3.org/2001/10/xml-exc-c14n#WithComments");

    // is "Direct Reference" preferable?  have tried it both ways
    outProps.put(WSHandlerConstants.ENC_KEY_ID, "X509KeyIdentifier"); 

    outProps.put("timeToLive", "600");  // = 10 min
    outProps.put(WSHandlerConstants.MUST_UNDERSTAND, "false");

    WSS4JOutInterceptor wssOut = new WSS4JOutInterceptor(outProps);
    client.getOutInterceptors().add(wssOut); 

    // add gzip interceptor  
    GZIPOutInterceptor gz = new GZIPOutInterceptor();
    gz.setForce(true); 
    client.getOutInterceptors().add(gz);

    [ create & populate Manifest Detail here]

    Header detailHeader = new Header(new QName("urn:us:gov:treasury:irs:ext:aca:air:7.0", "ACATransmitterManifestReqDtl"), aCATrnsmtManifestReqDtlType,
            new JAXBDataBinding(ACATrnsmtManifestReqDtlType.class));
    headers.add(detailHeader);  

    Header businessHeader = new Header(new QName("urn:us:gov:treasury:irs:ext:aca:air:7.0", "ACABusinessHeader"), aCABulkBusinessHeaderRequestType,
                                    new JAXBDataBinding(ACABulkBusinessHeaderRequestType.class));
    headers.add(businessHeader);

    // add headers to Request
    client.getRequestContext().put(Header.HEADER_LIST, headers); 

    // add namespaces:
    Map<String, String> nsMap = new HashMap<>();
    nsMap.put("soapenv", "http://schemas.xmlsoap.org/soap/envelope/");  
    nsMap.put("urn", "urn:us:gov:treasury:irs:ext:aca:air:7.0");
    nsMap.put("urn1", "urn:us:gov:treasury:irs:common");        
    nsMap.put("urn2", "urn:us:gov:treasury:irs:msg:acabusinessheader");
    nsMap.put("urn3", "urn:us:gov:treasury:irs:msg:irsacabulkrequesttransmitter");
    nsMap.put("urn4", "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd");
    client.getRequestContext().put("soap.env.ns.map", nsMap); 

    // then transmit, get TPE1122 error in Response

2 个答案:

答案 0 :(得分:1)

CXF安全中的Bulit在IRS提交中不起作用。您需要对拦截器进行编码以匹配IRS要求。

我准备了一个示例项目,可以执行提交和状态请求。这绝不是生产代码,但可以作为起点

https://github.com/sangramjadhav/irsclient

请参阅application.yml文件。您需要提供密钥库和其他配置以提交给IRS

答案 1 :(得分:0)

感谢两位响应人员的反馈意见。我们现在有它工作,主要问题是我们不应该使用加密。我发布的示例中的所有内容都有效(包括使用CXF签署标题的某些部分),但必须删除加密。

在传输到IRS AIR系统时,确实很难完成所有事情。通过更改其中一个wsdl生成的文件中的命名空间来解决下一个障碍,然后它通过,但他们的Linux系统的文件大小值比我们的Windows系统值小2个字符。 - 罪魁祸首是CRLF。

如果有人尝试使用Java,Apache-CXF和Windows,我会很乐意回答具体问题。