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.assertNotEquals;
22 import static org.junit.Assert.assertNull;
23 import static org.junit.Assert.assertTrue;
24
25 import java.io.IOException;
26 import java.util.ArrayList;
27 import java.util.List;
28
29 import org.apache.hadoop.hbase.HBaseTestingUtility;
30 import org.apache.hadoop.hbase.TableName;
31 import org.apache.hadoop.hbase.client.ConnectionManager.HConnectionImplementation;
32 import org.apache.hadoop.hbase.testclassification.ClientTests;
33 import org.apache.hadoop.hbase.testclassification.MediumTests;
34 import org.apache.hadoop.hbase.util.Bytes;
35 import org.junit.AfterClass;
36 import org.junit.BeforeClass;
37 import org.junit.Test;
38 import org.junit.experimental.categories.Category;
39
40 @Category({MediumTests.class, ClientTests.class})
41 public class TestRegionLocationCaching {
42
43 private final static HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility();
44 private static int SLAVES = 1;
45 private static int PER_REGIONSERVER_QUEUE_SIZE = 100000;
46 private static TableName TABLE_NAME = TableName.valueOf("TestRegionLocationCaching");
47 private static byte[] FAMILY = Bytes.toBytes("testFamily");
48 private static byte[] QUALIFIER = Bytes.toBytes("testQualifier");
49
50 @BeforeClass
51 public static void setUpBeforeClass() throws Exception {
52 TEST_UTIL.startMiniCluster(SLAVES);
53 TEST_UTIL.createTable(TABLE_NAME, new byte[][] { FAMILY });
54 TEST_UTIL.waitUntilAllRegionsAssigned(TABLE_NAME);
55 }
56
57 @AfterClass
58 public static void tearDownAfterClass() throws Exception {
59 TEST_UTIL.shutdownMiniCluster();
60 }
61
62 @Test
63 public void testCachingForHTableMultiplexerSinglePut() throws Exception {
64 HTableMultiplexer multiplexer =
65 new HTableMultiplexer(TEST_UTIL.getConfiguration(), PER_REGIONSERVER_QUEUE_SIZE);
66 byte[] row = Bytes.toBytes("htable_multiplexer_single_put");
67 byte[] value = Bytes.toBytes("value");
68
69 Put put = new Put(row);
70 put.addColumn(FAMILY, QUALIFIER, value);
71 assertTrue("Put request not accepted by multiplexer queue", multiplexer.put(TABLE_NAME, put));
72
73 checkRegionLocationIsCached(TABLE_NAME, multiplexer.getConnection());
74 checkExistence(TABLE_NAME, row, FAMILY, QUALIFIER);
75
76 multiplexer.close();
77 }
78
79 @Test
80 public void testCachingForHTableMultiplexerMultiPut() throws Exception {
81 HTableMultiplexer multiplexer =
82 new HTableMultiplexer(TEST_UTIL.getConfiguration(), PER_REGIONSERVER_QUEUE_SIZE);
83
84 List<Put> multiput = new ArrayList<Put>();
85 for (int i = 0; i < 10; i++) {
86 Put put = new Put(Bytes.toBytes("htable_multiplexer_multi_put" + i));
87 byte[] value = Bytes.toBytes("value_" + i);
88 put.addColumn(FAMILY, QUALIFIER, value);
89 multiput.add(put);
90 }
91
92 List<Put> failedPuts = multiplexer.put(TABLE_NAME, multiput);
93 assertNull("All put requests were not accepted by multiplexer queue", failedPuts);
94
95 checkRegionLocationIsCached(TABLE_NAME, multiplexer.getConnection());
96 for (int i = 0; i < 10; i++) {
97 checkExistence(TABLE_NAME, Bytes.toBytes("htable_multiplexer_multi_put" + i), FAMILY,
98 QUALIFIER);
99 }
100
101 multiplexer.close();
102 }
103
104 @Test
105 public void testCachingForHTableSinglePut() throws Exception {
106 byte[] row = Bytes.toBytes("htable_single_put");
107 byte[] value = Bytes.toBytes("value");
108
109 Put put = new Put(row);
110 put.addColumn(FAMILY, QUALIFIER, value);
111
112 try (Table table = TEST_UTIL.getConnection().getTable(TABLE_NAME)) {
113 table.put(put);
114 }
115
116 checkRegionLocationIsCached(TABLE_NAME, TEST_UTIL.getConnection());
117 checkExistence(TABLE_NAME, row, FAMILY, QUALIFIER);
118 }
119
120 @Test
121 public void testCachingForHTableMultiPut() throws Exception {
122 List<Put> multiput = new ArrayList<Put>();
123 for (int i = 0; i < 10; i++) {
124 Put put = new Put(Bytes.toBytes("htable_multi_put" + i));
125 byte[] value = Bytes.toBytes("value_" + i);
126 put.addColumn(FAMILY, QUALIFIER, value);
127 multiput.add(put);
128 }
129
130 try (Table table = TEST_UTIL.getConnection().getTable(TABLE_NAME)) {
131 table.put(multiput);
132 }
133 checkRegionLocationIsCached(TABLE_NAME, TEST_UTIL.getConnection());
134 for (int i = 0; i < 10; i++) {
135 checkExistence(TABLE_NAME, Bytes.toBytes("htable_multi_put" + i), FAMILY, QUALIFIER);
136 }
137 }
138
139
140
141
142
143
144 private void checkRegionLocationIsCached(final TableName tableName, final Connection conn)
145 throws InterruptedException, IOException {
146 for (int count = 0; count < 50; count++) {
147 int number = ((HConnectionImplementation) conn).getNumberOfCachedRegionLocations(tableName);
148 assertNotEquals("Expected non-zero number of cached region locations", 0, number);
149 Thread.sleep(100);
150 }
151 }
152
153
154
155
156 private static void checkExistence(final TableName tableName, final byte[] row,
157 final byte[] family, final byte[] qualifier) throws Exception {
158
159 Result r;
160 Get get = new Get(row);
161 get.addColumn(family, qualifier);
162 int nbTry = 0;
163 try (Table table = TEST_UTIL.getConnection().getTable(tableName)) {
164 do {
165 assertTrue("Failed to get row after " + nbTry + " tries", nbTry < 50);
166 nbTry++;
167 Thread.sleep(100);
168 r = table.get(get);
169 } while (r == null || r.getValue(family, qualifier) == null);
170 }
171 }
172 }