busser-bats 0.5.0 → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/ci.yml +32 -0
- data/.github/workflows/pr-title.yml +28 -0
- data/.github/workflows/publish.yml +67 -0
- data/.gitignore +0 -1
- data/.release-please-manifest.json +3 -0
- data/.rubocop.yml +2 -7
- data/.yamllint +6 -0
- data/CHANGELOG.md +23 -1
- data/CONTRIBUTING.md +86 -0
- data/Gemfile +9 -13
- data/README.md +100 -30
- data/Rakefile +43 -24
- data/busser-bats.gemspec +23 -15
- data/config/features/support/env.rb +0 -5
- data/features/support/env.rb +5 -14
- data/features/test_command.feature +31 -31
- data/lib/busser/bats/version.rb +3 -1
- data/lib/busser/runner_plugin/bats.rb +27 -3
- data/release-please-config.json +15 -0
- data/renovate.json +2 -2
- data/spec/busser/runner_plugin/bats_spec.rb +41 -0
- data/spec/spec_helper.rb +2 -0
- data/vendor/bats/LICENSE.md +53 -0
- data/vendor/bats/README.md +84 -242
- data/vendor/bats/VERSION.txt +1 -1
- data/vendor/bats/bin/bats +75 -0
- data/vendor/bats/install.sh +20 -28
- data/vendor/bats/lib/bats-core/common.bash +278 -0
- data/vendor/bats/lib/bats-core/formatter.bash +151 -0
- data/vendor/bats/lib/bats-core/preprocessing.bash +19 -0
- data/vendor/bats/lib/bats-core/semaphore.bash +113 -0
- data/vendor/bats/lib/bats-core/test_functions.bash +539 -0
- data/vendor/bats/lib/bats-core/tracing.bash +425 -0
- data/vendor/bats/lib/bats-core/validator.bash +37 -0
- data/vendor/bats/lib/bats-core/warnings.bash +44 -0
- data/vendor/bats/libexec/bats-core/bats +549 -0
- data/vendor/bats/libexec/bats-core/bats-exec-file +402 -0
- data/vendor/bats/libexec/bats-core/bats-exec-suite +342 -0
- data/vendor/bats/libexec/bats-core/bats-exec-test +383 -0
- data/vendor/bats/libexec/bats-core/bats-format-cat +6 -0
- data/vendor/bats/libexec/bats-core/bats-format-junit +293 -0
- data/vendor/bats/libexec/bats-core/bats-format-pretty +360 -0
- data/vendor/bats/libexec/bats-core/bats-format-tap +55 -0
- data/vendor/bats/libexec/bats-core/bats-format-tap13 +89 -0
- data/vendor/bats/libexec/bats-core/bats-gather-tests +402 -0
- data/vendor/bats/libexec/bats-core/bats-preprocess +118 -0
- data/vendor/bats/man/Makefile +16 -3
- data/vendor/bats/man/bats.1 +100 -58
- data/vendor/bats/man/bats.1.ronn +102 -12
- data/vendor/bats/man/bats.7 +205 -83
- data/vendor/bats/man/bats.7.ronn +262 -14
- data/vendor/bats/uninstall.sh +63 -0
- metadata +44 -22
- data/.github/dependabot.yml +0 -8
- data/.github/workflows/lint.yaml +0 -9
- data/.github/workflows/publish.yaml +0 -35
- data/.tool-versions +0 -1
- data/Guardfile +0 -26
- data/vendor/bats/.gitattributes +0 -3
- data/vendor/bats/.travis.yml +0 -5
- data/vendor/bats/LICENSE +0 -20
- data/vendor/bats/bin/bats +0 -1
- data/vendor/bats/package.json +0 -9
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
|
|
3
|
+
set -euo pipefail
|
|
4
|
+
|
|
5
|
+
# Note: We first need to use POSIX's `[ ... ]' instead of Bash's `[[ ... ]]'
|
|
6
|
+
# because this is the check for Bash, where the shell may not be Bash. Once we
|
|
7
|
+
# confirm that we are in Bash, we can use [[ ... ]] and (( ... )). Note that
|
|
8
|
+
# these [[ ... ]] and (( ... )) do not cause syntax errors in POSIX shells,
|
|
9
|
+
# though they can be parsed differently.
|
|
10
|
+
if [ -z "${BASH_VERSION-}" ] ||
|
|
11
|
+
[[ -z "${BASH_VERSINFO-}" ]] ||
|
|
12
|
+
((BASH_VERSINFO[0] < 3 || (BASH_VERSINFO[0] == 3 && BASH_VERSINFO[1] < 2)))
|
|
13
|
+
then
|
|
14
|
+
printf 'bats: this program needs to be run by Bash >= 3.2\n' >&2
|
|
15
|
+
exit 1
|
|
16
|
+
fi
|
|
17
|
+
|
|
18
|
+
if command -v greadlink >/dev/null; then
|
|
19
|
+
bats_readlinkf() {
|
|
20
|
+
greadlink -f "$1"
|
|
21
|
+
}
|
|
22
|
+
else
|
|
23
|
+
bats_readlinkf() {
|
|
24
|
+
readlink -f "$1"
|
|
25
|
+
}
|
|
26
|
+
fi
|
|
27
|
+
|
|
28
|
+
fallback_to_readlinkf_posix() {
|
|
29
|
+
bats_readlinkf() {
|
|
30
|
+
[ "${1:-}" ] || return 1
|
|
31
|
+
max_symlinks=40
|
|
32
|
+
CDPATH='' # to avoid changing to an unexpected directory
|
|
33
|
+
|
|
34
|
+
target=$1
|
|
35
|
+
[ -e "${target%/}" ] || target=${1%"${1##*[!/]}"} # trim trailing slashes
|
|
36
|
+
[ -d "${target:-/}" ] && target="$target/"
|
|
37
|
+
|
|
38
|
+
cd -P . 2>/dev/null || return 1
|
|
39
|
+
while [ "$max_symlinks" -ge 0 ] && max_symlinks=$((max_symlinks - 1)); do
|
|
40
|
+
if [ ! "$target" = "${target%/*}" ]; then
|
|
41
|
+
case $target in
|
|
42
|
+
/*) cd -P "${target%/*}/" 2>/dev/null || break ;;
|
|
43
|
+
*) cd -P "./${target%/*}" 2>/dev/null || break ;;
|
|
44
|
+
esac
|
|
45
|
+
target=${target##*/}
|
|
46
|
+
fi
|
|
47
|
+
|
|
48
|
+
if [ ! -L "$target" ]; then
|
|
49
|
+
target="${PWD%/}${target:+/}${target}"
|
|
50
|
+
printf '%s\n' "${target:-/}"
|
|
51
|
+
return 0
|
|
52
|
+
fi
|
|
53
|
+
|
|
54
|
+
# `ls -dl` format: "%s %u %s %s %u %s %s -> %s\n",
|
|
55
|
+
# <file mode>, <number of links>, <owner name>, <group name>,
|
|
56
|
+
# <size>, <date and time>, <pathname of link>, <contents of link>
|
|
57
|
+
# https://pubs.opengroup.org/onlinepubs/9699919799/utilities/ls.html
|
|
58
|
+
link=$(ls -dl -- "$target" 2>/dev/null) || break
|
|
59
|
+
target=${link#*" $target -> "}
|
|
60
|
+
done
|
|
61
|
+
return 1
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
if ! BATS_PATH=$(bats_readlinkf "${BASH_SOURCE[0]}" 2>/dev/null); then
|
|
66
|
+
fallback_to_readlinkf_posix
|
|
67
|
+
BATS_PATH=$(bats_readlinkf "${BASH_SOURCE[0]}")
|
|
68
|
+
fi
|
|
69
|
+
|
|
70
|
+
export BATS_SAVED_PATH=$PATH
|
|
71
|
+
BATS_BASE_LIBDIR=lib # this will be patched with the true value in install.sh
|
|
72
|
+
|
|
73
|
+
export BATS_ROOT=${BATS_PATH%/*/*}
|
|
74
|
+
export -f bats_readlinkf
|
|
75
|
+
exec env BATS_ROOT="$BATS_ROOT" BATS_LIBDIR="${BATS_BASE_LIBDIR:-lib}" "$BATS_ROOT/libexec/bats-core/bats" "$@"
|
data/vendor/bats/install.sh
CHANGED
|
@@ -1,37 +1,29 @@
|
|
|
1
1
|
#!/usr/bin/env bash
|
|
2
|
-
set -e
|
|
3
|
-
|
|
4
|
-
resolve_link() {
|
|
5
|
-
$(type -p greadlink readlink | head -1) "$1"
|
|
6
|
-
}
|
|
7
|
-
|
|
8
|
-
abs_dirname() {
|
|
9
|
-
local cwd="$(pwd)"
|
|
10
|
-
local path="$1"
|
|
11
2
|
|
|
12
|
-
|
|
13
|
-
cd "${path%/*}"
|
|
14
|
-
local name="${path##*/}"
|
|
15
|
-
path="$(resolve_link "$name" || true)"
|
|
16
|
-
done
|
|
3
|
+
set -e
|
|
17
4
|
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
}
|
|
5
|
+
BATS_ROOT="${0%/*}"
|
|
6
|
+
PREFIX="${1%/}"
|
|
7
|
+
LIBDIR="${2:-lib}"
|
|
21
8
|
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
9
|
+
if [[ -z "$PREFIX" ]]; then
|
|
10
|
+
printf '%s\n' \
|
|
11
|
+
"usage: $0 <prefix> [base_libdir]" \
|
|
12
|
+
" e.g. $0 /usr/local" \
|
|
13
|
+
" $0 /usr/local lib64" >&2
|
|
27
14
|
exit 1
|
|
28
15
|
fi
|
|
29
16
|
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
17
|
+
install -d -m 755 "$PREFIX"/{bin,libexec/bats-core,"${LIBDIR}"/bats-core,share/man/man{1,7}}
|
|
18
|
+
|
|
19
|
+
install -m 755 "$BATS_ROOT/bin"/* "$PREFIX/bin"
|
|
20
|
+
install -m 755 "$BATS_ROOT/libexec/bats-core"/* "$PREFIX/libexec/bats-core"
|
|
21
|
+
install -m 755 "$BATS_ROOT/lib/bats-core"/* "$PREFIX/${LIBDIR}/bats-core"
|
|
22
|
+
install -m 644 "$BATS_ROOT/man/bats.1" "$PREFIX/share/man/man1"
|
|
23
|
+
install -m 644 "$BATS_ROOT/man/bats.7" "$PREFIX/share/man/man7"
|
|
24
|
+
|
|
25
|
+
read -rd '' BATS_EXE_CONTENTS <"$PREFIX/bin/bats" || true
|
|
26
|
+
BATS_EXE_CONTENTS=${BATS_EXE_CONTENTS/"BATS_BASE_LIBDIR=lib"/"BATS_BASE_LIBDIR=${LIBDIR}"}
|
|
27
|
+
printf "%s" "$BATS_EXE_CONTENTS" >| "$PREFIX/bin/bats"
|
|
36
28
|
|
|
37
29
|
echo "Installed Bats to $PREFIX/bin/bats"
|
|
@@ -0,0 +1,278 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
|
|
3
|
+
bats_prefix_lines_for_tap_output() {
|
|
4
|
+
while IFS= read -r line; do
|
|
5
|
+
printf '# %s\n' "$line" || break # avoid feedback loop when errors are redirected into BATS_OUT (see #353)
|
|
6
|
+
done
|
|
7
|
+
if [[ -n "$line" ]]; then
|
|
8
|
+
printf '# %s\n' "$line"
|
|
9
|
+
fi
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
function bats_replace_filename() {
|
|
13
|
+
local line
|
|
14
|
+
while read -r line; do
|
|
15
|
+
printf "%s\n" "${line//$BATS_TEST_SOURCE/$BATS_TEST_FILENAME}"
|
|
16
|
+
done
|
|
17
|
+
if [[ -n "$line" ]]; then
|
|
18
|
+
printf "%s\n" "${line//$BATS_TEST_SOURCE/$BATS_TEST_FILENAME}"
|
|
19
|
+
fi
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
bats_quote_code() { # <var> <code>
|
|
23
|
+
printf -v "$1" -- "%s%s%s" "$BATS_BEGIN_CODE_QUOTE" "$2" "$BATS_END_CODE_QUOTE"
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
bats_check_valid_version() {
|
|
27
|
+
if [[ ! $1 =~ [0-9]+.[0-9]+.[0-9]+ ]]; then
|
|
28
|
+
printf "ERROR: version '%s' must be of format <major>.<minor>.<patch>!\n" "$1" >&2
|
|
29
|
+
exit 1
|
|
30
|
+
fi
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
# compares two versions. Return 0 when version1 < version2
|
|
34
|
+
bats_version_lt() { # <version1> <version2>
|
|
35
|
+
bats_check_valid_version "$1"
|
|
36
|
+
bats_check_valid_version "$2"
|
|
37
|
+
|
|
38
|
+
local -a version1_parts version2_parts
|
|
39
|
+
IFS=. read -ra version1_parts <<<"$1"
|
|
40
|
+
IFS=. read -ra version2_parts <<<"$2"
|
|
41
|
+
|
|
42
|
+
local -i i
|
|
43
|
+
for i in {0..2}; do
|
|
44
|
+
if ((version1_parts[i] < version2_parts[i])); then
|
|
45
|
+
return 0
|
|
46
|
+
elif ((version1_parts[i] > version2_parts[i])); then
|
|
47
|
+
return 1
|
|
48
|
+
fi
|
|
49
|
+
done
|
|
50
|
+
# if we made it this far, they are equal -> also not less then
|
|
51
|
+
return 2 # use other failing return code to distinguish equal from gt
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
# ensure a minimum version of bats is running or exit with failure
|
|
55
|
+
bats_require_minimum_version() { # <required version>
|
|
56
|
+
local required_minimum_version=$1
|
|
57
|
+
|
|
58
|
+
if bats_version_lt "$BATS_VERSION" "$required_minimum_version"; then
|
|
59
|
+
printf "BATS_VERSION=%s does not meet required minimum %s\n" "$BATS_VERSION" "$required_minimum_version"
|
|
60
|
+
exit 1
|
|
61
|
+
fi
|
|
62
|
+
|
|
63
|
+
if bats_version_lt "$BATS_GUARANTEED_MINIMUM_VERSION" "$required_minimum_version"; then
|
|
64
|
+
BATS_GUARANTEED_MINIMUM_VERSION="$required_minimum_version"
|
|
65
|
+
fi
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
# returns 0 when search-value is found in array
|
|
69
|
+
bats_linear_reverse_search() { # <search-value> <array-name>
|
|
70
|
+
local -r search_value=$1 array_name=$2
|
|
71
|
+
eval "local -ri array_length=\${#${array_name}[@]}"
|
|
72
|
+
# shellcheck disable=SC2154
|
|
73
|
+
for ((i=array_length - 1; i >=0; --i)); do
|
|
74
|
+
eval "local value=\"\${${array_name}[i]}\""
|
|
75
|
+
# shellcheck disable=SC2154
|
|
76
|
+
if [[ $value == "$search_value" ]]; then
|
|
77
|
+
return 0
|
|
78
|
+
fi
|
|
79
|
+
done
|
|
80
|
+
return 1
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
# returns 0 when search-value is found in array
|
|
84
|
+
bats_binary_search() { # <search-value> <array-name>
|
|
85
|
+
if [[ $# -ne 2 ]]; then
|
|
86
|
+
printf "ERROR: bats_binary_search requires exactly 2 arguments: <search value> <array name>\n" >&2
|
|
87
|
+
return 2
|
|
88
|
+
fi
|
|
89
|
+
|
|
90
|
+
local -r search_value=$1 array_name=$2
|
|
91
|
+
|
|
92
|
+
# we'd like to test if array is set but we cannot distinguish unset from empty arrays, so we need to skip that
|
|
93
|
+
|
|
94
|
+
local start=0 mid end mid_value
|
|
95
|
+
# start is inclusive, end is exclusive ...
|
|
96
|
+
eval "end=\${#${array_name}[@]}"
|
|
97
|
+
|
|
98
|
+
# so start == end means empty search space
|
|
99
|
+
while ((start < end)); do
|
|
100
|
+
mid=$(((start + end) / 2))
|
|
101
|
+
eval "mid_value=\${${array_name}[$mid]}"
|
|
102
|
+
if [[ "$mid_value" == "$search_value" ]]; then
|
|
103
|
+
return 0
|
|
104
|
+
elif [[ "$mid_value" < "$search_value" ]]; then
|
|
105
|
+
# This branch excludes equality -> +1 to skip the mid element.
|
|
106
|
+
# This +1 also avoids endless recursion on odd sized search ranges.
|
|
107
|
+
start=$((mid + 1))
|
|
108
|
+
else
|
|
109
|
+
end=$mid
|
|
110
|
+
fi
|
|
111
|
+
done
|
|
112
|
+
|
|
113
|
+
# did not find it -> its not there
|
|
114
|
+
return 1
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
# store the values in ascending (string!) order in result array
|
|
118
|
+
# Intended for short lists! (uses insertion sort)
|
|
119
|
+
bats_sort() { # <result-array-name> <values to sort...>
|
|
120
|
+
local -r result_name=$1
|
|
121
|
+
shift
|
|
122
|
+
|
|
123
|
+
if (($# == 1)) && [[ $1 == "" ]]; then
|
|
124
|
+
shift # remove leading "" to deal with bash 3 expanding "${empty_array[@]}" to one ""
|
|
125
|
+
fi
|
|
126
|
+
|
|
127
|
+
if (($# == 0)); then
|
|
128
|
+
eval "$result_name=()"
|
|
129
|
+
return 0
|
|
130
|
+
fi
|
|
131
|
+
|
|
132
|
+
local -a sorted_array=()
|
|
133
|
+
local -i i
|
|
134
|
+
while (( $# > 0 )); do # loop over input values
|
|
135
|
+
local current_value="$1"
|
|
136
|
+
shift
|
|
137
|
+
for ((i = ${#sorted_array[@]}; i >= 0; --i)); do # loop over output array from end
|
|
138
|
+
if (( i == 0 )) || [[ ${sorted_array[i - 1]} < $current_value ]]; then
|
|
139
|
+
# insert new element at (freed) desired location
|
|
140
|
+
sorted_array[i]=$current_value
|
|
141
|
+
break
|
|
142
|
+
else
|
|
143
|
+
# shift bigger elements one position to the end
|
|
144
|
+
sorted_array[i]=${sorted_array[i - 1]}
|
|
145
|
+
fi
|
|
146
|
+
done
|
|
147
|
+
done
|
|
148
|
+
|
|
149
|
+
eval "$result_name=(\"\${sorted_array[@]}\")"
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
# check if all search values (must be sorted!) are in the (sorted!) array
|
|
153
|
+
# Intended for short lists/arrays!
|
|
154
|
+
bats_all_in() { # <sorted-array> <sorted search values...>
|
|
155
|
+
local -r haystack_array=$1
|
|
156
|
+
shift
|
|
157
|
+
|
|
158
|
+
local -i haystack_length # just to appease shellcheck
|
|
159
|
+
eval "local -r haystack_length=\${#${haystack_array}[@]}"
|
|
160
|
+
|
|
161
|
+
local -i haystack_index=0 # initialize only here to continue from last search position
|
|
162
|
+
local search_value haystack_value # just to appease shellcheck
|
|
163
|
+
local -i i
|
|
164
|
+
for ((i = 1; i <= $#; ++i)); do
|
|
165
|
+
eval "local search_value=${!i}"
|
|
166
|
+
for (( ; haystack_index < haystack_length; ++haystack_index)); do
|
|
167
|
+
eval "local haystack_value=\${${haystack_array}[$haystack_index]}"
|
|
168
|
+
if [[ $haystack_value > "$search_value" ]]; then
|
|
169
|
+
# we passed the location this value would have been at -> not found
|
|
170
|
+
return 1
|
|
171
|
+
elif [[ $haystack_value == "$search_value" ]]; then
|
|
172
|
+
continue 2 # search value found -> try the next one
|
|
173
|
+
fi
|
|
174
|
+
done
|
|
175
|
+
return 1 # we ran of the end of the haystack without finding the value!
|
|
176
|
+
done
|
|
177
|
+
|
|
178
|
+
# did not return from loop above -> all search values were found
|
|
179
|
+
return 0
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
# check if any search value (must be sorted!) is in the (sorted!) array
|
|
183
|
+
# intended for short lists/arrays
|
|
184
|
+
bats_any_in() { # <sorted-array> <sorted search values>
|
|
185
|
+
local -r haystack_array=$1
|
|
186
|
+
shift
|
|
187
|
+
|
|
188
|
+
local -i haystack_length # just to appease shellcheck
|
|
189
|
+
eval "local -r haystack_length=\${#${haystack_array}[@]}"
|
|
190
|
+
|
|
191
|
+
local -i haystack_index=0 # initialize only here to continue from last search position
|
|
192
|
+
local search_value haystack_value # just to appease shellcheck
|
|
193
|
+
local -i i
|
|
194
|
+
for ((i = 1; i <= $#; ++i)); do
|
|
195
|
+
eval "local search_value=${!i}"
|
|
196
|
+
for (( ; haystack_index < haystack_length; ++haystack_index)); do
|
|
197
|
+
eval "local haystack_value=\${${haystack_array}[$haystack_index]}"
|
|
198
|
+
if [[ $haystack_value > "$search_value" ]]; then
|
|
199
|
+
continue 2 # search value not in array! -> try next
|
|
200
|
+
elif [[ $haystack_value == "$search_value" ]]; then
|
|
201
|
+
return 0 # search value found
|
|
202
|
+
fi
|
|
203
|
+
done
|
|
204
|
+
done
|
|
205
|
+
|
|
206
|
+
# did not return from loop above -> no search value was found
|
|
207
|
+
return 1
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
bats_trim() { # <output-variable> <string>
|
|
211
|
+
local -r bats_trim_ltrimmed=${2#"${2%%[![:space:]]*}"} # cut off leading whitespace
|
|
212
|
+
# shellcheck disable=SC2034 # used in eval!
|
|
213
|
+
local -r bats_trim_trimmed=${bats_trim_ltrimmed%"${bats_trim_ltrimmed##*[![:space:]]}"} # cut off trailing whitespace
|
|
214
|
+
eval "$1=\$bats_trim_trimmed"
|
|
215
|
+
}
|
|
216
|
+
|
|
217
|
+
# a helper function to work around unbound variable errors with ${arr[@]} on Bash 3
|
|
218
|
+
bats_append_arrays_as_args() { # <array...> -- <command ...>
|
|
219
|
+
local -a trailing_args=()
|
|
220
|
+
while (($# > 0)) && [[ $1 != -- ]]; do
|
|
221
|
+
local array=$1
|
|
222
|
+
shift
|
|
223
|
+
|
|
224
|
+
if eval "(( \${#${array}[@]} > 0 ))"; then
|
|
225
|
+
eval "trailing_args+=(\"\${${array}[@]}\")"
|
|
226
|
+
fi
|
|
227
|
+
done
|
|
228
|
+
shift # remove -- separator
|
|
229
|
+
|
|
230
|
+
if (($# == 0)); then
|
|
231
|
+
printf "Error: append_arrays_as_args is missing a command or -- separator\n" >&2
|
|
232
|
+
return 1
|
|
233
|
+
fi
|
|
234
|
+
|
|
235
|
+
if ((${#trailing_args[@]} > 0)); then
|
|
236
|
+
"$@" "${trailing_args[@]}"
|
|
237
|
+
else
|
|
238
|
+
"$@"
|
|
239
|
+
fi
|
|
240
|
+
}
|
|
241
|
+
|
|
242
|
+
bats_format_file_line_reference() { # <output> <file> <line>
|
|
243
|
+
# shellcheck disable=SC2034 # will be used in subimplementation
|
|
244
|
+
local output="${1?}"
|
|
245
|
+
shift
|
|
246
|
+
"bats_format_file_line_reference_${BATS_LINE_REFERENCE_FORMAT?}" "$@"
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
bats_format_file_line_reference_comma_line() {
|
|
250
|
+
printf -v "$output" "%s, line %d" "$@"
|
|
251
|
+
}
|
|
252
|
+
|
|
253
|
+
bats_format_file_line_reference_colon() {
|
|
254
|
+
printf -v "$output" "%s:%d" "$@"
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
# approximate realpath without subshell
|
|
258
|
+
bats_approx_realpath() { # <output-variable> <path>
|
|
259
|
+
local output=$1 path=$2
|
|
260
|
+
if [[ $path != /* ]]; then
|
|
261
|
+
path="$PWD/$path"
|
|
262
|
+
fi
|
|
263
|
+
# x/./y -> x/y
|
|
264
|
+
path=${path//\/.\//\/}
|
|
265
|
+
printf -v "$output" "%s" "$path"
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
bats_format_file_line_reference_uri() {
|
|
269
|
+
local filename=${1?} line=${2?}
|
|
270
|
+
bats_approx_realpath filename "$filename"
|
|
271
|
+
printf -v "$output" "file://%s:%d" "$filename" "$line"
|
|
272
|
+
}
|
|
273
|
+
|
|
274
|
+
# execute command with backed up path
|
|
275
|
+
# to prevent path mocks from interfering with our internals
|
|
276
|
+
bats_execute() { # <command...>
|
|
277
|
+
PATH="${BATS_SAVED_PATH?}" "$@"
|
|
278
|
+
}
|
|
@@ -0,0 +1,151 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
|
|
3
|
+
# reads (extended) bats tap streams from stdin and calls callback functions for each line
|
|
4
|
+
#
|
|
5
|
+
# Segmenting functions
|
|
6
|
+
# ====================
|
|
7
|
+
# bats_tap_stream_plan <number of tests> -> when the test plan is encountered
|
|
8
|
+
# bats_tap_stream_suite <file name> -> when a new file is begun WARNING: extended only
|
|
9
|
+
# bats_tap_stream_begin <test index> <test name> -> when a new test is begun WARNING: extended only
|
|
10
|
+
#
|
|
11
|
+
# Test result functions
|
|
12
|
+
# =====================
|
|
13
|
+
# If timing was enabled, BATS_FORMATTER_TEST_DURATION will be set to their duration in milliseconds
|
|
14
|
+
# bats_tap_stream_ok <test index> <test name> -> when a test was successful
|
|
15
|
+
# bats_tap_stream_not_ok <test index> <test name> -> when a test has failed. If the failure was due to a timeout,
|
|
16
|
+
# BATS_FORMATTER_TEST_TIMEOUT is set to the timeout duration in seconds
|
|
17
|
+
# bats_tap_stream_skipped <test index> <test name> <skip reason> -> when a test was skipped
|
|
18
|
+
#
|
|
19
|
+
# Context functions
|
|
20
|
+
# =================
|
|
21
|
+
# bats_tap_stream_comment <comment text without leading '# '> <scope> -> when a comment line was encountered,
|
|
22
|
+
# scope tells the last encountered of plan, begin, ok, not_ok, skipped, suite
|
|
23
|
+
# bats_tap_stream_unknown <full line> <scope> -> when a line is encountered that does not match the previous entries,
|
|
24
|
+
# scope @see bats_tap_stream_comment
|
|
25
|
+
# forwards all input as is, when there is no TAP test plan header
|
|
26
|
+
function bats_parse_internal_extended_tap() {
|
|
27
|
+
local header_pattern='[0-9]+\.\.[0-9]+'
|
|
28
|
+
IFS= read -r header
|
|
29
|
+
|
|
30
|
+
if [[ "$header" =~ $header_pattern ]]; then
|
|
31
|
+
bats_tap_stream_plan "${header:3}"
|
|
32
|
+
else
|
|
33
|
+
# If the first line isn't a TAP plan, print it and pass the rest through
|
|
34
|
+
printf '%s\n' "$header"
|
|
35
|
+
exec cat
|
|
36
|
+
fi
|
|
37
|
+
|
|
38
|
+
ok_line_regexpr="ok ([0-9]+) (.*)"
|
|
39
|
+
skip_line_regexpr="ok ([0-9]+) (.*) # skip( (.*))?$"
|
|
40
|
+
timeout_line_regexpr="not ok ([0-9]+) (.*) # timeout after ([0-9]+)s$"
|
|
41
|
+
not_ok_line_regexpr="not ok ([0-9]+) (.*)"
|
|
42
|
+
|
|
43
|
+
timing_expr="in ([0-9]+)ms$"
|
|
44
|
+
local test_name begin_index last_begin_index try_index ok_index not_ok_index index scope
|
|
45
|
+
begin_index=0
|
|
46
|
+
last_begin_index=-1
|
|
47
|
+
try_index=0
|
|
48
|
+
index=0
|
|
49
|
+
scope=plan
|
|
50
|
+
while IFS= read -r line; do
|
|
51
|
+
unset BATS_FORMATTER_TEST_DURATION BATS_FORMATTER_TEST_TIMEOUT
|
|
52
|
+
case "$line" in
|
|
53
|
+
'begin '*) # this might only be called in extended tap output
|
|
54
|
+
scope=begin
|
|
55
|
+
begin_index=${line#begin }
|
|
56
|
+
begin_index=${begin_index%% *}
|
|
57
|
+
if [[ $begin_index == "$last_begin_index" ]]; then
|
|
58
|
+
(( ++try_index ))
|
|
59
|
+
else
|
|
60
|
+
try_index=0
|
|
61
|
+
fi
|
|
62
|
+
test_name="${line#begin "$begin_index" }"
|
|
63
|
+
bats_tap_stream_begin "$begin_index" "$test_name"
|
|
64
|
+
;;
|
|
65
|
+
'ok '*)
|
|
66
|
+
((++index))
|
|
67
|
+
if [[ "$line" =~ $ok_line_regexpr ]]; then
|
|
68
|
+
ok_index="${BASH_REMATCH[1]}"
|
|
69
|
+
test_name="${BASH_REMATCH[2]}"
|
|
70
|
+
if [[ "$line" =~ $skip_line_regexpr ]]; then
|
|
71
|
+
scope=skipped
|
|
72
|
+
test_name="${BASH_REMATCH[2]}" # cut off name before "# skip"
|
|
73
|
+
local skip_reason="${BASH_REMATCH[4]}"
|
|
74
|
+
if [[ "$test_name" =~ $timing_expr ]]; then
|
|
75
|
+
local BATS_FORMATTER_TEST_DURATION="${BASH_REMATCH[1]}"
|
|
76
|
+
test_name="${test_name% in "${BATS_FORMATTER_TEST_DURATION}"ms}"
|
|
77
|
+
bats_tap_stream_skipped "$ok_index" "$test_name" "$skip_reason"
|
|
78
|
+
else
|
|
79
|
+
bats_tap_stream_skipped "$ok_index" "$test_name" "$skip_reason"
|
|
80
|
+
fi
|
|
81
|
+
else
|
|
82
|
+
scope=ok
|
|
83
|
+
if [[ "$line" =~ $timing_expr ]]; then
|
|
84
|
+
local BATS_FORMATTER_TEST_DURATION="${BASH_REMATCH[1]}"
|
|
85
|
+
bats_tap_stream_ok "$ok_index" "${test_name% in "${BASH_REMATCH[1]}"ms}"
|
|
86
|
+
else
|
|
87
|
+
bats_tap_stream_ok "$ok_index" "$test_name"
|
|
88
|
+
fi
|
|
89
|
+
fi
|
|
90
|
+
else
|
|
91
|
+
printf "ERROR: could not match ok line: %s" "$line" >&2
|
|
92
|
+
exit 1
|
|
93
|
+
fi
|
|
94
|
+
;;
|
|
95
|
+
'not ok '*)
|
|
96
|
+
((++index))
|
|
97
|
+
scope=not_ok
|
|
98
|
+
if [[ "$line" =~ $not_ok_line_regexpr ]]; then
|
|
99
|
+
not_ok_index="${BASH_REMATCH[1]}"
|
|
100
|
+
test_name="${BASH_REMATCH[2]}"
|
|
101
|
+
if [[ "$line" =~ $timeout_line_regexpr ]]; then
|
|
102
|
+
not_ok_index="${BASH_REMATCH[1]}"
|
|
103
|
+
test_name="${BASH_REMATCH[2]}"
|
|
104
|
+
# shellcheck disable=SC2034 # used in bats_tap_stream_ok
|
|
105
|
+
local BATS_FORMATTER_TEST_TIMEOUT="${BASH_REMATCH[3]}"
|
|
106
|
+
fi
|
|
107
|
+
if [[ "$test_name" =~ $timing_expr ]]; then
|
|
108
|
+
# shellcheck disable=SC2034 # used in bats_tap_stream_ok
|
|
109
|
+
local BATS_FORMATTER_TEST_DURATION="${BASH_REMATCH[1]}"
|
|
110
|
+
test_name="${test_name% in "${BASH_REMATCH[1]}"ms}"
|
|
111
|
+
fi
|
|
112
|
+
bats_tap_stream_not_ok "$not_ok_index" "$test_name"
|
|
113
|
+
else
|
|
114
|
+
printf "ERROR: could not match not ok line: %s" "$line" >&2
|
|
115
|
+
exit 1
|
|
116
|
+
fi
|
|
117
|
+
;;
|
|
118
|
+
'# '*)
|
|
119
|
+
bats_tap_stream_comment "${line:2}" "$scope"
|
|
120
|
+
;;
|
|
121
|
+
'#')
|
|
122
|
+
bats_tap_stream_comment "" "$scope"
|
|
123
|
+
;;
|
|
124
|
+
'suite '*)
|
|
125
|
+
scope=suite
|
|
126
|
+
# pass on the
|
|
127
|
+
bats_tap_stream_suite "${line:6}"
|
|
128
|
+
;;
|
|
129
|
+
*)
|
|
130
|
+
bats_tap_stream_unknown "$line" "$scope"
|
|
131
|
+
;;
|
|
132
|
+
esac
|
|
133
|
+
done
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
normalize_base_path() { # <target variable> <base path>
|
|
137
|
+
# the relative path root to use for reporting filenames
|
|
138
|
+
# this is mainly intended for suite mode, where this will be the suite root folder
|
|
139
|
+
local base_path="$2"
|
|
140
|
+
# use the containing directory when --base-path is a file
|
|
141
|
+
if [[ ! -d "$base_path" ]]; then
|
|
142
|
+
base_path="$(dirname "$base_path")"
|
|
143
|
+
fi
|
|
144
|
+
# get the absolute path
|
|
145
|
+
base_path="$(cd "$base_path" && pwd)"
|
|
146
|
+
# ensure the path ends with / to strip that later on
|
|
147
|
+
if [[ "${base_path}" != *"/" ]]; then
|
|
148
|
+
base_path="$base_path/"
|
|
149
|
+
fi
|
|
150
|
+
printf -v "$1" "%s" "$base_path"
|
|
151
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
|
|
3
|
+
bats_export_preprocess_source_BATS_TEST_SOURCE() {
|
|
4
|
+
# export to make it visible to bats_evaluate_preprocessed_source
|
|
5
|
+
# since the latter runs in bats-exec-test's bash while this runs in bats-exec-file's
|
|
6
|
+
export BATS_TEST_SOURCE="$BATS_RUN_TMPDIR/${BATS_TEST_FILE_NUMBER?}-${BATS_TEST_FILENAME##*/}.src"
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
bats_preprocess_source() { # index
|
|
10
|
+
bats_export_preprocess_source_BATS_TEST_SOURCE
|
|
11
|
+
# shellcheck disable=SC2153
|
|
12
|
+
CHECK_BATS_COMMENT_COMMANDS=1 "$BATS_ROOT/libexec/bats-core/bats-preprocess" "$BATS_TEST_FILENAME" >"$BATS_TEST_SOURCE"
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
bats_evaluate_preprocessed_source() {
|
|
16
|
+
# Dynamically loaded user files provided outside of Bats.
|
|
17
|
+
# shellcheck disable=SC1090
|
|
18
|
+
source "${BATS_TEST_SOURCE?}"
|
|
19
|
+
}
|