You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@geode.apache.org by bs...@apache.org on 2018/01/03 23:12:41 UTC

[geode] 02/02: GEODE-4113 Enhance experimental Java driver to support putting and getting objects

This is an automated email from the ASF dual-hosted git repository.

bschuchardt pushed a commit to branch develop
in repository https://gitbox.apache.org/repos/asf/geode.git

commit 7a4c3475cd08e5a15bd7fdbf10e21e36b54e5a5c
Author: Bruce Schuchardt <bs...@pivotal.io>
AuthorDate: Wed Jan 3 15:11:58 2018 -0800

    GEODE-4113 Enhance experimental Java driver to support putting and getting objects
    
    Added JSONWrapper to support storing/getting JSON documents as keys and values.
    Added unit tests for storing/fetching JSON docs.
    
    This closes #1218
---
 .../geode/experimental/driver/JSONWrapper.java     | 76 ++++++++++++++++++++++
 .../apache/geode/experimental/driver/Region.java   |  1 +
 .../geode/experimental/driver/ValueEncoder.java    |  4 ++
 .../experimental/driver/RegionIntegrationTest.java | 68 +++++++++++++++----
 .../experimental/driver/ValueEncoderTest.java      | 18 +++--
 5 files changed, 145 insertions(+), 22 deletions(-)

diff --git a/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/JSONWrapper.java b/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/JSONWrapper.java
new file mode 100644
index 0000000..8a88c3d
--- /dev/null
+++ b/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/JSONWrapper.java
@@ -0,0 +1,76 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more contributor license
+ * agreements. See the NOTICE file distributed with this work for additional information regarding
+ * copyright ownership. The ASF licenses this file to You under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the License. You may obtain a
+ * copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software distributed under the License
+ * is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
+ * or implied. See the License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package org.apache.geode.experimental.driver;
+
+import java.util.Objects;
+
+import org.apache.geode.annotations.Experimental;
+
+/**
+ * JSONWrapper is a holder of a JSON document. Use it to wrap your JSON document to store in Geode
+ * via the Region API. On the server the document will be stored in PDX serialized form, which is
+ * query-capable.
+ * <p>
+ * For example,<br>
+ * JSONWrapper wrapper = JSONWrapper.wrapJSON("{ \"name\", \"Xavier\", \"age\", \"35\"});<br>
+ * region.put("key", wrapper);<br>
+ * ...<br>
+ * wrapper = region.get("key");<br>
+ * String jsonDoc = wrapper.getJSON();<br>
+ * </p>
+ *
+ */
+@Experimental
+public class JSONWrapper implements Comparable<JSONWrapper> {
+
+  protected final String jsonDocument;
+
+  public static JSONWrapper wrapJSON(String jsonDocument) {
+    if (jsonDocument == null) {
+      throw new IllegalArgumentException("wrapped document may not be null");
+    }
+    return new JSONWrapper(jsonDocument);
+  }
+
+  private JSONWrapper(String jsonDocument) {
+    this.jsonDocument = jsonDocument;
+  }
+
+  public String getJSON() {
+    return jsonDocument;
+  }
+
+  @Override
+  public boolean equals(Object o) {
+    if (this == o) {
+      return true;
+    }
+    if (!(o instanceof JSONWrapper)) {
+      return false;
+    }
+    JSONWrapper that = (JSONWrapper) o;
+    return jsonDocument.equals(that.jsonDocument);
+  }
+
+  @Override
+  public int hashCode() {
+    return Objects.hash(jsonDocument);
+  }
+
+  @Override
+  public int compareTo(JSONWrapper o) {
+    return jsonDocument.compareTo(o.jsonDocument);
+  }
+}
diff --git a/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/Region.java b/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/Region.java
index ce32b53..f92d9a2 100644
--- a/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/Region.java
+++ b/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/Region.java
@@ -29,6 +29,7 @@ import org.apache.geode.annotations.Experimental;
  *
  * @param <K> Type of region keys.
  * @param <V> Type of region values.
