HBASE-9959 Remove some array copy - server side
git-svn-id: https://svn.apache.org/repos/asf/hbase/trunk@1543434 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
parent
b2582665f1
commit
dc8ecd9a9a
|
@ -93,6 +93,7 @@ public class HColumnDescriptor implements WritableComparable<HColumnDescriptor>
|
||||||
public static final String BLOOMFILTER = "BLOOMFILTER";
|
public static final String BLOOMFILTER = "BLOOMFILTER";
|
||||||
public static final String FOREVER = "FOREVER";
|
public static final String FOREVER = "FOREVER";
|
||||||
public static final String REPLICATION_SCOPE = "REPLICATION_SCOPE";
|
public static final String REPLICATION_SCOPE = "REPLICATION_SCOPE";
|
||||||
|
public static final byte[] REPLICATION_SCOPE_BYTES = Bytes.toBytes(REPLICATION_SCOPE);
|
||||||
public static final String MIN_VERSIONS = "MIN_VERSIONS";
|
public static final String MIN_VERSIONS = "MIN_VERSIONS";
|
||||||
public static final String KEEP_DELETED_CELLS = "KEEP_DELETED_CELLS";
|
public static final String KEEP_DELETED_CELLS = "KEEP_DELETED_CELLS";
|
||||||
public static final String COMPRESS_TAGS = "COMPRESS_TAGS";
|
public static final String COMPRESS_TAGS = "COMPRESS_TAGS";
|
||||||
|
@ -823,9 +824,9 @@ public class HColumnDescriptor implements WritableComparable<HColumnDescriptor>
|
||||||
* @return the scope tag
|
* @return the scope tag
|
||||||
*/
|
*/
|
||||||
public int getScope() {
|
public int getScope() {
|
||||||
String value = getValue(REPLICATION_SCOPE);
|
byte[] value = getValue(REPLICATION_SCOPE_BYTES);
|
||||||
if (value != null) {
|
if (value != null) {
|
||||||
return Integer.valueOf(value).intValue();
|
return Integer.valueOf(Bytes.toString(value));
|
||||||
}
|
}
|
||||||
return DEFAULT_REPLICATION_SCOPE;
|
return DEFAULT_REPLICATION_SCOPE;
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,7 +18,9 @@
|
||||||
|
|
||||||
package org.apache.hadoop.hbase.client;
|
package org.apache.hadoop.hbase.client;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
import java.util.Arrays;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
@ -123,6 +125,18 @@ public abstract class Mutation extends OperationWithAttributes implements Row, C
|
||||||
return kvWithTag;
|
return kvWithTag;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Create a KeyValue with this objects row key and the Put identifier.
|
||||||
|
*
|
||||||
|
* @return a KeyValue with this objects row key and the Put identifier.
|
||||||
|
*/
|
||||||
|
KeyValue createPutKeyValue(byte[] family, ByteBuffer qualifier, long ts, ByteBuffer value,
|
||||||
|
Tag[] tags) {
|
||||||
|
return new KeyValue(this.row, 0, this.row == null ? 0 : this.row.length,
|
||||||
|
family, 0, family == null ? 0 : family.length,
|
||||||
|
qualifier, ts, KeyValue.Type.Put, value, tags != null ? Arrays.asList(tags) : null);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Compile the column family (i.e. schema) information
|
* Compile the column family (i.e. schema) information
|
||||||
* into a Map. Useful for parsing and aggregation by debugging,
|
* into a Map. Useful for parsing and aggregation by debugging,
|
||||||
|
@ -407,4 +421,17 @@ public abstract class Mutation extends OperationWithAttributes implements Row, C
|
||||||
}
|
}
|
||||||
return row;
|
return row;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void checkRow(ByteBuffer row) {
|
||||||
|
if (row == null) {
|
||||||
|
throw new IllegalArgumentException("Row buffer is null");
|
||||||
|
}
|
||||||
|
if (row.remaining() == 0) {
|
||||||
|
throw new IllegalArgumentException("Row length is 0");
|
||||||
|
}
|
||||||
|
if (row.remaining() > HConstants.MAX_ROW_LENGTH) {
|
||||||
|
throw new IllegalArgumentException("Row length " + row.remaining() + " is > " +
|
||||||
|
HConstants.MAX_ROW_LENGTH);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,6 +20,7 @@
|
||||||
package org.apache.hadoop.hbase.client;
|
package org.apache.hadoop.hbase.client;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
@ -73,6 +74,27 @@ public class Put extends Mutation implements HeapSize, Comparable<Row> {
|
||||||
this(rowArray, rowOffset, rowLength, HConstants.LATEST_TIMESTAMP);
|
this(rowArray, rowOffset, rowLength, HConstants.LATEST_TIMESTAMP);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param row row key; we make a copy of what we are passed to keep local.
|
||||||
|
* @param ts timestamp
|
||||||
|
*/
|
||||||
|
public Put(ByteBuffer row, long ts) {
|
||||||
|
if (ts < 0) {
|
||||||
|
throw new IllegalArgumentException("Timestamp cannot be negative. ts=" + ts);
|
||||||
|
}
|
||||||
|
checkRow(row);
|
||||||
|
this.row = new byte[row.remaining()];
|
||||||
|
row.get(this.row);
|
||||||
|
this.ts = ts;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param row row key; we make a copy of what we are passed to keep local.
|
||||||
|
*/
|
||||||
|
public Put(ByteBuffer row) {
|
||||||
|
this(row, HConstants.LATEST_TIMESTAMP);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* We make a copy of the passed in row key to keep local.
|
* We make a copy of the passed in row key to keep local.
|
||||||
* @param rowArray
|
* @param rowArray
|
||||||
|
@ -152,6 +174,47 @@ public class Put extends Mutation implements HeapSize, Comparable<Row> {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add the specified column and value, with the specified timestamp as
|
||||||
|
* its version to this Put operation.
|
||||||
|
* @param family family name
|
||||||
|
* @param qualifier column qualifier
|
||||||
|
* @param ts version timestamp
|
||||||
|
* @param value column value
|
||||||
|
* @param tag the tags
|
||||||
|
* @return this
|
||||||
|
*/
|
||||||
|
public Put add(byte[] family, ByteBuffer qualifier, long ts, ByteBuffer value, Tag[] tag) {
|
||||||
|
if (ts < 0) {
|
||||||
|
throw new IllegalArgumentException("Timestamp cannot be negative. ts=" + ts);
|
||||||
|
}
|
||||||
|
List<Cell> list = getCellList(family);
|
||||||
|
KeyValue kv = createPutKeyValue(family, qualifier, ts, value, tag);
|
||||||
|
list.add(kv);
|
||||||
|
familyMap.put(kv.getFamily(), list);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add the specified column and value, with the specified timestamp as
|
||||||
|
* its version to this Put operation.
|
||||||
|
* @param family family name
|
||||||
|
* @param qualifier column qualifier
|
||||||
|
* @param ts version timestamp
|
||||||
|
* @param value column value
|
||||||
|
* @return this
|
||||||
|
*/
|
||||||
|
public Put add(byte[] family, ByteBuffer qualifier, long ts, ByteBuffer value) {
|
||||||
|
if (ts < 0) {
|
||||||
|
throw new IllegalArgumentException("Timestamp cannot be negative. ts=" + ts);
|
||||||
|
}
|
||||||
|
List<Cell> list = getCellList(family);
|
||||||
|
KeyValue kv = createPutKeyValue(family, qualifier, ts, value, null);
|
||||||
|
list.add(kv);
|
||||||
|
familyMap.put(kv.getFamily(), list);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add the specified KeyValue to this Put operation. Operation assumes that
|
* Add the specified KeyValue to this Put operation. Operation assumes that
|
||||||
* the passed KeyValue is immutable and its backing array will not be modified
|
* the passed KeyValue is immutable and its backing array will not be modified
|
||||||
|
|
|
@ -27,6 +27,7 @@ import java.lang.reflect.InvocationTargetException;
|
||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.lang.reflect.ParameterizedType;
|
import java.lang.reflect.ParameterizedType;
|
||||||
import java.lang.reflect.Type;
|
import java.lang.reflect.Type;
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
@ -481,7 +482,6 @@ public final class ProtobufUtil {
|
||||||
// TODO: Server-side at least why do we convert back to the Client types? Why not just pb it?
|
// TODO: Server-side at least why do we convert back to the Client types? Why not just pb it?
|
||||||
MutationType type = proto.getMutateType();
|
MutationType type = proto.getMutateType();
|
||||||
assert type == MutationType.PUT: type.name();
|
assert type == MutationType.PUT: type.name();
|
||||||
byte [] row = proto.hasRow()? proto.getRow().toByteArray(): null;
|
|
||||||
long timestamp = proto.hasTimestamp()? proto.getTimestamp(): HConstants.LATEST_TIMESTAMP;
|
long timestamp = proto.hasTimestamp()? proto.getTimestamp(): HConstants.LATEST_TIMESTAMP;
|
||||||
Put put = null;
|
Put put = null;
|
||||||
int cellCount = proto.hasAssociatedCellCount()? proto.getAssociatedCellCount(): 0;
|
int cellCount = proto.hasAssociatedCellCount()? proto.getAssociatedCellCount(): 0;
|
||||||
|
@ -503,17 +503,23 @@ public final class ProtobufUtil {
|
||||||
put.add(KeyValueUtil.ensureKeyValue(cell));
|
put.add(KeyValueUtil.ensureKeyValue(cell));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
put = new Put(row, timestamp);
|
if (proto.hasRow()) {
|
||||||
|
put = new Put(proto.getRow().asReadOnlyByteBuffer(), timestamp);
|
||||||
|
} else {
|
||||||
|
throw new IllegalArgumentException("row cannot be null");
|
||||||
|
}
|
||||||
// The proto has the metadata and the data itself
|
// The proto has the metadata and the data itself
|
||||||
for (ColumnValue column: proto.getColumnValueList()) {
|
for (ColumnValue column: proto.getColumnValueList()) {
|
||||||
byte[] family = column.getFamily().toByteArray();
|
byte[] family = column.getFamily().toByteArray();
|
||||||
for (QualifierValue qv: column.getQualifierValueList()) {
|
for (QualifierValue qv: column.getQualifierValueList()) {
|
||||||
byte[] qualifier = qv.getQualifier().toByteArray();
|
|
||||||
if (!qv.hasValue()) {
|
if (!qv.hasValue()) {
|
||||||
throw new DoNotRetryIOException(
|
throw new DoNotRetryIOException(
|
||||||
"Missing required field: qualifer value");
|
"Missing required field: qualifier value");
|
||||||
}
|
}
|
||||||
byte[] value = qv.getValue().toByteArray();
|
ByteBuffer qualifier =
|
||||||
|
qv.hasQualifier() ? qv.getQualifier().asReadOnlyByteBuffer() : null;
|
||||||
|
ByteBuffer value =
|
||||||
|
qv.hasValue() ? qv.getValue().asReadOnlyByteBuffer() : null;
|
||||||
long ts = timestamp;
|
long ts = timestamp;
|
||||||
if (qv.hasTimestamp()) {
|
if (qv.hasTimestamp()) {
|
||||||
ts = qv.getTimestamp();
|
ts = qv.getTimestamp();
|
||||||
|
|
|
@ -21,10 +21,16 @@ package org.apache.hadoop.hbase.client;
|
||||||
import static org.junit.Assert.assertEquals;
|
import static org.junit.Assert.assertEquals;
|
||||||
import static org.junit.Assert.assertNotNull;
|
import static org.junit.Assert.assertNotNull;
|
||||||
|
|
||||||
|
import org.apache.hadoop.hbase.Cell;
|
||||||
|
import org.apache.hadoop.hbase.CellUtil;
|
||||||
|
import org.apache.hadoop.hbase.HConstants;
|
||||||
|
import org.apache.hadoop.hbase.KeyValue;
|
||||||
import org.apache.hadoop.hbase.SmallTests;
|
import org.apache.hadoop.hbase.SmallTests;
|
||||||
|
import org.junit.Assert;
|
||||||
import org.junit.Test;
|
import org.junit.Test;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
@ -368,5 +374,51 @@ public class TestOperation {
|
||||||
Bytes.toStringBinary(QUALIFIER), kvMap.get("qualifier"));
|
Bytes.toStringBinary(QUALIFIER), kvMap.get("qualifier"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testPutCreationWithByteBuffer() {
|
||||||
|
Put p = new Put(ROW);
|
||||||
|
List<Cell> c = p.get(FAMILY, QUALIFIER);
|
||||||
|
Assert.assertEquals(0, c.size());
|
||||||
|
Assert.assertEquals(HConstants.LATEST_TIMESTAMP, p.getTimeStamp());
|
||||||
|
|
||||||
|
p.add(FAMILY, ByteBuffer.wrap(QUALIFIER), 1984L, ByteBuffer.wrap(VALUE));
|
||||||
|
c = p.get(FAMILY, QUALIFIER);
|
||||||
|
Assert.assertEquals(1, c.size());
|
||||||
|
Assert.assertEquals(1984L, c.get(0).getTimestamp());
|
||||||
|
Assert.assertArrayEquals(VALUE, CellUtil.cloneValue(c.get(0)));
|
||||||
|
Assert.assertEquals(HConstants.LATEST_TIMESTAMP, p.getTimeStamp());
|
||||||
|
Assert.assertEquals(0, KeyValue.COMPARATOR.compare(c.get(0), new KeyValue(c.get(0))));
|
||||||
|
|
||||||
|
p = new Put(ROW);
|
||||||
|
p.add(FAMILY, ByteBuffer.wrap(QUALIFIER), 2013L, null);
|
||||||
|
c = p.get(FAMILY, QUALIFIER);
|
||||||
|
Assert.assertEquals(1, c.size());
|
||||||
|
Assert.assertEquals(2013L, c.get(0).getTimestamp());
|
||||||
|
Assert.assertArrayEquals(new byte[]{}, CellUtil.cloneValue(c.get(0)));
|
||||||
|
Assert.assertEquals(HConstants.LATEST_TIMESTAMP, p.getTimeStamp());
|
||||||
|
Assert.assertEquals(0, KeyValue.COMPARATOR.compare(c.get(0), new KeyValue(c.get(0))));
|
||||||
|
|
||||||
|
p = new Put(ByteBuffer.wrap(ROW));
|
||||||
|
p.add(FAMILY, ByteBuffer.wrap(QUALIFIER), 2001L, null);
|
||||||
|
c = p.get(FAMILY, QUALIFIER);
|
||||||
|
Assert.assertEquals(1, c.size());
|
||||||
|
Assert.assertEquals(2001L, c.get(0).getTimestamp());
|
||||||
|
Assert.assertArrayEquals(new byte[]{}, CellUtil.cloneValue(c.get(0)));
|
||||||
|
Assert.assertArrayEquals(ROW, CellUtil.cloneRow(c.get(0)));
|
||||||
|
Assert.assertEquals(HConstants.LATEST_TIMESTAMP, p.getTimeStamp());
|
||||||
|
Assert.assertEquals(0, KeyValue.COMPARATOR.compare(c.get(0), new KeyValue(c.get(0))));
|
||||||
|
|
||||||
|
p = new Put(ByteBuffer.wrap(ROW), 1970L);
|
||||||
|
p.add(FAMILY, ByteBuffer.wrap(QUALIFIER), 2001L, null);
|
||||||
|
c = p.get(FAMILY, QUALIFIER);
|
||||||
|
Assert.assertEquals(1, c.size());
|
||||||
|
Assert.assertEquals(2001L, c.get(0).getTimestamp());
|
||||||
|
Assert.assertArrayEquals(new byte[]{}, CellUtil.cloneValue(c.get(0)));
|
||||||
|
Assert.assertArrayEquals(ROW, CellUtil.cloneRow(c.get(0)));
|
||||||
|
Assert.assertEquals(1970L, p.getTimeStamp());
|
||||||
|
Assert.assertEquals(0, KeyValue.COMPARATOR.compare(c.get(0), new KeyValue(c.get(0))));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -143,6 +143,7 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
|
|
||||||
public static final int KEYVALUE_WITH_TAGS_INFRASTRUCTURE_SIZE = ROW_OFFSET + TAGS_LENGTH_SIZE;
|
public static final int KEYVALUE_WITH_TAGS_INFRASTRUCTURE_SIZE = ROW_OFFSET + TAGS_LENGTH_SIZE;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Computes the number of bytes that a <code>KeyValue</code> instance with the provided
|
* Computes the number of bytes that a <code>KeyValue</code> instance with the provided
|
||||||
* characteristics would take up for its underlying data structure.
|
* characteristics would take up for its underlying data structure.
|
||||||
|
@ -430,7 +431,7 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
public KeyValue(final byte[] row, final byte[] family,
|
public KeyValue(final byte[] row, final byte[] family,
|
||||||
final byte[] qualifier, final long timestamp, final byte[] value,
|
final byte[] qualifier, final long timestamp, final byte[] value,
|
||||||
final Tag[] tags) {
|
final Tag[] tags) {
|
||||||
this(row, family, qualifier, timestamp, value, Arrays.asList(tags));
|
this(row, family, qualifier, timestamp, value, tags != null ? Arrays.asList(tags) : null);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -718,6 +719,17 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
this.offset = 0;
|
this.offset = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public KeyValue(byte[] row, int roffset, int rlength,
|
||||||
|
byte[] family, int foffset, int flength,
|
||||||
|
ByteBuffer qualifier, long ts, Type type, ByteBuffer value, List<Tag> tags) {
|
||||||
|
this.bytes = createByteArray(row, roffset, rlength, family, foffset, flength,
|
||||||
|
qualifier, 0, qualifier == null ? 0 : qualifier.remaining(), ts, type,
|
||||||
|
value, 0, value == null ? 0 : value.remaining(), tags);
|
||||||
|
this.length = bytes.length;
|
||||||
|
this.offset = 0;
|
||||||
|
}
|
||||||
|
|
||||||
public KeyValue(Cell c) {
|
public KeyValue(Cell c) {
|
||||||
this(c.getRowArray(), c.getRowOffset(), (int)c.getRowLength(),
|
this(c.getRowArray(), c.getRowOffset(), (int)c.getRowLength(),
|
||||||
c.getFamilyArray(), c.getFamilyOffset(), (int)c.getFamilyLength(),
|
c.getFamilyArray(), c.getFamilyOffset(), (int)c.getFamilyLength(),
|
||||||
|
@ -790,17 +802,13 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
* @param rlength row length
|
* @param rlength row length
|
||||||
* @param family family name
|
* @param family family name
|
||||||
* @param flength family length
|
* @param flength family length
|
||||||
* @param qualifier column qualifier
|
|
||||||
* @param qlength qualifier length
|
* @param qlength qualifier length
|
||||||
* @param value column value
|
|
||||||
* @param vlength value length
|
* @param vlength value length
|
||||||
*
|
*
|
||||||
* @throws IllegalArgumentException an illegal value was passed
|
* @throws IllegalArgumentException an illegal value was passed
|
||||||
*/
|
*/
|
||||||
private static void checkParameters(final byte [] row, final int rlength,
|
private static void checkParameters(final byte [] row, final int rlength,
|
||||||
final byte [] family, int flength,
|
final byte [] family, int flength, int qlength, int vlength)
|
||||||
final byte [] qualifier, int qlength,
|
|
||||||
final byte [] value, int vlength)
|
|
||||||
throws IllegalArgumentException {
|
throws IllegalArgumentException {
|
||||||
if (rlength > Short.MAX_VALUE) {
|
if (rlength > Short.MAX_VALUE) {
|
||||||
throw new IllegalArgumentException("Row > " + Short.MAX_VALUE);
|
throw new IllegalArgumentException("Row > " + Short.MAX_VALUE);
|
||||||
|
@ -814,7 +822,6 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
throw new IllegalArgumentException("Family > " + Byte.MAX_VALUE);
|
throw new IllegalArgumentException("Family > " + Byte.MAX_VALUE);
|
||||||
}
|
}
|
||||||
// Qualifier length
|
// Qualifier length
|
||||||
qlength = qualifier == null ? 0 : qlength;
|
|
||||||
if (qlength > Integer.MAX_VALUE - rlength - flength) {
|
if (qlength > Integer.MAX_VALUE - rlength - flength) {
|
||||||
throw new IllegalArgumentException("Qualifier > " + Integer.MAX_VALUE);
|
throw new IllegalArgumentException("Qualifier > " + Integer.MAX_VALUE);
|
||||||
}
|
}
|
||||||
|
@ -825,7 +832,6 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
Integer.MAX_VALUE);
|
Integer.MAX_VALUE);
|
||||||
}
|
}
|
||||||
// Value length
|
// Value length
|
||||||
vlength = value == null? 0 : vlength;
|
|
||||||
if (vlength > HConstants.MAXIMUM_VALUE_LENGTH) { // FindBugs INT_VACUOUS_COMPARISON
|
if (vlength > HConstants.MAXIMUM_VALUE_LENGTH) { // FindBugs INT_VACUOUS_COMPARISON
|
||||||
throw new IllegalArgumentException("Value length " + vlength + " > " +
|
throw new IllegalArgumentException("Value length " + vlength + " > " +
|
||||||
HConstants.MAXIMUM_VALUE_LENGTH);
|
HConstants.MAXIMUM_VALUE_LENGTH);
|
||||||
|
@ -864,7 +870,7 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
final long timestamp, final Type type,
|
final long timestamp, final Type type,
|
||||||
final byte [] value, final int voffset, int vlength, Tag[] tags) {
|
final byte [] value, final int voffset, int vlength, Tag[] tags) {
|
||||||
|
|
||||||
checkParameters(row, rlength, family, flength, qualifier, qlength, value, vlength);
|
checkParameters(row, rlength, family, flength, qlength, vlength);
|
||||||
|
|
||||||
// Calculate length of tags area
|
// Calculate length of tags area
|
||||||
int tagsLength = 0;
|
int tagsLength = 0;
|
||||||
|
@ -941,7 +947,7 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
final byte [] value, final int voffset,
|
final byte [] value, final int voffset,
|
||||||
int vlength, byte[] tags, int tagsOffset, int tagsLength) {
|
int vlength, byte[] tags, int tagsOffset, int tagsLength) {
|
||||||
|
|
||||||
checkParameters(row, rlength, family, flength, qualifier, qlength, value, vlength);
|
checkParameters(row, rlength, family, flength, qlength, vlength);
|
||||||
checkForTagsLength(tagsLength);
|
checkForTagsLength(tagsLength);
|
||||||
// Allocate right-sized byte array.
|
// Allocate right-sized byte array.
|
||||||
int keyLength = (int) getKeyDataStructureSize(rlength, flength, qlength);
|
int keyLength = (int) getKeyDataStructureSize(rlength, flength, qlength);
|
||||||
|
@ -972,14 +978,18 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
}
|
}
|
||||||
return bytes;
|
return bytes;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param qualifier can be a ByteBuffer or a byte[], or null.
|
||||||
|
* @param value can be a ByteBuffer or a byte[], or null.
|
||||||
|
*/
|
||||||
private static byte [] createByteArray(final byte [] row, final int roffset,
|
private static byte [] createByteArray(final byte [] row, final int roffset,
|
||||||
final int rlength, final byte [] family, final int foffset, int flength,
|
final int rlength, final byte [] family, final int foffset, int flength,
|
||||||
final byte [] qualifier, final int qoffset, int qlength,
|
final Object qualifier, final int qoffset, int qlength,
|
||||||
final long timestamp, final Type type,
|
final long timestamp, final Type type,
|
||||||
final byte [] value, final int voffset, int vlength, List<Tag> tags) {
|
final Object value, final int voffset, int vlength, List<Tag> tags) {
|
||||||
|
|
||||||
checkParameters(row, rlength, family, flength, qualifier, qlength, value, vlength);
|
checkParameters(row, rlength, family, flength, qlength, vlength);
|
||||||
|
|
||||||
// Calculate length of tags area
|
// Calculate length of tags area
|
||||||
int tagsLength = 0;
|
int tagsLength = 0;
|
||||||
|
@ -1005,13 +1015,21 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
if(flength != 0) {
|
if(flength != 0) {
|
||||||
pos = Bytes.putBytes(bytes, pos, family, foffset, flength);
|
pos = Bytes.putBytes(bytes, pos, family, foffset, flength);
|
||||||
}
|
}
|
||||||
if(qlength != 0) {
|
if (qlength > 0) {
|
||||||
pos = Bytes.putBytes(bytes, pos, qualifier, qoffset, qlength);
|
if (qualifier instanceof ByteBuffer) {
|
||||||
|
pos = Bytes.putByteBuffer(bytes, pos, (ByteBuffer) qualifier);
|
||||||
|
} else {
|
||||||
|
pos = Bytes.putBytes(bytes, pos, (byte[]) qualifier, qoffset, qlength);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
pos = Bytes.putLong(bytes, pos, timestamp);
|
pos = Bytes.putLong(bytes, pos, timestamp);
|
||||||
pos = Bytes.putByte(bytes, pos, type.getCode());
|
pos = Bytes.putByte(bytes, pos, type.getCode());
|
||||||
if (value != null && value.length > 0) {
|
if (vlength > 0) {
|
||||||
pos = Bytes.putBytes(bytes, pos, value, voffset, vlength);
|
if (value instanceof ByteBuffer) {
|
||||||
|
pos = Bytes.putByteBuffer(bytes, pos, (ByteBuffer) value);
|
||||||
|
} else {
|
||||||
|
pos = Bytes.putBytes(bytes, pos, (byte[]) value, voffset, vlength);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
// Add the tags after the value part
|
// Add the tags after the value part
|
||||||
if (tagsLength > 0) {
|
if (tagsLength > 0) {
|
||||||
|
@ -1023,7 +1041,6 @@ public class KeyValue implements Cell, HeapSize, Cloneable {
|
||||||
return bytes;
|
return bytes;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Needed doing 'contains' on List. Only compares the key portion, not the value.
|
* Needed doing 'contains' on List. Only compares the key portion, not the value.
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -305,6 +305,19 @@ public class Bytes {
|
||||||
return offset + 1;
|
return offset + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add the whole content of the ByteBuffer to the bytes arrays. The ByteBuffer is modified.
|
||||||
|
* @param bytes the byte array
|
||||||
|
* @param offset position in the array
|
||||||
|
* @param buf ByteBuffer to write out
|
||||||
|
* @return incremented offset
|
||||||
|
*/
|
||||||
|
public static int putByteBuffer(byte[] bytes, int offset, ByteBuffer buf) {
|
||||||
|
int len = buf.remaining();
|
||||||
|
buf.get(bytes, offset, len);
|
||||||
|
return offset + len;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a new byte array, copied from the given {@code buf},
|
* Returns a new byte array, copied from the given {@code buf},
|
||||||
* from the index 0 (inclusive) to the limit (exclusive),
|
* from the index 0 (inclusive) to the limit (exclusive),
|
||||||
|
|
|
@ -463,5 +463,15 @@ public class TestBytes extends TestCase {
|
||||||
assertFalse(array[i] == 0);
|
assertFalse(array[i] == 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testPutBuffer() {
|
||||||
|
byte[] b = new byte[100];
|
||||||
|
for (byte i = 0; i < 100; i++) {
|
||||||
|
Bytes.putByteBuffer(b, i, ByteBuffer.wrap(new byte[]{i}));
|
||||||
|
}
|
||||||
|
for (byte i = 0; i < 100; i++) {
|
||||||
|
Assert.assertEquals(i, b[i]);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -3305,11 +3305,12 @@ public class HRegionServer implements ClientProtos.ClientService.BlockingInterfa
|
||||||
// this will contain all the cells that we need to return. It's created later, if needed.
|
// this will contain all the cells that we need to return. It's created later, if needed.
|
||||||
List<CellScannable> cellsToReturn = null;
|
List<CellScannable> cellsToReturn = null;
|
||||||
MultiResponse.Builder responseBuilder = MultiResponse.newBuilder();
|
MultiResponse.Builder responseBuilder = MultiResponse.newBuilder();
|
||||||
|
RegionActionResult.Builder regionActionResultBuilder = RegionActionResult.newBuilder();
|
||||||
|
|
||||||
for (RegionAction regionAction : request.getRegionActionList()) {
|
for (RegionAction regionAction : request.getRegionActionList()) {
|
||||||
this.requestCount.add(regionAction.getActionCount());
|
this.requestCount.add(regionAction.getActionCount());
|
||||||
RegionActionResult.Builder regionActionResultBuilder = RegionActionResult.newBuilder();
|
|
||||||
HRegion region;
|
HRegion region;
|
||||||
|
regionActionResultBuilder.clear();
|
||||||
try {
|
try {
|
||||||
region = getRegion(regionAction.getRegion());
|
region = getRegion(regionAction.getRegion());
|
||||||
} catch (IOException e) {
|
} catch (IOException e) {
|
||||||
|
|
|
@ -1927,17 +1927,17 @@ public class TestHRegion {
|
||||||
// Putting data in Region
|
// Putting data in Region
|
||||||
Put put = null;
|
Put put = null;
|
||||||
put = new Put(row1);
|
put = new Put(row1);
|
||||||
put.add(fam1, null, ts, null);
|
put.add(fam1, (byte[]) null, ts, null);
|
||||||
put.add(fam2, null, ts, null);
|
put.add(fam2, (byte[]) null, ts, null);
|
||||||
put.add(fam3, null, ts, null);
|
put.add(fam3, (byte[]) null, ts, null);
|
||||||
put.add(fam4, null, ts, null);
|
put.add(fam4, (byte[]) null, ts, null);
|
||||||
region.put(put);
|
region.put(put);
|
||||||
|
|
||||||
put = new Put(row2);
|
put = new Put(row2);
|
||||||
put.add(fam1, null, ts, null);
|
put.add(fam1, (byte[]) null, ts, null);
|
||||||
put.add(fam2, null, ts, null);
|
put.add(fam2, (byte[]) null, ts, null);
|
||||||
put.add(fam3, null, ts, null);
|
put.add(fam3, (byte[]) null, ts, null);
|
||||||
put.add(fam4, null, ts, null);
|
put.add(fam4, (byte[]) null, ts, null);
|
||||||
region.put(put);
|
region.put(put);
|
||||||
|
|
||||||
Scan scan = new Scan();
|
Scan scan = new Scan();
|
||||||
|
|
Loading…
Reference in New Issue