Package com.sun.sgs.test.impl.service.channel

Source Code of com.sun.sgs.test.impl.service.channel.TestChannelServiceImplRelocatingSessions$MySessionStatusListener

/*
* Copyright 2007-2010 Sun Microsystems, Inc.
*
* This file is part of Project Darkstar Server.
*
* Project Darkstar Server is free software: you can redistribute it
* and/or modify it under the terms of the GNU General Public License
* version 2 as published by the Free Software Foundation and
* distributed hereunder to you.
*
* Project Darkstar Server is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program.  If not, see <http://www.gnu.org/licenses/>.
*
* --
*/

package com.sun.sgs.test.impl.service.channel;

import com.sun.sgs.service.ClientSessionStatusListener;
import com.sun.sgs.service.SimpleCompletionHandler;
import com.sun.sgs.test.util.SgsTestNode;
import com.sun.sgs.tools.test.FilteredNameRunner;
import com.sun.sgs.tools.test.IntegrationTest;
import java.math.BigInteger;
import java.nio.ByteBuffer;
import java.util.Collections;
import java.util.HashSet;
import java.util.Set;

import org.junit.Test;
import org.junit.runner.RunWith;

@RunWith(FilteredNameRunner.class)
public class TestChannelServiceImplRelocatingSessions
    extends AbstractChannelServiceTest
{
    private final static String REX = "rex";

    private final String[] oneUser = new String[] { REX };

    /** Constructs a test instance. */
    public TestChannelServiceImplRelocatingSessions() throws Exception {
    }

    protected void setUp(boolean clean) throws Exception {
  super.setUp(clean);
    }
   
    // -- Relocation test cases --

    @Test
    @IntegrationTest
    public void testChannelJoinAndRelocate() throws Exception {
  String channelName = "foo";
  createChannel(channelName);
  // All clients will log into server node.
  ClientGroup group = new ClientGroup(someUsers);
  SgsTestNode node1 = addNode();
  SgsTestNode node2 = addNode();
 
  try {
      // Join all users to channel and send some messages on channel.
      joinUsers(channelName, someUsers);
      checkUsersJoined(channelName, someUsers);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);
     
      // Move clients to new nodes.
      moveClient(group.getClient(MOE), serverNode, node1);
      moveClient(group.getClient(LARRY), serverNode, node2);
     
      // Make sure all members are still joined and can receive messages.
      checkUsersJoined(channelName, someUsers);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);

      // Disconnect each client and make sure that memberships/bindings
      // are cleaned up.
      group.disconnect(true);
      Thread.sleep(WAIT_TIME);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
    }

    @Test
    @IntegrationTest
    public void testChannelJoinAndRelocateMultipleTimes()
  throws Exception
    {
  String channelName = "foo";
  createChannel(channelName);
  // All clients will log into the server node.
  ClientGroup group = new ClientGroup(someUsers);
  Set<SgsTestNode> nodes = addNodes(3);
 
  try {
      // Join all users to channel and send some messages on channel.
      joinUsers(channelName, someUsers);
      checkUsersJoined(channelName, someUsers);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);
     
      // Move clients to new nodes.
      DummyClient relocatingClient = group.getClient(MOE);
      SgsTestNode oldNode = serverNode;
      for (SgsTestNode newNode : nodes) {
    moveClient(relocatingClient, oldNode, newNode);
    // Make sure all members are still joined and can receive
    // messages.
    checkUsersJoined(channelName, someUsers);
    sendMessagesToChannel(channelName, 2);
    checkChannelMessagesReceived(group, channelName, 2);
    oldNode = newNode;
      }
      // Disconnect each client and make sure that memberships/bindings
      // are cleaned up.
      group.disconnect(true);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
    }

    @Test
    @IntegrationTest
    public void testChannelJoinAndRelocateWithOldNodeFailure()
  throws Exception
    {
  String channelName = "foo";
 
  createChannel(channelName);
  // All clients will log into the server node.
  ClientGroup group = new ClientGroup(someUsers);
  SgsTestNode node1 = addNode();
  SgsTestNode node2 = addNode();
 
  try {
      // Join all users to channel and send some messages on channel.
      joinUsers(channelName, someUsers);
      checkUsersJoined(channelName, someUsers);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);
     
      // move client to node1
      DummyClient relocatingClient =
    group.getClient(MOE);
      moveClient(relocatingClient, serverNode, node1);
      // notify client to move to node2, but don't relocate yet.
      moveIdentityAndWaitForRelocationNotification(
    relocatingClient, node1, node2);
      // crash node1.
      node1.shutdown(false);
      // give recovery a chance.
      Thread.sleep(WAIT_TIME*3);
      group.removeSessionsFromGroup(node1.getAppPort());
      checkUsersJoined(channelName, LARRY, CURLY);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);
      // Disconnect each client and make sure that membership
      // is cleaned up.
      group.disconnect(true);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
    }

    @Test
    @IntegrationTest
    public void testChannelJoinToOldNodeDuringRelocate()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);
  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
 
  // Client will log into "oldNode"
  ClientGroup group = new ClientGroup(oldNode.getAppPort(), oneUser);
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(REX);
      // Hold up joins send to oldNode
      holdChannelServerMethodToNode(oldNode, "join");
      joinUsers(channelName, oneUser);
      waitForHeldChannelServerMethodToNode(oldNode);
      moveIdentity(relocatingClient, oldNode, newNode);
      Thread.sleep(200);
      releaseChannelServerMethodHeld(oldNode);
     
      // Finish relocation.
      relocatingClient.relocate(0, true, true);
     
      // Make sure all members are joined and can receive messages.
      checkUsersJoined(channelName, oneUser);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);

      // Disconnect each client and make sure that memberships/bindings
      // are cleaned up.
      group.disconnect(true);
      Thread.sleep(WAIT_TIME);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
    }
   
    @Test
    @IntegrationTest
    public void testChannelJoinToOldNodeAfterRelocate()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);
  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
 
  // Client will log into "oldNode"
  ClientGroup group = new ClientGroup(oldNode.getAppPort(), oneUser);
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(REX);
      // Hold up "join" to oldNode
      holdChannelServerMethodToNode(oldNode, "join");
      joinUsers(channelName, oneUser);
      waitForHeldChannelServerMethodToNode(oldNode);

      moveClient(relocatingClient, oldNode, newNode);
      // Release "join" to oldNode.
      releaseChannelServerMethodHeld(oldNode);
     
      // Make sure all members are joined and can receive messages.
      checkUsersJoined(channelName, oneUser);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);

      // Disconnect each client and make sure that memberships/bindings
      // are cleaned up.
      group.disconnect(true);
      Thread.sleep(WAIT_TIME);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
    }
   
    @Test
    @IntegrationTest
    public void testChannelJoinToOldNodeAfterRelocateTwice()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);
  SgsTestNode oldNode = addNode();
  SgsTestNode newNode1 = addNode();
  SgsTestNode newNode2 = addNode();
 
  // Client will log into "oldNode"
  ClientGroup group = new ClientGroup(oldNode.getAppPort(), oneUser);
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(REX);
      // Hold up joins send to oldNode
      holdChannelServerMethodToNode(oldNode, "join");
      joinUsers(channelName, oneUser);
      waitForHeldChannelServerMethodToNode(oldNode);
     
      moveClient(relocatingClient, oldNode, newNode1);
      moveClient(relocatingClient, newNode1, newNode2);
      // Release "join" to oldNode.
      releaseChannelServerMethodHeld(oldNode);
     
      // Make sure all members are joined and can receive messages.
      checkUsersJoined(channelName, oneUser);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);

      // Disconnect each client and make sure that memberships/bindings
      // are cleaned up.
      group.disconnect(true);
      Thread.sleep(WAIT_TIME);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
 
    }
   
    @Test
    @IntegrationTest
    public void testChannelJoinDuringRelocatePreparation()
  throws Exception
    {
  String channelName1 = "foo";
  String channelName2 = "bar";
  createChannel(channelName1);
  createChannel(channelName2);
  // All clients will log into server node.
  ClientGroup group = new ClientGroup(someUsers);
  SgsTestNode newNode = addNode();
  MySessionStatusListener mySessionStatusListener =
      new MySessionStatusListener();
  serverNode.getClientSessionService().
      addSessionStatusListener(mySessionStatusListener);
 
  try {

      joinUsers(channelName1, someUsers);
      checkUsersJoined(channelName1, someUsers);
     
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(MOE);
      moveIdentity(relocatingClient, serverNode, newNode);
      SimpleCompletionHandler handler =
    mySessionStatusListener.waitForPrepare();
     
      // Join all users (including relocating client) to channel during
      // prepare phase.
      joinUsers(channelName2, someUsers);

      Thread.sleep(200);
      // Mark preparation completed.
      handler.completed();
     
      // Finish relocation.
      relocatingClient.relocate(0, true, true);

      // Make sure all members are joined and can receive messages.
      checkUsersJoined(channelName2, someUsers);
      sendMessagesToChannel(channelName2, 2);
      checkChannelMessagesReceived(group, channelName2, 2);
      sendMessagesToChannel(channelName1, 2);
      checkChannelMessagesReceived(group, channelName1, 2);

      // Disconnect each client and make sure that memberships/bindings
      // are cleaned up.
      group.disconnect(true);
      Thread.sleep(WAIT_TIME);
      checkUsersJoined(channelName1, noUsers);
      checkUsersJoined(channelName2, noUsers);
     
  } finally {
      group.disconnect(false);
  }
 
    }

    @Test
    @IntegrationTest
    public void testChannelJoinDuringRelocate() throws Exception {
  String channelName = "foo";
  createChannel(channelName);
  // All clients will log into server node.
  ClientGroup
      group = new ClientGroup(someUsers);
  SgsTestNode newNode = addNode();
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(MOE);
      moveIdentityAndWaitForRelocationNotification(
    relocatingClient, serverNode, newNode);
     
      // Join all users (including relocating client) to channel.
      joinUsers(channelName, someUsers);

      // Finish relocation.
      relocatingClient.relocate(0, true, true);

      // Make sure all members are joined and can receive messages.
      checkUsersJoined(channelName, someUsers);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(group, channelName, 2);

      // Disconnect each client and make sure that memberships/bindings
      // are cleaned up.
      group.disconnect(true);
      Thread.sleep(WAIT_TIME);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
    }
   
    @Test
    @IntegrationTest
    public void testChannelLeaveAfterRelocate() throws Exception {
  String channelName = "foo";
  createChannel(channelName);
  // Client will log into server node.
  DummyClient client = new DummyClient(REX);
  client.connect(port).login();
  SgsTestNode node1 = addNode();
 
  try {
      // Join all users to channel and send some messages on channel.
      joinUsers(channelName, oneUser);
      checkUsersJoined(channelName, oneUser);
     
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(client, channelName, 2);
     
      // Move clients to new nodes.
      moveClient(client, serverNode, node1);
     
      // Make sure all members are still joined and leave after
      // relocation works correctly.
      checkUsersJoined(channelName, oneUser);
      leaveUsers(channelName, oneUser);
      client.assertLeftChannel(channelName);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      client.disconnect();
  }
    }


    @Test
    @IntegrationTest
    public void testChannelLeaveToOldNodeDuringRelocate()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);
  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
 
  // Client will log into "oldNode"
  ClientGroup group = new ClientGroup(oldNode.getAppPort(), oneUser);
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(REX);
      // Hold up "leave" to oldNode
      holdChannelServerMethodToNode(oldNode, "leave");
      joinUsers(channelName, oneUser);
      relocatingClient.assertJoinedChannel(channelName);
      checkUsersJoined(channelName, oneUser);
      leaveUsers(channelName, oneUser);
      waitForHeldChannelServerMethodToNode(oldNode);
      moveIdentity(relocatingClient, oldNode, newNode);
      Thread.sleep(200);
      releaseChannelServerMethodHeld(oldNode);
     
      // Finish relocation.
      relocatingClient.relocate(0, true, true);
     
      // Make sure that the session got the leave message and that
      // there are no channel members.
      relocatingClient.assertLeftChannel(channelName);
      Thread.sleep(2000);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
    }
   
    @Test
    @IntegrationTest
    public void testChannelLeaveToOldNodeAfterRelocate()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);
  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
 
  // Client will log into "oldNode"
  ClientGroup group = new ClientGroup(oldNode.getAppPort(), oneUser);
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(REX);
      // Hold up "leave" to oldNode
      holdChannelServerMethodToNode(oldNode, "leave");
      joinUsers(channelName, oneUser);
      relocatingClient.assertJoinedChannel(channelName);
      leaveUsers(channelName, oneUser);
      waitForHeldChannelServerMethodToNode(oldNode);

      // Relocate client
      moveClient(relocatingClient, oldNode, newNode);
      // Make sure client hasn't yet received "leave" notification.
      relocatingClient.assertJoinedChannel(channelName);
      // Release "leave" to oldNode.
      releaseChannelServerMethodHeld(oldNode);
     
      // Check that relocating client received leave message via new
      // node.
      relocatingClient.assertLeftChannel(channelName);
      checkUsersJoined(channelName, noUsers);
     
  } finally {
      group.disconnect(false);
  }
    }
   
    @Test
    @IntegrationTest
    public void testChannelLeaveAllAfterRelocate() throws Exception {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);
  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
 
  // Client will log into "oldNode"
  ClientGroup group = new ClientGroup(oldNode.getAppPort(), oneUser);
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(REX);
      joinUsers(channelName, oneUser);
      relocatingClient.assertJoinedChannel(channelName);
      holdChannelServerMethodToNode(oldNode, "close");
      // send leaveAll...
      leaveAll(channelName);
      // Hold up close sent to oldNode
      waitForHeldChannelServerMethodToNode(oldNode);
     
      moveClient(relocatingClient, oldNode, newNode);
      Thread.sleep(200);
      releaseChannelServerMethodHeld(oldNode);
     
      // Make sure that relocating session got "leave" message.
      checkUsersJoined(channelName, noUsers);
      relocatingClient.assertLeftChannel(channelName);
     
  } finally {
      group.disconnect(false);
  }
    }

    @Test
    @IntegrationTest
    public void testChannelSendToOldNodeDuringRelocate()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);
  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
 
  // Client will log into "oldNode"
  ClientGroup group = new ClientGroup(oldNode.getAppPort(), oneUser);
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(REX);
      joinUsers(channelName, oneUser);
      relocatingClient.assertJoinedChannel(channelName);
      // Hold up "send" to old node.
      holdChannelServerMethodToNode(oldNode, "send");
      sendMessagesToChannel(channelName, 3);
      waitForHeldChannelServerMethodToNode(oldNode);
      // Prepare client for relocation.
      moveIdentityAndWaitForRelocationNotification(
    relocatingClient, oldNode, newNode);
      releaseChannelServerMethodHeld(oldNode);
     
      // Finish relocation.
      relocatingClient.relocate(0, true, true);
     
      // Make sure client is joined and received all messages.
      checkUsersJoined(channelName, oneUser);
      checkChannelMessagesReceived(group, channelName, 3);
     
  } finally {
      group.disconnect(false);
  }
    }
   
    @Test
    @IntegrationTest
    public void testChannelSendToOldNodeAfterRelocate()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);
  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
 
  // Client will log into "oldNode"
  ClientGroup group = new ClientGroup(oldNode.getAppPort(), oneUser);
 
  try {
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(REX);
      joinUsers(channelName, oneUser);
      relocatingClient.assertJoinedChannel(channelName);
      // Hold up "send" to oldNode
      holdChannelServerMethodToNode(oldNode, "send");
      sendMessagesToChannel(channelName, 3);
      waitForHeldChannelServerMethodToNode(oldNode);

      // Relocate client
      moveClient(relocatingClient, oldNode, newNode);
      // Release "send" to oldNode.
      releaseChannelServerMethodHeld(oldNode);
     
      // Make sure client is joined and received all messages.
      checkUsersJoined(channelName, oneUser);
      checkChannelMessagesReceived(group, channelName, 3);
     
  } finally {
      group.disconnect(false);
  }
    }
   
    @Test
    @IntegrationTest
    public void testChannelSendToOldNodeDuringRelocateWithMemberOnNewNode()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);

  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
  String[] users = new String[]{ "relocatingClient", "otherClient"};
  DummyClient relocatingClient = createDummyClient(users[0], oldNode);
  DummyClient otherClient = createDummyClient(users[1], newNode);

  try {
      joinUsers(channelName, users);
      relocatingClient.assertJoinedChannel(channelName);
      otherClient.assertJoinedChannel(channelName);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(relocatingClient, channelName, 2);
      checkChannelMessagesReceived(otherClient, channelName, 2);
     
      // Hold up "send" to old node.
      holdChannelServerMethodToNode(oldNode, "send");
      sendMessagesToChannel(channelName, 3);
      waitForHeldChannelServerMethodToNode(oldNode);
      // Prepare client for relocation.
      moveIdentityAndWaitForRelocationNotification(
    relocatingClient, oldNode, newNode);
      releaseChannelServerMethodHeld(oldNode);
     
      // Finish relocation.
      relocatingClient.relocate(0, true, true);

      checkChannelMessagesReceived(relocatingClient, channelName, 3);
      checkChannelMessagesReceived(otherClient, channelName, 3);
     
  } finally {
      relocatingClient.disconnect();
      otherClient.disconnect();
  }
    }
   
    @Test
    @IntegrationTest
    public void  testChannelSendDuringRelocatePreparation()
  throws Exception
    {
  String channelName = "foo";
  createChannel(channelName);

  // All clients will log into server node.
  ClientGroup group = new ClientGroup(someUsers);
  SgsTestNode newNode = addNode();
  MySessionStatusListener mySessionStatusListener =
      new MySessionStatusListener();
  serverNode.getClientSessionService().
      addSessionStatusListener(mySessionStatusListener);
 
  try {

      joinUsers(channelName, someUsers);
      checkUsersJoined(channelName, someUsers);
     
      // Initiate client relocation to new node.
      DummyClient relocatingClient = group.getClient(MOE);
      moveIdentity(relocatingClient, serverNode, newNode);
      SimpleCompletionHandler handler =
    mySessionStatusListener.waitForPrepare();
     
      // Join all users (including relocating client) to channel during
      // prepare phase.
      //      sendMessagesToChannel(channelName, 3);
      sendMessagesToChannel(channelName, 20);
      //Thread.sleep(200);
      // Mark preparation completed.
      handler.completed();
     
      // Finish relocation.
      relocatingClient.relocate(0, true, true);

      // Make sure all members are joined and can receive messages.
      checkUsersJoined(channelName, someUsers);
      //checkChannelMessagesReceived(group, channelName, 3);
      checkChannelMessagesReceived(group, channelName, 20);
     
  } finally {
      group.disconnect(false);
  }
    }
   
    @Test
    @IntegrationTest
    public void testChannelSendDuringRelocate()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);

  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
  String[] users = new String[]{ "relocatingClient"};
  DummyClient relocatingClient = createDummyClient(users[0], oldNode);

  try {
      joinUsers(channelName, users);
      relocatingClient.assertJoinedChannel(channelName);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(relocatingClient, channelName, 2);
     
      // Prepare client for relocation & send messages.
      moveIdentityAndWaitForRelocationNotification(
    relocatingClient, oldNode, newNode);
      sendMessagesToChannel(channelName, 3);
     
      // Finish relocation.
      relocatingClient.relocate(0, true, true);
      checkChannelMessagesReceived(relocatingClient, channelName, 3);
     
  } finally {
      relocatingClient.disconnect();
  }
    }

    @Test
    @IntegrationTest
    public void testChannelSendDuringRelocateWithMemberOnNewNode()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);

  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
  String[] users = new String[]{ "relocatingClient", "otherClient"};
  DummyClient relocatingClient = createDummyClient(users[0], oldNode);
  DummyClient otherClient = createDummyClient(users[1], newNode);

  try {
      joinUsers(channelName, users);
      relocatingClient.assertJoinedChannel(channelName);
      otherClient.assertJoinedChannel(channelName);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(relocatingClient, channelName, 2);
      checkChannelMessagesReceived(otherClient, channelName, 2);
     
      // Prepare client for relocation & send messages.
      moveIdentityAndWaitForRelocationNotification(
    relocatingClient, oldNode, newNode);
      sendMessagesToChannel(channelName, 3);
      checkChannelMessagesReceived(otherClient, channelName, 3);
     
      // Finish relocation.
      relocatingClient.relocate(0, true, true);
      checkChannelMessagesReceived(relocatingClient, channelName, 3);
     
  } finally {
      relocatingClient.disconnect();
      otherClient.disconnect();
  }
    }

    @Test
    @IntegrationTest
    public void testSessionCleanupIfSessionFailsToPrepare()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);

  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
  MySessionStatusListener oldNodeListener =
      new MySessionStatusListener(true);
  oldNode.getClientSessionService().
      addSessionStatusListener(oldNodeListener);
  MySessionStatusListener newNodeListener =
      new MySessionStatusListener(false);
  newNode.getClientSessionService().
      addSessionStatusListener(newNodeListener);
  String[] users = new String[]{ "relocatingClient" };
  DummyClient relocatingClient = createDummyClient(users[0], oldNode);

  try {
      // Make sure that channel service is involved in relocation.
      joinUsers(channelName, users);
      relocatingClient.assertJoinedChannel(channelName);
      assertTrue(newNodeListener.disconnectedSessions.isEmpty());
      assertTrue(oldNodeListener.disconnectedSessions.isEmpty());
     
      // Prepare client for relocation.
      moveIdentity(relocatingClient, oldNode, newNode);

      // Wait for relocation timeout
      Thread.sleep(5000);
      checkUsersJoined(channelName, noUsers);
      assertNull(relocatingClient.getSession());
      assertFalse(newNodeListener.disconnectedSessions.isEmpty());
      assertFalse(oldNodeListener.disconnectedSessions.isEmpty());     
     
  } finally {
      relocatingClient.disconnect();
  }
    }
   
    @Test
    @IntegrationTest
    public void testSessionCleanupIfSessionFailsToRelocate()
  throws Exception
    {
  String channelName = "foo";
  // channel coordinator is on server node
  createChannel(channelName);

  SgsTestNode oldNode = addNode();
  SgsTestNode newNode = addNode();
  MySessionStatusListener newNodeListener =
      new MySessionStatusListener(false);
  newNode.getClientSessionService().
      addSessionStatusListener(newNodeListener);
  String[] users = new String[]{ "relocatingClient" };
  DummyClient relocatingClient = createDummyClient(users[0], oldNode);

  try {
      // Make sure that channel service is involved in relocation.
      joinUsers(channelName, users);
      relocatingClient.assertJoinedChannel(channelName);
      sendMessagesToChannel(channelName, 2);
      checkChannelMessagesReceived(relocatingClient, channelName, 2);
      assertTrue(newNodeListener.disconnectedSessions.isEmpty());
     
      // Prepare client for relocation & wait for notification
      moveIdentityAndWaitForRelocationNotification(
    relocatingClient, oldNode, newNode);

      // Wait for relocation timeout
      Thread.sleep(5000);
      checkUsersJoined(channelName, noUsers);
      assertNull(relocatingClient.getSession());
      assertFalse(newNodeListener.disconnectedSessions.isEmpty());
     
  } finally {
      relocatingClient.disconnect();
  }
    }
   
    // -- Other methods --

    /**
     * Reassigns the client's identity from {@code oldNode} to {@code newNode}.
     */
    private void moveIdentity(
  DummyClient client, SgsTestNode oldNode, SgsTestNode newNode)
  throws Exception
    {
  identityAssigner.
      moveIdentity(client.name, oldNode.getNodeId(), newNode.getNodeId());
    }
   
    /**
     * Reassigns the client's identity from {@code oldNode} to {@code newNode},
     * and waits for the client to receive the relocation notification.  The
     * client does not relocated unless instructed to do so via a {@code
     * relocate} invocation.
     */
    private void moveIdentityAndWaitForRelocationNotification(
  DummyClient client, SgsTestNode oldNode, SgsTestNode newNode)
  throws Exception
    {
  System.err.println("reassigning identity:" + client.name +
         " from node: " + oldNode.getNodeId() +
         " to node: " + newNode.getNodeId());
  moveIdentity(client, oldNode, newNode);
  client.waitForRelocationNotification(0);
    }
   
    /**
     * Moves the client from the server node to a new node.
     */
    private void moveClient(DummyClient client, SgsTestNode oldNode,
          SgsTestNode newNode)
  throws Exception
    {
  moveIdentityAndWaitForRelocationNotification(
      client, oldNode, newNode);
  client.relocate(0, true, true);
    }

    private class MySessionStatusListener
  implements ClientSessionStatusListener
    {
  private SimpleCompletionHandler handler = null;
  private final boolean controlledPreparation;

  private Set<BigInteger> disconnectedSessions =
      Collections.synchronizedSet(new HashSet<BigInteger>());
  private Set<BigInteger> relocatedSessions =
      Collections.synchronizedSet(new HashSet<BigInteger>());

  MySessionStatusListener() {
      this(true);
  }

  MySessionStatusListener(boolean controlledPreparation) {
      this.controlledPreparation = controlledPreparation;
  }
     
  public void disconnected(BigInteger sessionRefId, boolean isRelocating)
  {
      if (!isRelocating) {
    disconnectedSessions.add(sessionRefId);
      }
  }

  public void prepareToRelocate(BigInteger sessionRefId, long newNodeId,
              SimpleCompletionHandler handler)
  {
      synchronized (this) {
    this.handler = handler;
    notifyAll();
      }
      if (!controlledPreparation) {
    setPrepared();
      }
  }
 
  public void relocated(BigInteger sessionRefId) {
      relocatedSessions.add(sessionRefId);
  }

  SimpleCompletionHandler waitForPrepare() {
      synchronized (this) {
    if (handler == null) {
        try {
      wait(WAIT_TIME);
        } catch (InterruptedException e) {
        }
    }
      }
      return handler;
  }
 
  void setPrepared() {
      handler.completed();
  }
    }
}
TOP

Related Classes of com.sun.sgs.test.impl.service.channel.TestChannelServiceImplRelocatingSessions$MySessionStatusListener

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.