Java 如何使用 WebServiceTemplate 发送 SOAP 请求?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/34368029/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to send a SOAP request using WebServiceTemplate?
提问by Hyman
I am trying to send a request to a SOAP webservice. I read this tutorialand prepared the following code. However, I am going to send different requests to multiple SOAP webservices, whereas the tutorial focused on one request. How can I send SOAP request using WebserviceTemplate
?
我正在尝试向 SOAP 网络服务发送请求。我阅读了本教程并准备了以下代码。但是,我将向多个 SOAP Web 服务发送不同的请求,而本教程侧重于一个请求。如何使用 发送 SOAP 请求WebserviceTemplate
?
WebServiceTemplate
网络服务模板
SoapMessage soapMsg = new SoapMessage();
soapMsg.setUsername("Requester");
soapMsg.setPassword("Pass");
soapMsg.setLanguageCode("EN");
Request request = new Request();
request.setDeparture("FDH");
request.setDestination("HAM");
Date date = new Date();
SimpleDateFormat frm2 = new SimpleDateFormat("yyyy-MM-dd");
request.setDepartureDate(frm2.parse(frm2.format(date)));
request.setNumADT(1);
request.setNumCHD(0);
request.setNumInf(0);
request.setCurrencyCode("EUR");
request.setWaitForResult(true);
request.setNearByDepartures(true);
request.setNearByDestinations(true);
request.setRronly(false);
request.setMetaSearch(false);
soapMsg.setRequest(request);
WebServiceTemplate webServiceTemplate = new WebServiceTemplate(). //how to create object and send request!
Object response = webServiceTemplate.marshalSendAndReceive(
"https://aaa5.elsyarres.net", soapMsg);
Response msg = (Response) response;
System.err.println("size of results of wogolo:"
+ msg.getFlights().getFlight().size());
采纳答案by Daniel Newtown
You can use following code, you do not need to define anything in xml file.
您可以使用以下代码,您不需要在 xml 文件中定义任何内容。
try {
SaajSoapMessageFactory messageFactory = new SaajSoapMessageFactory(
MessageFactory.newInstance());
messageFactory.afterPropertiesSet();
WebServiceTemplate webServiceTemplate = new WebServiceTemplate(
messageFactory);
Jaxb2Marshaller marshaller = new Jaxb2Marshaller();
marshaller.setContextPath("PACKAGE");
marshaller.afterPropertiesSet();
webServiceTemplate.setMarshaller(marshaller);
webServiceTemplate.afterPropertiesSet();
Response response = (Response) webServiceTemplate
.marshalSendAndReceive(
"address",
searchFlights);
Response msg = (Response) response;
} catch (Exception s) {
s.printStackTrace();
}
回答by Pankaj Nimgade
Here is an Example what you should be looking for
这是您应该寻找的示例
Soap has a lot of restriction unlike REST
, It follows some standards which have to be meet before you get Network call to work,
Soap 有很多限制,不像REST
,它遵循一些标准,在您获得网络呼叫工作之前必须满足这些标准,
But unlike Rest
, in Soap if you have WSDL
URL you can get all the information needed to call the Soap call
但与Rest
Soap不同的是,如果您有WSDL
URL,则可以获取调用 Soap 调用所需的所有信息
private final String NAMESPACE = "http://www.w3schools.com/webservices/";
private final String URL = "http://www.w3schools.com/webservices/tempconvert.asmx?WSDL";
private final String SOAP_ACTION = "http://www.w3schools.com/webservices/CelsiusToFahrenheit";
private final String METHOD_NAME = "CelsiusToFahrenheit";
this code was written in Android
so you can ignore some part of it but I still kept it in answer so someone from android background can put a good use to it
这段代码是这样写的,Android
所以你可以忽略它的一部分,但我仍然保留它的答案,所以来自 android 背景的人可以很好地利用它
Open [WSDL][1]
in browser and check for the things which matter to call a remote method on server.
[WSDL][1]
在浏览器中打开并检查在服务器上调用远程方法重要的事情。
1 you will see an attribute
targetNamespace
whose value would beNamespace
which you will use in this caseNamespace
ishttp://www.w3schools.com/webservices/
2 Now you require the name of the method this
WSDL
has four method each of the are int attributes:element
with the value is the name of the Method in this case four methods areFahrenheitToCelsius
,FahrenheitToCelsiusResponse
,CelsiusToFahrenheit
,CelsiusToFahrenheitResponse
3 Now you have to fure out the
SOAP Action
which isNAMESPACE+METHOD
but WSDL also gives information about that as well, look for the tagsoap:operation
and it'ssoapAction
attribute havs the Soap action as it's value in this case which we want to call ishttp://www.w3schools.com/webservices/CelsiusToFahrenheit
1,你会看到一个属性
targetNamespace
,其价值将是Namespace
你会在这种情况下使用的Namespace
是http://www.w3schools.com/webservices/
2 现在你需要方法的名称,它
WSDL
有四个方法,每个都是 int 属性s:element
,值是方法的名称,在这种情况下,四个方法是FahrenheitToCelsius
,FahrenheitToCelsiusResponse
,CelsiusToFahrenheit
,CelsiusToFahrenheitResponse
3 现在您必须确定
SOAP Action
哪个是,NAMESPACE+METHOD
但 WSDL 也提供了相关信息,查找标记soap:operation
,它的soapAction
属性具有 Soap 操作,因为在这种情况下,我们要调用它的值是http://www.w3schools.com/webservices/CelsiusToFahrenheit
private class MyTask extends AsyncTask<Void, Void, String> {
@Override
protected void onPreExecute() {
super.onPreExecute();
progressDialog.show();
}
@Override
protected String doInBackground(Void... params) {
try {
SoapObject soapObject = new SoapObject(NAMESPACE, METHOD_NAME);
soapObject.addProperty("Celsius","12");
SoapSerializationEnvelope envelope = new SoapSerializationEnvelope(SoapEnvelope.VER11);
envelope.dotNet = true;
envelope.setOutputSoapObject(soapObject);
HttpTransportSE httpTransportSE = new HttpTransportSE(URL);
httpTransportSE.call(SOAP_ACTION, envelope);
SoapPrimitive soapPrimitive = (SoapPrimitive)envelope.getResponse();
Log.d("TAG", "doInBackground: "+soapPrimitive.toString());
return soapObject.toString();
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
@Override
protected void onPostExecute(String aVoid) {
super.onPostExecute(aVoid);
progressDialog.dismiss();
textView.setText(""+aVoid);
}
}
回答by smarquis
To send different SOAP requests to different SOAP services, you just need to make your WebServiceTemplate aware of all requests and responses it will have to process.
要将不同的 SOAP 请求发送到不同的 SOAP 服务,您只需让 WebServiceTemplate 知道它必须处理的所有请求和响应。
Create a Java class for each request and response like so:
为每个请求和响应创建一个 Java 类,如下所示:
package models;
import javax.xml.bind.annotation.XmlRootElement;
import java.io.Serializable;
@XmlRootElement
public class FlyRequest implements Serializable {
private boolean nearByDeparture;
public FlyRequest() {}
public boolean isNearByDeparture() {
return nearByDeparture;
}
public void setNearByDeparture(boolean nearByDeparture) {
this.nearByDeparture = nearByDeparture;
}
}
(The @XmlRootElement is because we use JAXB marshaller below; see Jaxb reference for more info).
(@XmlRootElement 是因为我们在下面使用 JAXB 编组器;有关更多信息,请参阅 Jaxb 参考)。
The setup of the template is done for example like so:
模板的设置是这样完成的:
SaajSoapMessageFactory messageFactory = new SaajSoapMessageFactory(MessageFactory.newInstance());
messageFactory.afterPropertiesSet();
WebServiceTemplate webServiceTemplate = new WebServiceTemplate(messageFactory);
Jaxb2Marshaller marshaller = new Jaxb2Marshaller();
marshaller.setContextPath("models");
marshaller.afterPropertiesSet();
webServiceTemplate.setMarshaller(marshaller);
webServiceTemplate.afterPropertiesSet();
"models" is the name of the package where the Request/Responses classes are, so that jaxb can find them.
“models”是请求/响应类所在的包的名称,以便 jaxb 可以找到它们。
Then you just instantiate the request of the class you want to perform the call, like so:
然后,您只需实例化要执行调用的类的请求,如下所示:
// call fly service:
FlyRequest flyRequest = new FlyRequest();
flyRequest.setNearByDeparture(false);
Object flyResponse = webServiceTemplate.marshalSendAndReceive("https://example.net/fly", flyRequest);
// call purchase service:
PurchaseRequest purchaseRequest = new PurchaseRequest();
purchaseRequest.setPrice(100);
Object purchaseResponse = webServiceTemplate.marshalSendAndReceive("https://example.net/purchase", purchaseRequest);
Similarly, you can cast the response objects into your JAXB classes defined above.
同样,您可以将响应对象转换为上面定义的 JAXB 类。
回答by Mike Murphy
Assuming that your SoapMessage is marhsallable
假设你的 SoapMessage 是 marhsallable
To send the same message to multiple endpoints you only need to loop on the sending code and the request handler.
要将相同的消息发送到多个端点,您只需要循环发送代码和请求处理程序。
Something like this:
像这样的东西:
{
String endpoint = "https://aaa5.elsyarres.net"
WebServiceTemplate webServiceTemplate = new WebServiceTemplate().
webServiceTemplate.setDefaultUri(endpoint);
Object response = webServiceTemplate.marshalSendAndReceive(soapMsg);
// handle you are response as you are currently doing.
// Loop changing the endpoint as you need.
}
This code uses the Spring WebServiceTemplate
此代码使用 Spring WebServiceTemplate