Skip to content

feat: add deployer host installer (#22) #789

feat: add deployer host installer (#22)

feat: add deployer host installer (#22) #789

Workflow file for this run

name: Validate ci-fleet prototype
on:
pull_request:
# `edited` revalidates the title when a contributor retitles the PR: the
# required check would otherwise stay green for the same head SHA.
types: [opened, synchronize, reopened, edited]
push:
branches: [main]
tags: ['**']
workflow_dispatch:
permissions:
contents: read
concurrency:
group: validate-${{ github.ref }}
cancel-in-progress: true
jobs:
commit-convention:
name: Enforce conventional commits and pull-request title
if: ${{ github.event_name != 'push' || github.event.deleted == false }}
runs-on: ubuntu-latest
timeout-minutes: 5
steps:
- name: Reject updates to published tags
if: ${{ github.event_name == 'push' && startsWith(github.ref, 'refs/tags/') && github.event.created == false }}
run: |
echo "published tags must not be moved" >&2
exit 1
- name: Check out repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7
with:
persist-credentials: false
fetch-depth: 0
- name: Load current main commit validator
env:
EVENT_NAME: ${{ github.event_name }}
BASE_REF: ${{ github.event.pull_request.base.ref }}
HEAD_SHA: ${{ github.event.pull_request.head.sha || github.sha }}
run: |
git fetch --no-tags origin +refs/heads/main:refs/remotes/origin/main
TRUSTED_SHA="$(git rev-parse origin/main)"
validator="$RUNNER_TEMP/trusted-validator.py"
if git cat-file -e "$TRUSTED_SHA:scripts/validate_commits.py" 2>/dev/null; then
git show "$TRUSTED_SHA:scripts/validate_commits.py" >"$validator"
elif [[ "$EVENT_NAME" == pull_request && "$BASE_REF" == main ]] && \
[[ -z "$(git rev-list -1 "$TRUSTED_SHA" -- scripts/validate_commits.py)" ]] && \
git cat-file -e "$HEAD_SHA:scripts/validate_commits.py" 2>/dev/null; then
# Bootstrap only the PR introducing the validator before it has any main history.
git show "$HEAD_SHA:scripts/validate_commits.py" >"$validator"
else
echo "trusted commit validator unavailable at '$TRUSTED_SHA'" >&2
exit 1
fi
- name: Validate pull-request title
if: ${{ github.event_name == 'pull_request' }}
env:
PR_TITLE: ${{ github.event.pull_request.title }}
run: python3 "$RUNNER_TEMP/trusted-validator.py" --pr-title "$PR_TITLE"
- name: Validate proposed commit messages
env:
EVENT_NAME: ${{ github.event_name }}
REF_TYPE: ${{ github.ref_type }}
TAG_NAME: ${{ github.ref_name }}
BASE_SHA: ${{ github.event_name == 'pull_request' && github.event.pull_request.base.sha || github.event_name == 'push' && github.event.before || '' }}
HEAD_SHA: ${{ github.event.pull_request.head.sha || github.sha }}
run: |
# The merge base selects commits, never executable validation policy.
if [[ "$EVENT_NAME" == push && ( -z "$BASE_SHA" || "$BASE_SHA" =~ ^0+$ ) ]]; then
if [[ "$REF_TYPE" == tag ]]; then
BASE_SHA="$(python3 "$RUNNER_TEMP/trusted-validator.py" --release-base-for "$HEAD_SHA" --exclude-tag "$TAG_NAME")"
if [[ -z "$BASE_SHA" ]]; then
BASE_SHA="$(git merge-base "$HEAD_SHA" origin/main)"
fi
else
BASE_SHA="$(git merge-base "$HEAD_SHA" origin/main)"
fi
fi
python3 "$RUNNER_TEMP/trusted-validator.py" --base "$BASE_SHA" --head "$HEAD_SHA"
- name: Validate release tags are SemVer 2.0.0
if: ${{ startsWith(github.ref, 'refs/tags/') }}
env:
TAG_NAME: ${{ github.ref_name }}
TAG_COMMIT: ${{ github.sha }}
run: |
# Tag policy uses the same current-main validator loaded above.
validator="$RUNNER_TEMP/trusted-validator.py"
RELEASE_BASE="$(python3 "$validator" --release-base-for "$TAG_COMMIT" --exclude-tag "$TAG_NAME")"
if [[ -n "$RELEASE_BASE" ]]; then
python3 "$validator" --base "$RELEASE_BASE" --head "$TAG_COMMIT"
elif parent=$(git rev-parse "$TAG_COMMIT^" 2>/dev/null); then
python3 "$validator" --base "$parent" --head "$TAG_COMMIT"
else
python3 "$validator" --head "$TAG_COMMIT"
fi
# Stable tags must point into the main line (fetch-depth 0 gives us
# origin/main); prerelease tags must NOT point into it (they are
# branch-local per docs/CONTRIBUTING.md).
python3 "$validator" --version "$TAG_NAME" --tag-commit "$TAG_COMMIT" \
--base "$RELEASE_BASE" --head "$TAG_COMMIT" --exclude-tag "$TAG_NAME"
validate:
name: Build without registering a runner
needs: commit-convention
if: ${{ !cancelled() && (github.event_name != 'push' || github.event.deleted == false) }}
runs-on: ubuntu-latest
timeout-minutes: 30
steps:
- name: Check out repository
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7
with:
persist-credentials: false
fetch-depth: 0
- name: Scan every proposed commit for secrets
env:
EVENT_NAME: ${{ github.event_name }}
REF_TYPE: ${{ github.ref_type }}
TAG_NAME: ${{ github.ref_name }}
BASE_SHA: ${{ github.event.pull_request.base.sha || github.event.before }}
HEAD_SHA: ${{ github.event.pull_request.head.sha || github.sha }}
run: |
git fetch --no-tags origin +refs/heads/main:refs/remotes/origin/main
TRUSTED_SHA="$(git rev-parse origin/main)"
scanner="$RUNNER_TEMP/trusted-secret-scanner.py"
if ! git cat-file -e "$TRUSTED_SHA:scripts/scan_committed_secrets.py" 2>/dev/null; then
echo "trusted secret scanner unavailable at '$TRUSTED_SHA'" >&2
exit 1
fi
git show "$TRUSTED_SHA:scripts/scan_committed_secrets.py" >"$scanner"
if [[ "$EVENT_NAME" == push && ( -z "$BASE_SHA" || "$BASE_SHA" =~ ^0+$ ) ]]; then
if [[ "$REF_TYPE" == tag ]]; then
validator="$RUNNER_TEMP/trusted-release-validator.py"
git show "$TRUSTED_SHA:scripts/validate_commits.py" >"$validator"
BASE_SHA="$(python3 "$validator" --release-base-for "$HEAD_SHA" --exclude-tag "$TAG_NAME")"
else
BASE_SHA="$(git merge-base "$HEAD_SHA" origin/main)"
fi
fi
if [[ -z "$BASE_SHA" || "$BASE_SHA" =~ ^0+$ ]]; then
git rev-list --reverse "$HEAD_SHA" >"$RUNNER_TEMP/proposed-commits"
else
if ! git rev-list --reverse "$BASE_SHA..$HEAD_SHA" >"$RUNNER_TEMP/proposed-commits"; then
if [[ "$EVENT_NAME" == push && "$REF_TYPE" == tag ]]; then
# A moved tag's old object may no longer be fetchable.
git rev-list --reverse "$HEAD_SHA" >"$RUNNER_TEMP/proposed-commits"
else
exit 1
fi
fi
fi
mapfile -t commits <"$RUNNER_TEMP/proposed-commits"
if [[ ! " ${commits[*]} " == *" $HEAD_SHA "* ]]; then
commits+=("$HEAD_SHA")
fi
for commit in "${commits[@]}"; do
python3 "$scanner" --repository "$GITHUB_WORKSPACE" --commit "$commit"
done
- name: Install static analysis tools
run: sudo apt-get update && sudo apt-get install -y shellcheck
- name: Check shell scripts
run: shellcheck scripts/*.sh examples/project/scripts/ci/*.sh templates/config-repository/scripts/*.sh
- name: Check documentation links
run: python3 scripts/check_doc_links.py
- name: Build and inspect inert prototype
run: scripts/validate.sh
- name: Validate public configuration template
run: |
cmp -s scripts/scan_committed_secrets.py templates/config-repository/scripts/scan_committed_secrets.py
python3 templates/config-repository/scripts/test_policy.py
python3 templates/config-repository/scripts/scan_committed_secrets.py
templates/config-repository/scripts/validate.sh
templates/config-repository/scripts/validate.sh --config templates/config-repository/examples/multi-host/fleet.json
temporary_directory="$(mktemp -d)"
if templates/config-repository/scripts/init.sh \
--organization test-company \
--project test-app \
--output "${temporary_directory}/missing-engine.json"; then
echo 'initializer accepted a missing engine revision' >&2
exit 1
fi
test ! -e "${temporary_directory}/missing-engine.json"
if templates/config-repository/scripts/init.sh \
--organization test-company \
--project test-app \
--registry BAD \
--engine-ref "$(git rev-parse HEAD)" \
--output "${temporary_directory}/invalid.json"; then
echo 'initializer accepted an invalid registry' >&2
exit 1
fi
test ! -e "${temporary_directory}/invalid.json"
templates/config-repository/scripts/init.sh \
--organization test-company \
--project test-app \
--engine-ref "$(git rev-parse HEAD)" \
--output "${temporary_directory}/fleet.json"
test "$(stat -c '%a' "${temporary_directory}/fleet.json")" = 644
- name: Require successful convention validation
env:
CONVENTION_RESULT: ${{ needs.commit-convention.result }}
run: |
test "$CONVENTION_RESULT" = success