HBASE-21723 Remove ConnectionImplementation and related classes
[hbase.git] / hbase-server / src / test / java / org / apache / hadoop / hbase / client / TestAdmin2.java
blob769295497b4890ad97541bec9928a7d29fa6e4e7
1 /**
2 * Licensed to the Apache Software Foundation (ASF) under one
3 * or more contributor license agreements. See the NOTICE file
4 * distributed with this work for additional information
5 * regarding copyright ownership. The ASF licenses this file
6 * to you under the Apache License, Version 2.0 (the
7 * "License"); you may not use this file except in compliance
8 * with the License. You may obtain a copy of the License at
10 * http://www.apache.org/licenses/LICENSE-2.0
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
18 package org.apache.hadoop.hbase.client;
20 import static org.junit.Assert.assertEquals;
21 import static org.junit.Assert.assertFalse;
22 import static org.junit.Assert.assertTrue;
23 import static org.junit.Assert.fail;
25 import java.io.IOException;
26 import java.util.ArrayList;
27 import java.util.EnumSet;
28 import java.util.HashMap;
29 import java.util.List;
30 import java.util.Random;
31 import java.util.concurrent.atomic.AtomicInteger;
32 import java.util.stream.Collectors;
33 import org.apache.hadoop.hbase.ClusterMetrics.Option;
34 import org.apache.hadoop.hbase.HBaseClassTestRule;
35 import org.apache.hadoop.hbase.HColumnDescriptor;
36 import org.apache.hadoop.hbase.HConstants;
37 import org.apache.hadoop.hbase.HTableDescriptor;
38 import org.apache.hadoop.hbase.MiniHBaseCluster;
39 import org.apache.hadoop.hbase.ServerName;
40 import org.apache.hadoop.hbase.TableExistsException;
41 import org.apache.hadoop.hbase.TableName;
42 import org.apache.hadoop.hbase.TableNotDisabledException;
43 import org.apache.hadoop.hbase.TableNotEnabledException;
44 import org.apache.hadoop.hbase.TableNotFoundException;
45 import org.apache.hadoop.hbase.UnknownRegionException;
46 import org.apache.hadoop.hbase.Waiter.Predicate;
47 import org.apache.hadoop.hbase.constraint.ConstraintException;
48 import org.apache.hadoop.hbase.master.HMaster;
49 import org.apache.hadoop.hbase.master.assignment.AssignmentManager;
50 import org.apache.hadoop.hbase.regionserver.HRegion;
51 import org.apache.hadoop.hbase.regionserver.HRegionServer;
52 import org.apache.hadoop.hbase.regionserver.HStore;
53 import org.apache.hadoop.hbase.testclassification.ClientTests;
54 import org.apache.hadoop.hbase.testclassification.LargeTests;
55 import org.apache.hadoop.hbase.util.Bytes;
56 import org.apache.hadoop.hbase.wal.AbstractFSWALProvider;
57 import org.junit.Assert;
58 import org.junit.ClassRule;
59 import org.junit.Test;
60 import org.junit.experimental.categories.Category;
61 import org.slf4j.Logger;
62 import org.slf4j.LoggerFactory;
64 import org.apache.hadoop.hbase.shaded.protobuf.ProtobufUtil;
65 import org.apache.hadoop.hbase.shaded.protobuf.RequestConverter;
67 /**
68 * Class to test HBaseAdmin.
69 * Spins up the minicluster once at test start and then takes it down afterward.
70 * Add any testing of HBaseAdmin functionality here.
72 @Category({LargeTests.class, ClientTests.class})
73 public class TestAdmin2 extends TestAdminBase {
75 @ClassRule
76 public static final HBaseClassTestRule CLASS_RULE =
77 HBaseClassTestRule.forClass(TestAdmin2.class);
79 private static final Logger LOG = LoggerFactory.getLogger(TestAdmin2.class);
81 @Test
82 public void testCreateBadTables() throws IOException {
83 String msg = null;
84 try {
85 ADMIN.createTable(new HTableDescriptor(TableName.META_TABLE_NAME));
86 } catch(TableExistsException e) {
87 msg = e.toString();
89 assertTrue("Unexcepted exception message " + msg, msg != null &&
90 msg.startsWith(TableExistsException.class.getName()) &&
91 msg.contains(TableName.META_TABLE_NAME.getNameAsString()));
93 // Now try and do concurrent creation with a bunch of threads.
94 final HTableDescriptor threadDesc = new HTableDescriptor(TableName.valueOf(name.getMethodName()));
95 threadDesc.addFamily(new HColumnDescriptor(HConstants.CATALOG_FAMILY));
96 int count = 10;
97 Thread [] threads = new Thread [count];
98 final AtomicInteger successes = new AtomicInteger(0);
99 final AtomicInteger failures = new AtomicInteger(0);
100 final Admin localAdmin = ADMIN;
101 for (int i = 0; i < count; i++) {
102 threads[i] = new Thread(Integer.toString(i)) {
103 @Override
104 public void run() {
105 try {
106 localAdmin.createTable(threadDesc);
107 successes.incrementAndGet();
108 } catch (TableExistsException e) {
109 failures.incrementAndGet();
110 } catch (IOException e) {
111 throw new RuntimeException("Failed threaded create" + getName(), e);
116 for (int i = 0; i < count; i++) {
117 threads[i].start();
119 for (int i = 0; i < count; i++) {
120 while(threads[i].isAlive()) {
121 try {
122 Thread.sleep(100);
123 } catch (InterruptedException e) {
124 // continue
128 // All threads are now dead. Count up how many tables were created and
129 // how many failed w/ appropriate exception.
130 assertEquals(1, successes.get());
131 assertEquals(count - 1, failures.get());
135 * Test for hadoop-1581 'HBASE: Unopenable tablename bug'.
136 * @throws Exception
138 @Test
139 public void testTableNameClash() throws Exception {
140 final String name = this.name.getMethodName();
141 HTableDescriptor htd1 = new HTableDescriptor(TableName.valueOf(name + "SOMEUPPERCASE"));
142 HTableDescriptor htd2 = new HTableDescriptor(TableName.valueOf(name));
143 htd1.addFamily(new HColumnDescriptor(HConstants.CATALOG_FAMILY));
144 htd2.addFamily(new HColumnDescriptor(HConstants.CATALOG_FAMILY));
145 ADMIN.createTable(htd1);
146 ADMIN.createTable(htd2);
147 // Before fix, below would fail throwing a NoServerForRegionException.
148 TEST_UTIL.getConnection().getTable(htd2.getTableName()).close();
151 /***
152 * HMaster.createTable used to be kind of synchronous call
153 * Thus creating of table with lots of regions can cause RPC timeout
154 * After the fix to make createTable truly async, RPC timeout shouldn't be an
155 * issue anymore
157 @Test
158 public void testCreateTableRPCTimeOut() throws Exception {
159 final String name = this.name.getMethodName();
160 int oldTimeout = TEST_UTIL.getConfiguration().
161 getInt(HConstants.HBASE_RPC_TIMEOUT_KEY, HConstants.DEFAULT_HBASE_RPC_TIMEOUT);
162 TEST_UTIL.getConfiguration().setInt(HConstants.HBASE_RPC_TIMEOUT_KEY, 1500);
163 try {
164 int expectedRegions = 100;
165 // Use 80 bit numbers to make sure we aren't limited
166 byte [] startKey = { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 };
167 byte [] endKey = { 9, 9, 9, 9, 9, 9, 9, 9, 9, 9 };
168 Admin hbaseadmin = TEST_UTIL.getAdmin();
169 HTableDescriptor htd = new HTableDescriptor(TableName.valueOf(name));
170 htd.addFamily(new HColumnDescriptor(HConstants.CATALOG_FAMILY));
171 hbaseadmin.createTable(htd, startKey, endKey, expectedRegions);
172 } finally {
173 TEST_UTIL.getConfiguration().setInt(HConstants.HBASE_RPC_TIMEOUT_KEY, oldTimeout);
178 * Test read only tables
179 * @throws Exception
181 @Test
182 public void testReadOnlyTable() throws Exception {
183 final TableName name = TableName.valueOf(this.name.getMethodName());
184 Table table = TEST_UTIL.createTable(name, HConstants.CATALOG_FAMILY);
185 byte[] value = Bytes.toBytes("somedata");
186 // This used to use an empty row... That must have been a bug
187 Put put = new Put(value);
188 put.addColumn(HConstants.CATALOG_FAMILY, HConstants.CATALOG_FAMILY, value);
189 table.put(put);
190 table.close();
194 * Test that user table names can contain '-' and '.' so long as they do not
195 * start with same. HBASE-771
197 @Test
198 public void testTableNames() throws IOException {
199 byte[][] illegalNames = new byte[][] {
200 Bytes.toBytes("-bad"),
201 Bytes.toBytes(".bad")
203 for (byte[] illegalName : illegalNames) {
204 try {
205 new HTableDescriptor(TableName.valueOf(illegalName));
206 throw new IOException("Did not detect '" +
207 Bytes.toString(illegalName) + "' as an illegal user table name");
208 } catch (IllegalArgumentException e) {
209 // expected
212 byte[] legalName = Bytes.toBytes("g-oo.d");
213 try {
214 new HTableDescriptor(TableName.valueOf(legalName));
215 } catch (IllegalArgumentException e) {
216 throw new IOException("Legal user table name: '" +
217 Bytes.toString(legalName) + "' caused IllegalArgumentException: " +
218 e.getMessage());
223 * For HADOOP-2579
225 @Test (expected=TableExistsException.class)
226 public void testTableExistsExceptionWithATable() throws IOException {
227 final TableName name = TableName.valueOf(this.name.getMethodName());
228 TEST_UTIL.createTable(name, HConstants.CATALOG_FAMILY).close();
229 TEST_UTIL.createTable(name, HConstants.CATALOG_FAMILY);
233 * Can't disable a table if the table isn't in enabled state
235 @Test (expected=TableNotEnabledException.class)
236 public void testTableNotEnabledExceptionWithATable() throws IOException {
237 final TableName name = TableName.valueOf(this.name.getMethodName());
238 TEST_UTIL.createTable(name, HConstants.CATALOG_FAMILY).close();
239 ADMIN.disableTable(name);
240 ADMIN.disableTable(name);
244 * Can't enable a table if the table isn't in disabled state
246 @Test(expected = TableNotDisabledException.class)
247 public void testTableNotDisabledExceptionWithATable() throws IOException {
248 final TableName name = TableName.valueOf(this.name.getMethodName());
249 try (Table t = TEST_UTIL.createTable(name, HConstants.CATALOG_FAMILY)) {
250 ADMIN.enableTable(name);
255 * For HADOOP-2579
257 @Test(expected = TableNotFoundException.class)
258 public void testTableNotFoundExceptionWithoutAnyTables() throws IOException {
259 TableName tableName = TableName.valueOf("testTableNotFoundExceptionWithoutAnyTables");
260 try (Table ht = TEST_UTIL.getConnection().getTable(tableName)) {
261 ht.get(new Get(Bytes.toBytes("e")));
265 @Test
266 public void testShouldUnassignTheRegion() throws Exception {
267 final TableName tableName = TableName.valueOf(name.getMethodName());
268 createTableWithDefaultConf(tableName);
270 RegionInfo info = null;
271 HRegionServer rs = TEST_UTIL.getRSForFirstRegionInTable(tableName);
272 List<RegionInfo> onlineRegions = ProtobufUtil.getOnlineRegions(rs.getRSRpcServices());
273 for (RegionInfo regionInfo : onlineRegions) {
274 if (!regionInfo.getTable().isSystemTable()) {
275 info = regionInfo;
276 ADMIN.unassign(regionInfo.getRegionName(), true);
279 boolean isInList = ProtobufUtil.getOnlineRegions(
280 rs.getRSRpcServices()).contains(info);
281 long timeout = System.currentTimeMillis() + 10000;
282 while ((System.currentTimeMillis() < timeout) && (isInList)) {
283 Thread.sleep(100);
284 isInList = ProtobufUtil.getOnlineRegions(
285 rs.getRSRpcServices()).contains(info);
288 assertFalse("The region should not be present in online regions list.",
289 isInList);
292 @Test
293 public void testCloseRegionIfInvalidRegionNameIsPassed() throws Exception {
294 final String name = this.name.getMethodName();
295 byte[] tableName = Bytes.toBytes(name);
296 createTableWithDefaultConf(tableName);
298 RegionInfo info = null;
299 HRegionServer rs = TEST_UTIL.getRSForFirstRegionInTable(TableName.valueOf(tableName));
300 List<RegionInfo> onlineRegions = ProtobufUtil.getOnlineRegions(rs.getRSRpcServices());
301 for (RegionInfo regionInfo : onlineRegions) {
302 if (!regionInfo.isMetaRegion()) {
303 if (regionInfo.getRegionNameAsString().contains(name)) {
304 info = regionInfo;
305 try {
306 ADMIN.unassign(Bytes.toBytes("sample"), true);
307 } catch (UnknownRegionException nsre) {
308 // expected, ignore it
313 onlineRegions = ProtobufUtil.getOnlineRegions(rs.getRSRpcServices());
314 assertTrue("The region should be present in online regions list.",
315 onlineRegions.contains(info));
318 @Test
319 public void testCloseRegionThatFetchesTheHRIFromMeta() throws Exception {
320 final TableName tableName = TableName.valueOf(name.getMethodName());
321 createTableWithDefaultConf(tableName);
323 RegionInfo info = null;
324 HRegionServer rs = TEST_UTIL.getRSForFirstRegionInTable(tableName);
325 List<RegionInfo> onlineRegions = ProtobufUtil.getOnlineRegions(rs.getRSRpcServices());
326 for (RegionInfo regionInfo : onlineRegions) {
327 if (!regionInfo.isMetaRegion()) {
328 if (regionInfo.getRegionNameAsString().contains("TestHBACloseRegion2")) {
329 info = regionInfo;
330 ADMIN.unassign(regionInfo.getRegionName(), true);
335 boolean isInList = ProtobufUtil.getOnlineRegions(
336 rs.getRSRpcServices()).contains(info);
337 long timeout = System.currentTimeMillis() + 10000;
338 while ((System.currentTimeMillis() < timeout) && (isInList)) {
339 Thread.sleep(100);
340 isInList = ProtobufUtil.getOnlineRegions(
341 rs.getRSRpcServices()).contains(info);
344 assertFalse("The region should not be present in online regions list.",
345 isInList);
348 private Admin createTable(TableName tableName) throws IOException {
349 Admin admin = TEST_UTIL.getAdmin();
351 HTableDescriptor htd = new HTableDescriptor(tableName);
352 HColumnDescriptor hcd = new HColumnDescriptor("value");
354 htd.addFamily(hcd);
355 admin.createTable(htd);
356 return admin;
359 private void createTableWithDefaultConf(byte[] TABLENAME) throws IOException {
360 createTableWithDefaultConf(TableName.valueOf(TABLENAME));
363 private void createTableWithDefaultConf(TableName TABLENAME) throws IOException {
364 HTableDescriptor htd = new HTableDescriptor(TABLENAME);
365 HColumnDescriptor hcd = new HColumnDescriptor("value");
366 htd.addFamily(hcd);
368 ADMIN.createTable(htd);
372 * For HBASE-2556
374 @Test
375 public void testGetTableRegions() throws IOException {
376 final TableName tableName = TableName.valueOf(name.getMethodName());
378 int expectedRegions = 10;
380 // Use 80 bit numbers to make sure we aren't limited
381 byte [] startKey = { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 };
382 byte [] endKey = { 9, 9, 9, 9, 9, 9, 9, 9, 9, 9 };
385 HTableDescriptor desc = new HTableDescriptor(tableName);
386 desc.addFamily(new HColumnDescriptor(HConstants.CATALOG_FAMILY));
387 ADMIN.createTable(desc, startKey, endKey, expectedRegions);
389 List<RegionInfo> RegionInfos = ADMIN.getRegions(tableName);
391 assertEquals("Tried to create " + expectedRegions + " regions " +
392 "but only found " + RegionInfos.size(),
393 expectedRegions, RegionInfos.size());
396 @Test
397 public void testMoveToPreviouslyAssignedRS() throws IOException, InterruptedException {
398 MiniHBaseCluster cluster = TEST_UTIL.getHBaseCluster();
399 HMaster master = cluster.getMaster();
400 final TableName tableName = TableName.valueOf(name.getMethodName());
401 Admin localAdmin = createTable(tableName);
402 List<RegionInfo> tableRegions = localAdmin.getRegions(tableName);
403 RegionInfo hri = tableRegions.get(0);
404 AssignmentManager am = master.getAssignmentManager();
405 ServerName server = am.getRegionStates().getRegionServerOfRegion(hri);
406 localAdmin.move(hri.getEncodedNameAsBytes(), server);
407 assertEquals("Current region server and region server before move should be same.", server,
408 am.getRegionStates().getRegionServerOfRegion(hri));
411 @Test
412 public void testWALRollWriting() throws Exception {
413 setUpforLogRolling();
414 String className = this.getClass().getName();
415 StringBuilder v = new StringBuilder(className);
416 while (v.length() < 1000) {
417 v.append(className);
419 byte[] value = Bytes.toBytes(v.toString());
420 HRegionServer regionServer = startAndWriteData(TableName.valueOf(name.getMethodName()), value);
421 LOG.info("after writing there are "
422 + AbstractFSWALProvider.getNumRolledLogFiles(regionServer.getWAL(null)) + " log files");
424 // flush all regions
425 for (HRegion r : regionServer.getOnlineRegionsLocalContext()) {
426 r.flush(true);
428 ADMIN.rollWALWriter(regionServer.getServerName());
429 int count = AbstractFSWALProvider.getNumRolledLogFiles(regionServer.getWAL(null));
430 LOG.info("after flushing all regions and rolling logs there are " +
431 count + " log files");
432 assertTrue(("actual count: " + count), count <= 2);
435 private void setUpforLogRolling() {
436 // Force a region split after every 768KB
437 TEST_UTIL.getConfiguration().setLong(HConstants.HREGION_MAX_FILESIZE,
438 768L * 1024L);
440 // We roll the log after every 32 writes
441 TEST_UTIL.getConfiguration().setInt("hbase.regionserver.maxlogentries", 32);
443 TEST_UTIL.getConfiguration().setInt(
444 "hbase.regionserver.logroll.errors.tolerated", 2);
445 TEST_UTIL.getConfiguration().setInt("hbase.rpc.timeout", 10 * 1000);
447 // For less frequently updated regions flush after every 2 flushes
448 TEST_UTIL.getConfiguration().setInt(
449 "hbase.hregion.memstore.optionalflushcount", 2);
451 // We flush the cache after every 8192 bytes
452 TEST_UTIL.getConfiguration().setInt(HConstants.HREGION_MEMSTORE_FLUSH_SIZE,
453 8192);
455 // Increase the amount of time between client retries
456 TEST_UTIL.getConfiguration().setLong("hbase.client.pause", 10 * 1000);
458 // Reduce thread wake frequency so that other threads can get
459 // a chance to run.
460 TEST_UTIL.getConfiguration().setInt(HConstants.THREAD_WAKE_FREQUENCY,
461 2 * 1000);
463 /**** configuration for testLogRollOnDatanodeDeath ****/
464 // lower the namenode & datanode heartbeat so the namenode
465 // quickly detects datanode failures
466 TEST_UTIL.getConfiguration().setInt("dfs.namenode.heartbeat.recheck-interval", 5000);
467 TEST_UTIL.getConfiguration().setInt("dfs.heartbeat.interval", 1);
468 // the namenode might still try to choose the recently-dead datanode
469 // for a pipeline, so try to a new pipeline multiple times
470 TEST_UTIL.getConfiguration().setInt("dfs.client.block.write.retries", 30);
471 TEST_UTIL.getConfiguration().setInt(
472 "hbase.regionserver.hlog.tolerable.lowreplication", 2);
473 TEST_UTIL.getConfiguration().setInt(
474 "hbase.regionserver.hlog.lowreplication.rolllimit", 3);
477 private HRegionServer startAndWriteData(TableName tableName, byte[] value)
478 throws IOException, InterruptedException {
479 // When the hbase:meta table can be opened, the region servers are running
480 TEST_UTIL.getConnection().getTable(TableName.META_TABLE_NAME).close();
482 // Create the test table and open it
483 HTableDescriptor desc = new HTableDescriptor(tableName);
484 desc.addFamily(new HColumnDescriptor(HConstants.CATALOG_FAMILY));
485 ADMIN.createTable(desc);
486 Table table = TEST_UTIL.getConnection().getTable(tableName);
488 HRegionServer regionServer = TEST_UTIL.getRSForFirstRegionInTable(tableName);
489 for (int i = 1; i <= 256; i++) { // 256 writes should cause 8 log rolls
490 Put put = new Put(Bytes.toBytes("row" + String.format("%1$04d", i)));
491 put.addColumn(HConstants.CATALOG_FAMILY, null, value);
492 table.put(put);
493 if (i % 32 == 0) {
494 // After every 32 writes sleep to let the log roller run
495 try {
496 Thread.sleep(2000);
497 } catch (InterruptedException e) {
498 // continue
503 table.close();
504 return regionServer;
507 @Test
508 public void testDisableCatalogTable() throws Exception {
509 try {
510 ADMIN.disableTable(TableName.META_TABLE_NAME);
511 fail("Expected to throw ConstraintException");
512 } catch (ConstraintException e) {
514 // Before the fix for HBASE-6146, the below table creation was failing as the hbase:meta table
515 // actually getting disabled by the disableTable() call.
516 HTableDescriptor htd =
517 new HTableDescriptor(TableName.valueOf(Bytes.toBytes(name.getMethodName())));
518 HColumnDescriptor hcd = new HColumnDescriptor(Bytes.toBytes("cf1"));
519 htd.addFamily(hcd);
520 TEST_UTIL.getAdmin().createTable(htd);
523 @Test
524 public void testIsEnabledOrDisabledOnUnknownTable() throws Exception {
525 try {
526 ADMIN.isTableEnabled(TableName.valueOf(name.getMethodName()));
527 fail("Test should fail if isTableEnabled called on unknown table.");
528 } catch (IOException e) {
531 try {
532 ADMIN.isTableDisabled(TableName.valueOf(name.getMethodName()));
533 fail("Test should fail if isTableDisabled called on unknown table.");
534 } catch (IOException e) {
538 @Test
539 public void testBalancer() throws Exception {
540 boolean initialState = ADMIN.isBalancerEnabled();
542 // Start the balancer, wait for it.
543 boolean prevState = ADMIN.balancerSwitch(!initialState, true);
545 // The previous state should be the original state we observed
546 assertEquals(initialState, prevState);
548 // Current state should be opposite of the original
549 assertEquals(!initialState, ADMIN.isBalancerEnabled());
551 // Reset it back to what it was
552 prevState = ADMIN.balancerSwitch(initialState, true);
554 // The previous state should be the opposite of the initial state
555 assertEquals(!initialState, prevState);
556 // Current state should be the original state again
557 assertEquals(initialState, ADMIN.isBalancerEnabled());
560 @Test
561 public void testRegionNormalizer() throws Exception {
562 boolean initialState = ADMIN.isNormalizerEnabled();
564 // flip state
565 boolean prevState = ADMIN.normalizerSwitch(!initialState);
567 // The previous state should be the original state we observed
568 assertEquals(initialState, prevState);
570 // Current state should be opposite of the original
571 assertEquals(!initialState, ADMIN.isNormalizerEnabled());
573 // Reset it back to what it was
574 prevState = ADMIN.normalizerSwitch(initialState);
576 // The previous state should be the opposite of the initial state
577 assertEquals(!initialState, prevState);
578 // Current state should be the original state again
579 assertEquals(initialState, ADMIN.isNormalizerEnabled());
582 @Test
583 public void testAbortProcedureFail() throws Exception {
584 Random randomGenerator = new Random();
585 long procId = randomGenerator.nextLong();
587 boolean abortResult = ADMIN.abortProcedure(procId, true);
588 assertFalse(abortResult);
591 @Test
592 public void testGetProcedures() throws Exception {
593 String procList = ADMIN.getProcedures();
594 assertTrue(procList.startsWith("["));
597 @Test
598 public void testGetLocks() throws Exception {
599 String lockList = ADMIN.getLocks();
600 assertTrue(lockList.startsWith("["));
603 @Test
604 public void testDecommissionRegionServers() throws Exception {
605 List<ServerName> decommissionedRegionServers = ADMIN.listDecommissionedRegionServers();
606 assertTrue(decommissionedRegionServers.isEmpty());
608 final TableName tableName = TableName.valueOf(name.getMethodName());
609 TEST_UTIL.createMultiRegionTable(tableName, Bytes.toBytes("f"), 6);
611 ArrayList<ServerName> clusterRegionServers =
612 new ArrayList<>(ADMIN.getClusterMetrics(EnumSet.of(Option.LIVE_SERVERS))
613 .getLiveServerMetrics().keySet());
615 assertEquals(3, clusterRegionServers.size());
617 HashMap<ServerName, List<RegionInfo>> serversToDecommssion = new HashMap<>();
618 // Get a server that has meta online. We will decommission two of the servers,
619 // leaving one online.
620 int i;
621 for (i = 0; i < clusterRegionServers.size(); i++) {
622 List<RegionInfo> regionsOnServer = ADMIN.getRegions(clusterRegionServers.get(i));
623 if (ADMIN.getRegions(clusterRegionServers.get(i)).stream().anyMatch(p -> p.isMetaRegion())) {
624 serversToDecommssion.put(clusterRegionServers.get(i), regionsOnServer);
625 break;
629 clusterRegionServers.remove(i);
630 // Get another server to decommission.
631 serversToDecommssion.put(clusterRegionServers.get(0),
632 ADMIN.getRegions(clusterRegionServers.get(0)));
634 ServerName remainingServer = clusterRegionServers.get(1);
636 // Decommission
637 ADMIN.decommissionRegionServers(new ArrayList<ServerName>(serversToDecommssion.keySet()), true);
638 assertEquals(2, ADMIN.listDecommissionedRegionServers().size());
640 // Verify the regions have been off the decommissioned servers, all on the one
641 // remaining server.
642 for (ServerName server : serversToDecommssion.keySet()) {
643 for (RegionInfo region : serversToDecommssion.get(server)) {
644 TEST_UTIL.assertRegionOnServer(region, remainingServer, 10000);
648 // Recommission and load the regions.
649 for (ServerName server : serversToDecommssion.keySet()) {
650 List<byte[]> encodedRegionNames = serversToDecommssion.get(server).stream()
651 .map(region -> region.getEncodedNameAsBytes()).collect(Collectors.toList());
652 ADMIN.recommissionRegionServer(server, encodedRegionNames);
654 assertTrue(ADMIN.listDecommissionedRegionServers().isEmpty());
655 // Verify the regions have been moved to the recommissioned servers
656 for (ServerName server : serversToDecommssion.keySet()) {
657 for (RegionInfo region : serversToDecommssion.get(server)) {
658 TEST_UTIL.assertRegionOnServer(region, server, 10000);
664 * TestCase for HBASE-21355
666 @Test
667 public void testGetRegionInfo() throws Exception {
668 final TableName tableName = TableName.valueOf(name.getMethodName());
669 Table table = TEST_UTIL.createTable(tableName, Bytes.toBytes("f"));
670 for (int i = 0; i < 100; i++) {
671 table.put(new Put(Bytes.toBytes(i)).addColumn(Bytes.toBytes("f"), Bytes.toBytes("q"),
672 Bytes.toBytes(i)));
674 ADMIN.flush(tableName);
676 HRegionServer rs = TEST_UTIL.getRSForFirstRegionInTable(table.getName());
677 List<HRegion> regions = rs.getRegions(tableName);
678 Assert.assertEquals(1, regions.size());
680 HRegion region = regions.get(0);
681 byte[] regionName = region.getRegionInfo().getRegionName();
682 HStore store = region.getStore(Bytes.toBytes("f"));
683 long expectedStoreFilesSize = store.getStorefilesSize();
684 Assert.assertNotNull(store);
685 Assert.assertEquals(expectedStoreFilesSize, store.getSize());
686 for (int i = 0; i < 10; i++) {
687 RegionInfo ri = ProtobufUtil
688 .toRegionInfo(TEST_UTIL.getAsyncConnection().getRegionServerAdmin(rs.getServerName())
689 .getRegionInfo(RequestConverter.buildGetRegionInfoRequest(regionName)).get()
690 .getRegionInfo());
692 Assert.assertEquals(region.getRegionInfo(), ri);
694 // Make sure that the store size is still the actual file system's store size.
695 Assert.assertEquals(expectedStoreFilesSize, store.getSize());
699 @Test
700 public void testTableSplitFollowedByModify() throws Exception {
701 final TableName tableName = TableName.valueOf(name.getMethodName());
702 TEST_UTIL.createTable(tableName, Bytes.toBytes("f"));
704 // get the original table region count
705 List<RegionInfo> regions = ADMIN.getRegions(tableName);
706 int originalCount = regions.size();
707 assertEquals(1, originalCount);
709 // split the table and wait until region count increases
710 ADMIN.split(tableName, Bytes.toBytes(3));
711 TEST_UTIL.waitFor(30000, new Predicate<Exception>() {
713 @Override
714 public boolean evaluate() throws Exception {
715 return ADMIN.getRegions(tableName).size() > originalCount;
719 // do some table modification
720 TableDescriptor tableDesc = TableDescriptorBuilder.newBuilder(ADMIN.getDescriptor(tableName))
721 .setMaxFileSize(11111111)
722 .build();
723 ADMIN.modifyTable(tableDesc);
724 assertEquals(11111111, ADMIN.getDescriptor(tableName).getMaxFileSize());
727 @Test
728 public void testTableMergeFollowedByModify() throws Exception {
729 final TableName tableName = TableName.valueOf(name.getMethodName());
730 TEST_UTIL.createTable(tableName, new byte[][] { Bytes.toBytes("f") },
731 new byte[][] { Bytes.toBytes(3) });
733 // assert we have at least 2 regions in the table
734 List<RegionInfo> regions = ADMIN.getRegions(tableName);
735 int originalCount = regions.size();
736 assertTrue(originalCount >= 2);
738 byte[] nameOfRegionA = regions.get(0).getEncodedNameAsBytes();
739 byte[] nameOfRegionB = regions.get(1).getEncodedNameAsBytes();
741 // merge the table regions and wait until region count decreases
742 ADMIN.mergeRegionsAsync(nameOfRegionA, nameOfRegionB, true);
743 TEST_UTIL.waitFor(30000, new Predicate<Exception>() {
745 @Override
746 public boolean evaluate() throws Exception {
747 return ADMIN.getRegions(tableName).size() < originalCount;
751 // do some table modification
752 TableDescriptor tableDesc = TableDescriptorBuilder.newBuilder(ADMIN.getDescriptor(tableName))
753 .setMaxFileSize(11111111)
754 .build();
755 ADMIN.modifyTable(tableDesc);
756 assertEquals(11111111, ADMIN.getDescriptor(tableName).getMaxFileSize());