Typically, in Unit Test, we will use Mocking frameworks such as Mockito, PowerMock to simulate how objects will execute when our Unit Test code calls their methods. Similarly, in Mule ESB, we also have the Mock component used in MUnit to simulate how endpoints in a Mule Flow execute. How is it in details? Let’s find out in this tutorial.
First, I will create a Mule Maven project as an example:
with Mule Flow has the following content:
This Mule Flow will allow users to access our application and pass a request parameter named “name”. Then, our Mule Flow will invoke a SOAP Web Service that we implemented in this tutorial so that we can return the result to the user with “Hello,” plus with the value of the parameter name.
Inside:
The HTTP Listener Connector is configured so that the client can access our application using http://localhost:8082/mock.
You can see how to configure HTTP Listener Connector here. The user can pass the parameter name by request as follows: http://localhost:8082/mock?name=Khanh.
The first Transform Message will build a request message sent to the SOAP Web Service.
The SOAP Web Service that we use is implemented in the tutorial Expose SOAP Web Service using CXF component in Mule ESB. Therefore, the Transform Message will have the following contents:
1 2 3 4 5 6 7 8 9 10 11 12 |
%dw 1.0 %output application/xml %namespace hdj http://muleesbcxfsoapexpose.huongdanjava.com/ --- { hdj#hello: { arg0: inboundProperties."http.query.params".name } } |
Next is the configuration for the Web Service Consumer component.
I have run the SOAP Web Service in the tutorial Expose SOAP Web Service using CXF component in Mule ESB at http://localhost:8081/hello with the WSDL file has following contents:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 |
This XML file does not appear to have any style information associated with it. The document tree is shown below. <wsdl:definitions xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:tns="http://muleesbcxfsoapexpose.huongdanjava.com/" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:ns1="http://schemas.xmlsoap.org/soap/http" name="HelloWorldServiceService" targetNamespace="http://muleesbcxfsoapexpose.huongdanjava.com/"> <wsdl:types> <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:tns="http://muleesbcxfsoapexpose.huongdanjava.com/" elementFormDefault="unqualified" targetNamespace="http://muleesbcxfsoapexpose.huongdanjava.com/" version="1.0"> <xs:element name="hello" type="tns:hello" /> <xs:element name="helloResponse" type="tns:helloResponse" /> <xs:complexType name="hello"> <xs:sequence> <xs:element minOccurs="0" name="arg0" type="xs:string" /> </xs:sequence> </xs:complexType> <xs:complexType name="helloResponse"> <xs:sequence> <xs:element minOccurs="0" name="return" type="xs:string" /> </xs:sequence> </xs:complexType> </xs:schema> </wsdl:types> <wsdl:message name="helloResponse"> <wsdl:part element="tns:helloResponse" name="parameters"></wsdl:part> </wsdl:message> <wsdl:message name="hello"> <wsdl:part element="tns:hello" name="parameters"></wsdl:part> </wsdl:message> <wsdl:portType name="HelloWorldService"> <wsdl:operation name="hello"> <wsdl:input message="tns:hello" name="hello"></wsdl:input> <wsdl:output message="tns:helloResponse" name="helloResponse"></wsdl:output> </wsdl:operation> </wsdl:portType> <wsdl:binding name="HelloWorldServiceServiceSoapBinding" type="tns:HelloWorldService"> <soap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http" /> <wsdl:operation name="hello"> <soap:operation soapAction="" style="document" /> <wsdl:input name="hello"> <soap:body use="literal" /> </wsdl:input> <wsdl:output name="helloResponse"> <soap:body use="literal" /> </wsdl:output> </wsdl:operation> </wsdl:binding> <wsdl:service name="HelloWorldServiceService"> <wsdl:port binding="tns:HelloWorldServiceServiceSoapBinding" name="HelloWorldServicePort"> <soap:address location="http://localhost:8081/hello" /> </wsdl:port> </wsdl:service> </wsdl:definitions> |
Therefore, the Web Service Consumer will have the following configuration:
Global Configuration:
with the hello.wsdl file located in your src/main/resource directory.
After receiving a response from the SOAP Web Service, I will use the Transform Message to retrieve the message to be returned to the user.
The message response from the SOAP Web Service should look like this:
1 2 3 4 |
<?xml version="1.0" encoding="UTF-8"?> <ns2:helloResponse xmlns:ns2="http://muleesbcxfsoapexpose.huongdanjava.com/" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"> <return>Hello, Khanh</return> </ns2:helloResponse> |
The message should be returned to the user with the content “Hello, Khanh” so I will configure this Transform Message as follows:
1 2 3 4 5 6 7 8 |
%dw 1.0 %output application/java %namespace ns0 http://muleesbcxfsoapexpose.huongdanjava.com/ --- payload.ns0#helloResponse.return |
The last endpoint I used was Huong Dan Java Logger to log the message content that should be returned to the user.
The configuration of Huong Dan Java Logger is as follows:
Global Configuration:
At this point, if you run this application will see the results as follows:
OK, now we will use MUnit to write Unit Test for our Mule Flow.
As I have introduced to you about MUnit in this tutorial, I will create a MUnit file with the original content as follows:
The Set Message component will allow us to create a request message with the Inbound Property so that we can pass a request with the name parameter and the value is Khanh.
Its configuration is as follows:
Assert Equals will assert the content returned to the user with the content which we expect.
In this example, the content of Assert Equals would look like this:
Now, we will go to the most important part in this tutorial.
As you can see, if you run it normally to test the application, our SOAP Web Service http://localhost:8081/hello is available so we can run it. But when running MUnit, most of SOAP Web Service does not exist. To ensure that we can run MUnit anywhere, we have to emulate it with the Mock component of the Mule ESB.
To do this, look at it in the Mule Palette Mock component:
then drag and drop into the Setup section of MUnit as follows:
The configuration for the Mock component will look like this:
There are two things we need to configure for a Mock component: Which endpoint do we emulate in Mule Flow, and then what would the return value be?
All of these configurations will be in the Matching Processor Condition section of the Mock component.
To select the endpoint to simulate, click on the search button next to “When message processor matches” and select the Web Service Consumer, as follows:
And what is the return value, we will configure in the “Then return message with payload” box.
For simple return values, you can enter this value directly into this cell, but because the value returned in this tutorial is a bit too much, so I will use the other way. I’m going to use MEL with the getResource() method to get the contents returned from a file, like this:
As you can see, I used the getResource() method with the parameter name of the file containing the return value. This file is located in your /src/test/resources directory. After taking the contents of the data.xml file, we can convert the contents of the file through the String as we did above, and we can also convert the content of the file into a Stream or ByteArray as follows.
1 2 |
#[getResource('data.xml').asStream()] #[getResource('data.xml').asByteArray()] |
Selecting the MIME type is also important to specify the payload format.
Now you can run the MUnit that we just wrote to test the result: