1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.apache.hadoop.hbase.util;
21
22 import java.io.IOException;
23 import java.util.List;
24
25 import org.apache.hadoop.conf.Configuration;
26 import org.apache.hadoop.hbase.HConstants;
27 import org.apache.hadoop.hbase.HRegionInfo;
28 import org.apache.hadoop.hbase.HServerAddress;
29 import org.apache.hadoop.hbase.NotServingRegionException;
30 import org.apache.hadoop.hbase.ZooKeeperConnectionException;
31 import org.apache.hadoop.hbase.client.HConnectionManager;
32 import org.apache.hadoop.hbase.ipc.HRegionInterface;
33 import org.apache.hadoop.hbase.zookeeper.ZKAssign;
34 import org.apache.zookeeper.KeeperException;
35
36 public class HBaseFsckRepair {
37
38
39
40
41
42
43
44
45
46
47
48
49 public static void fixDupeAssignment(Configuration conf, HRegionInfo region,
50 List<HServerAddress> servers)
51 throws IOException, KeeperException, InterruptedException {
52
53 HRegionInfo actualRegion = new HRegionInfo(region);
54
55
56 for(HServerAddress server : servers) {
57 closeRegionSilentlyAndWait(conf, server, actualRegion);
58 }
59
60
61 forceOfflineInZK(conf, actualRegion);
62 }
63
64
65
66
67
68
69
70
71
72
73 public static void fixUnassigned(Configuration conf, HRegionInfo region)
74 throws IOException, KeeperException {
75 HRegionInfo actualRegion = new HRegionInfo(region);
76
77
78 forceOfflineInZK(conf, actualRegion);
79 }
80
81 private static void forceOfflineInZK(Configuration conf, HRegionInfo region)
82 throws ZooKeeperConnectionException, KeeperException, IOException {
83 ZKAssign.createOrForceNodeOffline(
84 HConnectionManager.getConnection(conf).getZooKeeperWatcher(),
85 region, HConstants.HBCK_CODE_NAME);
86 }
87
88 protected static void closeRegionSilentlyAndWait(Configuration conf,
89 HServerAddress server, HRegionInfo region)
90 throws IOException, InterruptedException {
91 HRegionInterface rs =
92 HConnectionManager.getConnection(conf).getHRegionConnection(server);
93 rs.closeRegion(region, false);
94 long timeout = conf.getLong("hbase.hbck.close.timeout", 120000);
95 long expiration = timeout + System.currentTimeMillis();
96 while (System.currentTimeMillis() < expiration) {
97 try {
98 HRegionInfo rsRegion = rs.getRegionInfo(region.getRegionName());
99 if (rsRegion == null) throw new NotServingRegionException();
100 } catch (Exception e) {
101 return;
102 }
103 Thread.sleep(1000);
104 }
105 throw new IOException("Region " + region + " failed to close within" +
106 " timeout " + timeout);
107 }
108 }