/**
 * 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.hcatalog.hbase;

import java.io.File;
import java.io.IOException;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Random;
import java.util.Set;

import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.fs.FileSystem;
import org.apache.hadoop.fs.Path;
import org.apache.hadoop.hbase.HBaseConfiguration;
import org.apache.hadoop.hbase.HColumnDescriptor;
import org.apache.hadoop.hbase.HTableDescriptor;
import org.apache.hadoop.hbase.client.HBaseAdmin;
import org.apache.hadoop.hive.conf.HiveConf;
import org.junit.AfterClass;
import org.junit.BeforeClass;

/**
 * Base class for HBase Tests which need a mini cluster instance
 */
public abstract class SkeletonHBaseTest {

    protected static String TEST_DIR = System.getProperty("test.data.dir", "./");

    protected final static String DEFAULT_CONTEXT_HANDLE = "default";

    protected static Map<String, Context> contextMap = new HashMap<String, Context>();
    protected static Set<String> tableNames = new HashSet<String>();

    /**
     * Allow tests to alter the default MiniCluster configuration.
     * (requires static initializer block as all setup here is static)
     */
    protected static Configuration testConf = null;

    protected void createTable(String tableName, String[] families) {
        try {
            HBaseAdmin admin = new HBaseAdmin(getHbaseConf());
            HTableDescriptor tableDesc = new HTableDescriptor(tableName);
            for (String family : families) {
                HColumnDescriptor columnDescriptor = new HColumnDescriptor(family);
                tableDesc.addFamily(columnDescriptor);
            }
            admin.createTable(tableDesc);
        } catch (Exception e) {
            e.printStackTrace();
            throw new IllegalStateException(e);
        }

    }

    protected String newTableName(String prefix) {
        String name = null;
        int tries = 100;
        do {
            name = prefix + "_" + Math.abs(new Random().nextLong());
        } while (tableNames.contains(name) && --tries > 0);
        if (tableNames.contains(name))
            throw new IllegalStateException("Couldn't find a unique table name, tableNames size: " + tableNames.size());
        tableNames.add(name);
        return name;
    }


    /**
     * startup an hbase cluster instance before a test suite runs
     */
    @BeforeClass
    public static void setup() {
        if (!contextMap.containsKey(getContextHandle()))
            contextMap.put(getContextHandle(), new Context(getContextHandle()));

        contextMap.get(getContextHandle()).start();
    }

    /**
     * shutdown an hbase cluster instance ant the end of the test suite
     */
    @AfterClass
    public static void tearDown() {
        contextMap.get(getContextHandle()).stop();
    }

    /**
     * override this with a different context handle if tests suites are run simultaneously
     * and ManyMiniCluster instances shouldn't be shared
     * @return
     */
    public static String getContextHandle() {
        return DEFAULT_CONTEXT_HANDLE;
    }

    /**
     * @return working directory for a given test context, which normally is a test suite
     */
    public String getTestDir() {
        return contextMap.get(getContextHandle()).getTestDir();
    }

    /**
     * @return ManyMiniCluster instance
     */
    public ManyMiniCluster getCluster() {
        return contextMap.get(getContextHandle()).getCluster();
    }

    /**
     * @return configuration of MiniHBaseCluster
     */
    public Configuration getHbaseConf() {
        return contextMap.get(getContextHandle()).getHbaseConf();
    }

    /**
     * @return configuration of MiniMRCluster
     */
    public Configuration getJobConf() {
        return contextMap.get(getContextHandle()).getJobConf();
    }

    /**
     * @return configuration of Hive Metastore
     */
    public HiveConf getHiveConf() {
        return contextMap.get(getContextHandle()).getHiveConf();
    }

    /**
     * @return filesystem used by ManyMiniCluster daemons
     */
    public FileSystem getFileSystem() {
        return contextMap.get(getContextHandle()).getFileSystem();
    }

    /**
     * class used to encapsulate a context which is normally used by
     * a single TestSuite or across TestSuites when multi-threaded testing is turned on
     */
    public static class Context {
        protected String testDir;
        protected ManyMiniCluster cluster;

        protected Configuration hbaseConf;
        protected Configuration jobConf;
        protected HiveConf hiveConf;

        protected FileSystem fileSystem;

        protected int usageCount = 0;

        public Context(String handle) {
            try {
                testDir = new File(TEST_DIR + "/test_" + handle + "_" + Math.abs(new Random().nextLong()) + "/").getCanonicalPath();
            } catch (IOException e) {
                throw new IllegalStateException("Failed to generate testDir", e);
            }
            System.out.println("Cluster work directory: " + testDir);
        }

        public void start() {
            if (usageCount++ == 0) {
                ManyMiniCluster.Builder b = ManyMiniCluster.create(new File(testDir));
                if (testConf != null) {
                    b.hbaseConf(HBaseConfiguration.create(testConf));
                }
                cluster = b.build();
                cluster.start();
                this.hbaseConf = cluster.getHBaseConf();
                jobConf = cluster.getJobConf();
                fileSystem = cluster.getFileSystem();
                hiveConf = cluster.getHiveConf();
            }
        }

        public void stop() {
            if (--usageCount == 0) {
                try {
                    cluster.stop();
                    cluster = null;
                } finally {
                    System.out.println("Trying to cleanup: " + testDir);
                    try {
                        FileSystem fs = FileSystem.get(jobConf);
                        fs.delete(new Path(testDir), true);
                    } catch (IOException e) {
                        throw new IllegalStateException("Failed to cleanup test dir", e);
                    }
                    
                }
            }
        }

        public String getTestDir() {
            return testDir;
        }

        public ManyMiniCluster getCluster() {
            return cluster;
        }

        public Configuration getHbaseConf() {
            return hbaseConf;
        }

        public Configuration getJobConf() {
            return jobConf;
        }

        public HiveConf getHiveConf() {
            return hiveConf;
        }

        public FileSystem getFileSystem() {
            return fileSystem;
        }
    }

}
