hbase-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From t...@apache.org
Subject svn commit: r956689 - in /hbase/trunk: CHANGES.txt src/main/java/org/apache/hadoop/hbase/client/MetaScanner.java src/test/java/org/apache/hadoop/hbase/client/TestMetaScanner.java
Date Mon, 21 Jun 2010 20:52:32 GMT
Author: todd
Date: Mon Jun 21 20:52:31 2010
New Revision: 956689

URL: http://svn.apache.org/viewvc?rev=956689&view=rev
Log:
HBASE-2760. Fix MetaScanner TableNotFoundException when scanning starting at the first row
in a table.


Added:
    hbase/trunk/src/test/java/org/apache/hadoop/hbase/client/TestMetaScanner.java
Modified:
    hbase/trunk/CHANGES.txt
    hbase/trunk/src/main/java/org/apache/hadoop/hbase/client/MetaScanner.java

Modified: hbase/trunk/CHANGES.txt
URL: http://svn.apache.org/viewvc/hbase/trunk/CHANGES.txt?rev=956689&r1=956688&r2=956689&view=diff
==============================================================================
--- hbase/trunk/CHANGES.txt (original)
+++ hbase/trunk/CHANGES.txt Mon Jun 21 20:52:31 2010
@@ -400,6 +400,8 @@ Release 0.21.0 - Unreleased
    HBASE-2756  MetaScanner.metaScan doesn't take configurations
    HBASE-2656  HMaster.getRegionTableClosest should not return null for closed
                regions
+   HBASE-2760  Fix MetaScanner TableNotFoundException when scanning starting at
+               the first row in a table.
 
   IMPROVEMENTS
    HBASE-1760  Cleanup TODOs in HTable

Modified: hbase/trunk/src/main/java/org/apache/hadoop/hbase/client/MetaScanner.java
URL: http://svn.apache.org/viewvc/hbase/trunk/src/main/java/org/apache/hadoop/hbase/client/MetaScanner.java?rev=956689&r1=956688&r2=956689&view=diff
==============================================================================
--- hbase/trunk/src/main/java/org/apache/hadoop/hbase/client/MetaScanner.java (original)
+++ hbase/trunk/src/main/java/org/apache/hadoop/hbase/client/MetaScanner.java Mon Jun 21 20:52:31
2010
@@ -89,32 +89,41 @@ public class MetaScanner {
     int rowUpperLimit = rowLimit > 0 ? rowLimit: Integer.MAX_VALUE;
 
     HConnection connection = HConnectionManager.getConnection(configuration);
-    byte [] startRow = tableName == null || tableName.length == 0 ?
-        HConstants.EMPTY_START_ROW :
-          HRegionInfo.createRegionName(tableName, row, HConstants.ZEROES,
-              false);
-
     // if row is not null, we want to use the startKey of the row's region as
     // the startRow for the meta scan.
+    byte[] startRow;
     if (row != null) {
+      // Scan starting at a particular row in a particular table
+      assert tableName != null;
+      byte[] searchRow =
+        HRegionInfo.createRegionName(tableName, row, HConstants.NINES,
+          false);
+
       HTable metaTable = new HTable(configuration, HConstants.META_TABLE_NAME);
-      Result startRowResult = metaTable.getRowOrBefore(startRow,
+      Result startRowResult = metaTable.getRowOrBefore(searchRow,
           HConstants.CATALOG_FAMILY);
       if (startRowResult == null) {
         throw new TableNotFoundException("Cannot find row in .META. for table: "
-            + Bytes.toString(tableName) + ", row=" + Bytes.toString(startRow));
+            + Bytes.toString(tableName) + ", row=" + Bytes.toString(searchRow));
       }
       byte[] value = startRowResult.getValue(HConstants.CATALOG_FAMILY,
           HConstants.REGIONINFO_QUALIFIER);
       if (value == null || value.length == 0) {
         throw new IOException("HRegionInfo was null or empty in Meta for " +
-          Bytes.toString(tableName) + ", row=" + Bytes.toString(startRow));
+          Bytes.toString(tableName) + ", row=" + Bytes.toString(searchRow));
       }
       HRegionInfo regionInfo = Writables.getHRegionInfo(value);
 
       byte[] rowBefore = regionInfo.getStartKey();
       startRow = HRegionInfo.createRegionName(tableName, rowBefore,
           HConstants.ZEROES, false);
+    } else if (tableName == null || tableName.length == 0) {
+      // Full META scan
+      startRow = HConstants.EMPTY_START_ROW;
+    } else {
+      // Scan META for an entire table
+      startRow = HRegionInfo.createRegionName(
+          tableName, HConstants.EMPTY_START_ROW, HConstants.ZEROES, false);
     }
 
     // Scan over each meta region

