#!/usr/bin/env bash

function _usage()
{
  local command="git sync"
  cat << EOS
Usage:
  ${command} [<remote> <branch>]
  ${command} -h | --help

Sync local branch with <remote>/<branch>.
When <remote> and <branch> are not specified on the command line, upstream of local branch will be used by default.
All changes and untracked files and directories will be removed.

Examples:
  Sync with upstream of local branch:
    ${command}

  Sync with origin/master:
    ${command} origin master
EOS
}

function main()
{
  while [ "$1" != "" ]; do
    case $1 in
      -h | --help)
        _usage
        exit
        ;;
      * )
        if [ "${remote}" = "" ]; then
          local remote="$1"
        elif [ "${branch}" = "" ]; then
          local branch="$1"
        else
          echo -e "Error: too many arguments.\n"
          _usage
          exit 1
        fi
        ;;
    esac
    shift
  done

  local remote_branch
  if [ "${remote}" = "" ]; then
    if ! remote_branch="$(git rev-parse --abbrev-ref --symbolic-full-name @{u} 2>/dev/null)"; then
      echo "There is no upstream information of local branch."
      exit 1
    fi
    local branch="$(git rev-parse --abbrev-ref --symbolic-full-name @)"
    local remote=$(git config "branch.${branch}.remote")
  elif [ "${branch}" = "" ]; then
    echo -e "Error: too few arguments.\n"
    _usage
    exit 1
  else
    remote_branch="${remote}/${branch}"
  fi

  echo "Are you sure you want to clean all changes & sync with '${remote_branch}'? [y/N]"
  local res
  read res
  case "${res}" in
    "Y" | "y" | "yes" | "Yes" | "YES" )
      git fetch "${remote}" "${branch}" && git reset --hard "${remote_branch}" && git clean -d -f -x
      ;;
    * )
      echo "Canceled."
      ;;
  esac
}

main "$@"

