<commit_before>package com.yahoo.ycsb.db;

import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.Vector;

import com.gemstone.gemfire.cache.Cache;
import com.gemstone.gemfire.cache.CacheFactory;
import com.gemstone.gemfire.cache.GemFireCache;
import com.gemstone.gemfire.cache.Region;
import com.gemstone.gemfire.cache.RegionExistsException;
import com.gemstone.gemfire.cache.RegionFactory;
import com.gemstone.gemfire.cache.RegionShortcut;
import com.gemstone.gemfire.cache.client.ClientCache;
import com.gemstone.gemfire.cache.client.ClientCacheFactory;
import com.gemstone.gemfire.cache.client.ClientRegionFactory;
import com.gemstone.gemfire.cache.client.ClientRegionShortcut;
import com.yahoo.ycsb.DB;
import com.yahoo.ycsb.DBException;

public class GemFireClient extends DB {

  private static final int SUCCESS = 0;
  private static final int ERROR = -1;
  
  private GemFireCache cache;
  
  private int serverPort;
  
  @Override
  public void init() throws DBException {
    Properties props = getProperties();
    if (props != null && !props.isEmpty()) {
      String serverPortStr = props.getProperty("gemfire.serverport");
      if (serverPortStr != null) {
        serverPort = Integer.parseInt(serverPortStr);
      }
      String topology = props.getProperty("gemfire.topology");
      if (topology != null) {
        if (topology.equals("embedded")) {
          cache = new CacheFactory().create();
        }
        return;
      }
    }
    cache = new ClientCacheFactory().create();
    
  }
  
  @Override
  public int read(String table, String key, Set<String> fields,
      HashMap<String, String> result) {
    Region<String, Map<String, String>> r = getRegion(table);
    Map<String, String> val = r.get(key);
    if (val != null) {
      if (fields == null) {
        result.putAll(val);
      } else {
        for (String field : fields) {
          result.put(field, val.get(field));
        }
      }
      return SUCCESS;
    }
    return ERROR;
  }

  @Override
  public int scan(String table, String startkey, int recordcount,
      Set<String> fields, Vector<HashMap<String, String>> result) {
    // TODO 
    return SUCCESS;
  }

  @Override
  public int update(String table, String key, HashMap<String, String> values) {
    getRegion(table).put(key, values);
    return 0;
  }

  @Override
  public int insert(String table, String key, HashMap<String, String> values) {
    getRegion(table).put(key, values);
    return 0;
  }

  @Override
  public int delete(String table, String key) {
    getRegion(table).destroy(key);
    return 0;
  }

