Friday, April 16, 2010

Code To test internal generic methods with user code in them

How does one test this code

public String SendMessage(String request) throws JMSException {

TextMessage reply = (TextMessage) jmsTemplate.execute(new ProducerCallback() {
public Object doInJms(Session session,MessageProducer producer) throws JMSException {
TemporaryQueue queue = session.createTemporaryQueue();
TextMessage message = session.createTextMessage();
message.setText("Some Text");
message.setJMSReplyTo(queue);
producer.send(message);
return session.createConsumer(queue).receive(10000);
}
});

if (reply != null){
// System.err.println("Message recieved");
} else{
// System.err.println("*** NOT received");
}

return reply.getText();

}


here is my junit mockito 1.8 test


import javax.jms.JMSException;
import javax.jms.Message;
import javax.jms.MessageConsumer;
import javax.jms.MessageProducer;
import javax.jms.TemporaryQueue;
import javax.jms.TextMessage;

import org.junit.After;
import org.junit.Before;
import org.junit.Test;
import org.mockito.invocation.InvocationOnMock;
import org.mockito.stubbing.Answer;

import static org.mockito.Mockito.*;
import org.springframework.jms.core.JmsTemplate;
import org.springframework.jms.core.ProducerCallback;

import com.sun.messaging.jms.Session;

public class PrivateMessageSenderTest {

PrivateMessageSender classUnderTest;
JmsTemplate mockJmsTemplate;
Session mockSession;
MessageProducer mockMessageProducer;
TemporaryQueue mockTemporaryQueue;
TextMessage mockTextMessage;
@Before
public void setUp() throws Exception {
classUnderTest = new OpenMQPrivateMessageSender();

mockJmsTemplate = mock(JmsTemplate.class);
mockSession = mock(Session.class);
mockMessageProducer = mock(MessageProducer.class);
mockTemporaryQueue = mock(TemporaryQueue.class);
mockTextMessage = mock(TextMessage.class);

/** Boiler plate mock code to inject mock session and messageProducer into
* Generic Spring ProducerCallback class which has our internal code
* To test
**/
when(mockJmsTemplate.execute((ProducerCallback)anyObject())).thenAnswer(
new Answer() {
public Object answer(InvocationOnMock invocation) throws JMSException {
Object[] args = invocation.getArguments();
//Object mock = invocation.getMock();
return ((ProducerCallback)args[0]).doInJms(mockSession, mockMessageProducer);
}
});

when(mockSession.createTemporaryQueue()).thenReturn(mockTemporaryQueue);
when(mockSession.createTextMessage()).thenReturn(mockTextMessage);



its missing the tests for it, but this pretty much sets it up to set mocks into the internal method.