#!/bin/bash

#######################################################################################
##  Shell script to read a CSV file and create schema file for Jaguar database
##
##  Usage: createTableFromCSV.sh  <inputfile.csv>
##
##  DataJaguar, Inc. All Rights Reserved.
##  Author: Xiyang Lu
##
#######################################################################################

#choose the file to read
fname=$1
if [[ "x$fname" = "x" ]]; then
    echo "Usage: $0  <inputfile.csv>"
    echo "Please provide the input csv file"
    exit 1
fi

if [[ ! -f "$fname" ]]; then
    echo "Error: $fname does not exist"
    exit 1
fi

### Table name is first part of input file name
table_name=`basename $fname|awk -F'.' '{print $1}'`

tmpfname="${fname}.2820219$$"
tr '\r' '\n' < $fname > $tmpfname
/bin/mv -f $tmpfname  $fname

###Get title of each column
my_title=`head -1 $fname|tr -d '\r'`
OLD_IFS="$IFS"
IFS=","
array1=($my_title)
IFS="$OLD_IFS"

###Calculate number of rows and columns
tmpfname="${fname}.2820219$$"
num_col=${#array1[@]}
num_row=`wc -l $fname | awk '{print $1}'`
((an=num_row-1))
#tail -n $an $fname | shuf -n 1000 | tr -d '\r' > $tmpfname
tail -n $an $fname | shuf -n 1000 > $tmpfname
fname=$tmpfname

###Echo the title column into array
declare -a first_result
for i in "${!array1[@]}"; do
  first_result[$i]=${array1[$i]}
done

#declare data type and data result
declare -a data_result
#assign data type
char="char"
int="int"
date="date"
numeric="numeric"
datetime="datetime"

#determine the data type of examples
#try to use awk to set field delimiter

n=1
while read line; do
  n=`expr $n + 1`
  example_data=`echo $line | awk -v v='"' 'BEGIN{FS=OFS=v}{gsub(","," ",$2); print}'`
  OLD_IFS="$IFS"
  IFS=","
  array2=($example_data)
  IFS="$OLD_IFS"
  for ((j = 0; j < ${#array1[@]}; j++)); do
      result1=$(echo "${array2[$j]}" | grep -Eo "[[:digit:]]+" | wc -l|cut -d' ' -f1)
      result2=$(echo "${array2[$j]}" | grep -Eo "[[:alpha:]]+|\/" | wc -l|cut -d ' ' -f1)
      #determine datatype
      data_result[$j]=$char
      if [ $result1 -eq 0 -a $result2 -eq 0 ]; then
        data_result[$j]=$char
      elif [ $result1 -gt 0 -a $result2 -gt 0 ]; then
        data_result[$j]=$char
      elif [[ $result2 -eq 0 ]]; then
        if [[ `echo "${array2[$j]}" | sed 's/[0-9]//g'` ]];then
          data_result[$j]=$int
        elif [[ `echo "${array2[$j]}" | grep '^[0-9]{1,2}-[0-9a-zA-Z]{1,3}-[0-9]{4}$'` ]]; then
          data_result[$j]=$date
        elif [[ `echo "${array2[$j]}" | grep '^[1-9][0-9]/{3/}-[0-1][0-9]-[0-9]/{2/}\ [0-2][0-9]:[0-6][0-9]:[0-6][0-9]$'` ]]; then
          data_result[$j]=$datetime
        elif [[  ! -z  $(echo ${array2[$j]} | sed 's/[^.]//g') ]]; then
          data_result[$j]=$numeric
        fi
      elif [[ $result1 -eq 0 ]]; then
        data_result[$j]=$char
      fi
  done
  if (($n > 18)); then
    break
  fi
done < $fname


#find data_length
declare -a data_length=( $(for i in $(seq 1 $num_col); do echo 0; done) )
while read line
do
  example_data=`echo $line | awk -v v='"' 'BEGIN{FS=OFS=v}{gsub(","," ",$2); print}'`
  OLD_IFS="$IFS"
  IFS=","
  array_data_length=($example_data)
  IFS="$OLD_IFS"
  for ((j = 0; j < $num_col; j++)); do
    length=${#array_data_length[$j]}
    ((length=length+length%32 + 32))
    if [[ "$length" -gt "${data_length[$j]}" ]]; then
      data_length[$j]=$length
    fi
  done
done < $fname


#merge three array together
declare -a final_result
for ((k = 0; k < ${#array1[@]}; k++)); do
  if [[ k -eq 0 ]]; then
    final_result[$k]="key: ${first_result[$k]} ${data_result[$k]}(${data_length[$k]}),"
  elif [[ k -eq 2 ]]; then
    final_result[$k]="value: ${first_result[$k]} ${data_result[$k]}(${data_length[$k]}),"
  else
    final_result[$k]="${first_result[$k]} ${data_result[$k]}(${data_length[$k]}),"
  fi
done


#print out the output
seperate1="("
seperate2=");"

echo
echo "create table $table_name "
echo "$seperate1"
for ((ENTRY = 0; ENTRY < ${#array1[@]}; ENTRY++)) do
    if [[ ENTRY -eq 0 ]]; then
      echo "    ${final_result[$ENTRY]}"
    elif [[ ENTRY -eq 2 ]]; then
      echo "    ${final_result[$ENTRY]}"
    else
      echo "         ${final_result[$ENTRY]}"
    fi
done
echo "$seperate2"
/bin/rm -f $tmpfname

