Updated Branches:
  refs/heads/1.5.1-SNAPSHOT 19e6b1018 -> b93032190
  refs/heads/1.6.0-SNAPSHOT db42aba02 -> 4f86e0001
  refs/heads/master 39a10c8bc -> ffd530135


ACCUMULO-2299 Check that read field value has same length as expected

Signed-off-by: Mike Drob <md...@cloudera.com>


Project: http://git-wip-us.apache.org/repos/asf/accumulo/repo
Commit: http://git-wip-us.apache.org/repos/asf/accumulo/commit/b9303219
Tree: http://git-wip-us.apache.org/repos/asf/accumulo/tree/b9303219
Diff: http://git-wip-us.apache.org/repos/asf/accumulo/diff/b9303219

Branch: refs/heads/1.5.1-SNAPSHOT
Commit: b93032190b4cc1bd00c7c0faf121899464c80919
Parents: 19e6b10
Author: Vikram Srivastava <vikr...@cloudera.com>
Authored: Sun Feb 2 21:04:04 2014 -0800
Committer: Mike Drob <md...@cloudera.com>
Committed: Fri Feb 7 18:35:22 2014 -0500

----------------------------------------------------------------------
 .../core/iterators/user/WholeRowIterator.java   | 55 +++++++++-----------
 .../iterators/user/WholeRowIteratorTest.java    | 24 +++++++--
 2 files changed, 44 insertions(+), 35 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/accumulo/blob/b9303219/core/src/main/java/org/apache/accumulo/core/iterators/user/WholeRowIterator.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/accumulo/core/iterators/user/WholeRowIterator.java
 
