Skip to content

Commit

Permalink
feat(RELEASE-910): add run-collectors task
Browse files Browse the repository at this point in the history
This commit adds a new task run-collectors which will run all defined
collectors in the ReleasePlan and ReleasePlanAdmission and write the
results to a passed resultsDir.

Signed-off-by: Johnny Bieren <[email protected]>
  • Loading branch information
johnbieren committed Oct 1, 2024
1 parent a29dd09 commit b224574
Show file tree
Hide file tree
Showing 11 changed files with 927 additions and 0 deletions.
12 changes: 12 additions & 0 deletions tasks/run-collectors/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# run-collectors

Tekton task to run the collectors defined in the ReleasePlan and ReleasePlanAdmission. The results are saved in the resultsDir,
one file per collector.

## Parameters

| Name | Description | Optional | Default value |
|--------------------------|---------------------------------------------------------------------------|----------|---------------|
| releasePlanAdmissionPath | Path to the JSON string of the ReleasePlanAdmission in the data workspace | No | - |
| releasePlanPath | Path to the JSON string of the ReleasePlan in the data workspace | No | - |
| resultsDir | The relative path in the workspace to save the collector results to | No | - |
99 changes: 99 additions & 0 deletions tasks/run-collectors/run-collectors.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
---
apiVersion: tekton.dev/v1
kind: Task
metadata:
name: run-collectors
labels:
app.kubernetes.io/version: "0.1.0"
annotations:
tekton.dev/pipelines.minVersion: "0.12.1"
tekton.dev/tags: release
spec:
description: >-
Tekton task to run collectors defined in the ReleasePlan and ReleasePlanAdmission
params:
- name: releasePlanAdmissionPath
type: string
description: Path to the JSON string of the ReleasePlanAdmission in the data workspace
- name: releasePlanPath
type: string
description: Path to the JSON string of the ReleasePlan in the data workspace
- name: resultsDir
type: string
description: The relative path in the workspace to save the collector results to
workspaces:
- name: data
description: Workspace where the CRs are stored
steps:
- name: run-collectors
image: quay.io/konflux-ci/release-service-utils:e633d51cd41d73e4b3310face21bb980af7a662f
script: |
#!/usr/bin/env bash
set -xeo pipefail
DEFAULT_TIMEOUT=900
COLLECTORS_REPOSITORY="https://github.com/SOME_ORG/SOME_REPO" # TODO - update this once repo is created
RELEASEPLAN_FILE="$(workspaces.data.path)/$(params.releasePlanPath)"
RELEASEPLANADMISSION_FILE="$(workspaces.data.path)/$(params.releasePlanAdmissionPath)"
RESULTS_DIR="$(workspaces.data.path)/$(params.resultsDir)"
CONCURRENT_LIMIT=4
execute_collector() { # Expected arguments are [collector json, type of collector]
collector="$1"
name="$(jq -r '.name' <<< "$collector")"
type="$(jq -r '.type' <<< "$collector")"
TIMEOUT="$(jq -r --arg default "$DEFAULT_TIMEOUT" '.timeout // $default' <<< "$collector")"
ARGS=()
NUM_ARGS="$(jq '.params | length' <<< "$collector")"
for ((j = 0; j < NUM_ARGS; j++)) ; do
param="$(jq -c --argjson j "$j" '.params[$j]' <<< "$collector")"
arg_name="$(jq -r '.name' <<< "$param")"
arg_value="$(jq -r '.value' <<< "$param")"
ARGS=("${ARGS[@]}" --"${arg_name}" "${arg_value}")
done
# Execute collector
timeout "$TIMEOUT" python3 "$type" "${ARGS[@]}" | tee "$RESULTS_DIR"/"$2"-"$name".json
}
if [ ! -d "${RESULTS_DIR}" ] ; then
echo The passed results directory does not exist. Failing as there is nowhere to save the results to
exit 1
fi
git clone "${COLLECTORS_REPOSITORY}" collectors
pushd collectors
RUNNING_JOBS="\j" # Bash parameter for number of jobs currently running
if [ ! -f "${RELEASEPLAN_FILE}" ] ; then
echo "No valid releasePlan file was found so no tenant collectors will be run."
else
NUM_TENANT_COLLECTORS="$(jq '.spec.collectors | length' "${RELEASEPLAN_FILE}")"
for ((i = 0; i < NUM_TENANT_COLLECTORS; i++)) ; do
collector="$(jq -c --argjson i "$i" '.spec.collectors[$i]' "${RELEASEPLAN_FILE}")"
# Limit batch size to concurrent limit
while (( ${RUNNING_JOBS@P} >= "$CONCURRENT_LIMIT" )); do
wait -n
done
execute_collector "$collector" tenant &
done
fi
if [ ! -f "${RELEASEPLANADMISSION_FILE}" ] ; then
echo "No valid releasePlanAdmission file was found so no managed collectors will be run."
else
NUM_MANAGED_COLLECTORS="$(jq '.spec.collectors | length' "${RELEASEPLANADMISSION_FILE}")"
for ((i = 0; i < NUM_MANAGED_COLLECTORS; i++)) ; do
collector="$(jq -c --argjson i "$i" '.spec.collectors[$i]' "${RELEASEPLANADMISSION_FILE}")"
# Limit batch size to concurrent limit
while (( ${RUNNING_JOBS@P} >= "$CONCURRENT_LIMIT" )); do
wait -n
done
execute_collector "$collector" managed &
done
fi
# Wait for remaining processes to finish
while (( ${RUNNING_JOBS@P} > 0 )); do
wait -n
done
46 changes: 46 additions & 0 deletions tasks/run-collectors/tests/mocks.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
#!/usr/bin/env bash
set -xeo pipefail

