Files
ansible-freeipa/utils/run-tests.sh
Rafael Guterres Jeffman 68bca84481 utils: Rewrite run-tests.sh to use functions and extenal scripts
To modify Azure tests and depend on shell scripts and pytest instead
of molecule, the run-tests.sh script has been rewritten to depend on
bash functions and on a bash script that prepare and start a testing
container.

This patch adds a new script, 'utils/setup_test_container.sh' that
can be used to start a new container, using either podman or docker,
based on the available ansible-freeipa images. The new container can
then be used to run ansible-freeipa tests against it.

Also the following files with bash functions were added, and are
used by both scripts:

    utils/shansible: Functions to run playbooks in the container
    utils/shcontainer: Functions to setup/run a container
    utils/shfun: Generic shell helper functions (e.g.: log)
2024-08-02 17:19:39 +02:00

197 lines
6.5 KiB
Bash
Executable File

#!/bin/bash -eu
SCRIPTDIR="$(readlink -f "$(dirname "$0")")"
TOPDIR="$(readlink -f "${SCRIPTDIR}/..")"
# shellcheck source=utils/shfun
. "${SCRIPTDIR}/shfun"
# shellcheck source=utils/shcontainer
. "${SCRIPTDIR}/shcontainer"
# shellcheck source=utils/shansible
. "${SCRIPTDIR}/shansible"
usage() {
local prog="${0##*/}"
cat <<EOF
usage: ${prog} [-h] [-l] [-e] [-K] [-A|-a ANSIBLE] [-p INTERPRETER] [-c CONTAINER] [-s TESTS_SUITE] [-x] [-S SEED.GRP] [-i IMAGE] [-m MEMORY] [-v...] [TEST...]
${prog} runs playbook(s) TEST using an ansible-freeipa testing image.
EOF
}
help() {
usage
echo -e "$(cat <<EOF
positional arguments:
TEST A list of playbook tests to be executed.
Either a TEST or a MODULE must be provided.
optional arguments:
-h display this message and exit
-a ANSIBLE Ansible version to use, e.g. "ansible-core==2.16.0"
(default: latest ansible-core for the python version)
-A Do not install Ansible, use host's provided one.
-c CONTAINER use container CONTAINER to run tests
-K keep container, even if tests succeed
-l list available images
-e force recreation of the virtual environment
-i IMAGE select image to run the tests (default: fedora-latest)
-m MEMORY container memory, in GiB (default: 3)
-p INTERPRETER Python interpreter to use on target container
-s TEST_SUITE run all playbooks for test suite, which is a directory
under ${WHITE}tests${RST}
-S SEED.GROUP Replicate Azure's test group and seed (seed is YYYYMMDD)
-v Increase Ansible verbosity (can be used multiple times)
-x Stop on first error.
EOF
)"
}
# Defaults
verbose=""
engine="${engine:-"podman"}"
CONTINUE_ON_ERROR=""
STOP_CONTAINER="Y"
STOP_VIRTUALENV="N"
declare -a ENABLED_MODULES
declare -a ENABLED_TESTS
read -r -a ENABLED_MODULES <<< "${IPA_ENABLED_MODULES:-""}"
read -r -a ENABLED_TESTS <<< "${IPA_ENABLED_MODULES:-""}"
IMAGE_TAG="fedora-latest"
scenario="freeipa-tests"
MEMORY=3
IPA_HOSTNAME="ipaserver.test.local"
SEED="$(date "+%Y%m%d")"
GROUP=1
SPLITS=0
ANSIBLE_COLLECTIONS=${ANSIBLE_COLLECTIONS:-"${engine_collection}"}
SKIP_ANSIBLE=""
ansible_interpreter="/usr/bin/python3"
EXTRA_OPTIONS=""
unset ANSIBLE_VERSION
# Process command options
while getopts ":ha:Ac:ei:Klm:p:s:S:vx" option
do
case "$option" in
h) help && exit 0 ;;
A)
[ -n "${ANSIBLE_VERSION:-""}" ] && die "Can't use -A with '-a'"
SKIP_ANSIBLE="YES"
;;
a)
[ "${SKIP_ANSIBLE:-"no"}" == "YES" ] && die "Can't use -A with '-a'"
ANSIBLE_VERSION="${OPTARG}"
;;
c) scenario="${OPTARG}" ;;
e) FORCE_ENV="Y" ;;
i) IMAGE_TAG="${OPTARG}" ;;
K) STOP_CONTAINER="N" ;;
l) "${SCRIPTDIR}"/setup_test_container.sh -l && exit 0 || exit 1 ;;
m) MEMORY="${OPTARG}" ;;
p) ansible_interpreter="${OPTARG}" ;;
s)
[ ${SPLITS} -ne 0 ] && die -u "Can't use '-S' with '-s'"
if [ -d "${TOPDIR}/tests/${OPTARG}" ]
then
ENABLED_MODULES+=("${OPTARG}")
else
log error "Invalid suite: ${OPTARG}"
fi
;;
S)
[ ${#ENABLED_MODULES[@]} -eq 0 ] || die -u "Can't use '-A' with '-s'"
SEED="$(cut -d. -f1 <<< "${OPTARG}" | tr -d "-")"
GROUP="$(cut -d. -f2 <<< "${OPTARG}")"
if [ -z "${SEED}" ] || [ -z "${GROUP}" ]
then
die -u "Seed for '-A' must have the format YYYYMMDD.N"
fi
SPLITS=3
;;
v) verbose=${verbose:--}${option} ;;
x) EXTRA_OPTIONS="$EXTRA_OPTIONS --exitfirst" ;;
*) die -u "Invalid option: ${OPTARG}" ;;
esac
done
for test in "${@:${OPTIND}}"
do
# shellcheck disable=SC2207
if stat "$test" >/dev/null 2>&1
then
[ ${SPLITS} -ne 0 ] && die -u "Can't define tests and use '-A'"
ENABLED_TESTS+=($(basename "${test}" .yml))
else
log error "Test not found: ${test}"
fi
done
[ ${SPLITS} -eq 0 ] && [ ${#ENABLED_MODULES[@]} -eq 0 ] && [ ${#ENABLED_TESTS[@]} -eq 0 ] && die -u "No test defined."
export STOP_CONTAINER FORCE_ENV STOP_VIRTUALENV ansible_interpreter
# Ensure $python is set
[ -z "${python}" ] && python="python3"
log info "Controller Python executable: ${python}"
${python} --version
# Prepare virtual environment
start_virtual_environment
log info "Installing dependencies from 'requirements-tests.txt'"
pip install --upgrade -r "${TOPDIR}/requirements-tests.txt"
[ -z "${SKIP_ANSIBLE}" ] && install_ansible "${ANSIBLE_VERSION:-"ansible-core"}"
# Ansible configuration
export ANSIBLE_ROLES_PATH="${TOPDIR}/roles"
export ANSIBLE_LIBRARY="${TOPDIR}/plugins"
export ANSIBLE_MODULE_UTILS="${TOPDIR}/plugins/module_utils"
# Start container
"${SCRIPTDIR}/setup_test_container.sh" -e "${engine}" -m "${MEMORY}" -p "${ansible_interpreter}" -i "${IMAGE_TAG}" -n "${IPA_HOSTNAME}" -a "${scenario}" || die "Failed to setup test container"
# run tests
RESULT=0
export RUN_TESTS_IN_DOCKER=${engine}
export IPA_SERVER_HOST="${scenario}"
# Ensure proper ansible_python_interpreter is used by pytest.
export IPA_PYTHON_PATH="${ansible_interpreter}"
if [ ${SPLITS} -ne 0 ]
then
EXTRA_OPTIONS="${EXTRA_OPTIONS} --splits=${SPLITS} --group=${GROUP} --randomly-seed=${SEED}"
log info "Running tests for group ${GROUP} of ${SPLITS} with seed ${SEED}"
else
# shellcheck disable=SC2086
joined="$(printf "%s," "${ENABLED_MODULES[@]}")"
# shelcheck disable=SC2178
IPA_ENABLED_MODULES="${joined%,}"
joined="$(printf "%s," "${ENABLED_TESTS[@]}")"
# shelcheck disable=SC2178
IPA_ENABLED_TESTS="${joined%,}"
export IPA_ENABLED_MODULES IPA_ENABLED_TESTS
[ -n "${IPA_ENABLED_MODULES}" ] && log info "Test suites: ${IPA_ENABLED_MODULES}"
[ -n "${IPA_ENABLED_TESTS}" ] && log info "Individual tests: ${IPA_ENABLED_TESTS}"
fi
IPA_VERBOSITY="${verbose}"
[ -n "${IPA_VERBOSITY}" ] && export IPA_VERBOSITY
# shellcheck disable=SC2086
if ! pytest -m "playbook" --verbose --color=yes --suppress-no-test-exit-code --junit-xml=TEST-results-group-${GROUP:-1}.xml ${EXTRA_OPTIONS}
then
RESULT=2
log error "Container not stopped for verification: ${scenario}"
log info "Container: $(${engine} ps -f "name=${scenario}" --format "{{.Names}} - {{.ID}}")"
fi
[ -z "${CONTINUE_ON_ERROR}" ] && [ $RESULT -ne 0 ] && die "Stopping on test failure."
# cleanup environment
cleanup "${scenario}" "${engine}"