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

import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import org.apache.commons.lang.StringUtils;
import org.apache.hadoop.hive.conf.HiveConf;
import org.apache.hadoop.hive.metastore.MetaStoreUtils;
import org.apache.hadoop.hive.metastore.TableType;
import org.apache.hadoop.hive.metastore.api.FieldSchema;
import org.apache.hadoop.hive.metastore.api.Order;
import org.apache.hadoop.hive.metastore.api.SerDeInfo;
import org.apache.hadoop.hive.metastore.api.StorageDescriptor;
import org.apache.hadoop.hive.metastore.api.Table;
import org.apache.hadoop.hive.ql.io.IgnoreKeyTextOutputFormat;
import org.apache.hadoop.hive.ql.io.RCFileInputFormat;
import org.apache.hadoop.hive.ql.io.RCFileOutputFormat;
import org.apache.hadoop.hive.ql.metadata.HiveException;
import org.apache.hadoop.hive.ql.metadata.HiveStorageHandler;
import org.apache.hadoop.hive.ql.metadata.HiveUtils;
import org.apache.hadoop.hive.serde2.columnar.ColumnarSerDe;
import org.apache.hadoop.mapred.SequenceFileInputFormat;
import org.apache.hadoop.mapred.SequenceFileOutputFormat;
import org.apache.hadoop.mapred.TextInputFormat;
import org.apache.hcatalog.common.HCatException;
import org.apache.hcatalog.data.schema.HCatFieldSchema;
import org.apache.hcatalog.data.schema.HCatSchemaUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

/**
 * The Class HCatCreateTableDesc for defining attributes for a new table.
 */
@SuppressWarnings("deprecation")
public class HCatCreateTableDesc{

    private static final Logger LOG = LoggerFactory.getLogger(HCatCreateTableDesc.class);

    private String tableName;
    private String dbName;
    private boolean isExternal;
    private String comment;
    private String location;
    private List<HCatFieldSchema> cols;
    private List<HCatFieldSchema> partCols;
    private List<String> bucketCols;
    private int numBuckets;
    private List<Order> sortCols;
    private Map<String, String> tblProps;
    private boolean ifNotExists;
    private String fileFormat;
    private String inputformat;
    private String outputformat;
    private String serde;
    private String storageHandler;

    private HCatCreateTableDesc(String dbName, String tableName, List<HCatFieldSchema> columns){
        this.dbName = dbName;
        this.tableName = tableName;
        this.cols = columns;
    }

    /**
     * Creates a builder for defining attributes.
     *
     * @param dbName the db name
     * @param tableName the table name
     * @param columns the columns
     * @return the builder
     */
    public static Builder create(String dbName, String tableName, List<HCatFieldSchema> columns){
        return new Builder(dbName, tableName, columns);
    }

    Table toHiveTable(HiveConf conf) throws HCatException{

        Table newTable = new Table();
        newTable.setDbName(dbName);
        newTable.setTableName(tableName);
        if (tblProps != null) {
            newTable.setParameters(tblProps);
        }

        if (isExternal) {
            newTable.putToParameters("EXTERNAL", "TRUE");
            newTable.setTableType(TableType.EXTERNAL_TABLE.toString());
        } else {
            newTable.setTableType(TableType.MANAGED_TABLE.toString());
        }

        StorageDescriptor sd = new StorageDescriptor();
        sd.setSerdeInfo(new SerDeInfo());
        if (location != null) {
            sd.setLocation(location);
        }
        if (this.comment != null) {
            newTable.putToParameters("comment", comment);
        }
        if (!StringUtils.isEmpty(fileFormat)) {
            sd.setInputFormat(inputformat);
            sd.setOutputFormat(outputformat);
            if (serde != null) {
                sd.getSerdeInfo().setSerializationLib(serde);
            } else {
                LOG.info("Using LazySimpleSerDe for table " + tableName);
                sd.getSerdeInfo()
                        .setSerializationLib(
                                org.apache.hadoop.hive.serde2.lazy.LazySimpleSerDe.class
                                        .getName());
            }
        } else {
            try {
                LOG.info("Creating instance of storage handler to get input/output, serder info.");
                HiveStorageHandler sh = HiveUtils.getStorageHandler(conf,
                        storageHandler);
                sd.setInputFormat(sh.getInputFormatClass().getName());
                sd.setOutputFormat(sh.getOutputFormatClass().getName());
                sd.getSerdeInfo().setSerializationLib(
                        sh.getSerDeClass().getName());
                newTable.putToParameters(
                        org.apache.hadoop.hive.metastore.api.Constants.META_TABLE_STORAGE,
                        storageHandler);
            } catch (HiveException e) {
                throw new HCatException(
                        "Exception while creating instance of storage handler",
                        e);
            }
        }
        newTable.setSd(sd);
        if (this.partCols != null) {
            ArrayList<FieldSchema> hivePtnCols = new ArrayList<FieldSchema>();
            for (HCatFieldSchema fs : this.partCols) {
                hivePtnCols.add(HCatSchemaUtils.getFieldSchema(fs));
            }
            newTable.setPartitionKeys(hivePtnCols);
        }

        if (this.cols != null) {
            ArrayList<FieldSchema> hiveTblCols = new ArrayList<FieldSchema>();
            for (HCatFieldSchema fs : this.cols) {
                hiveTblCols.add(HCatSchemaUtils.getFieldSchema(fs));
            }
            newTable.getSd().setCols(hiveTblCols);
        }

        if (this.bucketCols != null) {
            newTable.getSd().setBucketCols(bucketCols);
            newTable.getSd().setNumBuckets(numBuckets);
        }

        if (this.sortCols != null) {
            newTable.getSd().setSortCols(sortCols);
        }

        newTable.setCreateTime((int) (System.currentTimeMillis() / 1000));
        newTable.setLastAccessTimeIsSet(false);
        return newTable;
    }