# mocks to be injected into task step scripts

function git() {
echo Mock git called with: $*
echo $* >> $(workspaces.data.path)/mock_git.txt

if [[ "$*" == "clone "* ]]
then
mkdir collectors
return
fi

echo Error: Unexpected git call
exit 1
}

function timeout() {
echo Mock timeout called with: $* >&2
echo $* >> $(workspaces.data.path)/mock_timeout.txt

if [[ "$*" == *"python3 dummy-collector --test-arg test-value" ]]
then
echo '{"name": "dummy", "example-argument": "test-value", "issues": ["RELEASE-1", "RELEASE-2"]}'
return
fi

if [[ "$*" == *"python3 parallel-collector --test-arg test-value" ]]
then
date +%s >> $(workspaces.data.path)/parallel-time.txt
sleep 5
echo '{"name": "dummy", "example-argument": "test-value", "issues": ["RELEASE-1", "RELEASE-2"]}'
date +%s >> $(workspaces.data.path)/parallel-time.txt
return
fi

if [[ "$*" == *"python3 timeout-collector --test-arg test-value" ]]
then
exit 124 # timeout exits 124 if it times out
fi

echo Error: Unexpected call
exit 1
}
7 changes: 7 additions & 0 deletions tasks/run-collectors/tests/pre-apply-task-hook.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
#!/usr/bin/env bash

TASK_PATH="$1"
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )

