001/* 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018package org.apache.hadoop.hbase.regionserver; 019 020import static org.junit.Assert.assertEquals; 021import static org.junit.Assert.assertFalse; 022import static org.junit.Assert.assertTrue; 023 024import java.util.Iterator; 025import java.util.SortedSet; 026import org.apache.hadoop.hbase.Cell; 027import org.apache.hadoop.hbase.CellComparatorImpl; 028import org.apache.hadoop.hbase.CellUtil; 029import org.apache.hadoop.hbase.ExtendedCell; 030import org.apache.hadoop.hbase.HBaseClassTestRule; 031import org.apache.hadoop.hbase.KeyValue; 032import org.apache.hadoop.hbase.testclassification.RegionServerTests; 033import org.apache.hadoop.hbase.testclassification.SmallTests; 034import org.apache.hadoop.hbase.util.Bytes; 035import org.junit.Before; 036import org.junit.ClassRule; 037import org.junit.Rule; 038import org.junit.Test; 039import org.junit.experimental.categories.Category; 040import org.junit.rules.TestName; 041 042@Category({ RegionServerTests.class, SmallTests.class }) 043public class TestCellSkipListSet { 044 045 @ClassRule 046 public static final HBaseClassTestRule CLASS_RULE = 047 HBaseClassTestRule.forClass(TestCellSkipListSet.class); 048 049 private final CellSet<ExtendedCell> csls = new CellSet<>(CellComparatorImpl.COMPARATOR); 050 051 @Rule 052 public TestName name = new TestName(); 053 054 @Before 055 public void setUp() throws Exception { 056 this.csls.clear(); 057 } 058 059 @Test 060 public void testAdd() throws Exception { 061 byte[] bytes = Bytes.toBytes(name.getMethodName()); 062 KeyValue kv = new KeyValue(bytes, bytes, bytes, bytes); 063 this.csls.add(kv); 064 assertTrue(this.csls.contains(kv)); 065 assertEquals(1, this.csls.getDelegatee().size()); 066 Cell first = this.csls.first(); 067 assertTrue(kv.equals(first)); 068 assertTrue(Bytes.equals(kv.getValueArray(), kv.getValueOffset(), kv.getValueLength(), 069 first.getValueArray(), first.getValueOffset(), first.getValueLength())); 070 // Now try overwritting 071 byte[] overwriteValue = Bytes.toBytes("overwrite"); 072 KeyValue overwrite = new KeyValue(bytes, bytes, bytes, overwriteValue); 073 this.csls.add(overwrite); 074 assertEquals(1, this.csls.getDelegatee().size()); 075 first = this.csls.first(); 076 assertTrue(Bytes.equals(overwrite.getValueArray(), overwrite.getValueOffset(), 077 overwrite.getValueLength(), first.getValueArray(), first.getValueOffset(), 078 first.getValueLength())); 079 assertFalse(Bytes.equals(CellUtil.cloneValue(overwrite), CellUtil.cloneValue(kv))); 080 } 081 082 @Test 083 public void testIterator() throws Exception { 084 byte[] bytes = Bytes.toBytes(name.getMethodName()); 085 byte[] value1 = Bytes.toBytes("1"); 086 byte[] value2 = Bytes.toBytes("2"); 087 final int total = 3; 088 for (int i = 0; i < total; i++) { 089 this.csls.add(new KeyValue(bytes, bytes, Bytes.toBytes("" + i), value1)); 090 } 091 // Assert that we added 'total' values and that they are in order 092 int count = 0; 093 for (Cell kv : this.csls) { 094 assertEquals("" + count, 095 Bytes.toString(kv.getQualifierArray(), kv.getQualifierOffset(), kv.getQualifierLength())); 096 assertTrue(Bytes.equals(kv.getValueArray(), kv.getValueOffset(), kv.getValueLength(), value1, 097 0, value1.length)); 098 count++; 099 } 100 assertEquals(total, count); 101 // Now overwrite with a new value. 102 for (int i = 0; i < total; i++) { 103 this.csls.add(new KeyValue(bytes, bytes, Bytes.toBytes("" + i), value2)); 104 } 105 // Assert that we added 'total' values and that they are in order and that 106 // we are getting back value2 107 count = 0; 108 for (Cell kv : this.csls) { 109 assertEquals("" + count, 110 Bytes.toString(kv.getQualifierArray(), kv.getQualifierOffset(), kv.getQualifierLength())); 111 assertTrue(Bytes.equals(kv.getValueArray(), kv.getValueOffset(), kv.getValueLength(), value2, 112 0, value2.length)); 113 count++; 114 } 115 assertEquals(total, count); 116 } 117 118 @Test 119 public void testDescendingIterator() throws Exception { 120 byte[] bytes = Bytes.toBytes(name.getMethodName()); 121 byte[] value1 = Bytes.toBytes("1"); 122 byte[] value2 = Bytes.toBytes("2"); 123 final int total = 3; 124 for (int i = 0; i < total; i++) { 125 this.csls.add(new KeyValue(bytes, bytes, Bytes.toBytes("" + i), value1)); 126 } 127 // Assert that we added 'total' values and that they are in order 128 int count = 0; 129 for (Iterator<ExtendedCell> i = this.csls.descendingIterator(); i.hasNext();) { 130 Cell kv = i.next(); 131 assertEquals("" + (total - (count + 1)), 132 Bytes.toString(kv.getQualifierArray(), kv.getQualifierOffset(), kv.getQualifierLength())); 133 assertTrue(Bytes.equals(kv.getValueArray(), kv.getValueOffset(), kv.getValueLength(), value1, 134 0, value1.length)); 135 count++; 136 } 137 assertEquals(total, count); 138 // Now overwrite with a new value. 139 for (int i = 0; i < total; i++) { 140 this.csls.add(new KeyValue(bytes, bytes, Bytes.toBytes("" + i), value2)); 141 } 142 // Assert that we added 'total' values and that they are in order and that 143 // we are getting back value2 144 count = 0; 145 for (Iterator<ExtendedCell> i = this.csls.descendingIterator(); i.hasNext();) { 146 Cell kv = i.next(); 147 assertEquals("" + (total - (count + 1)), 148 Bytes.toString(kv.getQualifierArray(), kv.getQualifierOffset(), kv.getQualifierLength())); 149 assertTrue(Bytes.equals(kv.getValueArray(), kv.getValueOffset(), kv.getValueLength(), value2, 150 0, value2.length)); 151 count++; 152 } 153 assertEquals(total, count); 154 } 155 156 @Test 157 public void testHeadTail() throws Exception { 158 byte[] bytes = Bytes.toBytes(name.getMethodName()); 159 byte[] value1 = Bytes.toBytes("1"); 160 byte[] value2 = Bytes.toBytes("2"); 161 final int total = 3; 162 KeyValue splitter = null; 163 for (int i = 0; i < total; i++) { 164 KeyValue kv = new KeyValue(bytes, bytes, Bytes.toBytes("" + i), value1); 165 if (i == 1) splitter = kv; 166 this.csls.add(kv); 167 } 168 SortedSet<ExtendedCell> tail = this.csls.tailSet(splitter); 169 assertEquals(2, tail.size()); 170 SortedSet<ExtendedCell> head = this.csls.headSet(splitter); 171 assertEquals(1, head.size()); 172 // Now ensure that we get back right answer even when we do tail or head. 173 // Now overwrite with a new value. 174 for (int i = 0; i < total; i++) { 175 this.csls.add(new KeyValue(bytes, bytes, Bytes.toBytes("" + i), value2)); 176 } 177 tail = this.csls.tailSet(splitter); 178 assertTrue(Bytes.equals(tail.first().getValueArray(), tail.first().getValueOffset(), 179 tail.first().getValueLength(), value2, 0, value2.length)); 180 head = this.csls.headSet(splitter); 181 assertTrue(Bytes.equals(head.first().getValueArray(), head.first().getValueOffset(), 182 head.first().getValueLength(), value2, 0, value2.length)); 183 } 184}