      /**
       * Gets the if not exists.
       *
       * @return the if not exists
       */
      public boolean getIfNotExists() {
          return this.ifNotExists;
      }

     /**
      * Gets the table name.
      *
      * @return the table name
      */
     public String getTableName() {
          return this.tableName;
      }

      /**
       * Gets the cols.
       *
       * @return the cols
       */
      public List<HCatFieldSchema> getCols() {
         return this.cols;
      }

      /**
       * Gets the partition cols.
       *
       * @return the partition cols
       */
      public List<HCatFieldSchema> getPartitionCols() {
          return this.partCols;
      }

      /**
       * Gets the bucket cols.
       *
       * @return the bucket cols
       */
      public List<String> getBucketCols() {
          return this.bucketCols;
      }

      public int getNumBuckets() {
          return this.numBuckets;
      }

      /**
       * Gets the comments.
       *
       * @return the comments
       */
      public String getComments() {
          return this.comment;
      }

      /**
       * Gets the storage handler.
       *
       * @return the storage handler
       */
      public String getStorageHandler() {
          return this.storageHandler;
      }

      /**
       * Gets the location.
       *
       * @return the location
       */
      public String getLocation() {
          return this.location;
      }

      /**
       * Gets the external.
       *
       * @return the external
       */
      public boolean getExternal() {
          return this.isExternal;
      }

      /**
       * Gets the sort cols.
       *
       * @return the sort cols
       */
      public List<Order> getSortCols() {
          return this.sortCols;
      }

      /**
       * Gets the tbl props.
       *
       * @return the tbl props
       */
      public Map<String, String> getTblProps() {
          return this.tblProps;
      }

      /**
       * Gets the file format.
       *
       * @return the file format
       */
      public String getFileFormat(){
          return this.fileFormat;
      }

      /**
       * Gets the database name.
       *
       * @return the database name
       */
      public String getDatabaseName() {
          return this.dbName;
      }

      @Override
    public String toString() {
        return "HCatCreateTableDesc ["
                + (tableName != null ? "tableName=" + tableName + ", " : "tableName=null")
                + (dbName != null ? "dbName=" + dbName + ", " : "dbName=null")
                + "isExternal="
                + isExternal
                + ", "
                + (comment != null ? "comment=" + comment + ", " : "comment=null")
                + (location != null ? "location=" + location + ", " : "location=null")
                + (cols != null ? "cols=" + cols + ", " : "cols=null")
                + (partCols != null ? "partCols=" + partCols + ", " : "partCols=null")
                + (bucketCols != null ? "bucketCols=" + bucketCols + ", " : "bucketCols=null")
                + "numBuckets="
                + numBuckets
                + ", "
                + (sortCols != null ? "sortCols=" + sortCols + ", " : "sortCols=null")
                + (tblProps != null ? "tblProps=" + tblProps + ", " : "tblProps=null")
                + "ifNotExists="
                + ifNotExists
                + ", "
                + (fileFormat != null ? "fileFormat=" + fileFormat + ", " : "fileFormat=null")
                + (inputformat != null ? "inputformat=" + inputformat + ", "
                        : "inputformat=null")
                + (outputformat != null ? "outputformat=" + outputformat + ", "
                        : "outputformat=null")
                + (serde != null ? "serde=" + serde + ", " : "serde=null")
                + (storageHandler != null ? "storageHandler=" + storageHandler
                        : "storageHandler=null") + "]";
    }

    public static class Builder{