b/core/src/main/java/org/apache/accumulo/core/iterators/user/WholeRowIterator.java
index e594b0c..525f27c 100644
--- 
a/core/src/main/java/org/apache/accumulo/core/iterators/user/WholeRowIterator.java
+++ 
b/core/src/main/java/org/apache/accumulo/core/iterators/user/WholeRowIterator.java
@@ -66,7 +66,25 @@ public class WholeRowIterator implements 
SortedKeyValueIterator<Key,Value> {
   WholeRowIterator(SortedKeyValueIterator<Key,Value> source) {
     this.sourceIter = source;
   }
-  
+
+  /**
+   * Returns the byte array containing the field of row key from the given 
DataInputStream din.
+   * Assumes that din first has the length of the field, followed by the field 
itself.
+   */
+  private static byte[] readField(DataInputStream din) throws IOException {
+    int len = din.readInt();
+    byte[] b = new byte[len];
+    int readLen = din.read(b);
+    // Check if expected length is not same as read length.
+    // We ignore the zero length case because DataInputStream.read can return 
-1
+    // if zero length was expected and end of stream has been reached.
+    if (len > 0 && len != readLen) {
+      throw new IOException(String.format("Expected to read %d bytes but read 
%d",
+          len, readLen));
+    }
+    return b;
+  }
+
   // decode a bunch of key value pairs that have been encoded into a single 
value
   public static final SortedMap<Key,Value> decodeRow(Key rowKey, Value 
rowValue) throws IOException {
     SortedMap<Key,Value> map = new TreeMap<Key,Value>();
@@ -74,36 +92,11 @@ public class WholeRowIterator implements 
SortedKeyValueIterator<Key,Value> {
     DataInputStream din = new DataInputStream(in);
     int numKeys = din.readInt();
     for (int i = 0; i < numKeys; i++) {
-      byte[] cf;
-      byte[] cq;
-      byte[] cv;
-      byte[] valBytes;
-      // read the col fam
-      {
-        int len = din.readInt();
-        cf = new byte[len];
-        din.read(cf);
-      }
-      // read the col qual
-      {
-        int len = din.readInt();
-        cq = new byte[len];
-        din.read(cq);
-      }
-      // read the col visibility
-      {
-        int len = din.readInt();
-        cv = new byte[len];
-        din.read(cv);
-      }
-      // read the timestamp
-      long timestamp = din.readLong();
-      // read the value
-      {
-        int len = din.readInt();
-        valBytes = new byte[len];
-        din.read(valBytes);
-      }
+      byte[] cf = readField(din); // read the col fam
+      byte[] cq = readField(din); // read the col qual
+      byte[] cv = readField(din); // read the col visibility
+      long timestamp = din.readLong(); // read the timestamp
+      byte[] valBytes = readField(din); // read the value
       map.put(new Key(rowKey.getRowData().toArray(), cf, cq, cv, timestamp, 
false, false), new Value(valBytes, false));
     }
     return map;

http://git-wip-us.apache.org/repos/asf/accumulo/blob/b9303219/core/src/test/java/org/apache/accumulo/core/iterators/user/WholeRowIteratorTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/accumulo/core/iterators/user/WholeRowIteratorTest.java
 
b/core/src/test/java/org/apache/accumulo/core/iterators/user/WholeRowIteratorTest.java
index 2b86bb1..8ad97a9 100644
--- 
a/core/src/test/java/org/apache/accumulo/core/iterators/user/WholeRowIteratorTest.java
+++ 
b/core/src/test/java/org/apache/accumulo/core/iterators/user/WholeRowIteratorTest.java
@@ -16,8 +16,11 @@
  */
 package org.apache.accumulo.core.iterators.user;
 
+import static org.junit.Assert.*;
+
 import java.io.IOException;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collections;
 import java.util.HashMap;
 import java.util.List;
@@ -25,8 +28,6 @@ import java.util.Map;
 import java.util.SortedMap;
 import java.util.TreeMap;
 
-import junit.framework.TestCase;
-
 import org.apache.accumulo.core.data.ByteSequence;
 import org.apache.accumulo.core.data.Key;
 import org.apache.accumulo.core.data.Range;
@@ -35,9 +36,22 @@ import 
org.apache.accumulo.core.iterators.SortedKeyValueIterator;
 import org.apache.accumulo.core.iterators.SortedMapIterator;
 import org.apache.accumulo.core.iterators.system.MultiIterator;
 import org.apache.hadoop.io.Text;
+import org.junit.Test;
 
-public class WholeRowIteratorTest extends TestCase {
-  
+import com.google.common.collect.ImmutableList;
+
+public class WholeRowIteratorTest {
+
+  @Test(expected=IOException.class)
+  public void testBadDecodeRow() throws IOException {
+    Key k = new Key(new Text("r1"), new Text("cf1234567890"));
+    Value v = new Value("v1".getBytes());
+    Value encoded = WholeRowIterator.encodeRow(ImmutableList.of(k), 
ImmutableList.of(v));
+    encoded.set(Arrays.copyOfRange(encoded.get(), 0, 10)); // truncate to 10 
bytes only
+    WholeRowIterator.decodeRow(k, encoded);
+  }
+
+  @Test
   public void testEmptyStuff() throws IOException {
     SortedMap<Key,Value> map = new TreeMap<Key,Value>();
     SortedMap<Key,Value> map2 = new TreeMap<Key,Value>();
@@ -108,6 +122,7 @@ public class WholeRowIteratorTest extends TestCase {
     map.put(new Key(new Text(row), new Text(cf), new Text(cq), new Text(cv), 
ts), new Value(val.getBytes()));
   }
   
+  @Test
   public void testContinue() throws Exception {
     SortedMap<Key,Value> map1 = new TreeMap<Key,Value>();
     pkv(map1, "row1", "cf1", "cq1", "cv1", 5, "foo");
@@ -149,6 +164,7 @@ public class WholeRowIteratorTest extends TestCase {
     
   }
   
+  @Test
   public void testBug1() throws Exception {
     SortedMap<Key,Value> map1 = new TreeMap<Key,Value>();
     pkv(map1, "row1", "cf1", "cq1", "cv1", 5, "foo");

Reply via email to