如何使用 Java 更改 SOAP 消息的 Mime Headers

How to change Mime Headers of SOAP message using Java

我必须为 SOAP 请求更改 Mime header,尤其是 'content type' header,我的代码已经适用于大多数 header,但对于某些我取回内容类型 header:

的旧值的原因

这是带注释的简化代码:

public static synchronized SOAPMessage sendSoapRequest(String endpointUrl, SOAPMessage request) throws NoSuchAlgorithmException, KeyManagementException, KeyStoreException {
SOAPMessage response = null;


HashMap<String,String> headers =  ConfigManager.GetInstance().GetHeaders(); 

int number_of_retries = ConfigManager.GetInstance().GetNumberOfAttempts();
if (number_of_retries==0)
  {
    number_of_retries = 10;
  }

for (int i = 0; i <=number_of_retries ; i++) {
 try {

    
    // Send HTTP SOAP request and get response
    SOAPConnection soapConnection
            = SOAPConnectionFactory.newInstance().createConnection();
    ***// here I have mime headers with "Content-Type: text/xml; charset=utf-8"***
    if (headers != null)
        {
        Iterator it = headers.entrySet().iterator();
        while (it.hasNext()) {
            HashMap.Entry pair = (HashMap.Entry)it.next();
           
            // request.getMimeHeaders().addHeader(pair.getKey().toString(),  pair.getValue().toString());
            request.getMimeHeaders().setHeader(pair.getKey().toString(), pair.getValue().toString()); ***// I set here: "Content-Type => application/soap+xml"***
          
            }
        request.saveChanges();   ***// I got back mime headers with "Content-Type: text/xml;*** charset=utf-8"
        }
   

    response = soapConnection.call(request, endpointUrl); ***// If I don't use request.saveChanges(), I also get back mime headers with "Content-Type: text/xml; charset=utf-8"***
    // Close connection
    soapConnection.close();
   
    return response;
  } 
 }
 return null;
}

我不明白为什么 Content-Type 设置回 'text/xml; charset=utf-8' 以及如何解决它。

根据您的代码和评论,在我看来您正在使用 SAAJ 对 SOAP 1.2 端点进行 SOAP 调用并且您尝试设置正确的内容类型与任何内容冲突SAAJ在幕后做事。

SAAJ 允许您在为您处理 SOAP 详细信息的同时使用对象树。默认情况下,它知道使用 SOAP 1.1。这里要注意的主要是 SOAP 1.1。内容类型是 text/xml,SOAP XML 命名空间是 http://schemas.xmlsoap.org/soap/envelope/.

您想发送 application/soap+xml,这是 SOAP 1.2 的内容类型。在这种情况下,SOAP XML 名称空间将是 http://www.w3.org/2003/05/soap-envelope.

因此,即使您设法设置了所需的内容类型,SAAJ 创建的 XML 消息仍然是错误的,因为它具有 SOAP 1.1 的命名空间。因为这是默认值。

如果要调用SOAP 1.2。您需要告诉 SAAJ 的端点。您的 SAAJ 对象树可能是使用 MessageFactory 构建的,它具有默认的 SOAP 1.1 实例化。与:

MessageFactory mf = MessageFactory.newInstance();

如果您需要 SOAP 1.2。你需要用这个告诉 SAAJ:

MessageFactory mf = MessageFactory.newInstance(SOAPConstants.SOAP_1_2_PROTOCOL);

如果你这样做,你仍然会遇到内容类型的问题,但这次将是 SAAJ 设置 application/soap+xml(这就是你想要的)并且设置正确的 XML消息中的 SOAP 命名空间。