From 353f9226c3ba2637ddf365e53a9eb6862c7cb3af Mon Sep 17 00:00:00 2001 From: zhangduo Date: Sat, 20 Apr 2019 07:55:34 +0800 Subject: [PATCH] HBASE-22236 AsyncNonMetaRegionLocator should not cache HRegionLocation with null location --- .../apache/hadoop/hbase/RegionLocations.java | 17 ++++++++++++++++- .../hbase/client/AsyncNonMetaRegionLocator.java | 4 ++++ .../hbase/client/AsyncRegionLocatorHelper.java | 3 ++- 3 files changed, 22 insertions(+), 2 deletions(-) diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/RegionLocations.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/RegionLocations.java index f98bf03b7926..e119ebbb2fcf 100644 --- a/hbase-client/src/main/java/org/apache/hadoop/hbase/RegionLocations.java +++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/RegionLocations.java @@ -19,7 +19,6 @@ package org.apache.hadoop.hbase; import java.util.Collection; - import org.apache.hadoop.hbase.client.RegionInfo; import org.apache.hadoop.hbase.client.RegionReplicaUtil; import org.apache.hadoop.hbase.util.Bytes; @@ -185,6 +184,22 @@ public RegionLocations remove(int replicaId) { return new RegionLocations(newLocations); } + /** + * Set the element to null if its getServerName method returns null. Returns null if all the + * elements are removed. + */ + public RegionLocations removeElementsWithNullLocation() { + HRegionLocation[] newLocations = new HRegionLocation[locations.length]; + boolean hasNonNullElement = false; + for (int i = 0; i < locations.length; i++) { + if (locations[i] != null && locations[i].getServerName() != null) { + hasNonNullElement = true; + newLocations[i] = locations[i]; + } + } + return hasNonNullElement ? new RegionLocations(newLocations) : null; + } + /** * Merges this RegionLocations list with the given list assuming * same range, and keeping the most up to date version of the diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/client/AsyncNonMetaRegionLocator.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/client/AsyncNonMetaRegionLocator.java index bbb84d04f3a9..069a324fa949 100644 --- a/hbase-client/src/main/java/org/apache/hadoop/hbase/client/AsyncNonMetaRegionLocator.java +++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/client/AsyncNonMetaRegionLocator.java @@ -314,6 +314,10 @@ private boolean onScanNext(TableName tableName, LocateRequest req, Result result LOG.debug("The fetched location of '{}', row='{}', locateType={} is {}", tableName, Bytes.toStringBinary(req.row), req.locateType, locs); } + // remove HRegionLocation with null location, i.e, getServerName returns null. + if (locs != null) { + locs = locs.removeElementsWithNullLocation(); + } // the default region location should always be presented when fetching from meta, otherwise // let's fail the request. diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/client/AsyncRegionLocatorHelper.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/client/AsyncRegionLocatorHelper.java index 2836e4b11e86..5f4bc9f999fa 100644 --- a/hbase-client/src/main/java/org/apache/hadoop/hbase/client/AsyncRegionLocatorHelper.java +++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/client/AsyncRegionLocatorHelper.java @@ -76,7 +76,8 @@ static void updateCachedLocationOnError(HRegionLocation loc, Throwable exception RegionMovedException rme = (RegionMovedException) cause; HRegionLocation newLoc = new HRegionLocation(loc.getRegion(), rme.getServerName(), rme.getLocationSeqNum()); - LOG.debug("Try updating {} with the new location {} constructed by {}", loc, newLoc, rme); + LOG.debug("Try updating {} with the new location {} constructed by {}", loc, newLoc, + rme.toString()); addToCache.accept(newLoc); } else { LOG.debug("Try removing {} from cache", loc);