diff --git a/divingbell/templates/bin/_exec.sh.tpl b/divingbell/templates/bin/_exec.sh.tpl new file mode 100644 index 0000000..a042d55 --- /dev/null +++ b/divingbell/templates/bin/_exec.sh.tpl @@ -0,0 +1,163 @@ +#!/bin/bash + +{{/* +# Copyright 2017 AT&T Intellectual Property. All other rights reserved. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +*/}} + +set -e + +cat <<'UNIQUE_EOF_9c341059-25a0-4725-9489-1789e255e381' > {{ .Values.conf.chroot_mnt_path | quote }}/tmp/exec_host_{{ .Chart.Version }}.sh +{{ include "divingbell.shcommon" . }} + +exec_path='/var/divingbell/exec' + +if [ ! -d "${exec_path}" ]; then + mkdir -p "${exec_path}" +fi + +write_test "${exec_path}" +cd "${exec_path}" + +{{- if hasKey .Values.conf "exec" }} + {{- $sorted_keys := keys $.Values.conf.exec | sortAlpha }} + + {{- range $index, $script := $sorted_keys }} + {{- $keypath := index $.Values.conf.exec $script }} + + {{/* Need to sort key/values before assessing hash, since helm only preserves order for lists */}} + {{- $_ := set $.Values "__values_hash" list }} + {{- range $i, $k := ($keypath | keys | sortAlpha) }} + {{/* env is the only nested dict, so the same operation needs to be repeated there lacking helm recursion */}} + {{- if eq $k "env" }} + {{- range $i2, $k2 := ($keypath.env | keys | sortAlpha) }} + {{- $_ := set $.Values "__values_hash" (append $.Values.__values_hash (print $.Values.__values_hash ";" ($k | toString) ":" ($k2 | toString) ":" (index $keypath.env $k2 | toString))) }} + {{- end }} + {{- else }} + {{- $_ := set $.Values "__values_hash" (append $.Values.__values_hash (print $.Values.__values_hash ";" ($k | toString) ":" (index $keypath $k | toString))) }} + {{- end }} + {{- end }} + {{- $hash := $.Values.__values_hash | toString | sha256sum }} + + hash={{ $hash | squote }} + if [ ! -d "${hash}" ]; then + mkdir -p "${hash}" + fi + + {{- $_ := set $.Values "__rerun_policy" "always" }} + {{- if hasKey $keypath "rerun_policy" }} + {{- if and (not (eq $keypath.rerun_policy "always")) (not (eq $keypath.rerun_policy "never")) (not (eq $keypath.rerun_policy "once_successfully")) }} + {{- fail (print "BAD 'rerun_policy' FOR '" $script "': Got '" $keypath.rerun_policy "', but expected 'always', 'never', or 'once_successfully'.") }} + {{- end }} + {{- $_ := set $.Values "__rerun_policy" $keypath.rerun_policy }} + {{- end }} + + {{- $_ := set $.Values "__blocking_policy" "foreground" }} + {{- if hasKey $keypath "blocking_policy" }} + {{- if and (not (eq $keypath.blocking_policy "foreground")) (not (eq $keypath.blocking_policy "background")) (not (eq $keypath.blocking_policy "foreground_halt_pod_on_failure")) }} + {{- fail (print "BAD 'blocking_policy' FOR '" $script "': Got '" $keypath.blocking_policy "', but expected 'foreground', 'background', or 'foreground_halt_pod_on_failure'.") }} + {{- end }} + {{- if eq $keypath.blocking_policy "background" }} + {{- fail (print "NOT IMPLEMENTED: 'blocking_policy' FOR '" $script "'") }} + {{- end }} + {{- $_ := set $.Values "__blocking_policy" $keypath.blocking_policy }} + {{- end }} + + {{- $_ := set $.Values "__timeout" 3600 }} + {{- if hasKey $keypath "timeout" }} + {{- fail (print "NOT IMPLEMENTED: 'timeout' FOR '" $script "'") }} + {{- $_ := set $.Values "__timeout" $keypath.timeout }} + {{- end }} + + {{- $_ := set $.Values "__rerun_interval" "infinite" }} + {{- if hasKey $keypath "rerun_interval" }} + {{- fail (print "NOT IMPLEMENTED: 'rerun_interval' FOR '" $script "'") }} + {{- $_ := set $.Values "__rerun_interval" $keypath.rerun_interval }} + {{- end }} + + {{- $_ := set $.Values "__rerun_interval_persist" "false" }} + {{- if hasKey $keypath "rerun_interval_persist" }} + {{- fail (print "NOT IMPLEMENTED: 'rerun_interval_persist' FOR '" $script "'") }} + {{- $_ := set $.Values "__rerun_interval_persist" $keypath.rerun_interval_persist }} + {{- end }} + + {{- $_ := set $.Values "__rerun_max_count" "infinite" }} + {{- if hasKey $keypath "rerun_max_count" }} + {{- fail (print "NOT IMPLEMENTED: 'rerun_max_count' FOR '" $script "'") }} + {{- $_ := set $.Values "__rerun_max_count" $keypath.rerun_max_count }} + {{- end }} + + {{- $_ := set $.Values "__retry_interval" $.Values.__rerun_interval }} + {{- if hasKey $keypath "retry_interval" }} + {{- fail (print "NOT IMPLEMENTED: 'retry_interval' FOR '" $script "'") }} + {{- $_ := set $.Values "__retry_interval" $keypath.retry_interval }} + {{- end }} + + {{- $_ := set $.Values "__retry_interval_persist" "false" }} + {{- if hasKey $keypath "retry_interval_persist" }} + {{- fail (print "NOT IMPLEMENTED: 'retry_interval_persist' FOR '" $script "'") }} + {{- $_ := set $.Values "__retry_interval_persist" $keypath.retry_interval_persist }} + {{- end }} + + {{- $_ := set $.Values "__retry_max_count" "infinite" }} + {{- if hasKey $keypath "retry_max_count" }} + {{- fail (print "NOT IMPLEMENTED: 'retry_max_count' FOR '" $script "'") }} + {{- $_ := set $.Values "__retry_max_count" $keypath.retry_max_count }} + {{- end }} + cat <<'UNIQUE_EOF_1840dbd4-09e1-4725-87f5-3b6944b80526' > {{ $script }} +{{ $keypath.data }} +UNIQUE_EOF_1840dbd4-09e1-4725-87f5-3b6944b80526 + chmod 700 {{ $script }} + if [[ {{ $.Values.__rerun_policy }} = always ]] || \ + [[ ! -f ${hash}/exit_code ]] || \ + ([[ {{ $.Values.__rerun_policy }} = once_successfully ]] && \ + [[ -f ${hash}/exit_code ]] && \ + [[ $(cat ${hash}/exit_code) != 0 ]]); then + {{- if hasKey $keypath "env" }} + {{- range $env_key, $env_val := $keypath.env }} + {{ $env_key }}={{ $env_val | squote }} \ + {{- end }} + {{- end }} + ./{{ $script | squote }} \ + {{- if hasKey $keypath "args" }} + {{- range $arg := $keypath.args }} + {{ $arg | squote }} \ + {{- end }} + {{- end }} + && echo 0 > "${hash}/exit_code" || echo $? > "${hash}/exit_code" + {{- if hasKey $keypath "blocking_policy" }} + {{- if eq $keypath.blocking_policy "foreground_halt_pod_on_failure" }} + if [[ $(cat "${hash}/exit_code") != '0' ]]; then + die "Killing pod due to non-zero exit code from '{{ $script }}'." + fi + {{- end }} + {{- end }} + fi + {{ end }} +{{- end }} + +exit 0 +UNIQUE_EOF_9c341059-25a0-4725-9489-1789e255e381 + +chmod 700 {{ .Values.conf.chroot_mnt_path | quote }}/tmp/exec_host_{{ .Chart.Version }}.sh +chroot {{ .Values.conf.chroot_mnt_path | quote }} /tmp/exec_host_{{ .Chart.Version }}.sh + +sleep 1 +echo 'INFO Putting the daemon to sleep.' + +while [ 1 ]; do + sleep 300 +done + +exit 0 diff --git a/divingbell/templates/bin/_sysctl.sh.tpl b/divingbell/templates/bin/_sysctl.sh.tpl index 064f68b..43e3401 100644 --- a/divingbell/templates/bin/_sysctl.sh.tpl +++ b/divingbell/templates/bin/_sysctl.sh.tpl @@ -96,9 +96,9 @@ add_sysctl_param {{ $key | squote }} {{ $value | squote }} # Revert any previously applied sysctl settings which are now absent prev_files="$(find "${defaults_path}" -type f)" if [ -n "${prev_files}" ]; then - basename -a ${prev_files} | sort > /tmp/prev_settings - echo "${curr_settings}" | sort > /tmp/curr_settings - revert_list="$(comm -23 /tmp/prev_settings /tmp/curr_settings)" + basename -a ${prev_files} | sort > /tmp/prev_sysctl + echo "${curr_settings}" | sort > /tmp/curr_sysctl + revert_list="$(comm -23 /tmp/prev_sysctl /tmp/curr_sysctl)" IFS=$'\n' for orig_sysctl_setting in ${revert_list}; do rm "${persist_path}/${orig_sysctl_setting}" diff --git a/divingbell/templates/daemonset-exec.yaml b/divingbell/templates/daemonset-exec.yaml new file mode 100644 index 0000000..c78e7ba --- /dev/null +++ b/divingbell/templates/daemonset-exec.yaml @@ -0,0 +1,71 @@ +{{/* +# Copyright 2017 AT&T Intellectual Property. All other rights reserved. +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +*/}} + +{{- define "divingbell.daemonset.exec" }} + {{- $daemonset := index . 0 }} + {{- $secretName := index . 1 }} + {{- $envAll := index . 2 }} + {{- with $envAll }} +--- +apiVersion: extensions/v1beta1 +kind: DaemonSet +metadata: + name: {{ $daemonset }} + annotations: + {{ tuple $envAll | include "helm-toolkit.snippets.release_uuid" }} +spec: +{{ tuple $envAll $daemonset | include "helm-toolkit.snippets.kubernetes_upgrades_daemonset" | indent 2 }} + template: + metadata: + labels: +{{ list $envAll .Chart.Name $daemonset | include "helm-toolkit.snippets.kubernetes_metadata_labels" | indent 8 }} + spec: + hostNetwork: true + hostPID: true + hostIPC: true + containers: + - name: {{ $daemonset }} + image: {{ .Values.images.divingbell }} + imagePullPolicy: {{ .Values.images.pull_policy }} +{{ tuple $envAll $envAll.Values.pod.resources.exec | include "helm-toolkit.snippets.kubernetes_resources" | indent 8 }} + command: + - /tmp/{{ $daemonset }}.sh + volumeMounts: + - name: rootfs-{{ $daemonset }} + mountPath: {{ .Values.conf.chroot_mnt_path }} + - name: {{ $secretName }} + mountPath: /tmp/{{ $daemonset }}.sh + subPath: {{ $daemonset }} + readOnly: true + securityContext: + privileged: true + volumes: + - name: rootfs-{{ $daemonset }} + hostPath: + path: / + - name: {{ $secretName }} + secret: + secretName: {{ $secretName }} + defaultMode: 0555 + {{- end }} +{{- end }} +{{- if .Values.manifests.daemonset_exec }} +{{- $daemonset := "exec" }} +{{- $secretName := "divingbell-exec" }} +{{- $daemonset_yaml := list $daemonset $secretName . | include "divingbell.daemonset.exec" | toString | fromYaml }} +{{- $secret_include := "divingbell.secret.exec" }} +{{- list $daemonset $daemonset_yaml $secret_include $secretName . | include "helm-toolkit.utils.daemonset_overrides" }} +{{- end }} diff --git a/divingbell/templates/secret-exec.yaml b/divingbell/templates/secret-exec.yaml new file mode 100644 index 0000000..0288aeb --- /dev/null +++ b/divingbell/templates/secret-exec.yaml @@ -0,0 +1,29 @@ +{{/* +Copyright 2017 The Openstack-Helm Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/}} + +{{- define "divingbell.secret.exec" }} +{{- $secretName := index . 0 }} +{{- $envAll := index . 1 }} +{{- with $envAll }} +--- +apiVersion: v1 +kind: Secret +metadata: + name: {{ $secretName }} +data: + exec: {{ tuple "bin/_exec.sh.tpl" . | include "helm-toolkit.utils.template" | b64enc }} +{{- end }} +{{- end }} diff --git a/divingbell/values.yaml b/divingbell/values.yaml index d8351f5..5d3fc55 100644 --- a/divingbell/values.yaml +++ b/divingbell/values.yaml @@ -121,6 +121,10 @@ pod: enabled: true min_ready_seconds: 0 max_unavailable: 100% + exec: + enabled: true + min_ready_seconds: 0 + max_unavailable: 100% resources: enabled: false ethtool: @@ -172,6 +176,13 @@ pod: requests: memory: "128Mi" cpu: "100m" + exec: + limits: + memory: "128Mi" + cpu: "100m" + requests: + memory: "128Mi" + cpu: "100m" manifests: daemonset_ethtool: true @@ -181,3 +192,4 @@ manifests: daemonset_limits: true daemonset_apt: true daemonset_perm: true + daemonset_exec: true diff --git a/doc/source/index.rst b/doc/source/index.rst index 2fa9353..edc297f 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -170,6 +170,88 @@ way:: question_type: boolean answer: false +exec +^^^^ + +Used to execute scripts on nodes, ex:: + + exec: + 002-script2.sh: + data: | + #!/bin/bash + echo ${BASH_SOURCE} + 001-script1.sh: + blocking_policy: foreground_halt_pod_on_failure + env: + env1: env1-val + env2: env2-val + args: + - arg1 + - arg2 + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} + echo args: $@ + echo env: $env1 $env2 $env3 + +Scripts are executed in alphanumeric order with the key names used. Therefore +in this example, 001-script1.sh runs first, followed by 002-script2.sh. +Targeting of directives to specific nodes by hostname or node label is +achievable by use of the overrides capability described below. + +The following set of options are fully implemeneted:: + + ``rerun_policy`` may be optionally set to ``always``, ``never``, or + ``once_successfully`` for a given script. That script would always be rerun, + never be rerun, or rerun until the first successful execution respectively. + Default value is ``always``. This is tracked via a hash of the dict object + for the script (i.e. script name, script data, script args, script env, etc). + If any of that info changes, so will the hash, and it will be seen as a new + object which will be executed regardless of this setting. + +The following set of options are partially implemeneted:: + + ``blocking_policy`` may optionally be set to ``background``, ``foreground``, + or ``foreground_halt_pod_on_failure`` for a given script. This may be used to + run a script in the background (running in parallel, i.e. non-blocking) or + in the foreground (blocking). In either case, a failure of the script does + not cause a failure (crashloop) of the pod. The third option may be used + where the reverse behavior is desired (i.e., it would not proceed with + running the next script in the sequence until the current script ran + successfully). ``background`` option is not yet implemeneted. Default value + Deafult value is ``foreground``. + +The following set of options are not yet implemeneted:: + + ``script_timeout`` may optionally be set to the number of seconds to wait for + script completion before termination. Default value is ``3600`` (1 hour). + + ``rerun_interval`` may be optionally set to the number of seconds to wait + between rerunning a given script which ran successfully the previous time. + Default value is ``infinite``. + + ``rerun_interval_persist`` may be optionally set to ``true`` for + a given script. This allows a script to persist its rerun interval through a + pod/node restart. Otherwise, the time since last successful script execution + will not be considered on pod/node startup. Default value is ``false``. + + ``rerun_max_count`` may be optionally set to the maximum number of times a + succeeding script should be retried. Successful exec count does not persist + through pod/node restart. Default value is ``infinite``. + + ``retry_interval`` may be optionally set to the number of seconds to wait + between rerunning a given script which did not run successfully the previous + time. Default value is set to the ``rerun_interval``. + + ``retry_interval_persist`` may be optionally set to ``true`` for + a given script. This allows a script to persist its retry interval through a + pod/node restart. Otherwise, the time since last failed script execution + will not be considered on pod/node startup. Default value is ``false``. + + ``retry_max_count`` may be optionally set to the maximum number of times a + failing script should be retried. Failed exec count does not persist + through pod/node restart. Default value is ``infinite``. + Operations ---------- diff --git a/tools/gate/scripts/020-test-divingbell.sh b/tools/gate/scripts/020-test-divingbell.sh index d766108..c408c66 100755 --- a/tools/gate/scripts/020-test-divingbell.sh +++ b/tools/gate/scripts/020-test-divingbell.sh @@ -55,6 +55,7 @@ APT_VERSION3=3.8.1-1ubuntu2 APT_PACKAGE4=less APT_PACKAGE5=python-setuptools APT_PACKAGE6=telnetd +EXEC_DIR=/var/${NAME}/exec type lshw || apt -y install lshw nic_info="$(lshw -class network)" physical_nic='' @@ -236,6 +237,31 @@ _test_sysctl_value(){ test "$(cat /etc/sysctl.d/60-${NAME}-${key}.conf)" = "${key}=${2}" } +_test_exec_match(){ + expected_result="$1" + exec_testfile="$2" + testID="$3" + if [[ $expected_result != $(cat $exec_testfile) ]]; then + echo "[FAIL] exec $testID failed. Expected:" + echo $expected_result + echo but got: + echo $(cat $exec_testfile) + exit 1 + fi + rm $exec_testfile +} + +_test_exec_count(){ + script_location="${1}" + script_name="${2}" + script_expected_run_count="${3}" + script_run_count=$(cat "${script_location}" | wc -l) + if [[ ${script_run_count} -ne ${script_expected_run_count} ]]; then + echo "[FAIL] Expected '${script_name}' to run '${script_expected_run_count}' times, but instead it ran '$script_run_count' times" + exit 1 + fi +} + _test_clog_msg(){ [[ $CLOGS = *${1}* ]] || (echo "Did not find expected string: '${1}'" @@ -958,6 +984,202 @@ test_apt(){ echo '[SUCCESS] apt test6 passed successfully' >> "${TEST_RESULTS}" } +# test exec module +test_exec(){ + # test script execution ordering, args, and env vars + local overrides_yaml=${LOGS_SUBDIR}/${FUNCNAME}-set1.yaml + echo 'conf: + exec: + 030-script5.sh: + blocking_policy: foreground_halt_pod_on_failure + env: + env1: env1-val + env2: env2-val + env3: env3-val + args: + - arg1 + - arg2 + - arg3 + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> exec_testfile + echo args: "$@" >> exec_testfile + echo env: "$env1 $env2 $env3" >> exec_testfile + 005-script1.sh: + blocking_policy: foreground + data: | + #!/bin/bash + rm exec_testfile 2> /dev/null || true + echo script name: ${BASH_SOURCE} >> exec_testfile + 015-script3.sh: + blocking_policy: foreground_halt_pod_on_failure + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> exec_testfile + 008-script2.sh: + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> exec_testfile + 025-script4.sh: + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> exec_testfile' > "${overrides_yaml}" + install_base "--values=${overrides_yaml}" + get_container_status exec + expected_result='script name: ./005-script1.sh +script name: ./008-script2.sh +script name: ./015-script3.sh +script name: ./025-script4.sh +script name: ./030-script5.sh +args: arg1 arg2 arg3 +env: env1-val env2-val env3-val' + _test_exec_match "$expected_result" "${EXEC_DIR}/exec_testfile" "test1" + echo '[SUCCESS] exec test1 passed successfully' >> "${TEST_RESULTS}" + + # Test blocking_policy + local overrides_yaml=${LOGS_SUBDIR}/${FUNCNAME}-set2.yaml + echo 'conf: + exec: + 030-script5.sh: + blocking_policy: foreground_halt_pod_on_failure + env: + env1: env1-val + env2: env2-val + env3: env3-val + args: + - arg1 + - arg2 + - arg3 + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> exec_testfile + echo args: "$@" >> exec_testfile + echo env: "$env1 $env2 $env3" >> exec_testfile + 005-script1.sh: + blocking_policy: foreground + data: | + #!/bin/bash + rm exec_testfile 2> /dev/null || true + echo script name: ${BASH_SOURCE} >> exec_testfile + 015-script3.sh: + blocking_policy: foreground_halt_pod_on_failure + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> exec_testfile + false + 008-script2.sh: + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> exec_testfile + 025-script4.sh: + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> exec_testfile' > "${overrides_yaml}" + install_base "--values=${overrides_yaml}" + get_container_status exec expect_failure + expected_result='script name: ./005-script1.sh +script name: ./008-script2.sh +script name: ./015-script3.sh' + _test_exec_match "$expected_result" "${EXEC_DIR}/exec_testfile" "test2" + echo '[SUCCESS] exec test2 passed successfully' >> "${TEST_RESULTS}" + + # Test invalid rerun_policy + overrides_yaml=${LOGS_SUBDIR}/${FUNCNAME}-set3.yaml + echo 'conf: + exec: + 030-script5.sh: + rerun_policy: foo + data: | + #!/bin/bash + true' > "${overrides_yaml}" + install_base "--values=${overrides_yaml}" 2>&1 | grep 'BAD .rerun_policy. FOR' || \ + (echo "[FAIL] exec test3 did not receive expected 'BAD .rerun_policy. FOR' error" && exit 1) + echo '[SUCCESS] exec test3 passed successfully' >> "${TEST_RESULTS}" + + # Test invalid blocking_policy + overrides_yaml=${LOGS_SUBDIR}/${FUNCNAME}-set4.yaml + echo 'conf: + exec: + 030-script5.sh: + blocking_policy: foo + data: | + #!/bin/bash + true' > "${overrides_yaml}" + install_base "--values=${overrides_yaml}" 2>&1 | grep 'BAD .blocking_policy. FOR' || \ + (echo "[FAIL] exec test4 did not receive expected 'BAD .blocking_policy. FOR' error" && exit 1) + echo '[SUCCESS] exec test4 passed successfully' >> "${TEST_RESULTS}" + + # Test rerun_policies: + # 1. Unspecified + # 2. always + # 3. once_successfully, when script passes + # 4. once_successfully, when script fails + # 5. never + + # first execution + overrides_yaml=${LOGS_SUBDIR}/${FUNCNAME}-set5.yaml + echo 'conf: + exec: + 001-script1.sh: + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> script1 + 002-script2.sh: + rerun_policy: always + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> script2 + 003-script3.sh: + rerun_policy: once_successfully + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> script3 + 004-script4.sh: + rerun_policy: once_successfully + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> script4 + false + 005-script5.sh: + rerun_policy: never + data: | + #!/bin/bash + echo script name: ${BASH_SOURCE} >> script5 + env: + env3: env3-val + env1: env1-val + env2: env2-val + args: + - arg2 + - arg1 + - arg3 +manifests: + daemonset_ethtool: false + daemonset_mounts: false + daemonset_uamlite: false + daemonset_sysctl: false + daemonset_limits: false + daemonset_apt: false + daemonset_perm: false' > "${overrides_yaml}" + + install_base "--values=${overrides_yaml}" + get_container_status exec + + # run several times with the same values and evaluate results + # (ensure no ordering issues cause hashing inconsistencies) + for i in $(seq 0 11); do + install_base "--values=${overrides_yaml}" + get_container_status exec + _test_exec_count "${EXEC_DIR}/script1" '001-script1.sh' $(($i + 2)) + _test_exec_count "${EXEC_DIR}/script2" '002-script1.sh' $(($i + 2)) + _test_exec_count "${EXEC_DIR}/script3" '003-script1.sh' '1' + _test_exec_count "${EXEC_DIR}/script4" '004-script1.sh' $(($i + 2)) + _test_exec_count "${EXEC_DIR}/script5" '005-script1.sh' '1' + echo "[SUCCESS] exec test$(($i + 5)) passed successfully" >> "${TEST_RESULTS}" + done + +} + # test daemonset value overrides for hosts and labels test_overrides(){ overrides_yaml=${LOGS_SUBDIR}/${FUNCNAME}-dryrun.yaml @@ -1053,7 +1275,7 @@ test_overrides(){ # Compare against expected number of generated daemonsets daemonset_count="$(echo "${tc_output}" | grep 'kind: DaemonSet' | wc -l)" - if [ "${daemonset_count}" != "15" ]; then + if [ "${daemonset_count}" != "16" ]; then echo '[FAILURE] overrides test 1 failed' >> "${TEST_RESULTS}" echo "Expected 15 daemonsets; got '${daemonset_count}'" >> "${TEST_RESULTS}" exit 1 @@ -1240,6 +1462,7 @@ if [[ -z $SKIP_BASE_TESTS ]]; then test_ethtool test_uamlite test_apt + test_exec fi purge_containers test_overrides