1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.hadoop.hbase.client;
20
21 import static org.junit.Assert.assertEquals;
22 import static org.junit.Assert.assertNotNull;
23 import org.apache.hadoop.hbase.Cell;
24 import org.apache.hadoop.hbase.CellUtil;
25 import org.apache.hadoop.hbase.HConstants;
26 import org.apache.hadoop.hbase.KeyValue;
27 import org.apache.hadoop.hbase.testclassification.SmallTests;
28 import org.junit.Assert;
29 import org.junit.Test;
30
31 import java.io.IOException;
32 import java.nio.ByteBuffer;
33 import java.util.Arrays;
34 import java.util.HashMap;
35 import java.util.List;
36 import java.util.Map;
37
38 import org.apache.hadoop.hbase.filter.BinaryComparator;
39 import org.apache.hadoop.hbase.filter.ColumnCountGetFilter;
40 import org.apache.hadoop.hbase.filter.ColumnPaginationFilter;
41 import org.apache.hadoop.hbase.filter.ColumnPrefixFilter;
42 import org.apache.hadoop.hbase.filter.ColumnRangeFilter;
43 import org.apache.hadoop.hbase.filter.CompareFilter.CompareOp;
44 import org.apache.hadoop.hbase.filter.DependentColumnFilter;
45 import org.apache.hadoop.hbase.filter.FamilyFilter;
46 import org.apache.hadoop.hbase.filter.Filter;
47 import org.apache.hadoop.hbase.filter.FilterList;
48 import org.apache.hadoop.hbase.filter.FilterList.Operator;
49 import org.apache.hadoop.hbase.filter.FirstKeyOnlyFilter;
50 import org.apache.hadoop.hbase.filter.InclusiveStopFilter;
51 import org.apache.hadoop.hbase.filter.KeyOnlyFilter;
52 import org.apache.hadoop.hbase.filter.MultipleColumnPrefixFilter;
53 import org.apache.hadoop.hbase.filter.PageFilter;
54 import org.apache.hadoop.hbase.filter.PrefixFilter;
55 import org.apache.hadoop.hbase.filter.QualifierFilter;
56 import org.apache.hadoop.hbase.filter.RowFilter;
57 import org.apache.hadoop.hbase.filter.SingleColumnValueFilter;
58 import org.apache.hadoop.hbase.filter.SingleColumnValueExcludeFilter;
59 import org.apache.hadoop.hbase.filter.SkipFilter;
60 import org.apache.hadoop.hbase.filter.TimestampsFilter;
61 import org.apache.hadoop.hbase.filter.ValueFilter;
62 import org.apache.hadoop.hbase.filter.WhileMatchFilter;
63 import org.apache.hadoop.hbase.util.BuilderStyleTest;
64 import org.apache.hadoop.hbase.util.Bytes;
65 import org.codehaus.jackson.map.ObjectMapper;
66 import org.junit.experimental.categories.Category;
67
68
69
70
71
72 @Category(SmallTests.class)
73 public class TestOperation {
74 private static byte [] ROW = Bytes.toBytes("testRow");
75 private static byte [] FAMILY = Bytes.toBytes("testFamily");
76 private static byte [] QUALIFIER = Bytes.toBytes("testQualifier");
77 private static byte [] VALUE = Bytes.toBytes("testValue");
78
79 private static ObjectMapper mapper = new ObjectMapper();
80
81 private static List<Long> TS_LIST = Arrays.asList(2L, 3L, 5L);
82 private static TimestampsFilter TS_FILTER = new TimestampsFilter(TS_LIST);
83 private static String STR_TS_FILTER =
84 TS_FILTER.getClass().getSimpleName() + " (3/3): [2, 3, 5]";
85
86 private static List<Long> L_TS_LIST =
87 Arrays.asList(0L, 1L, 2L, 3L, 4L, 5L, 6L, 7L, 8L, 9L, 10L);
88 private static TimestampsFilter L_TS_FILTER =
89 new TimestampsFilter(L_TS_LIST);
90 private static String STR_L_TS_FILTER =
91 L_TS_FILTER.getClass().getSimpleName() + " (5/11): [0, 1, 2, 3, 4]";
92
93 private static String COL_NAME_1 = "col1";
94 private static ColumnPrefixFilter COL_PRE_FILTER =
95 new ColumnPrefixFilter(COL_NAME_1.getBytes());
96 private static String STR_COL_PRE_FILTER =
97 COL_PRE_FILTER.getClass().getSimpleName() + " " + COL_NAME_1;
98
99 private static String COL_NAME_2 = "col2";
100 private static ColumnRangeFilter CR_FILTER = new ColumnRangeFilter(
101 COL_NAME_1.getBytes(), true, COL_NAME_2.getBytes(), false);
102 private static String STR_CR_FILTER = CR_FILTER.getClass().getSimpleName()
103 + " [" + COL_NAME_1 + ", " + COL_NAME_2 + ")";
104
105 private static int COL_COUNT = 9;
106 private static ColumnCountGetFilter CCG_FILTER =
107 new ColumnCountGetFilter(COL_COUNT);
108 private static String STR_CCG_FILTER =
109 CCG_FILTER.getClass().getSimpleName() + " " + COL_COUNT;
110
111 private static int LIMIT = 3;
112 private static int OFFSET = 4;
113 private static ColumnPaginationFilter CP_FILTER =
114 new ColumnPaginationFilter(LIMIT, OFFSET);
115 private static String STR_CP_FILTER = CP_FILTER.getClass().getSimpleName()
116 + " (" + LIMIT + ", " + OFFSET + ")";
117
118 private static String STOP_ROW_KEY = "stop";
119 private static InclusiveStopFilter IS_FILTER =
120 new InclusiveStopFilter(STOP_ROW_KEY.getBytes());
121 private static String STR_IS_FILTER =
122 IS_FILTER.getClass().getSimpleName() + " " + STOP_ROW_KEY;
123
124 private static String PREFIX = "prefix";
125 private static PrefixFilter PREFIX_FILTER =
126 new PrefixFilter(PREFIX.getBytes());
127 private static String STR_PREFIX_FILTER = "PrefixFilter " + PREFIX;
128
129 private static byte[][] PREFIXES = {
130 "0".getBytes(), "1".getBytes(), "2".getBytes()};
131 private static MultipleColumnPrefixFilter MCP_FILTER =
132 new MultipleColumnPrefixFilter(PREFIXES);
133 private static String STR_MCP_FILTER =
134 MCP_FILTER.getClass().getSimpleName() + " (3/3): [0, 1, 2]";
135
136 private static byte[][] L_PREFIXES = {
137 "0".getBytes(), "1".getBytes(), "2".getBytes(), "3".getBytes(),
138 "4".getBytes(), "5".getBytes(), "6".getBytes(), "7".getBytes()};
139 private static MultipleColumnPrefixFilter L_MCP_FILTER =
140 new MultipleColumnPrefixFilter(L_PREFIXES);
141 private static String STR_L_MCP_FILTER =
142 L_MCP_FILTER.getClass().getSimpleName() + " (5/8): [0, 1, 2, 3, 4]";
143
144 private static int PAGE_SIZE = 9;
145 private static PageFilter PAGE_FILTER = new PageFilter(PAGE_SIZE);
146 private static String STR_PAGE_FILTER =
147 PAGE_FILTER.getClass().getSimpleName() + " " + PAGE_SIZE;
148
149 private static SkipFilter SKIP_FILTER = new SkipFilter(L_TS_FILTER);
150 private static String STR_SKIP_FILTER =
151 SKIP_FILTER.getClass().getSimpleName() + " " + STR_L_TS_FILTER;
152
153 private static WhileMatchFilter WHILE_FILTER =
154 new WhileMatchFilter(L_TS_FILTER);
155 private static String STR_WHILE_FILTER =
156 WHILE_FILTER.getClass().getSimpleName() + " " + STR_L_TS_FILTER;
157
158 private static KeyOnlyFilter KEY_ONLY_FILTER = new KeyOnlyFilter();
159 private static String STR_KEY_ONLY_FILTER =
160 KEY_ONLY_FILTER.getClass().getSimpleName();
161
162 private static FirstKeyOnlyFilter FIRST_KEY_ONLY_FILTER =
163 new FirstKeyOnlyFilter();
164 private static String STR_FIRST_KEY_ONLY_FILTER =
165 FIRST_KEY_ONLY_FILTER.getClass().getSimpleName();
166
167 private static CompareOp CMP_OP = CompareOp.EQUAL;
168 private static byte[] CMP_VALUE = "value".getBytes();
169 private static BinaryComparator BC = new BinaryComparator(CMP_VALUE);
170 private static DependentColumnFilter DC_FILTER =
171 new DependentColumnFilter(FAMILY, QUALIFIER, true, CMP_OP, BC);
172 private static String STR_DC_FILTER = String.format(
173 "%s (%s, %s, %s, %s, %s)", DC_FILTER.getClass().getSimpleName(),
174 Bytes.toStringBinary(FAMILY), Bytes.toStringBinary(QUALIFIER), true,
175 CMP_OP.name(), Bytes.toStringBinary(BC.getValue()));
176
177 private static FamilyFilter FAMILY_FILTER = new FamilyFilter(CMP_OP, BC);
178 private static String STR_FAMILY_FILTER =
179 FAMILY_FILTER.getClass().getSimpleName() + " (EQUAL, value)";
180
181 private static QualifierFilter QUALIFIER_FILTER =
182 new QualifierFilter(CMP_OP, BC);
183 private static String STR_QUALIFIER_FILTER =
184 QUALIFIER_FILTER.getClass().getSimpleName() + " (EQUAL, value)";
185
186 private static RowFilter ROW_FILTER = new RowFilter(CMP_OP, BC);
187 private static String STR_ROW_FILTER =
188 ROW_FILTER.getClass().getSimpleName() + " (EQUAL, value)";
189
190 private static ValueFilter VALUE_FILTER = new ValueFilter(CMP_OP, BC);
191 private static String STR_VALUE_FILTER =
192 VALUE_FILTER.getClass().getSimpleName() + " (EQUAL, value)";
193
194 private static SingleColumnValueFilter SCV_FILTER =
195 new SingleColumnValueFilter(FAMILY, QUALIFIER, CMP_OP, CMP_VALUE);
196 private static String STR_SCV_FILTER = String.format("%s (%s, %s, %s, %s)",
197 SCV_FILTER.getClass().getSimpleName(), Bytes.toStringBinary(FAMILY),
198 Bytes.toStringBinary(QUALIFIER), CMP_OP.name(),
199 Bytes.toStringBinary(CMP_VALUE));
200
201 private static SingleColumnValueExcludeFilter SCVE_FILTER =
202 new SingleColumnValueExcludeFilter(FAMILY, QUALIFIER, CMP_OP, CMP_VALUE);
203 private static String STR_SCVE_FILTER = String.format("%s (%s, %s, %s, %s)",
204 SCVE_FILTER.getClass().getSimpleName(), Bytes.toStringBinary(FAMILY),
205 Bytes.toStringBinary(QUALIFIER), CMP_OP.name(),
206 Bytes.toStringBinary(CMP_VALUE));
207
208 private static FilterList AND_FILTER_LIST = new FilterList(
209 Operator.MUST_PASS_ALL, Arrays.asList((Filter) TS_FILTER, L_TS_FILTER,
210 CR_FILTER));
211 private static String STR_AND_FILTER_LIST = String.format(
212 "%s AND (3/3): [%s, %s, %s]", AND_FILTER_LIST.getClass().getSimpleName(),
213 STR_TS_FILTER, STR_L_TS_FILTER, STR_CR_FILTER);
214
215 private static FilterList OR_FILTER_LIST = new FilterList(
216 Operator.MUST_PASS_ONE, Arrays.asList((Filter) TS_FILTER, L_TS_FILTER,
217 CR_FILTER));
218 private static String STR_OR_FILTER_LIST = String.format(
219 "%s OR (3/3): [%s, %s, %s]", AND_FILTER_LIST.getClass().getSimpleName(),
220 STR_TS_FILTER, STR_L_TS_FILTER, STR_CR_FILTER);
221
222 private static FilterList L_FILTER_LIST = new FilterList(
223 Arrays.asList((Filter) TS_FILTER, L_TS_FILTER, CR_FILTER, COL_PRE_FILTER,
224 CCG_FILTER, CP_FILTER, PREFIX_FILTER, PAGE_FILTER));
225 private static String STR_L_FILTER_LIST = String.format(
226 "%s AND (5/8): [%s, %s, %s, %s, %s, %s]",
227 L_FILTER_LIST.getClass().getSimpleName(), STR_TS_FILTER, STR_L_TS_FILTER,
228 STR_CR_FILTER, STR_COL_PRE_FILTER, STR_CCG_FILTER, STR_CP_FILTER);
229
230 private static Filter[] FILTERS = {
231 TS_FILTER,
232 L_TS_FILTER,
233 COL_PRE_FILTER,
234 CP_FILTER,
235 CR_FILTER,
236 CCG_FILTER,
237 IS_FILTER,
238 PREFIX_FILTER,
239 PAGE_FILTER,
240 SKIP_FILTER,
241 WHILE_FILTER,
242 KEY_ONLY_FILTER,
243 FIRST_KEY_ONLY_FILTER,
244 MCP_FILTER,
245 L_MCP_FILTER,
246 DC_FILTER,
247 FAMILY_FILTER,
248 QUALIFIER_FILTER,
249 ROW_FILTER,
250 VALUE_FILTER,
251 SCV_FILTER,
252 SCVE_FILTER,
253 AND_FILTER_LIST,
254 OR_FILTER_LIST,
255 L_FILTER_LIST,
256 };
257
258 private static String[] FILTERS_INFO = {
259 STR_TS_FILTER,
260 STR_L_TS_FILTER,
261 STR_COL_PRE_FILTER,
262 STR_CP_FILTER,
263 STR_CR_FILTER,
264 STR_CCG_FILTER,
265 STR_IS_FILTER,
266 STR_PREFIX_FILTER,
267 STR_PAGE_FILTER,
268 STR_SKIP_FILTER,
269 STR_WHILE_FILTER,
270 STR_KEY_ONLY_FILTER,
271 STR_FIRST_KEY_ONLY_FILTER,
272 STR_MCP_FILTER,
273 STR_L_MCP_FILTER,
274 STR_DC_FILTER,
275 STR_FAMILY_FILTER,
276 STR_QUALIFIER_FILTER,
277 STR_ROW_FILTER,
278 STR_VALUE_FILTER,
279 STR_SCV_FILTER,
280 STR_SCVE_FILTER,
281 STR_AND_FILTER_LIST,
282 STR_OR_FILTER_LIST,
283 STR_L_FILTER_LIST,
284 };
285
286 static {
287 assertEquals("The sizes of static arrays do not match: "
288 + "[FILTERS: %d <=> FILTERS_INFO: %d]",
289 FILTERS.length, FILTERS_INFO.length);
290 }
291
292
293
294
295
296
297 @Test
298 public void testOperationJSON()
299 throws IOException {
300
301 Scan scan = new Scan(ROW);
302 scan.addColumn(FAMILY, QUALIFIER);
303
304 String json = scan.toJSON();
305 Map<String, Object> parsedJSON = mapper.readValue(json, HashMap.class);
306
307 assertEquals("startRow incorrect in Scan.toJSON()",
308 Bytes.toStringBinary(ROW), parsedJSON.get("startRow"));
309
310 List familyInfo = (List) ((Map) parsedJSON.get("families")).get(
311 Bytes.toStringBinary(FAMILY));
312 assertNotNull("Family absent in Scan.toJSON()", familyInfo);
313 assertEquals("Qualifier absent in Scan.toJSON()", 1, familyInfo.size());
314 assertEquals("Qualifier incorrect in Scan.toJSON()",
315 Bytes.toStringBinary(QUALIFIER),
316 familyInfo.get(0));
317
318
319 Get get = new Get(ROW);
320 get.addColumn(FAMILY, QUALIFIER);
321
322 json = get.toJSON();
323 parsedJSON = mapper.readValue(json, HashMap.class);
324
325 assertEquals("row incorrect in Get.toJSON()",
326 Bytes.toStringBinary(ROW), parsedJSON.get("row"));
327
328 familyInfo = (List) ((Map) parsedJSON.get("families")).get(
329 Bytes.toStringBinary(FAMILY));
330 assertNotNull("Family absent in Get.toJSON()", familyInfo);
331 assertEquals("Qualifier absent in Get.toJSON()", 1, familyInfo.size());
332 assertEquals("Qualifier incorrect in Get.toJSON()",
333 Bytes.toStringBinary(QUALIFIER),
334 familyInfo.get(0));
335
336
337 Put put = new Put(ROW);
338 put.add(FAMILY, QUALIFIER, VALUE);
339
340 json = put.toJSON();
341 parsedJSON = mapper.readValue(json, HashMap.class);
342
343 assertEquals("row absent in Put.toJSON()",
344 Bytes.toStringBinary(ROW), parsedJSON.get("row"));
345
346 familyInfo = (List) ((Map) parsedJSON.get("families")).get(
347 Bytes.toStringBinary(FAMILY));
348 assertNotNull("Family absent in Put.toJSON()", familyInfo);
349 assertEquals("KeyValue absent in Put.toJSON()", 1, familyInfo.size());
350 Map kvMap = (Map) familyInfo.get(0);
351 assertEquals("Qualifier incorrect in Put.toJSON()",
352 Bytes.toStringBinary(QUALIFIER),
353 kvMap.get("qualifier"));
354 assertEquals("Value length incorrect in Put.toJSON()",
355 VALUE.length, kvMap.get("vlen"));
356
357
358 Delete delete = new Delete(ROW);
359 delete.deleteColumn(FAMILY, QUALIFIER);
360
361 json = delete.toJSON();
362 parsedJSON = mapper.readValue(json, HashMap.class);
363
364 assertEquals("row absent in Delete.toJSON()",
365 Bytes.toStringBinary(ROW), parsedJSON.get("row"));
366
367 familyInfo = (List) ((Map) parsedJSON.get("families")).get(
368 Bytes.toStringBinary(FAMILY));
369 assertNotNull("Family absent in Delete.toJSON()", familyInfo);
370 assertEquals("KeyValue absent in Delete.toJSON()", 1, familyInfo.size());
371 kvMap = (Map) familyInfo.get(0);
372 assertEquals("Qualifier incorrect in Delete.toJSON()",
373 Bytes.toStringBinary(QUALIFIER), kvMap.get("qualifier"));
374 }
375
376 @Test
377 public void testPutCreationWithByteBuffer() {
378 Put p = new Put(ROW);
379 List<Cell> c = p.get(FAMILY, QUALIFIER);
380 Assert.assertEquals(0, c.size());
381 Assert.assertEquals(HConstants.LATEST_TIMESTAMP, p.getTimeStamp());
382
383 p.add(FAMILY, ByteBuffer.wrap(QUALIFIER), 1984L, ByteBuffer.wrap(VALUE));
384 c = p.get(FAMILY, QUALIFIER);
385 Assert.assertEquals(1, c.size());
386 Assert.assertEquals(1984L, c.get(0).getTimestamp());
387 Assert.assertArrayEquals(VALUE, CellUtil.cloneValue(c.get(0)));
388 Assert.assertEquals(HConstants.LATEST_TIMESTAMP, p.getTimeStamp());
389 Assert.assertEquals(0, KeyValue.COMPARATOR.compare(c.get(0), new KeyValue(c.get(0))));
390
391 p = new Put(ROW);
392 p.add(FAMILY, ByteBuffer.wrap(QUALIFIER), 2013L, null);
393 c = p.get(FAMILY, QUALIFIER);
394 Assert.assertEquals(1, c.size());
395 Assert.assertEquals(2013L, c.get(0).getTimestamp());
396 Assert.assertArrayEquals(new byte[]{}, CellUtil.cloneValue(c.get(0)));
397 Assert.assertEquals(HConstants.LATEST_TIMESTAMP, p.getTimeStamp());
398 Assert.assertEquals(0, KeyValue.COMPARATOR.compare(c.get(0), new KeyValue(c.get(0))));
399
400 p = new Put(ByteBuffer.wrap(ROW));
401 p.add(FAMILY, ByteBuffer.wrap(QUALIFIER), 2001L, null);
402 c = p.get(FAMILY, QUALIFIER);
403 Assert.assertEquals(1, c.size());
404 Assert.assertEquals(2001L, c.get(0).getTimestamp());
405 Assert.assertArrayEquals(new byte[]{}, CellUtil.cloneValue(c.get(0)));
406 Assert.assertArrayEquals(ROW, CellUtil.cloneRow(c.get(0)));
407 Assert.assertEquals(HConstants.LATEST_TIMESTAMP, p.getTimeStamp());
408 Assert.assertEquals(0, KeyValue.COMPARATOR.compare(c.get(0), new KeyValue(c.get(0))));
409
410 p = new Put(ByteBuffer.wrap(ROW), 1970L);
411 p.add(FAMILY, ByteBuffer.wrap(QUALIFIER), 2001L, null);
412 c = p.get(FAMILY, QUALIFIER);
413 Assert.assertEquals(1, c.size());
414 Assert.assertEquals(2001L, c.get(0).getTimestamp());
415 Assert.assertArrayEquals(new byte[]{}, CellUtil.cloneValue(c.get(0)));
416 Assert.assertArrayEquals(ROW, CellUtil.cloneRow(c.get(0)));
417 Assert.assertEquals(1970L, p.getTimeStamp());
418 Assert.assertEquals(0, KeyValue.COMPARATOR.compare(c.get(0), new KeyValue(c.get(0))));
419 }
420
421 @Test
422 @SuppressWarnings("rawtypes")
423 public void testOperationSubClassMethodsAreBuilderStyle() {
424
425
426
427
428
429
430
431
432
433
434
435
436 Class[] classes = new Class[] {
437 Operation.class,
438 OperationWithAttributes.class,
439 Mutation.class,
440 Query.class,
441 Delete.class,
442 Increment.class,
443 Append.class,
444 Put.class,
445 Get.class,
446 Scan.class};
447
448 BuilderStyleTest.assertClassesAreBuilderStyle(classes);
449 }
450
451 }
452