Added: hbase/trunk/src/test/java/org/apache/hadoop/hbase/client/TestMetaScanner.java
URL: http://svn.apache.org/viewvc/hbase/trunk/src/test/java/org/apache/hadoop/hbase/client/TestMetaScanner.java?rev=956689&view=auto
==============================================================================
--- hbase/trunk/src/test/java/org/apache/hadoop/hbase/client/TestMetaScanner.java (added)
+++ hbase/trunk/src/test/java/org/apache/hadoop/hbase/client/TestMetaScanner.java Mon Jun
21 20:52:31 2010
@@ -0,0 +1,96 @@
+/**
+ * Copyright 2010 The Apache Software Foundation
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.hadoop.hbase.client;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.hadoop.conf.Configuration;
+import org.apache.hadoop.hbase.HBaseTestingUtility;
+import org.apache.hadoop.hbase.HConstants;
+import org.apache.hadoop.hbase.util.Bytes;
+import org.junit.AfterClass;
+import org.junit.BeforeClass;
+import org.junit.Test;
+
+import static org.mockito.Mockito.*;
+
+public class TestMetaScanner {
+  final Log LOG = LogFactory.getLog(getClass());
+  private final static HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility();
+
+  @BeforeClass
+  public static void setUpBeforeClass() throws Exception {
+    TEST_UTIL.startMiniCluster(1);
+  }
+
+  /**
+   * @throws java.lang.Exception
+   */
+  @AfterClass
+  public static void tearDownAfterClass() throws Exception {
+    TEST_UTIL.shutdownMiniCluster();
+  }
+
+  @Test
+  public void testMetaScanner() throws Exception {
+    LOG.info("Starting testMetaScanner");
+    final byte[] TABLENAME = Bytes.toBytes("testMetaScanner");
+    final byte[] FAMILY = Bytes.toBytes("family");
+    TEST_UTIL.createTable(TABLENAME, FAMILY);
+    Configuration conf = TEST_UTIL.getConfiguration();
+    HTable table = new HTable(conf, TABLENAME);
+    TEST_UTIL.createMultiRegions(conf, table, FAMILY,
+        new byte[][]{
+          HConstants.EMPTY_START_ROW,
+          Bytes.toBytes("region_a"),
+          Bytes.toBytes("region_b")});
+    // Make sure all the regions are deployed
+    TEST_UTIL.countRows(table);
+    
+    MetaScanner.MetaScannerVisitor visitor = 
+      mock(MetaScanner.MetaScannerVisitor.class);
+    doReturn(true).when(visitor).processRow((Result)anyObject());
+
+    // Scanning the entire table should give us three rows
+    MetaScanner.metaScan(conf, visitor, TABLENAME);
+    verify(visitor, times(3)).processRow((Result)anyObject());
+    
+    // Scanning the table with a specified empty start row should also
+    // give us three META rows
+    reset(visitor);
+    doReturn(true).when(visitor).processRow((Result)anyObject());
+    MetaScanner.metaScan(conf, visitor, TABLENAME, HConstants.EMPTY_BYTE_ARRAY, 1000);
+    verify(visitor, times(3)).processRow((Result)anyObject());
+    
+    // Scanning the table starting in the middle should give us two rows:
+    // region_a and region_b
+    reset(visitor);
+    doReturn(true).when(visitor).processRow((Result)anyObject());
+    MetaScanner.metaScan(conf, visitor, TABLENAME, Bytes.toBytes("region_ac"), 1000);
+    verify(visitor, times(2)).processRow((Result)anyObject());
+    
+    // Scanning with a limit of 1 should only give us one row
+    reset(visitor);
+    doReturn(true).when(visitor).processRow((Result)anyObject());
+    MetaScanner.metaScan(conf, visitor, TABLENAME, Bytes.toBytes("region_ac"), 1);
+    verify(visitor, times(1)).processRow((Result)anyObject());
+        
+  }
+}



Mime
View raw message