#!/usr/pkg/bin/bash

# Configuration
#
# Directory where to hold the memos
# MEMO_DIR=~/memo

# commands
ack_cmd=ack
man_cmd=man
tree_cmd=tree
git_cmd=git
# comment pandoc_cmd to fall back to cat
pandoc_cmd=pandoc


# Script

MEMO_FOLDER="${MEMO_DIR:-$HOME/memo}"

function precondition::provide_memo_folder(){
    if [[ ! -d ${MEMO_FOLDER} ]]
    then
        echo "create memo folder : ${MEMO_FOLDER}"
        mkdir -p ${MEMO_FOLDER}
    fi
}

function precondition::provide_topic(){
    topic_name=$1
    topic_path=${MEMO_FOLDER}/${topic_name}
    topic_file=${topic_path}/memo.md

    if [[ ! -d ${topic_path} ]]
    then
        echo "create memo topic : ${topic_name}"
        mkdir -p ${topic_path}
        echo "# Memo" > ${topic_file}
    fi
}

#
# git commands
#

IS_GIT_REPO=0
# check if it is a gitrepository
# use the IS_GIT_REPO variable to
# verify later if it is a git repo
function git:status(){
  cd ${MEMO_FOLDER}
  ${git_cmd} status &> /dev/null
  if [[ $? -eq 0 ]]
  then
    IS_GIT_REPO=1
  else
    IS_GIT_REPO=0
  fi
}

# run before commit
function git:add_all_topics(){
  if [[ ${IS_GIT_REPO} -eq 1 ]]
  then
    cd ${MEMO_FOLDER}
    ${git_cmd} add .
  fi
}

# make a commit
function git:commit(){
  local message="${1:-blind commit}"
  if [[ ${IS_GIT_REPO} -eq 1 ]]
  then
    cd ${MEMO_FOLDER}
    ${git_cmd} commit -m "${message}"
  fi
}

function git:run_command(){
  cd ${MEMO_FOLDER}
  ${git_cmd} $@
}

#
# remove command
#

function remove_topic (){
    topic_name=$1
    #precondition::provide_topic ${topic_name}
    topic_path=${MEMO_FOLDER}/${topic_name}

    if [[ -d ${topic_path} ]]
    then
        rm -rf ${topic_path}
    fi

    git:add_all_topics
    git:commit "edit : ${topic_name}"
}

#
# edit command
#

function edit_topic () {
    topic_name=$1
    precondition::provide_topic ${topic_name}
    topic_path=${MEMO_FOLDER}/${topic_name}

    if [[ -z ${EDITOR} ]]
    then
      echo "you have to define the ${EDITOR} variable"
      exit 1
    fi

    ${EDITOR} ${topic_file}

    git:add_all_topics
    git:commit "edit : ${topic_name}"
}

#
# add command
#

function add_memo(){
    topic_name=$1
    precondition::provide_topic ${topic_name}
    topic_path=${MEMO_FOLDER}/${topic_name}
    topic_file=${topic_path}/memo.md

    shift
    if [[ $# -gt 0 ]]
    then
        memo=$@
        echo "append memo to ${topic_name}"
        cat >>${topic_file} <<EOF

${memo}
EOF
    else
        echo "append input to ${topic_name}"
        echo "" >>${topic_file}
        cat >>${topic_file} -
    fi

    git:add_all_topics
    git:commit "add : ${topic_name}"

}




#
# copy command
#

function copy_file(){
    topic_name=$1
    shift
    path=$@

    if [[ -z "${path}" ]]
    then
        show_help
        echo
        echo "!! path not given"
        echo
        exit 1
    fi

    if [[ ! -e "${path}" ]]
    then
        echo "path '${path}' does not exist"
        exit 1
    fi

    precondition::provide_topic ${topic_name}

    topic_path=${MEMO_FOLDER}/${topic_name}
    echo "copy '${path}' to '${topic_name}'"
    cp -r "${path}" ${topic_path}/

    git:add_all_topics
    git:commit "copy $( dirname ${path} ): ${topic_name}"

}





#
# search command
#

function search_term(){
    search_terms=$@

    if [[ -z "${search_terms}" ]]
    then
        show_help
        echo
        echo "!! no search terms given"
        echo
        exit 1
    fi

    cd ${MEMO_FOLDER}
    ${ack_cmd} "${search_terms}"
}



#
# show command
#

function show_topic(){
    topic_name=$1
    topic_path=${MEMO_FOLDER}/${topic_name}
    topic_file=${topic_path}/memo.md

    if [[ ! -d ${topic_path} ]]
    then
        echo "${topic_name} does not exist"
        exit 1
    fi

    if [[ -f ${topic_file} ]]
    then
        echo
        if [[ -z ${pandoc_cmd} ]]
        then
            cat ${topic_file}
            echo
        else
        cat <(
            echo "% ${topic_name}" && \
            echo "% $( whoami )" && \
            echo "% $( date +%Y-%m-%d )" && \
            cat ${topic_file} && \
            echo && \
            echo "# Folders" && \
            echo && \
            find ${topic_path} -printf "* %p\n") | \
            ${pandoc_cmd} - -s -t man | \
            ${man_cmd} -l -
        fi
    fi
}





#
# list command
#

function list_topics(){
    echo
    echo "topics : "
    echo
    ${tree_cmd} -L 1 ${MEMO_FOLDER}
}


#
# show help command
#

function show_help() {
    cat <<EOF

  /\/\   ___  /\/\   ___   /__   \___   ___   / /
 /    \ / _ \/    \ / _ \    / /\/ _ \ / _ \ / /
/ /\/\ \  __/ /\/\ \ (_) |  / / | (_) | (_) / /___
\/    \/\___\/    \/\___/   \/   \___/ \___/\____/


Usage:
  memo <command> arguments

Commands:
  add <topic> [memo]
    adds a memo.md in ${MEMO_FOLDER}/<topic>/
    containing the text
    if memo is not given it will read from input
    so piping is possible.
    Example: cat file.txt | memo add topic

  rm <topic>
    remove ${MEMO_FOLDER}/<topic> (with all its content)

  copy <topic> <file to copy>
    copy a file to ${MEMO_FOLDER}/<topic>/

  search <term to search>
    search for a term in
    ${MEMO_FOLDER}/<memo-title>/

  show <topic>
    show topic file and list all file in the
    ${MEMO_FOLDER}/<topic>/

  edit <topic>
    edit topic ${MEMO_FOLDER}/<topic>.md

  list
    prints a list of all topics

  git <command>
    run git <command> in ${MEMO_FOLDER}

EOF
}



#
# main
#

command=$1
shift

precondition::provide_memo_folder
git:status

case $command in
    add) add_memo $@
         ;;
    copy)
        copy_file $@
        ;;
    search)
        search_term $@
        ;;
    show)
        show_topic $@
        ;;
    edit)
        edit_topic $@
        ;;
    list)
        list_topics
        ;;
    git)
        git:run_command $@
        ;;
    rm)
        remove_topic $@
        ;;
    *) show_help
       ;;
esac