# Add mocks to the beginning of task step script
yq -i '.spec.steps[0].script = load_str("'$SCRIPT_DIR'/mocks.sh") + .spec.steps[0].script' "$TASK_PATH"
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
---
apiVersion: tekton.dev/v1
kind: Pipeline
metadata:
name: test-run-collectors-fail-no-results-dir
annotations:
test/assert-task-failure: "run-task"
spec:
description: |
Run the collectors task with no directory present as the passed resultsDir. The task should fail
workspaces:
- name: tests-workspace
tasks:
- name: run-task
taskRef:
name: run-collectors
params:
- name: releasePlanPath
value: test_release_plan.json
- name: releasePlanAdmissionPath
value: test_release_plan_admission.json
- name: resultsDir
value: results
workspaces:
- name: data
workspace: tests-workspace
108 changes: 108 additions & 0 deletions tasks/run-collectors/tests/test-run-collectors-fail-timeout.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
---
apiVersion: tekton.dev/v1
kind: Pipeline
metadata:
name: test-run-collectors-fail-timeout
annotations:
test/assert-task-failure: "run-task"
spec:
description: |
Run the collectors task with a collector in only the ReleasePlan that takes longer than its timeout.
The task should fail
workspaces:
- name: tests-workspace
tasks:
- name: setup
taskSpec:
steps:
- name: create-crs
image: quay.io/konflux-ci/release-service-utils:e633d51cd41d73e4b3310face21bb980af7a662f
script: |
#!/usr/bin/env bash
set -eux
mkdir "$(workspaces.data.path)"/results
cat > "$(workspaces.data.path)"/test_release_plan.json << EOF
{
"apiVersion": "appstudio.redhat.com/v1alpha1",
"kind": "ReleasePlan",
"metadata": {
"name": "test-rp",
"namespace": "default"
},
"spec": {
"application": "app",
"collectors": [
{
"name": "test-collector",
"type": "timeout-collector",
"timeout": 1,
"params": [
{
"name": "test-arg",
"value": "test-value"
}
]
}
],
"target": "managed"
}
}
EOF
cat > "$(workspaces.data.path)"/test_release_plan_admission.json << EOF
{
"apiVersion": "appstudio.redhat.com/v1alpha1",
"kind": "ReleasePlanAdmission",
"metadata": {
"name": "test-rpa",
"namespace": "default"
},
"spec": {
"applications": [
"app"
],
"policy": "policy",
"pipeline": {
"pipelineRef": {
"resolver": "git",
"params": [
{
"name": "url",
"value": "github.com"
},
{
"name": "revision",
"value": "production"
},
{
"name": "pathInRepo",
"value": "pipeline.yaml"
}
]
},
"serviceAccountName": "sa"
},
"origin": "dev"
}
}
EOF
workspaces:
- name: data
workspace: tests-workspace
- name: run-task
taskRef:
name: run-collectors
params:
- name: releasePlanPath
value: test_release_plan.json
- name: releasePlanAdmissionPath
value: test_release_plan_admission.json
- name: resultsDir
value: results
runAfter:
- setup
workspaces:
- name: data
workspace: tests-workspace
60 changes: 60 additions & 0 deletions tasks/run-collectors/tests/test-run-collectors-no-crs.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
---
apiVersion: tekton.dev/v1
kind: Pipeline
metadata:
name: test-run-collectors-no-crs
spec:
description: |
Run the collectors task with no ReleasePlan or ReleasePlanAdmission. The task should still pass
workspaces:
- name: tests-workspace
tasks:
- name: setup
taskSpec:
steps:
- name: setup
image: quay.io/konflux-ci/release-service-utils:e633d51cd41d73e4b3310face21bb980af7a662f
script: |
#!/usr/bin/env bash
set -eux
mkdir "$(workspaces.data.path)"/results
workspaces:
- name: data
workspace: tests-workspace
- name: run-task
taskRef:
name: run-collectors
params:
- name: releasePlanPath
value: test_release_plan.json
- name: releasePlanAdmissionPath
value: test_release_plan_admission.json
- name: resultsDir
value: results
runAfter:
- setup
workspaces:
- name: data
workspace: tests-workspace
- name: check-result
workspaces:
- name: data
workspace: tests-workspace
runAfter:
- run-task
taskSpec:
workspaces:
- name: data
steps:
- name: check-result
image: quay.io/konflux-ci/release-service-utils:e633d51cd41d73e4b3310face21bb980af7a662f
script: |
#!/usr/bin/env bash
set -eux
if [ "$(find "$(workspaces.data.path)/results" -type f | wc -l)" -ne 0 ] ; then
echo "No collectors should have been run, but that was not not the case. Collector files:"
ls "$(workspaces.data.path)/results"
exit 1
fi
Loading

0 comments on commit b224574

Please sign in to comment.