+ * @see org.apache.geode.experimental.driver.JSONWrapper
  */
 @Experimental
 public interface Region<K, V> {
diff --git a/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/ValueEncoder.java b/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/ValueEncoder.java
index 4b99913..7912373 100644
--- a/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/ValueEncoder.java
+++ b/geode-experimental-driver/src/main/java/org/apache/geode/experimental/driver/ValueEncoder.java
@@ -53,6 +53,8 @@ class ValueEncoder {
       builder.setBooleanResult((Boolean) unencodedValue);
     } else if (String.class.equals(unencodedValue.getClass())) {
       builder.setStringResult((String) unencodedValue);
+    } else if (JSONWrapper.class == unencodedValue.getClass()) {
+      builder.setJsonObjectResult(((JSONWrapper) unencodedValue).getJSON());
     } else {
       throw new IllegalStateException("We don't know how to handle an object of type "
           + unencodedValue.getClass() + ": " + unencodedValue);
@@ -87,6 +89,8 @@ class ValueEncoder {
         return (short) encodedValue.getShortResult();
       case STRINGRESULT:
         return encodedValue.getStringResult();
+      case JSONOBJECTRESULT:
+        return JSONWrapper.wrapJSON(encodedValue.getJsonObjectResult());
       case VALUE_NOT_SET:
         return null;
       default:
diff --git a/geode-experimental-driver/src/test/java/org/apache/geode/experimental/driver/RegionIntegrationTest.java b/geode-experimental-driver/src/test/java/org/apache/geode/experimental/driver/RegionIntegrationTest.java
index 58d5884..465fff8 100644
--- a/geode-experimental-driver/src/test/java/org/apache/geode/experimental/driver/RegionIntegrationTest.java
+++ b/geode-experimental-driver/src/test/java/org/apache/geode/experimental/driver/RegionIntegrationTest.java
@@ -14,7 +14,10 @@
  */
 package org.apache.geode.experimental.driver;
 
+import static org.apache.geode.internal.Assert.assertTrue;
 import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNull;
 
 import java.io.IOException;
 import java.util.Properties;
@@ -32,6 +35,7 @@ import org.apache.geode.cache.RegionShortcut;
 import org.apache.geode.cache.server.CacheServer;
 import org.apache.geode.distributed.ConfigurationProperties;
 import org.apache.geode.distributed.Locator;
+import org.apache.geode.pdx.PdxInstance;
 import org.apache.geode.test.junit.categories.IntegrationTest;
 
 @Category(IntegrationTest.class)
@@ -39,14 +43,22 @@ public class RegionIntegrationTest {
   @Rule
   public RestoreSystemProperties restoreSystemProperties = new RestoreSystemProperties();
 
-  public static final String REGION = "region";
-  private int locatorPort;
+  /** a JSON document */
+  private static final String jsonDocument =
+      "{" + System.lineSeparator() + "  \"name\" : \"Charlemagne\"," + System.lineSeparator()
+          + "  \"age\" : 1276," + System.lineSeparator() + "  \"nationality\" : \"french\","
+          + System.lineSeparator() + "  \"emailAddress\" : \"none\"" + System.lineSeparator() + "}";
+
+
+  private static final String REGION = "region";
   private Locator locator;
-  private CacheServer server;
   private Cache cache;
+  private Driver driver;
+
+  private org.apache.geode.cache.Region<Object, Object> serverRegion;
 
   @Before
-  public void createServer() throws IOException {
+  public void createServerAndDriver() throws Exception {
     System.setProperty("geode.feature-protobuf-protocol", "true");
 
     // Create a cache
@@ -56,15 +68,19 @@ public class RegionIntegrationTest {
 
     // Start a locator
     locator = Locator.startLocatorAndDS(0, null, new Properties());
-    locatorPort = locator.getPort();
+    int locatorPort = locator.getPort();
 
     // Start a server
-    server = cache.addCacheServer();
+    CacheServer server = cache.addCacheServer();
     server.setPort(0);
     server.start();
 
     // Create a region
-    cache.createRegionFactory(RegionShortcut.REPLICATE).create(REGION);
+    serverRegion = cache.createRegionFactory(RegionShortcut.REPLICATE).create(REGION);
+
+    // Create a driver connected to the server
+    driver = new DriverFactory().addLocator("localhost", locatorPort).create();
+
   }
 
   @After
@@ -73,32 +89,60 @@ public class RegionIntegrationTest {
     cache.close();
   }
 
+
+
   @Test
   public void getShouldReturnPutValue() throws Exception {
-    Driver driver = new DriverFactory().addLocator("localhost", locatorPort).create();
     Region<String, String> region = driver.getRegion("region");
 
     region.put("key", "value");
     assertEquals("value", region.get("key"));
 
     region.remove("key");
-    assertEquals(null, region.get("key"));
+    assertFalse(serverRegion.containsKey("key"));
+    assertNull(region.get("key"));
   }
 
   @Test
   public void putWithIntegerKey() throws Exception {
-    Driver driver = new DriverFactory().addLocator("localhost", locatorPort).create();
     Region<Integer, Integer> region = driver.getRegion("region");
     region.put(37, 42);
+    assertTrue(serverRegion.containsKey(37));
     assertEquals(42, region.get(37).intValue());
   }
 
   @Test
   public void removeWithIntegerKey() throws Exception {
-    Driver driver = new DriverFactory().addLocator("localhost", locatorPort).create();
     Region<Integer, Integer> region = driver.getRegion("region");
     region.put(37, 42);
     region.remove(37);
-    assertEquals(null, region.get(37));
+    assertFalse(serverRegion.containsKey(37));
+    assertNull(region.get(37));
   }
+
+  @Test
+  public void putWithJSONKeyAndValue() throws Exception {
+    Region<JSONWrapper, JSONWrapper> region = driver.getRegion("region");
+    JSONWrapper document = JSONWrapper.wrapJSON(jsonDocument);
+    region.put(document, document);
+    JSONWrapper value = region.get(document);
+    assertEquals(document, value);
+
+    assertEquals(1, serverRegion.size());
+    org.apache.geode.cache.Region.Entry entry =
+        (org.apache.geode.cache.Region.Entry) serverRegion.entrySet().iterator().next();
+    assertTrue(PdxInstance.class.isAssignableFrom(entry.getKey().getClass()));
+    assertTrue(PdxInstance.class.isAssignableFrom(entry.getValue().getClass()));
+  }
+
+  @Test
+  public void removeWithJSONKey() throws Exception {
+    Region<JSONWrapper, JSONWrapper> region = driver.getRegion("region");
+    JSONWrapper document = JSONWrapper.wrapJSON(jsonDocument);
+    region.put(document, document);
+    region.remove(document);
+    assertEquals(0, serverRegion.size());
+    assertNull(region.get(document));
+  }
+
 }
diff --git a/geode-experimental-driver/src/test/java/org/apache/geode/experimental/driver/ValueEncoderTest.java b/geode-experimental-driver/src/test/java/org/apache/geode/experimental/driver/ValueEncoderTest.java
index 827a0a7..c8e7353 100644
--- a/geode-experimental-driver/src/test/java/org/apache/geode/experimental/driver/ValueEncoderTest.java
+++ b/geode-experimental-driver/src/test/java/org/apache/geode/experimental/driver/ValueEncoderTest.java
@@ -25,9 +25,16 @@ import org.apache.geode.test.junit.categories.UnitTest;
 
 @Category(UnitTest.class)
 public class ValueEncoderTest {
+  /** a JSON document */
+  private static final String jsonDocument =
+      "{" + System.lineSeparator() + "  \"name\" : \"Charlemagne\"," + System.lineSeparator()
+          + "  \"age\" : 1276," + System.lineSeparator() + "  \"nationality\" : \"french\","
+          + System.lineSeparator() + "  \"emailAddress\" : \"none\"" + System.lineSeparator() + "}";
+
   @Test
   public void encodeAndDecode() throws Exception {
-    final Object[] objects = {37, (short) 37, (byte) 37, 37L, 37., 37.F, true, "hello, world"};
+    final Object[] objects = {37, (short) 37, (byte) 37, 37L, 37., 37.F, true, "hello, world",
+        JSONWrapper.wrapJSON(jsonDocument)};
     for (Object object : objects) {
       assertEquals(object, ValueEncoder.decodeValue(ValueEncoder.encodeValue(object)));
     }
@@ -35,13 +42,4 @@ public class ValueEncoderTest {
     final byte[] bytes = new byte[] {(byte) 0xDE, (byte) 0xAD, (byte) 0xBE, (byte) 0xEF};
     assertArrayEquals(bytes, (byte[]) ValueEncoder.decodeValue(ValueEncoder.encodeValue(bytes)));
   }
-
-  @Test(expected = IllegalStateException.class)
-  public void cantDecodeJson() throws Exception {
-    BasicTypes.EncodedValue.Builder builder = BasicTypes.EncodedValue.newBuilder();
-
-    builder.setJsonObjectResult("hello").build();
-
-    ValueEncoder.decodeValue(builder.build());
-  }
 }

-- 
To stop receiving notification emails like this one, please contact
"commits@geode.apache.org" <co...@geode.apache.org>.