          private String tableName;
          private boolean isExternal;
          private List<HCatFieldSchema> cols;
          private List<HCatFieldSchema> partCols;
          private List<String> bucketCols;
          private List<Order> sortCols;
          private int numBuckets;
          private String comment;
          private String fileFormat;
          private String location;
          private String storageHandler;
          private Map<String, String> tblProps;
          private boolean ifNotExists;
          private String dbName;


          private Builder(String dbName, String tableName, List<HCatFieldSchema> columns) {
              this.dbName = dbName;
              this.tableName = tableName;
              this.cols = columns;
          }


          /**
           * If not exists.
           *
           * @param ifNotExists If set to true, hive will not throw exception, if a
           * table with the same name already exists.
           * @return the builder
           */
          public Builder ifNotExists(boolean ifNotExists) {
            this.ifNotExists = ifNotExists;
            return this;
          }


          /**
           * Partition cols.
           *
           * @param partCols the partition cols
           * @return the builder
           */
          public Builder partCols(ArrayList<HCatFieldSchema> partCols) {
              this.partCols = partCols;
              return this;
          }


          /**
           * Bucket cols.
           *
           * @param bucketCols the bucket cols
           * @return the builder
           */
          public Builder bucketCols(ArrayList<String> bucketCols, int buckets) {
            this.bucketCols = bucketCols;
            this.numBuckets = buckets;
            return this;
          }

          /**
           * Storage handler.
           *
           * @param storageHandler the storage handler
           * @return the builder
           */
          public Builder storageHandler(String storageHandler) {
            this.storageHandler = storageHandler;
            return this;
          }

          /**
           * Location.
           *
           * @param location the location
           * @return the builder
           */
          public Builder location(String location) {
            this.location = location;
            return this;
          }

          /**
           * Comments.
           *
           * @param comment the comment
           * @return the builder
           */
          public Builder comments(String comment) {
            this.comment = comment;
            return this;
          }

          /**
           * Checks if is table external.
           *
           * @param isExternal the is external
           * @return the builder
           */
          public Builder isTableExternal(boolean isExternal) {
            this.isExternal = isExternal;
            return this;
          }

          /**
           * Sort cols.
           *
           * @param sortCols the sort cols
           * @return the builder
           */
          public Builder sortCols(ArrayList<Order> sortCols) {
            this.sortCols = sortCols;
            return this;
          }

          /**
           * Tbl props.
           *
           * @param tblProps the tbl props
           * @return the builder
           */
          public Builder tblProps(Map<String, String> tblProps) {
            this.tblProps = tblProps;
            return this;
          }

          /**
           * File format.
           *
           * @param format the format
           * @return the builder
           */
          public Builder fileFormat(String format){
              this.fileFormat = format;
              return this;
          }

          /**
           * Builds the HCatCreateTableDesc.
           *
           * @return HCatCreateTableDesc
           * @throws HCatException
           */
          public HCatCreateTableDesc build() throws HCatException {
              if(this.dbName == null){
                LOG.info("Database name found null. Setting db to :"
                        + MetaStoreUtils.DEFAULT_DATABASE_NAME);
                this.dbName = MetaStoreUtils.DEFAULT_DATABASE_NAME;
              }
              HCatCreateTableDesc desc = new HCatCreateTableDesc(this.dbName,
                      this.tableName, this.cols);
              desc.ifNotExists = this.ifNotExists;
              desc.isExternal = this.isExternal;
              desc.comment = this.comment;
              desc.partCols = this.partCols;
              desc.bucketCols = this.bucketCols;
              desc.numBuckets = this.numBuckets;
              desc.location = this.location;
              desc.tblProps = this.tblProps;
              desc.sortCols = this.sortCols;
              desc.serde = null;
              if (!StringUtils.isEmpty(fileFormat)) {
                  desc.fileFormat = fileFormat;
                  if ("SequenceFile".equalsIgnoreCase(fileFormat)) {
                      desc.inputformat = SequenceFileInputFormat.class.getName();
                      desc.outputformat = SequenceFileOutputFormat.class
                              .getName();
                  } else if ("RCFile".equalsIgnoreCase(fileFormat)) {
                      desc.inputformat = RCFileInputFormat.class.getName();
                      desc.outputformat = RCFileOutputFormat.class.getName();
                      desc.serde = ColumnarSerDe.class.getName();
                  }
                  desc.storageHandler = StringUtils.EMPTY;
              } else if (!StringUtils.isEmpty(storageHandler)) {
                  desc.storageHandler = storageHandler;
              } else {
                  desc.fileFormat = "TextFile";
                  LOG.info("Using text file format for the table.");
                  desc.inputformat = TextInputFormat.class.getName();
                  LOG.info("Table input format:" + desc.inputformat);
                  desc.outputformat = IgnoreKeyTextOutputFormat.class
                          .getName();
                  LOG.info("Table output format:" + desc.outputformat);
              }
              return desc;
          }
      }
}
