-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathminimist.sh
More file actions
executable file
·143 lines (126 loc) · 4.1 KB
/
Copy pathminimist.sh
File metadata and controls
executable file
·143 lines (126 loc) · 4.1 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
#!/bin/bash
# https://github.com/zix99/bash-minimist
# Usage:
#
# Minimist is modeled after a similar script by the same name written for nodejs/javascript
# Its goal is to provide a minimal command-line parser for input into scripts
# Unlike classical approaches, no help-doc or pre-defined variable sets are defined
#
# Quickstart
# In your script call
# source minimist.sh
#
# Or to not override $@ call
# source minimist.sh $@
#
# To read values once parse
# -a ARG_a=y
# -ab ARG_a=y ARG_b=y
# --abc ARG_ABC=y
# --abc 123 ARG_ABC=123
# --abc=234 ARG_ABC=234
# -a a b ARG_a=y ARGV="a b"
# --a-b#c ARG_A_B_C=y
#
# ARG_0 preserves $0
# ARG_V is the positionals before a ending marker --
# $1...n are only positional arguments, exclusive of flags
# Everything following -- marker are treated as positional arguments
# $@ includes all positional arguments, excluding flags
#
# Functional changes
# To change basic functional requirements, please see configuration below
# Either change it inline, or declare it before calling `source minimist.sh`
# Configuration
# If y, a flag that looks like "--abc 123", 123 will be positional rather than a value of 'abc'
AOPT_POSITIONAL_OVER_FLAG=${AOPT_POSITIONAL_OVER_FLAG:-y}
# Arguments for `declare`. Defaults to -r for readonly. eg adding `-x` will export values
AOPT_DECLARE_FLAGS=${AOPT_DECLARE_FLAGS:--r}
# If y, will override -- ($@) to be the full positional argument set, rather than remaining unparsed variables
AOPT_SET_ARGS=${AOPT_SET_ARGS:-y}
# Value to set for truthy flags
AOPT_TRUTHY=${AOPT_TRUTHY:-y}
# Name of a function to call on error
AOPT_ON_ERROR=${AOPT_ON_ERROR:-}
# If y, exit on error
AOPT_EXIT_ON_ERROR=${AOPT_EXIT_ON_ERROR:-y}
# Prefix of exported arguments
AOPT_PREFIX=${AOPT_PREFIX:-ARG_}
# Array of valid flags (If empty, assume all flags are valid)
[[ -z $AOPT_VALID_ARGS ]] && AOPT_VALID_ARGS=()
################
function __handleError() {
[[ ! -z $AOPT_ON_ERROR ]] && $AOPT_ON_ERROR "$1" || echo "$1"
if [[ ${AOPT_EXIT_ON_ERROR^^} == 'Y' ]]; then
exit 2
fi
}
function __handleInvalidKey() {
__handleError "Invalid key: '$1', as part of '${2:-$1}'"
}
function __validateArgument() {
if [[ ${#AOPT_VALID_ARGS[@]} -gt 0 && ! " ${AOPT_VALID_ARGS[*]^^} " =~ " ${1^^} " ]]; then
__handleError "Invalid argument: --${1}"
fi
}
function __sanitize() {
local CLEAN=$@
CLEAN=${CLEAN//[^a-zA-Z0-9_]/_}
echo -n $CLEAN
}
ARG_0=$0
ARGV=
while (( "$#" )); do
case "$1" in
--) # Stop parsing args (the rest is positional)
shift
break
;;
--*=*) # --abc=123
KEY=${1%=*}
KEY=${KEY:2}
KEY=$(__sanitize $KEY)
__validateArgument ${KEY}
declare ${AOPT_DECLARE_FLAGS} "${AOPT_PREFIX}${KEY^^}=${1#*=}" 2>/dev/null || __handleInvalidKey $KEY
shift
;;
--*) # --abc OR --abc 123
KEY=$(__sanitize $1)
__validateArgument ${KEY:2}
KEY=${KEY^^}
shift
if [[ ! -z $1 && ${1:0:1} != '-' && ${AOPT_POSITIONAL_OVER_FLAG^^} != 'Y' ]]; then
declare ${AOPT_DECLARE_FLAGS} "${AOPT_PREFIX}${KEY:2}=$1" 2>/dev/null || __handleInvalidKey $KEY
shift
else
declare ${AOPT_DECLARE_FLAGS} "${AOPT_PREFIX}${KEY:2}=$AOPT_TRUTHY" 2>/dev/null || __handleInvalidKey $KEY
fi
;;
-*) # Multi-flag single-char args; -abc -a -b -C
KEY=$1
for (( i=1; i<${#KEY}; i++ )); do
[[ ${#AOPT_VALID_ARGS[@]} -gt 0 && ! " ${AOPT_VALID_ARGS[*]} " =~ " ${1:$i:1} " ]] \
&& __handleError "Invalid flag: -${1:$i:1}"
declare ${AOPT_DECLARE_FLAGS} "${AOPT_PREFIX}${KEY:$i:1}=$AOPT_TRUTHY" 2>/dev/null || __handleInvalidKey ${KEY:$i:1} $KEY
done
shift
;;
*) # positional args
ARGV="${ARGV:+$ARGV }$1"
shift
;;
esac
done
# Reset positional arguments
declare ${AOPT_DECLARE_FLAGS} "${AOPT_PREFIX}V=${ARGV}"
declare ${AOPT_DECLARE_FLAGS} "${AOPT_PREFIX}0=${ARG_0}"
if [[ ${AOPT_SET_ARGS^^} == 'Y' ]]; then
set -- ${ARGV} "$@"
fi
# Cleanup non-exported things (since this will be sourced)
unset ARGV
unset KEY
unset __sanitize
unset __handleInvalidKey
unset __handleError
unset __validateArgument