View Javadoc
1   /*
2    * Copyright (c) MuleSoft, Inc.  All rights reserved.  http://www.mulesoft.com
3    * The software in this package is published under the terms of the CPAL v1.0
4    * license, a copy of which has been included with this distribution in the
5    * LICENSE.txt file.
6    */
7   package org.mule.transport.udp.functional;
8   
9   import org.mule.api.MuleMessage;
10  import org.mule.module.client.MuleClient;
11  import org.mule.tck.junit4.FunctionalTestCase;
12  
13  import java.util.HashSet;
14  import java.util.Set;
15  
16  import org.junit.Test;
17  
18  import static org.junit.Assert.fail;
19  
20  public class UdpConnectorFunctionalTestCase extends FunctionalTestCase
21  {
22  
23      public static final String MESSAGE = "hello";
24      public static final int TOTAL_MESSAGE_COUNT = 1000;
25      public static final int MAX_NUMBER_OF_BATCHES = 128;
26      public static final long MAX_PAUSE_PERIOD = 2000;
27      public static final long MIN_PAUSE_PERIOD = 10;
28      public static final long BETWEEN_BATCH_PAUSE = 5000;
29  
30      @Override
31      protected String getConfigResources()
32      {
33          return "udp-functional-test.xml";
34      }
35  
36      /**
37       * We try progressively smaller batches to see if there are issues with internal
38       * buffers.  If we don't get 100% success eventually, we fail.
39       */
40      @Test
41      public void testMany() throws Exception
42      {
43          int numberOfBatches = 0;
44          boolean ok = false;
45          while (!ok && numberOfBatches < MAX_NUMBER_OF_BATCHES)
46          {
47              numberOfBatches = 0 == numberOfBatches ? 1 : numberOfBatches * 2;
48              ok = doTestSome(TOTAL_MESSAGE_COUNT, TOTAL_MESSAGE_COUNT / numberOfBatches);
49              if (!ok)
50              {
51                  logger.warn("UDP failed to send " + TOTAL_MESSAGE_COUNT + " messages in " + numberOfBatches + " batches");
52  
53                  // clean out the system
54                  try
55                  {
56                      synchronized(this)
57                      {
58                          this.wait(BETWEEN_BATCH_PAUSE);
59                      }
60                  }
61                  catch (InterruptedException e)
62                  {
63                      // ignore
64                  }
65                  MuleClient client = new MuleClient(muleContext);
66                  int dropped = 0;
67                  while (null != client.request("vm://foo", MAX_PAUSE_PERIOD))
68                  {
69                      // discard old messages
70                      dropped++;
71                  }
72                  logger.info("Cleaned out " + dropped + " messages");
73              }
74          }
75  
76          if (!ok)
77          {
78              fail("Couldn't get UDP to 100% with a batch size of " + TOTAL_MESSAGE_COUNT / numberOfBatches);
79          }
80          else
81          {
82              logger.info("Required " + numberOfBatches + " batches before UDP 100% OK ("
83                      + TOTAL_MESSAGE_COUNT + " messages)");
84          }
85      }
86  
87      /**
88       * @param numberOfMessages Total number of tests
89       * @param burst Number of mesages to send between wait periods
90       * @return true if all messages received
91       * @throws Exception
92       */
93      protected boolean doTestSome(int numberOfMessages, int burst) throws Exception
94      {
95          logger.info("Trying " + numberOfMessages + " messages in batches of " + burst);
96          MuleClient client = new MuleClient(muleContext);
97  
98          int burstCount = 0;
99          Set receivedMessages = new HashSet(numberOfMessages);
100         for (int sentPackets = 0; sentPackets < numberOfMessages; sentPackets++)
101         {
102             burstCount++;
103             String msg = MESSAGE + sentPackets;
104             client.dispatch("serverEndpoint", msg, null);
105 
106             if (burst == burstCount || sentPackets == numberOfMessages-1)
107             {
108                 long pause = MAX_PAUSE_PERIOD;
109                 for (int i = 0; i < burstCount; i++)
110                 {
111                     MuleMessage message = client.request("vm://foo", pause);
112                     // reduce waiting time once we have a bunch of messages coming in
113                     // (without this, we can end up waiting for very long times....)
114                     pause = Math.max(MIN_PAUSE_PERIOD, pause / 2);
115                     if (null != message)
116                     {
117                         receivedMessages.add(message.getPayloadAsString());
118                     }
119                 }
120                 burstCount = 0;
121             }
122         }
123 
124         boolean ok = receivedMessages.size() == numberOfMessages;
125         if (!ok)
126         {
127             logger.info("Received " + receivedMessages.size() + " messages");
128         }
129         return ok;
130     }
131 
132 }