Skip to content

Commit

Permalink
Minor refactor (denisidoro#57)
Browse files Browse the repository at this point in the history
- [x] Define OPTIONS as global in opts::eval
- [x] Add script
- [x] Minor changes
  • Loading branch information
denisidoro authored Sep 24, 2019
1 parent 2ee253a commit 36cd52f
Show file tree
Hide file tree
Showing 13 changed files with 187 additions and 37 deletions.
6 changes: 3 additions & 3 deletions cheats/kubernetes.cheat
Original file line number Diff line number Diff line change
Expand Up @@ -3,16 +3,16 @@
# Print resource documentation
kubectl explain <resource>

# Get nodes (add option `-o wide` for details)
# Get nodes (add option '-o wide' for details)
kubectl get nodes

# Get namespaces
kubectl get namespaces

# Get pods from namespace (add option `-o wide` for details)
# Get pods from namespace (add option '-o wide' for details)
kubectl get pods -n <namespace>

# Get pods from all namespace (add option `-o wide` for details)
# Get pods from all namespace (add option '-o wide' for details)
kubectl get pods --all-namespaces

# Get services from namespace
Expand Down
10 changes: 2 additions & 8 deletions navi
Original file line number Diff line number Diff line change
Expand Up @@ -35,13 +35,7 @@ source "${SCRIPT_DIR}/src/main.sh"
##? full docs
##? Please refer to the README at https://github.com/denisidoro/navi

VERSION="0.9.1"
VERSION="0.9.2"

# workaround while dict::* can't handle newlines
case "${1:-}" in
help|--help) opts::extract_help "$0" && exit 0 ;;
esac

OPTIONS="$(opts::eval "$@")"
export NAVI_PATH="$(dict::get "$OPTIONS" path)"
opts::eval "$@"
main "$@"
21 changes: 21 additions & 0 deletions scripts/docker
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
#!/usr/bin/env bash
set -euo pipefail

debian="${1:-false}"

if $debian; then
docker run \
-it \
--entrypoint /bin/bash \
-v "$(pwd):/navi" \
debian \
-c 'apt update; apt install -y git curl; git clone --depth 1 https://github.com/junegunn/fzf.git ~/.fzf && yes | ~/.fzf/install; export PATH=$PATH:/navi; bash'
else
docker run \
-it \
--entrypoint /bin/bash \
-v "$(pwd):/navi" \
ellerbrock/alpine-bash-git \
-c 'git clone --depth 1 https://github.com/junegunn/fzf.git ~/.fzf && yes | ~/.fzf/install; export PATH=$PATH:/navi; bash'
fi

8 changes: 5 additions & 3 deletions scripts/install
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ script() {
echo "${SCRIPT_DIR}/navi" '"$@"'
}

BIN="/usr/local/bin/navi"
script > "$BIN"
chmod +x "$BIN"
folder="${1:-/usr/local/bin}"
bin="${folder}/navi"

script > "$bin"
chmod +x "$bin"
10 changes: 6 additions & 4 deletions src/arg.sh
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
#!/usr/bin/env bash

ARG_REGEX="<[0-9a-zA-Z_]+>"
ARG_DELIMITER="£"
ARG_DELIMITER="\f"

arg::dict() {
local -r fn="$(awk -F'---' '{print $1}')"
local -r opts="$(awk -F'---' '{print $2}')"
local -r input="$(cat)"

local -r fn="$(echo "$input" | awk -F'---' '{print $1}')"
local -r opts="$(echo "$input" | awk -F'---' '{print $2}')"

dict::new fn "$fn" opts "$opts"
}
Expand Down Expand Up @@ -34,7 +36,7 @@ arg::deserialize() {
local -r out="$arg"
fi

echo "$out" | sed "s/${ARG_DELIMITER}/ /g"
echo "$out" | tr "${ARG_DELIMITER}" " "
}

# TODO: separation of concerns
Expand Down
9 changes: 8 additions & 1 deletion src/dict.sh
Original file line number Diff line number Diff line change
@@ -1,5 +1,12 @@
#!/usr/bin/env bash

# for an explanation behind this namespace, please check
# https://medium.com/@den.isidoro/dictionaries-in-shell-scripts-61d34e1c91c6

# LIMITATIONS:
# values with non-trivial whitespaces (newlines, subsequent spaces, etc)
# aren't handled very well

