Implementing a Soap Plugin for Apache JMeter ============================================ JMeter already has a WebService(SOAP) Request which works fine. Unfortunately it can not handle authentication. This is why I had to write this plugin. The plugin uses a interface very similar to WebService(SOAP) Request. My hope is that later JMeter will adopt the authentication feature to JMeter core. Plugin Installation ------------------- The installation is quite simple just download jmetersoapplugin.jar and put it in $JMETER_HOME/lib/ext. Once you restart JMeter you should see a new option under Add -> Samplers called "Enhanced JDBC Request". It works just like the standard WebService(SOAP) Request. You will also need the spring-ws client libraries. Additional libs for JMeter in lib/ext: o spring-ws-2.1.0.RELEASE-all o springframework.*-3.1.0.RELEASE o wss4j-1.6.6.jar o xmlsec-1.5.2.jar Implementing a simple Soap webservice ===================================== This section describes how I created a simple webservice. I started from this excellent tutorial: http://blog.espenberntsen.net/2010/02/26/generate-jaxb-classes-from-an-xsd-schema-and-the-schema-from-an-xml-sample-document/ Generating an XSD schema from a sample XML document --------------------------------------------------- Here a sample XML file for a start: <addRequest> <a>10</a> <b>20</b> </addRequest> The XSD schema is generated from the sample XML using the Trang project which lives here: http://code.google.com/p/jing-trang/ build -f build-generate-schema.xml <?xml version="1.0" encoding="UTF-8"?> <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified"> <xs:element name="addRequest"> <xs:complexType> <xs:sequence> <xs:element maxOccurs="unbounded" ref="value"/> </xs:sequence> </xs:complexType> </xs:element> <xs:element name="value" type="xs:integer"/> </xs:schema> The XSD needs some tweaking (here the finalized version): <?xml version="1.0" encoding="UTF-8"?> <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified" targetNamespace="http://www.testing-software.org/calc" xmlns:o="http://www.testing-software.org/calc"> <xs:element name="addRequest"> <xs:complexType> <xs:sequence> <xs:element name="a" type="xs:integer" /> <xs:element name="b" type="xs:integer" /> </xs:sequence> </xs:complexType> </xs:element> <xs:element name="addResponse"> <xs:complexType> <xs:sequence> <xs:element name="result" type="xs:integer" /> </xs:sequence> </xs:complexType> </xs:element> </xs:schema> Generating class files from XSD using JAXB ------------------------------------------ From Java 1.6 on JAXB is included! So nothing to install/download here. JAXB will generate some class files in the src/org/testingsoftware/org/generated folder: ant -f build-generate-jaxb.xml Where is the WSDL? ------------------ You don’t need to create a WSDL file with Spring WS. WSDL4J does create the WSDL dynamically for you. Building the war file --------------------- To build just run maven: mvn package Running demo_server using Tomcat -------------------------------- Start Tomcat using maven: mvn tomcat:run Now you can access the new service: http://localhost:8080/demo_server/calc-service/calcServiceDefinition.wsdl Playing with the demo_server ---------------------------- In case you do not provide valid parameters, you get a nice SoapFault: <SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"> <SOAP-ENV:Header/> <SOAP-ENV:Body> <SOAP-ENV:Fault> <faultcode>SOAP-ENV:Client</faultcode> <faultstring xml:lang="en">Validation error</faultstring> <detail> <spring-ws:ValidationError xmlns:spring-ws="http://springframework.org/spring-ws">cvc-datatype-valid.1.2.1: 'xy' is not a valid value for 'integer'.</spring-ws:ValidationError> <spring-ws:ValidationError xmlns:spring-ws="http://springframework.org/spring-ws">cvc-type.3.1.3: The value 'xy' of element 'calc:a' is not valid.</spring-ws:ValidationError> </detail> </SOAP-ENV:Fault> </SOAP-ENV:Body> </SOAP-ENV:Envelope> Once you provide valid input like the following: <soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:calc="http://www.testing-software.org/calc"> <soapenv:Header/> <soapenv:Body> <calc:addRequest> <calc:a>10</calc:a> <calc:b>20</calc:b> </calc:addRequest> </soapenv:Body> </soapenv:Envelope> You can do that for example using curl (on the command line): curl -X POST -H 'Content-type: text/xml' --data @soap_request.xml http://localhost:8080/demo_server/calc-service ...the CalcService does a nice job: <SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"> <SOAP-ENV:Header/> <SOAP-ENV:Body> <ns2:addResponse xmlns:ns2="http://www.testing-software.org/calc"> <ns2:result>30</ns2:result> </ns2:addResponse> </SOAP-ENV:Body> </SOAP-ENV:Envelope> Now the demo_server is ready to be used. Implementing a simple Soap webservice test (client) =================================================== This section describes how I created a simple webservice test. The test runs against a real webservice (see above). I started from this excellent tutorial: http://blog.espenberntsen.net/2010/02/28/spring-ws-client/ The junit testcase looks like the following (all in src/test/...): public class CalcServiceTest { @Autowired @Qualifier("webServiceTemplate") private WebServiceTemplate webServiceTemplate; @Test public void testCalcService() { AddRequest request = new ObjectFactory().createAddRequest(); request.setA(BigInteger.valueOf(10)); request.setB(BigInteger.valueOf(20)); AddResponse response = (AddResponse) webServiceTemplate .marshalSendAndReceive(request); assertEquals(BigInteger.valueOf(30), response.getResult()); } (... more tests here) The test needs wiring information in test-config.xml: <bean id="webServiceTemplate" class="org.springframework.ws.client.core.WebServiceTemplate"> <property name="marshaller" ref="marshaller" /> <property name="unmarshaller" ref="marshaller" /> <property name="defaultUri" value="http://localhost:8080/demo_server/calc-service" /> </bean> Now you can run the test (make sure the server is started).
Foxsly/JMeterSoapPlugin
The plugin provides a similar interface as the built in WebService(SOAP) Request. It can handle Digest Authentication as well.
Java