org.apache.hadoop.hbase.regionserver.metrics.TestSchemaConfigured.java Source code

Java tutorial

Introduction

Here is the source code for org.apache.hadoop.hbase.regionserver.metrics.TestSchemaConfigured.java

Source

/*
 * Copyright 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.regionserver.metrics;

import static org.junit.Assert.*;

import java.util.regex.Pattern;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.hbase.HBaseConfiguration;
import org.apache.hadoop.hbase.SmallTests;
import org.apache.hadoop.hbase.regionserver.HRegion;
import org.codehaus.jettison.json.JSONException;
import org.codehaus.jettison.json.JSONStringer;
import org.junit.Test;
import org.junit.experimental.categories.Category;

@Category(SmallTests.class)
public class TestSchemaConfigured {
    private static final Log LOG = LogFactory.getLog(TestSchemaConfigured.class);
    private final String TABLE_NAME = "myTable";
    private final String CF_NAME = "myColumnFamily";

    private static final Path TMP_HFILE_PATH = new Path(
            "/hbase/myTable/myRegion/" + HRegion.REGION_TEMP_SUBDIR + "/hfilename");

    /** Test if toString generates real JSON */
    @Test
    public void testToString() throws JSONException {
        SchemaConfigured sc = new SchemaConfigured(null, TABLE_NAME, CF_NAME);
        JSONStringer json = new JSONStringer();
        json.object();
        json.key("tableName");
        json.value(TABLE_NAME);
        json.key("cfName");
        json.value(CF_NAME);
        json.endObject();
        assertEquals(json.toString(), sc.schemaConfAsJSON());
    }

    /** Don't allow requesting metrics before setting table/CF name */
    @Test
    public void testDelayedInitialization() {
        SchemaConfigured unconfigured = new SchemaConfigured();
        try {
            unconfigured.getSchemaMetrics();
            fail(IllegalStateException.class.getSimpleName() + " expected");
        } catch (IllegalStateException ex) {
            assertTrue("Unexpected exception message: " + ex.getMessage(),
                    Pattern.matches(".* metrics requested before .* initialization.*", ex.getMessage()));
            LOG.debug("Expected exception: " + ex.getMessage());
        }

        SchemaMetrics.setUseTableNameInTest(false);
        SchemaConfigured other = new SchemaConfigured(null, TABLE_NAME, CF_NAME);
        other.passSchemaMetricsTo(unconfigured);
        unconfigured.getSchemaMetrics(); // now this should succeed
    }

    /** Don't allow setting table/CF name twice */
    @Test
    public void testInitializingTwice() {
        Configuration conf = HBaseConfiguration.create();
        for (int i = 0; i < 4; ++i) {
            SchemaConfigured sc = new SchemaConfigured(conf, TABLE_NAME, CF_NAME);
            SchemaConfigured target = new SchemaConfigured(conf, TABLE_NAME + (i % 2 == 1 ? "1" : ""),
                    CF_NAME + ((i & 2) != 0 ? "1" : ""));
            if (i == 0) {
                sc.passSchemaMetricsTo(target); // No exception expected.
                continue;
            }

            String testDesc = "Trying to re-configure " + target.schemaConfAsJSON() + " with "
                    + sc.schemaConfAsJSON();
            try {
                sc.passSchemaMetricsTo(target);
                fail(IllegalArgumentException.class.getSimpleName() + " expected");
            } catch (IllegalArgumentException ex) {
                final String errorMsg = testDesc + ". Unexpected exception message: " + ex.getMessage();
                final String exceptionRegex = "Trying to change table .* CF .*";
                assertTrue(errorMsg, Pattern.matches(exceptionRegex, ex.getMessage()));
                LOG.debug("Expected exception: " + ex.getMessage());
            }
        }
    }

    @Test(expected = IllegalStateException.class)
    public void testConfigureWithUnconfigured1() {
        SchemaConfigured unconfigured = new SchemaConfigured(null, "t1", null);
        SchemaConfigured target = new SchemaConfigured();
        unconfigured.passSchemaMetricsTo(target);
    }

    @Test(expected = IllegalStateException.class)
    public void testConfigureWithUnconfigured2() {
        SchemaConfigured unconfigured = new SchemaConfigured(null, null, "cf1");
        SchemaConfigured target = new SchemaConfigured();
        unconfigured.passSchemaMetricsTo(target);
    }

    /**
     * Configuring with an uninitialized object is equivalent to re-setting
     * schema metrics configuration.
     */
    public void testConfigureWithNull() {
        SchemaConfigured unconfigured = new SchemaConfigured();
        SchemaConfigured target = new SchemaConfigured(null, "t1", "cf1");
        unconfigured.passSchemaMetricsTo(target);
        assertTrue(target.getTableName() == null);
        assertTrue(target.getColumnFamilyName() == null);
    }

    public void testConfigurePartiallyDefined() {
        final SchemaConfigured sc = new SchemaConfigured(null, "t1", "cf1");
        final SchemaConfigured target1 = new SchemaConfigured(null, "t2", null);
        sc.passSchemaMetricsTo(target1);
        assertEquals("t2", target1.getColumnFamilyName());
        assertEquals("cf1", target1.getColumnFamilyName());

        final SchemaConfigured target2 = new SchemaConfigured(null, null, "cf2");
        sc.passSchemaMetricsTo(target2);
        assertEquals("t1", target2.getColumnFamilyName());
        assertEquals("cf2", target2.getColumnFamilyName());

        final SchemaConfigured target3 = new SchemaConfigured(null, null, null);
        sc.passSchemaMetricsTo(target3);
        assertEquals("t1", target2.getColumnFamilyName());
        assertEquals("cf1", target2.getColumnFamilyName());
    }

    @Test(expected = IllegalArgumentException.class)
    public void testConflictingConf() {
        SchemaConfigured sc = new SchemaConfigured(null, "t1", "cf1");
        SchemaConfigured target = new SchemaConfigured(null, "t2", "cf1");
        sc.passSchemaMetricsTo(target);
    }

    /** We allow setting CF to unknown and then reconfiguring it */
    public void testReconfigureUnknownCF() {
        SchemaConfigured sc = new SchemaConfigured(null, "t1", "cf1");
        SchemaConfigured target = new SchemaConfigured(null, "t1", SchemaMetrics.UNKNOWN);
        sc.passSchemaMetricsTo(target);
    }

    /**
     * When the "column family" deduced from the path is ".tmp" (this happens
     * for files written on compaction) we allow re-setting the CF to another
     * value.
     */
    @Test
    public void testTmpPath() {
        SchemaConfigured sc = new SchemaConfigured(null, "myTable", "myCF");
        SchemaConfigured target = new SchemaConfigured(TMP_HFILE_PATH);
        sc.passSchemaMetricsTo(target);
    }

    /**
     * Even if CF is initially undefined (".tmp"), we don't allow to change
     * table name.
     */
    @Test(expected = IllegalArgumentException.class)
    public void testTmpPathButInvalidTable() {
        SchemaConfigured sc = new SchemaConfigured(null, "anotherTable", "myCF");
        SchemaConfigured target = new SchemaConfigured(TMP_HFILE_PATH);
        sc.passSchemaMetricsTo(target);
    }

    @Test
    public void testSchemaConfigurationHook() {
        SchemaConfigured sc = new SchemaConfigured(null, "myTable", "myCF");
        final StringBuilder newCF = new StringBuilder();
        final StringBuilder newTable = new StringBuilder();
        SchemaConfigured target = new SchemaConfigured() {
            @Override
            protected void schemaConfigurationChanged() {
                newCF.append(getColumnFamilyName());
                newTable.append(getTableName());
            }
        };
        sc.passSchemaMetricsTo(target);
        assertEquals("myTable", newTable.toString());
        assertEquals("myCF", newCF.toString());
    }

    @Test
    public void testResetSchemaMetricsConf() {
        SchemaConfigured target = new SchemaConfigured(null, "t1", "cf1");
        SchemaConfigured.resetSchemaMetricsConf(target);
        new SchemaConfigured(null, "t2", "cf2").passSchemaMetricsTo(target);
        assertEquals("t2", target.getTableName());
        assertEquals("cf2", target.getColumnFamilyName());
    }

    @Test
    public void testPathTooShort() {
        // This has too few path components (four, the first one is empty).
        SchemaConfigured sc1 = new SchemaConfigured(new Path("/a/b/c/d"));
        assertEquals(SchemaMetrics.UNKNOWN, sc1.getTableName());
        assertEquals(SchemaMetrics.UNKNOWN, sc1.getColumnFamilyName());

        SchemaConfigured sc2 = new SchemaConfigured(new Path("a/b/c/d"));
        assertEquals(SchemaMetrics.UNKNOWN, sc2.getTableName());
        assertEquals(SchemaMetrics.UNKNOWN, sc2.getColumnFamilyName());

        SchemaConfigured sc3 = new SchemaConfigured(new Path("/hbase/tableName/regionId/cfName/hfileName"));
        assertEquals("tableName", sc3.getTableName());
        assertEquals("cfName", sc3.getColumnFamilyName());

        SchemaConfigured sc4 = new SchemaConfigured(new Path("hbase/tableName/regionId/cfName/hfileName"));
        assertEquals("tableName", sc4.getTableName());
        assertEquals("cfName", sc4.getColumnFamilyName());
    }

    @org.junit.Rule
    public org.apache.hadoop.hbase.ResourceCheckerJUnitRule cu = new org.apache.hadoop.hbase.ResourceCheckerJUnitRule();
}