DICT_DELIMITER='\f'

dict::_post() {
Expand Down Expand Up @@ -64,7 +71,7 @@ dict::get() {
if [ $matches -gt 1 ]; then
echo "$result" | dict::_unescape_value
else
echo "$result" | sed -E "s/${prefix}//" | dict::_unescape_value
echo "$result" | sed -E "s/${prefix}//" | dict::_unescape_value | sed -E 's/^[[:space:]]*//'
fi
}

Expand Down
20 changes: 16 additions & 4 deletions src/main.sh
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
#!/usr/bin/env bash

if ${NAVI_FORCE_GNU:-false}; then
source "${DOTFILES}/scripts/core/main.sh"
fi

source "${SCRIPT_DIR}/src/arg.sh"
source "${SCRIPT_DIR}/src/cheat.sh"
source "${SCRIPT_DIR}/src/dict.sh"
Expand Down Expand Up @@ -56,8 +60,12 @@ handler::preview() {
[ -n "$cheat" ] && selection::cmd "$selection" "$cheat"
}

handler::text() {
dict::get "$OPTIONS" text
handler::help() {
echo "$TEXT"
}

handler::version() {
echo "${VERSION:-unknown}"
}

main() {
Expand All @@ -66,15 +74,19 @@ main() {
local -r query="$(dict::get "$OPTIONS" query)"
handler::preview "$query" \
|| echo "Unable to find command for '$query'"
echo "$NAVI_PATH"
;;
search)
health::fzf
local -r query="$(dict::get "$OPTIONS" query)"
search::save "$query" || true
handler::main
;;
text)
handler::text
version)
handler::version
;;
help)
handler::help
;;
*)
health::fzf
Expand Down
7 changes: 4 additions & 3 deletions src/opts.sh
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,8 @@ opts::eval() {
case $arg in
--print) print=true ;;
--no-interpolation) interpolation=false ;;
--version|version) dict::new entry_point "text" text "${VERSION:-unknown}" && exit 0 ;;
help|--help) dict::new entry_point "text" text "$(opts::extract_help "$0")" && exit 0 ;;
--version|version) entry_point="version" ;;
help|--help) entry_point="help"; TEXT="$(opts::extract_help "$0")" ;;
--command-for) wait_for="command-for" ;;
--no-preview) preview=false ;;
--path) wait_for="path" ;;
Expand All @@ -36,5 +36,6 @@ opts::eval() {
esac
done

dict::new entry_point "$entry_point" print "$print" interpolation "$interpolation" preview "$preview" query "${query:-}" path "$path"
OPTIONS="$(dict::new entry_point "$entry_point" print "$print" interpolation "$interpolation" preview "$preview" query "${query:-}")"
export NAVI_PATH="$path"
}
2 changes: 1 addition & 1 deletion src/selection.sh
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ selection::dict() {
local -r tags="$(echo "$str" | awk -F'[' '{print $NF}' | tr -d ']')"
local -r core="$(echo "$str" | sed -e "s/ \[${tags}\]$//")"

dict::new core "$core" tags "$tags"
dict::new core "$core" tags "$tags" | sed "s/'''/'/g"
}

