package org.jboss.cache.eviction;

import junit.framework.Test;
import junit.framework.TestCase;
import junit.framework.TestSuite;
import org.jboss.cache.Fqn;


/**
 * @author Ben Wang, Feb 11, 2004
 * @author Daniel Huang (dhuang@jboss.org)
 */
public class RegionTest extends TestCase
{
   RegionManager regionManager_;
   EvictionAlgorithm algorithm;

   public RegionTest(String s)
   {
      super(s);
   }

   public void setUp() throws Exception
   {
      super.setUp();
      algorithm = new LRUAlgorithm();
      regionManager_ = new RegionManager();
      regionManager_.createRegion("/a/b", new DummyEvictionPolicy(), new DummyEvictionConfiguration());
   }

   public void tearDown() throws Exception
   {
      super.tearDown();
   }

   public void testAddedQueue()
   {
      Fqn fqn1 = Fqn.fromString("/a/b/c");
      Fqn fqn2 = Fqn.fromString("/a/b/d");
      Fqn fqn3 = Fqn.fromString("/a/b/e");

      Region region = regionManager_.getRegion("/a/b");
      region.setAddedNode(fqn1);
      region.setAddedNode(fqn2);
      region.setAddedNode(fqn3);

      assertEquals("AddedNode queue size ", 3, region.nodeEventQueueSize());
      EvictedEventNode node = (EvictedEventNode) region.takeLastEventNode();
      Fqn fqn = node.getFqn();
      assertEquals("DataNode retrieved should be FILO ", fqn, fqn1);
      assertEquals("AddedNode queue size ", 2, region.nodeEventQueueSize());
      fqn = ((EvictedEventNode) region.takeLastEventNode()).getFqn();
      fqn = ((EvictedEventNode) region.takeLastEventNode()).getFqn();
      node = ((EvictedEventNode) region.takeLastEventNode());
      assertNull("DataNode should be null", node);
   }

   public void testEventQueue()
   {
      Fqn fqn1 = Fqn.fromString("/a/b/c");
      Fqn fqn2 = Fqn.fromString("/a/b/d");
      Fqn fqn3 = Fqn.fromString("/a/b/e");

      Region region = regionManager_.getRegion("/a/b");
      region.setRemovedNode(fqn1);
      region.setAddedNode(fqn2);
      region.setVisitedNode(fqn3);

      assertEquals("RemovedNode queue size ", 3, region.nodeEventQueueSize());
      int event = ((EvictedEventNode) region.takeLastEventNode()).getEvent();
      assertEquals("DataNode retrieved should be: ", EvictedEventNode.REMOVE_NODE_EVENT, event);
      Fqn fqn = ((EvictedEventNode) region.takeLastEventNode()).getFqn();
      fqn = ((EvictedEventNode) region.takeLastEventNode()).getFqn();
      EvictedEventNode node = ((EvictedEventNode) region.takeLastEventNode());
      assertNull("DataNode should be null", node);
   }

   public void testMassivePutOnQueue()
   {
      Fqn fqn2 = Fqn.fromString("/a/b/d");

      Region region = regionManager_.getRegion("/a/b");
      // This should succeed, alhtough it will produce warning over the threshold.
      for (int i = 0; i < RegionManager.CAPACITY - 1; i++)
      {
         region.setAddedNode(fqn2);
      }

   }

   void log(String msg)
   {
      System.out.println("-- " + msg);
   }

   public static Test suite()
   {
      return new TestSuite(RegionTest.class);
   }

   public static void main(String[] args)
   {
      junit.textui.TestRunner.run(suite());
   }

}