  private Region<String, Map<String, String>> getRegion(String table) {
    Region<String, Map<String, String>> r = cache.getRegion(table);
    if (r == null) {
      try {
        if (cache instanceof ClientCache) {
          ClientRegionFactory<String, Map<String, String>> crf = ((ClientCache) cache).createClientRegionFactory(ClientRegionShortcut.PROXY);
          r = crf.create(table);
        } else {
          RegionFactory<String, Map<String, String>> rf = ((Cache)cache).createRegionFactory(RegionShortcut.PARTITION);
          r = rf.create(table);
        }
      } catch (RegionExistsException e) {
        // another thread created the region<commit_msg>improving support for gemfire in client-server topology by adding command line properties to configure - server host and port - locators - topology Also adding javadocs<commit_after>package com.yahoo.ycsb.db;

import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.Vector;

import com.gemstone.gemfire.cache.Cache;
import com.gemstone.gemfire.cache.CacheFactory;
import com.gemstone.gemfire.cache.GemFireCache;
import com.gemstone.gemfire.cache.Region;
import com.gemstone.gemfire.cache.RegionExistsException;
import com.gemstone.gemfire.cache.RegionFactory;
import com.gemstone.gemfire.cache.RegionShortcut;
import com.gemstone.gemfire.cache.client.ClientCache;
import com.gemstone.gemfire.cache.client.ClientCacheFactory;
import com.gemstone.gemfire.cache.client.ClientRegionFactory;
import com.gemstone.gemfire.cache.client.ClientRegionShortcut;
import com.gemstone.gemfire.internal.admin.remote.DistributionLocatorId;
import com.yahoo.ycsb.DB;
import com.yahoo.ycsb.DBException;

/**
 * VMware vFabric GemFire client for the YCSB benchmark.<br />
 * <p>By default acts as a GemFire client and tries to connect
 * to GemFire cache server running on localhost with default
 * cache server port. Hostname and port of a GemFire cacheServer
 * can be provided using <code>gemfire.serverport=port</code> and <code>
 * gemfire.serverhost=host</code> properties on YCSB command line.
 * A locator may also be used for discovering a cacheServer
 * by using the property <code>gemfire.locator=host[port]</code></p>
 * 
 * <p>To run this client in a peer-to-peer topology with other GemFire
 * nodes, use the property <code>gemfire.topology=p2p</code>. Running
 * in p2p mode will enable embedded caching in this client.</p>
 * 
 * <p>YCSB by default does its operations against "usertable". When running
 * as a client this is a <code>ClientRegionShortcut.PROXY</code> region,
 * when running in p2p mode it is a <code>RegionShortcut.PARTITION</code>
 * region. A cache.xml defining "usertable" region can be placed in the
 * working directory to override these region definitions.</p>
 * 
 * @author <NAME> (sbawaska at vmware)
 *
 */
public class GemFireClient extends DB {

  private static final int SUCCESS = 0;
  private static final int ERROR = -1;
  private static final String SERVERPORT_PROPERTY_NAME = "gemfire.serverport";
  private static final String SERVERHOST_PROPERTY_NAME = "gemfire.serverhost";
  private static final String SERVERHOST_PROPERTY_DEFAULT = "localhost";
  private static final String LOCATOR_PROPERTY_NAME = "gemfire.locator";
  private static final String TOPOLOGY_PROPERTY_NAME = "gemfire.topology";
  private static final String TOPOLOGY_P2P_VALUE = "p2p";
  
  private GemFireCache cache;

  /**
   * true if ycsb client runs as a client to a
   * GemFire cache server
   */
  private boolean isClient;
  
  @Override
  public void init() throws DBException {
    Properties props = getProperties();
    // hostName where GemFire cacheServer is running
    String serverHost = null;
    // port of GemFire cacheServer
    int serverPort = 0;
    String locatorStr = null;

    if (props != null && !props.isEmpty()) {
      String serverPortStr = props.getProperty(SERVERPORT_PROPERTY_NAME);
      if (serverPortStr != null) {
        serverPort = Integer.parseInt(serverPortStr);
      }
      serverHost = props.getProperty(SERVERHOST_PROPERTY_NAME, SERVERHOST_PROPERTY_DEFAULT);
      locatorStr = props.getProperty(LOCATOR_PROPERTY_NAME);
      
      String topology = props.getProperty(TOPOLOGY_PROPERTY_NAME);
      if (topology != null && topology.equals(TOPOLOGY_P2P_VALUE)) {
        CacheFactory cf = new CacheFactory();
        if (locatorStr != null) {
          cf.set("locators", locatorStr);
        }
        cache = cf.create();
        isClient = false;
        return;
      }
    }
    isClient = true;
    DistributionLocatorId locator = null;
    if (locatorStr != null) {
      locator = new DistributionLocatorId(locatorStr);
    }
    ClientCacheFactory ccf = new ClientCacheFactory();
    if (serverPort != 0) {
      ccf.addPoolServer(serverHost, serverPort);
    } else if (locator != null) {
      ccf.addPoolLocator(locator.getHost().getCanonicalHostName(), locator.getPort());
    }
    cache = ccf.create();
  }
  
  @Override
  public int read(String table, String key, Set<String> fields,
      HashMap<String, String> result) {
    Region<String, Map<String, String>> r = getRegion(table);
    Map<String, String> val = r.get(key);
    if (val != null) {
      if (fields == null) {
        result.putAll(val);
      } else {
        for (String field : fields) {
          result.put(field, val.get(field));
        }
      }
      return SUCCESS;
    }
    return ERROR;
  }

  @Override
  public int scan(String table, String startkey, int recordcount,
      Set<String> fields, Vector<HashMap<String, String>> result) {
    // TODO GemFire does not support scan
    return ERROR;
  }

  @Override
  public int update(String table, String key, HashMap<String, String> values) {
    getRegion(table).put(key, values);
    return 0;
  }

  @Override
  public int insert(String table, String key, HashMap<String, String> values) {
    getRegion(table).put(key, values);
    return 0;
  }

  @Override
  public int delete(String table, String key) {
    getRegion(table).destroy(key);
    return 0;
  }

  private Region<String, Map<String, String>> getRegion(String table) {
    Region<String, Map<String, String>> r = cache.getRegion(table);
    if (r == null) {
      try {
        if (isClient) {
          ClientRegionFactory<String, Map<String, String>> crf = ((ClientCache) cache).createClientRegionFactory(ClientRegionShortcut.PROXY);
          r = crf.create(table);
        } else {
          RegionFactory<String, Map<String, String>> rf = ((Cache)cache).createRegionFactory(RegionShortcut.PARTITION);
          r = rf.create(table);
        }
      } catch (RegionExistsException e) {
        // another thread created the region
{'fraction_non_alphanumeric': 0.10694103849024417, 'fraction_numerical': 0.0019191811493762662, 'mean_word_length': 3.4837476099426388, 'pattern_counts': {'":': 0, '<': 59, '<?xml version=': 0, '>': 59, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 1}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6641324', 'n_tokens_mistral': 2821, 'n_tokens_neox': 2790, 'n_words': 744}