Skip to content

Commit c007ce5

Browse files
committed
HBASE-23281: Track meta region locations in masters (apache#830)
* HBASE-23281: Track meta region changes on masters This patch adds a simple cache that tracks the meta region replica locations. It keeps an eye on the region movements so that the cached locations are not stale. This information is used for servicing client RPCs for connections that use master based registry (HBASE-18095). The RPC end points will be added in a separate patch. Signed-off-by: Nick Dimiduk <ndimiduk@apache.org> (cherry picked from commit 8571d38)
1 parent 6da9f67 commit c007ce5

22 files changed

+585
-82
lines changed

hbase-client/src/main/java/org/apache/hadoop/hbase/shaded/protobuf/ProtobufUtil.java

Lines changed: 41 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/**
1+
/*
22
* Licensed to the Apache Software Foundation (ASF) under one
33
* or more contributor license agreements. See the NOTICE file
44
* distributed with this work for additional information
@@ -80,6 +80,7 @@
8080
import org.apache.hadoop.hbase.client.Put;
8181
import org.apache.hadoop.hbase.client.RegionInfoBuilder;
8282
import org.apache.hadoop.hbase.client.RegionLoadStats;
83+
import org.apache.hadoop.hbase.client.RegionReplicaUtil;
8384
import org.apache.hadoop.hbase.client.RegionStatesCount;
8485
import org.apache.hadoop.hbase.client.Result;
8586
import org.apache.hadoop.hbase.client.Scan;
@@ -93,6 +94,7 @@
9394
import org.apache.hadoop.hbase.filter.ByteArrayComparable;
9495
import org.apache.hadoop.hbase.filter.Filter;
9596
import org.apache.hadoop.hbase.io.TimeRange;
97+
import org.apache.hadoop.hbase.master.RegionState;
9698
import org.apache.hadoop.hbase.protobuf.ProtobufMagic;
9799
import org.apache.hadoop.hbase.protobuf.ProtobufMessageConverter;
98100
import org.apache.hadoop.hbase.quotas.QuotaScope;
@@ -3071,6 +3073,44 @@ public static ProcedureDescription buildProcedureDescription(String signature, S
30713073
return builder.build();
30723074
}
30733075

3076+
/**
3077+
* Get the Meta region state from the passed data bytes. Can handle both old and new style
3078+
* server names.
3079+
* @param data protobuf serialized data with meta server name.
3080+
* @param replicaId replica ID for this region
3081+
* @return RegionState instance corresponding to the serialized data.
3082+
* @throws DeserializationException if the data is invalid.
3083+
*/
3084+
public static RegionState parseMetaRegionStateFrom(final byte[] data, int replicaId)
3085+
throws DeserializationException {
3086+
RegionState.State state = RegionState.State.OPEN;
3087+
ServerName serverName;
3088+
if (data != null && data.length > 0 && ProtobufUtil.isPBMagicPrefix(data)) {
3089+
try {
3090+
int prefixLen = ProtobufUtil.lengthOfPBMagic();
3091+
ZooKeeperProtos.MetaRegionServer rl =
3092+
ZooKeeperProtos.MetaRegionServer.parser().parseFrom(data, prefixLen,
3093+
data.length - prefixLen);
3094+
if (rl.hasState()) {
3095+
state = RegionState.State.convert(rl.getState());
3096+
}
3097+
HBaseProtos.ServerName sn = rl.getServer();
3098+
serverName = ServerName.valueOf(
3099+
sn.getHostName(), sn.getPort(), sn.getStartCode());
3100+
} catch (InvalidProtocolBufferException e) {
3101+
throw new DeserializationException("Unable to parse meta region location");
3102+
}
3103+
} else {
3104+
// old style of meta region location?
3105+
serverName = parseServerNameFrom(data);
3106+
}
3107+
if (serverName == null) {
3108+
state = RegionState.State.OFFLINE;
3109+
}
3110+
return new RegionState(RegionReplicaUtil.getRegionInfoForReplica(
3111+
RegionInfoBuilder.FIRST_META_REGIONINFO, replicaId), state, serverName);
3112+
}
3113+
30743114
/**
30753115
* Get a ServerName from the passed in data bytes.
30763116
* @param data Data with a serialize server name in it; can handle the old style

hbase-client/src/main/java/org/apache/hadoop/hbase/zookeeper/ZNodePaths.java

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,8 @@ public class ZNodePaths {
4141
// TODO: Replace this with ZooKeeper constant when ZOOKEEPER-277 is resolved.
4242
public static final char ZNODE_PATH_SEPARATOR = '/';
4343

44-
private static final String META_ZNODE_PREFIX = "meta-region-server";
44+
public static final String META_ZNODE_PREFIX_CONF_KEY = "zookeeper.znode.metaserver";
45+
public static final String META_ZNODE_PREFIX = "meta-region-server";
4546
private static final String DEFAULT_SNAPSHOT_CLEANUP_ZNODE = "snapshot-cleanup";
4647

4748
// base znode for this cluster
@@ -104,7 +105,7 @@ public class ZNodePaths {
104105
public ZNodePaths(Configuration conf) {
105106
baseZNode = conf.get(ZOOKEEPER_ZNODE_PARENT, DEFAULT_ZOOKEEPER_ZNODE_PARENT);
106107
ImmutableMap.Builder<Integer, String> builder = ImmutableMap.builder();
107-
metaZNodePrefix = conf.get("zookeeper.znode.metaserver", META_ZNODE_PREFIX);
108+
metaZNodePrefix = conf.get(META_ZNODE_PREFIX_CONF_KEY, META_ZNODE_PREFIX);
108109
String defaultMetaReplicaZNode = ZNodePaths.joinZNode(baseZNode, metaZNodePrefix);
109110
builder.put(DEFAULT_REPLICA_ID, defaultMetaReplicaZNode);
110111
int numMetaReplicas = conf.getInt(META_REPLICAS_NUM, DEFAULT_META_REPLICA_NUM);
@@ -189,7 +190,19 @@ public String getZNodeForReplica(int replicaId) {
189190
}
190191

191192
/**
192-
* Parse the meta replicaId from the passed znode name.
193+
* Parses the meta replicaId from the passed path.
194+
* @param path the name of the full path which includes baseZNode.
195+
* @return replicaId
196+
*/
197+
public int getMetaReplicaIdFromPath(String path) {
198+
// Extract the znode from path. The prefix is of the following format.
199+
// baseZNode + PATH_SEPARATOR.
200+
int prefixLen = baseZNode.length() + 1;
201+
return getMetaReplicaIdFromZnode(path.substring(prefixLen));
202+
}
203+
204+
/**
205+
* Parse the meta replicaId from the passed znode
193206
* @param znode the name of the znode, does not include baseZNode
194207
* @return replicaId
195208
*/

hbase-server/src/main/java/org/apache/hadoop/hbase/master/HMaster.java

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
/**
1+
/*
22
* Licensed to the Apache Software Foundation (ASF) under one
33
* or more contributor license agreements. See the NOTICE file
44
* distributed with this work for additional information
@@ -350,6 +350,12 @@ public void run() {
350350
// manager of assignment nodes in zookeeper
351351
private AssignmentManager assignmentManager;
352352

353+
/**
354+
* Cache for the meta region replica's locations. Also tracks their changes to avoid stale
355+
* cache entries.
356+
*/
357+
private final MetaRegionLocationCache metaRegionLocationCache;
358+
353359
// manager of replication
354360
private ReplicationPeerManager replicationPeerManager;
355361

@@ -501,8 +507,7 @@ public void doGet(HttpServletRequest request,
501507
* #finishActiveMasterInitialization(MonitoredTask) after
502508
* the master becomes the active one.
503509
*/
504-
public HMaster(final Configuration conf)
505-
throws IOException, KeeperException {
510+
public HMaster(final Configuration conf) throws IOException {
506511
super(conf);
507512
TraceUtil.initTracer(conf);
508513
try {
@@ -515,7 +520,6 @@ public HMaster(final Configuration conf)
515520
} else {
516521
maintenanceMode = false;
517522
}
518-
519523
this.rsFatals = new MemoryBoundedLogMessageBuffer(
520524
conf.getLong("hbase.master.buffer.for.rs.fatals", 1 * 1024 * 1024));
521525
LOG.info("hbase.rootdir={}, hbase.cluster.distributed={}", getDataRootDir(),
@@ -563,8 +567,10 @@ public HMaster(final Configuration conf)
563567

564568
// Some unit tests don't need a cluster, so no zookeeper at all
565569
if (!conf.getBoolean("hbase.testing.nocluster", false)) {
570+
this.metaRegionLocationCache = new MetaRegionLocationCache(this.zooKeeper);
566571
this.activeMasterManager = new ActiveMasterManager(zooKeeper, this.serverName, this);
567572
} else {
573+
this.metaRegionLocationCache = null;
568574
this.activeMasterManager = null;
569575
}
570576
cachedClusterId = new CachedClusterId(conf);
@@ -3790,4 +3796,8 @@ public String getClusterId() {
37903796
}
37913797
return cachedClusterId.getFromCacheOrFetch();
37923798
}
3799+
3800+
public MetaRegionLocationCache getMetaRegionLocationCache() {
3801+
return this.metaRegionLocationCache;
3802+
}
37933803
}

0 commit comments

Comments
 (0)