#!/usr/bin/env sh

# From Kehet
## https://gist.github.com/Kehet/5ba8a530e52ea3a0ae251d756faef680

# Vars {{{
readonly PROGNAME=$(basename "${0}")
readonly PROGDIR=$(readlink -m $(dirname "${0}"))
readonly ARGS="${*}"
readonly NBARGS="${#}"
[ -z "${DEBUG}" ] && DEBUG=1

## Current tasks temp file
readonly TASKW_CURRENT_LIST="/tmp/rofi-task.sh-current.tasks"

# }}}
usage() {                                                       # {{{

	cat <<- EOF
usage: $PROGNAME [-d|-h]

Start any taskwarrior task or allow to stop a running one.

EXAMPLES :
    - Open rofi launcher with the list of pending tasks :
        ${PROGNAME}

OPTIONS :
    -d,--debug
        Enable debug messages.

    -h,--help
        Print this help message.

	EOF

}
# }}}
debug_message() {                                               # {{{

	local_message="${1}"

	## Print message if DEBUG is enable (=0)
	[ "${DEBUG}" -eq "0" ] && printf '\e[1;35m%-6b\e[m\n' "DEBUG − ${PROGNAME} : ${local_message}"

	return 0
}
# }}}
error_message() {                                               # {{{

	local_error_message="${1}"
	local_error_code="${2}"

	## Print message if DEBUG is enable (=0)
	[ "${DEBUG}" -eq "0" ] && printf '%b\n' "ERROR − ${PROGNAME} : ${RED}${local_error_message}${RESET}"

	exit "${local_error_code:=66}"
}
# }}}

is_task_running() {                                             # {{{

	if task active >/dev/null 2>&1; then
		return_is_task_running="0"
		debug_message "is_task_running − \
A task is ${RED}running${COLOR_DEBUG}."
	else
		return_is_task_running="1"
		debug_message "is_task_running − \
No task currently running."
	fi

	return "${return_is_task_running:=/dev/null}"
}
# }}}
display_current_task() {                                        # {{{

	## List active task(s) in a temp file
	touch -- "${TASKW_CURRENT_LIST}"
	printf '%b\n\n' "			Choose a task to STOP" >> "${TASKW_CURRENT_LIST}"
	task +ACTIVE export | jq -r 'sort_by( -.urgency )[] | [ (.id|tostring), .description ] | join("	")' >> "${TASKW_CURRENT_LIST}"

	## Display active tasks list and get title from the choosen one
	TITLE=$(rofi -theme solarized_alternate -location 2 -l 5 -no-auto-select -i -dmenu -p "RUNNING task(s)" < "${TASKW_CURRENT_LIST}" |
		cut --delimiter="	" --field=2 |
		sed "s/[0-9]//g")
	ID=$(task "${TITLE}" simpleid | grep --after-context=2 -- ID | tail --lines=1 || return 0)

	## Remove temp file
	rm --force -- "${TASKW_CURRENT_LIST}"

	## If no task was selected (empty var) then exit
	if [ -z "${TITLE}" ]; then
		echo "Cancelled."
		debug_message "display_current_task − \
TITLE var is ${RED}empty${COLOR_DEBUG}."
		exit 0
	else
		debug_message "display_current_task − \
TITLE var: ${RED}${TITLE}${RESET}."
	fi

	## If no ID was found (empty var) then exit
	if [ -z "${ID}" ]; then
		echo "Cancelled."
		debug_message "display_current_task − \
ID var is ${RED}empty${COLOR_DEBUG}."
		exit 0
	else
		debug_message "display_current_task − \
ID var: ${RED}${ID}${RESET}."
	fi

	## Kill any pomodorrior process running for the current task
	pkill --full -- "${TITLE}"

	## Also kill any "sleep 60" remaining process
	pkill --full -- "sleep 60"

	## Stop the selected task and exit
	task "${ID}" stop >/dev/null \
		&& rm --force -- ~/.task/.current.task \
		&& exit 0
}
# }}}
select_task() {                                                 # {{{
	## Display pending tasks list and get title from the choosen one
	TITLE=$(task status:pending export | jq -r 'sort_by( -.urgency )[] | [ (.id|tostring), .description ] | join("	")' | sort --numeric-sort --reverse |
		rofi -theme solarized_alternate -location 2 -no-auto-select -i -dmenu -p "Task" |
		cut --delimiter="	" --field=2)

	[ -z "${TITLE}" ] && echo "Cancelled." && exit 0

	## Start task with pomodorrior script (task end after 25 minutes)
	pomodorrior "${TITLE}" && exit 0
}
# }}}

main() {                                                        # {{{

	is_task_running \
		&& display_current_task \
		&& exit 0

	select_task \
		&& exit 0

}
# }}}

# Manage arguments                                                # {{{
# This code can't be in a function due to argument management

if [ ! "${NBARGS}" -eq "0" ]; then

	manage_arg="0"

	## If the first argument is not an option
	if ! printf -- '%s' "${1}" | grep -q -E -- "^-+";
	then
		## Print help message and exit
		printf '%b\n' "${RED}Invalid option: ${1}${RESET}"
		printf '%b\n' "---"
		usage

		exit 1
	fi

	# Parse all options (start with a "-") one by one
	while printf -- '%s' "${1}" | grep -q -E -- "^-+"; do

	case "${1}" in
		-d|--debug )                          ## debug
			DEBUG=0
			;;
		-h|--help )                           ## help
			usage
			## Exit after help informations
			exit 0
			;;
		* )                                   ## unknow option
			printf '%b\n' "${RED}Invalid option: ${1}${RESET}"
			printf '%b\n' "---"
			usage
			exit 1
			;;
	esac

	debug_message "Arguments management − \
${RED}${1}${COLOR_DEBUG} option managed."

	## Move to the next argument
	shift
	manage_arg=$((manage_arg+1))

	done

	debug_message "Arguments management − \
${RED}${manage_arg}${COLOR_DEBUG} argument(s) successfully managed."
else
	debug_message "Arguments management − \
No arguments/options to manage."
fi

# }}}

main

exit 255