selection::core_is_comment() {
Expand Down
6 changes: 6 additions & 0 deletions src/str.sh
Original file line number Diff line number Diff line change
Expand Up @@ -29,3 +29,9 @@ str::last_paragraph_line() {
str::first_word() {
awk '{print $1}'
}

str::index_last_occurrence() {
local -r char="$1"

awk 'BEGIN{FS=""}{ for(i=1;i<=NF;i++){ if($i=="'"$char"'"){ p=i } }}END{ print p }'
}
7 changes: 5 additions & 2 deletions test/cheat_test.sh
Original file line number Diff line number Diff line change
@@ -1,4 +1,7 @@
#!/usr/bin/env bash

test::run "We can find at least one known cheatsheet" \
'cheat::find | grep -q "docker.cheat"'
assert_docker_cheat() {
cheat::find | grep -q "docker.cheat"
}

test::run "We can find at least one known cheatsheet" assert_docker_cheat
16 changes: 8 additions & 8 deletions test/core.sh
Original file line number Diff line number Diff line change
@@ -1,27 +1,27 @@
#!/usr/bin/env bash

source "${SCRIPT_DIR}/src/main.sh"
source "${SCRIPT_DIR}/test/log.sh"

OPTIONS="$(opts::eval "$@")"
export NAVI_PATH="$(dict::get "$OPTIONS" path)"
opts::eval "$@"

PASSED=0
FAILED=0

test::success() {
PASSED=$((PASSED+1))
echo "Test passed!"
log::success "Test passed!"
}

test::fail() {
FAILED=$((FAILED+1))
echo "Test failed..."
log::error "Test failed..."
return
}

test::run() {
echo
echo "-> $1"
log::note "$1"
shift
eval "$*" && test::success || test::fail
}
Expand All @@ -31,18 +31,18 @@ test::equals() {
local -r expected="$(echo "${1:-}" | tr -d '\n' | sed 's/\\n//g')"

if [[ "$actual" != "$expected" ]]; then
echo "Expected '${expected}' but got '${actual}'"
log::success "Expected '${expected}' but got '${actual}'"
return 2
fi
}

test::finish() {
echo
if [ $FAILED -gt 0 ]; then
echo "${PASSED} tests passed but ${FAILED} failed... :("
log::error "${PASSED} tests passed but ${FAILED} failed... :("
exit "${FAILED}"
else
echo "All ${PASSED} tests passed! :)"
log::success "All ${PASSED} tests passed! :)"
exit 0
fi
}
102 changes: 102 additions & 0 deletions test/log.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
#!/usr/bin/env bash

_export_colors() {
if ! ${DOT_COLORS_EXPORTED:-false}; then
if [ -z ${TERM:-} ] || [ $TERM = "dumb" ]; then
bold=""
underline=""
freset=""
purple=""
red=""
green=""
tan=""
blue=""
else
bold=$(tput bold)
underline=$(tput sgr 0 1)
freset=$(tput sgr0)
purple=$(tput setaf 171)
red=$(tput setaf 1)
green=$(tput setaf 76)
tan=$(tput setaf 3)
blue=$(tput setaf 38)
fi

log_black=30
log_red=31
log_green=32
log_yellow=33
log_blue=34
log_purple=35
log_cyan=36
log_white=37

log_regular=0
log_bold=1
log_underline=4

readonly DOT_COLORS_EXPORTED=true
fi
}

log::color() {
_export_colors
local bg=false
case "$@" in
*reset*) echo "\e[0m"; exit 0 ;;
*black*) color=$log_black ;;
*red*) color=$log_red ;;
*green*) color=$log_green ;;
*yellow*) color=$log_yellow ;;
*blue*) color=$log_blue ;;
*purple*) color=$log_purple ;;
*cyan*) color=$log_cyan ;;
*white*) color=$log_white ;;
esac
case "$@" in
*regular*) mod=$log_regular ;;
*bold*) mod=$log_bold ;;
*underline*) mod=$log_underline ;;
esac
case "$@" in
*background*) bg=true ;;
*bg*) bg=true ;;
esac

if $bg; then
echo "\e[${color}m"
else
echo "\e[${mod:-$log_regular};${color}m"
fi
}

if [ -z ${LOG_FILE+x} ]; then
readonly LOG_FILE="/tmp/$(basename "$0").log"
fi

_log() {
local template=$1
shift
if ${log_to_file:-false}; then
echo -e $(printf "$template" "$@") | tee -a "$LOG_FILE" >&2
else
echo -e $(printf "$template" "$@")
fi
}

_header() {
local TOTAL_CHARS=60
local total=$TOTAL_CHARS-2
local size=${#1}
local left=$((($total - $size) / 2))
local right=$(($total - $size - $left))
printf "%${left}s" '' | tr ' ' =
printf " $1 "
printf "%${right}s" '' | tr ' ' =
}

log::header() { _export_colors && _log "\n${bold}${purple}$(_header "$1")${freset}\n"; }
log::success() { _export_colors && _log "${green}✔ %s${freset}\n" "$@"; }
log::error() { _export_colors && _log "${red}✖ %s${freset}\n" "$@"; }
log::warning() { _export_colors && _log "${tan}➜ %s${freset}\n" "$@"; }
log::note() { _export_colors && _log "${blue}➜ %s${freset}\n" "$@"; }

0 comments on commit 36cd52f

Please sign in to comment.