@SuppressWarnings("unchecked")
  @Test
  @Ignore
  public void testMulticastSender() throws Exception {
    QueueChannel channel = new QueueChannel(2);
    int port = SocketUtils.findAvailableUdpSocket();
    UnicastReceivingChannelAdapter adapter =
        new MulticastReceivingChannelAdapter("225.6.7.9", port);
    adapter.setOutputChannel(channel);
    String nic = SocketTestUtils.chooseANic(true);
    if (nic == null) { // no multicast support
      LogFactory.getLog(this.getClass()).error("No Multicast support");
      return;
    }
    adapter.setLocalAddress(nic);
    adapter.start();
    SocketTestUtils.waitListening(adapter);

    MulticastSendingMessageHandler handler = new MulticastSendingMessageHandler("225.6.7.9", port);
    handler.setLocalAddress(nic);
    Message<byte[]> message = MessageBuilder.withPayload("ABCD".getBytes()).build();
    handler.handleMessage(message);

    Message<byte[]> receivedMessage = (Message<byte[]>) channel.receive(2000);
    assertNotNull(receivedMessage);
    assertEquals(new String(message.getPayload()), new String(receivedMessage.getPayload()));
    adapter.stop();
  }
 @Test
 public void verifySendMulticast() throws Exception {
   MulticastSocket socket;
   try {
     socket = new MulticastSocket();
   } catch (Exception e) {
     return;
   }
   final int testPort = socket.getLocalPort();
   final String multicastAddress = this.multicastRule.getGroup();
   final String payload = "foo";
   final CountDownLatch listening = new CountDownLatch(2);
   final CountDownLatch received = new CountDownLatch(2);
   Runnable catcher =
       new Runnable() {
         @Override
         public void run() {
           try {
             byte[] buffer = new byte[8];
             DatagramPacket receivedPacket = new DatagramPacket(buffer, buffer.length);
             MulticastSocket socket = new MulticastSocket(testPort);
             socket.setInterface(InetAddress.getByName(multicastRule.getNic()));
             InetAddress group = InetAddress.getByName(multicastAddress);
             socket.joinGroup(group);
             listening.countDown();
             LogFactory.getLog(getClass())
                 .debug(Thread.currentThread().getName() + " waiting for packet");
             socket.receive(receivedPacket);
             socket.close();
             byte[] src = receivedPacket.getData();
             int length = receivedPacket.getLength();
             int offset = receivedPacket.getOffset();
             byte[] dest = new byte[length];
             System.arraycopy(src, offset, dest, 0, length);
             assertEquals(payload, new String(dest));
             LogFactory.getLog(getClass())
                 .debug(Thread.currentThread().getName() + " received packet");
             received.countDown();
           } catch (Exception e) {
             listening.countDown();
             e.printStackTrace();
           }
         }
       };
   Executor executor = Executors.newFixedThreadPool(2);
   executor.execute(catcher);
   executor.execute(catcher);
   assertTrue(listening.await(10000, TimeUnit.MILLISECONDS));
   MulticastSendingMessageHandler handler =
       new MulticastSendingMessageHandler(multicastAddress, testPort);
   handler.setLocalAddress(this.multicastRule.getNic());
   handler.handleMessage(MessageBuilder.withPayload(payload).build());
   assertTrue(received.await(10000, TimeUnit.MILLISECONDS));
   handler.stop();
   socket.close();
 }
 @Test
 public void testOutUdpMulticast() {
   DirectFieldAccessor dfa = new DirectFieldAccessor(udpOutMulticast);
   assertTrue(udpOutMulticast.getPort() >= 5600);
   assertEquals("225.6.7.8", dfa.getPropertyValue("host"));
   int ackPort = (Integer) dfa.getPropertyValue("ackPort");
   assertTrue("Expected ackPort >= 5500 was:" + ackPort, ackPort >= 5500);
   DatagramPacketMessageMapper mapper =
       (DatagramPacketMessageMapper) dfa.getPropertyValue("mapper");
   String ackAddress = (String) new DirectFieldAccessor(mapper).getPropertyValue("ackAddress");
   assertEquals("somehost:" + ackPort, ackAddress);
   assertEquals(51, dfa.getPropertyValue("ackTimeout"));
   assertEquals(true, dfa.getPropertyValue("waitForAck"));
   assertEquals(52, dfa.getPropertyValue("soReceiveBufferSize"));
   assertEquals(53, dfa.getPropertyValue("soSendBufferSize"));
   assertEquals(54, dfa.getPropertyValue("soTimeout"));
   assertEquals(55, dfa.getPropertyValue("timeToLive"));
   assertEquals(12, dfa.getPropertyValue("order"));
 }
  @Test
  public void verifySendMulticastWithAcks() throws Exception {

    MulticastSocket socket;
    try {
      socket = new MulticastSocket();
    } catch (Exception e) {
      return;
    }
    final int testPort = socket.getLocalPort();
    final AtomicInteger ackPort = new AtomicInteger();

    final String multicastAddress = "225.6.7.8";
    final String payload = "foobar";
    final CountDownLatch listening = new CountDownLatch(2);
    final CountDownLatch ackListening = new CountDownLatch(1);
    final CountDownLatch ackSent = new CountDownLatch(2);
    Runnable catcher =
        new Runnable() {
          @Override
          public void run() {
            try {
              byte[] buffer = new byte[1000];
              DatagramPacket receivedPacket = new DatagramPacket(buffer, buffer.length);
              MulticastSocket socket = new MulticastSocket(testPort);
              socket.setInterface(InetAddress.getByName(multicastRule.getNic()));
              socket.setSoTimeout(8000);
              InetAddress group = InetAddress.getByName(multicastAddress);
              socket.joinGroup(group);
              listening.countDown();
              assertTrue(ackListening.await(10, TimeUnit.SECONDS));
              LogFactory.getLog(getClass())
                  .debug(Thread.currentThread().getName() + " waiting for packet");
              socket.receive(receivedPacket);
              socket.close();
              byte[] src = receivedPacket.getData();
              int length = receivedPacket.getLength();
              int offset = receivedPacket.getOffset();
              byte[] dest = new byte[6];
              System.arraycopy(src, offset + length - 6, dest, 0, 6);
              assertEquals(payload, new String(dest));
              LogFactory.getLog(getClass())
                  .debug(Thread.currentThread().getName() + " received packet");
              DatagramPacketMessageMapper mapper = new DatagramPacketMessageMapper();
              mapper.setAcknowledge(true);
              mapper.setLengthCheck(true);
              Message<byte[]> message = mapper.toMessage(receivedPacket);
              Object id = message.getHeaders().get(IpHeaders.ACK_ID);
              byte[] ack = id.toString().getBytes();
              DatagramPacket ackPack =
                  new DatagramPacket(
                      ack,
                      ack.length,
                      new InetSocketAddress(multicastRule.getNic(), ackPort.get()));
              DatagramSocket out = new DatagramSocket();
              out.send(ackPack);
              LogFactory.getLog(getClass())
                  .debug(
                      Thread.currentThread().getName()
                          + " sent ack to "
                          + ackPack.getSocketAddress());
              out.close();
              ackSent.countDown();
              socket.close();
            } catch (Exception e) {
              listening.countDown();
              e.printStackTrace();
            }
          }
        };
    Executor executor = Executors.newFixedThreadPool(2);
    executor.execute(catcher);
    executor.execute(catcher);
    assertTrue(listening.await(10000, TimeUnit.MILLISECONDS));
    MulticastSendingMessageHandler handler =
        new MulticastSendingMessageHandler(
            multicastAddress, testPort, true, true, "localhost", 0, 10000);
    handler.setLocalAddress(this.multicastRule.getNic());
    handler.setMinAcksForSuccess(2);
    handler.afterPropertiesSet();
    handler.start();
    waitAckListening(handler);
    ackPort.set(handler.getAckPort());
    ackListening.countDown();
    handler.handleMessage(MessageBuilder.withPayload(payload).build());
    assertTrue(ackSent.await(10000, TimeUnit.MILLISECONDS));
    handler.stop();
    socket.close();
  }