@Test
  @RedisAvailable
  public void testDelayerHandlerRescheduleWithRedisMessageStore() throws Exception {
    AbstractApplicationContext context =
        new ClassPathXmlApplicationContext(
            "DelayerHandlerRescheduleIntegrationTests-context.xml", this.getClass());
    MessageChannel input = context.getBean("input", MessageChannel.class);
    MessageGroupStore messageStore = context.getBean("messageStore", MessageGroupStore.class);

    String delayerMessageGroupId = DELAYER_ID + ".messageGroupId";

    messageStore.removeMessageGroup(delayerMessageGroupId);

    Message<String> message1 = MessageBuilder.withPayload("test1").build();
    input.send(message1);
    input.send(MessageBuilder.withPayload("test2").build());

    // Emulate restart and check DB state before next start
    // Interrupt taskScheduler as quickly as possible
    ThreadPoolTaskScheduler taskScheduler =
        (ThreadPoolTaskScheduler) IntegrationContextUtils.getTaskScheduler(context);
    taskScheduler.shutdown();
    taskScheduler.getScheduledExecutor().awaitTermination(10, TimeUnit.SECONDS);
    context.destroy();

    try {
      context.getBean("input", MessageChannel.class);
      fail("IllegalStateException expected");
    } catch (Exception e) {
      assertTrue(e instanceof IllegalStateException);
      assertTrue(
          e.getMessage()
              .contains("BeanFactory not initialized or already closed - call 'refresh'"));
    }

    assertEquals(1, messageStore.getMessageGroupCount());
    assertEquals(delayerMessageGroupId, messageStore.iterator().next().getGroupId());
    assertEquals(2, messageStore.messageGroupSize(delayerMessageGroupId));
    assertEquals(2, messageStore.getMessageCountForAllMessageGroups());
    MessageGroup messageGroup = messageStore.getMessageGroup(delayerMessageGroupId);
    Message<?> messageInStore = messageGroup.getMessages().iterator().next();
    Object payload = messageInStore.getPayload();

    // INT-3049
    assertTrue(payload instanceof DelayHandler.DelayedMessageWrapper);
    assertEquals(message1, ((DelayHandler.DelayedMessageWrapper) payload).getOriginal());

    context.refresh();

    PollableChannel output = context.getBean("output", PollableChannel.class);

    Message<?> message = output.receive(20000);
    assertNotNull(message);

    Object payload1 = message.getPayload();

    message = output.receive(20000);
    assertNotNull(message);
    Object payload2 = message.getPayload();
    assertNotSame(payload1, payload2);

    assertEquals(1, messageStore.getMessageGroupCount());
    assertEquals(0, messageStore.messageGroupSize(delayerMessageGroupId));

    messageStore.removeMessageGroup(delayerMessageGroupId);
  }
  public void testObtainConnectionIds(AbstractServerConnectionFactory serverFactory)
      throws Exception {
    final List<IpIntegrationEvent> events =
        Collections.synchronizedList(new ArrayList<IpIntegrationEvent>());
    int expectedEvents =
        serverFactory instanceof TcpNetServerConnectionFactory
            ? 7 // Listening, + OPEN, CLOSE, EXCEPTION for each side
            : 5; // Listening, + OPEN, CLOSE (but we *might* get exceptions, depending on timing).
    final CountDownLatch serverListeningLatch = new CountDownLatch(1);
    final CountDownLatch eventLatch = new CountDownLatch(expectedEvents);
    ApplicationEventPublisher publisher =
        new ApplicationEventPublisher() {

          @Override
          public void publishEvent(ApplicationEvent event) {
            LogFactory.getLog(this.getClass()).trace("Received: " + event);
            events.add((IpIntegrationEvent) event);
            if (event instanceof TcpConnectionServerListeningEvent) {
              serverListeningLatch.countDown();
            }
            eventLatch.countDown();
          }

          @Override
          public void publishEvent(Object event) {}
        };
    serverFactory.setBeanName("serverFactory");
    serverFactory.setApplicationEventPublisher(publisher);
    serverFactory = spy(serverFactory);
    final CountDownLatch serverConnectionInitLatch = new CountDownLatch(1);
    doAnswer(
            invocation -> {
              Object result = invocation.callRealMethod();
              serverConnectionInitLatch.countDown();
              return result;
            })
        .when(serverFactory)
        .wrapConnection(any(TcpConnectionSupport.class));
    ThreadPoolTaskScheduler scheduler = new ThreadPoolTaskScheduler();
    scheduler.setPoolSize(10);
    scheduler.afterPropertiesSet();
    BeanFactory bf = mock(BeanFactory.class);
    when(bf.containsBean(IntegrationContextUtils.TASK_SCHEDULER_BEAN_NAME)).thenReturn(true);
    when(bf.getBean(IntegrationContextUtils.TASK_SCHEDULER_BEAN_NAME, TaskScheduler.class))
        .thenReturn(scheduler);
    serverFactory.setBeanFactory(bf);
    TcpReceivingChannelAdapter adapter = new TcpReceivingChannelAdapter();
    adapter.setOutputChannel(new NullChannel());
    adapter.setConnectionFactory(serverFactory);
    adapter.start();
    assertTrue("Listening event not received", serverListeningLatch.await(10, TimeUnit.SECONDS));
    assertThat(events.get(0), instanceOf(TcpConnectionServerListeningEvent.class));
    assertThat(
        ((TcpConnectionServerListeningEvent) events.get(0)).getPort(),
        equalTo(serverFactory.getPort()));
    int port = serverFactory.getPort();
    TcpNetClientConnectionFactory clientFactory =
        new TcpNetClientConnectionFactory("localhost", port);
    clientFactory.registerListener(message -> false);
    clientFactory.setBeanName("clientFactory");
    clientFactory.setApplicationEventPublisher(publisher);
    clientFactory.start();
    TcpConnectionSupport client = clientFactory.getConnection();
    List<String> clients = clientFactory.getOpenConnectionIds();
    assertEquals(1, clients.size());
    assertTrue(clients.contains(client.getConnectionId()));
    assertTrue(
        "Server connection failed to register",
        serverConnectionInitLatch.await(1, TimeUnit.SECONDS));
    List<String> servers = serverFactory.getOpenConnectionIds();
    assertEquals(1, servers.size());
    assertTrue(serverFactory.closeConnection(servers.get(0)));
    servers = serverFactory.getOpenConnectionIds();
    assertEquals(0, servers.size());
    int n = 0;
    clients = clientFactory.getOpenConnectionIds();
    while (n++ < 100 && clients.size() > 0) {
      Thread.sleep(100);
      clients = clientFactory.getOpenConnectionIds();
    }
    assertEquals(0, clients.size());
    assertTrue(eventLatch.await(10, TimeUnit.SECONDS));
    assertThat(
        "Expected at least " + expectedEvents + " events; got: " + events.size() + " : " + events,
        events.size(),
        greaterThanOrEqualTo(expectedEvents));

    FooEvent event = new FooEvent(client, "foo");
    client.publishEvent(event);
    assertThat(
        "Expected at least " + expectedEvents + " events; got: " + events.size() + " : " + events,
        events.size(),
        greaterThanOrEqualTo(expectedEvents + 1));

    try {
      event = new FooEvent(mock(TcpConnectionSupport.class), "foo");
      client.publishEvent(event);
      fail("Expected exception");
    } catch (IllegalArgumentException e) {
      assertTrue("Can only publish events with this as the source".equals(e.getMessage()));
    }

    SocketAddress address = serverFactory.getServerSocketAddress();
    if (address instanceof InetSocketAddress) {
      InetSocketAddress inetAddress = (InetSocketAddress) address;
      assertEquals(port, inetAddress.getPort());
    }
    serverFactory.stop();
    scheduler.shutdown();
  }
Example #3
0
 public void onApplicationEvent(ContextClosedEvent event) {
   System.out.println("==================Spring Context is shutting down==============");
   scheduler.shutdown();
   executor.shutdown();
 }