package org.cachebench.cachewrappers;

import org.cachebench.CacheWrapper;
import org.infinispan.Cache;
import org.infinispan.remoting.transport.Address;
import org.infinispan.factories.ComponentRegistry;
import org.infinispan.context.Flag;
import org.infinispan.manager.CacheManager;
import org.infinispan.manager.DefaultCacheManager;
import org.jgroups.logging.Log;
import org.jgroups.logging.LogFactory;

import javax.transaction.TransactionManager;
import java.util.List;

public class InfinispanWrapper implements CacheWrapper {

   private static Log log = LogFactory.getLog(InfinispanWrapper.class);
   CacheManager cacheManager;
   Cache<Object, Object> cache;
   TransactionManager tm;
   boolean started = false;
   String config;

   public void init(String config) throws Exception {
      this.config = config;
      setUp();
   }

   public void setUp() throws Exception {
      if (!started) {
         cacheManager = new DefaultCacheManager(config);
         // use the default cache
         cache = cacheManager.getCache();
         started = true;
      }
      log.info("Loading jgroups form: " + org.jgroups.Version.class.getProtectionDomain().getCodeSource().getLocation());
      log.info("JGroups /descriptio////version: " + org.jgroups.Version.description);
   }

   public void tearDown() throws Exception {
      List<Address> addressList = cacheManager.getMembers();
      if (started) {
         cacheManager.stop();
         log.trace("Stopped, previous view is " + addressList);
         started = false;
      }
   }

   public void put(String bucket, Object key, Object value) throws Exception {
      cache.put(bucket + key, value);
   }

   public Object get(String bucket, Object key) throws Exception {
      return cache.get(bucket + key);
   }

   public void empty() throws Exception {
      log.info("Cache size before clear: " + cache.size());
      cache.getAdvancedCache().withFlags(Flag.CACHE_MODE_LOCAL).clear();
      log.info("Cache size after clear: " + cache.size());
   }

   public int getNumMembers() {
      ComponentRegistry componentRegistry = cache.getAdvancedCache().getComponentRegistry();
      if (componentRegistry.getStatus().startingUp()) {
         log.trace("We're in the process of starting up.");
      }
      if (cacheManager.getMembers() != null) {
         log.trace("Members are: " + cacheManager.getMembers());
      }
      return cacheManager.getMembers() == null ? 0 : cacheManager.getMembers().size();
   }

   public String getInfo() {
      return cache.getVersion();
   }

   public Object getReplicatedData(String bucket, String key) throws Exception {
      return get(bucket, key);
   }

   public Object startTransaction() {
      if (tm == null) return null;
      try {
         tm.begin();
         return tm.getTransaction();
      }
      catch (Exception e) {
         throw new RuntimeException(e);
      }
   }

   public void endTransaction(boolean successful) {
      if (tm == null) return;
      try {
         if (successful)
            tm.commit();
         else
            tm.rollback();
      }
      catch (Exception e) {
         throw new RuntimeException(e);
      }
   }
}

@@ -816,16 +816,121 @@
  config;
+                                                                                                         
 %0A      s
@@ -1323,23 +1323,8 @@
 ups 
-/descriptio////
 vers
@@ -1352,17 +1352,22 @@
 Version.
-d
+printD
 escripti
@@ -1368,16 +1368,18 @@
 cription
+()
 );%0A   %7D%0A
@@ -3268,11 +3268,198 @@
   %7D%0A   %7D
+%0A%0A   public static void main(String%5B%5D args) throws Exception %7B%0A      InfinispanWrapper wrapper = new InfinispanWrapper();%0A      wrapper.init(%22dist-async.xml%22);%0A      wrapper.setUp();%0A   %7D
 %0A%7D%0A

update logging