Files
RustNotMC/tools/ci/protect_pipeline.sh
T
SashegDev 874b6f20c2 Клиент: начальный импорт кодовой базы
Основа — Horizon (MIT). История апстрима не переносится: этот репозиторий ведёт свою.
2026-10-29 22:04:28 +03:00

55 lines
3.0 KiB
Bash
Executable File

#!/usr/bin/env bash
# Makes main's branch protection require the code owners' review (docs/security.md): a pull request that
# changes a file .github/CODEOWNERS lists waits for Ludovic's approval; every other one still merges as soon as
# `verify` passes (no approvals are required otherwise). Approvals are dismissed by a later push. Everything
# else in the protection (the required `verify` from GitHub Actions, admins included) is kept as it is.
#
# Ludovic is the only code owner, and GitHub never counts an author's approval of their own pull request, so his
# own pull requests to listed files could never merge. He is therefore the one account allowed to bypass the
# pull-request rules (bypass_pull_request_allowances). The alternative, not enforcing the protection on admins,
# would also let an admin merge without `verify`; here `verify` stays required for everyone, admins and Ludovic
# included (enforce_admins stays on), and only the review requirement has an exception, for him alone.
#
# Apply it only once agents open, push and merge pull requests as the horizon-agent GitHub App, not as ludovic111:
# while agents use his token, his bypass is theirs too, and their changes to listed files would skip his review.
#
# tools/ci/protect_pipeline.sh # print the protection it would set, change nothing
# tools/ci/protect_pipeline.sh --apply # set it (needs the maintainer's admin login)
set -euo pipefail
repo=${GITHUB_REPOSITORY:-horizon-rust/horizon}
api="repos/$repo/branches/main/protection"
body=$(gh api "$api" | jq '{
required_status_checks: (.required_status_checks
| {strict, checks: [.checks[] | {context, app_id}]}),
enforce_admins: .enforce_admins.enabled,
required_pull_request_reviews: {
require_code_owner_reviews: true,
required_approving_review_count: 0,
dismiss_stale_reviews: true,
require_last_push_approval: false,
bypass_pull_request_allowances: {users: ["ludovic111"], teams: [], apps: []}
},
restrictions: null,
required_linear_history: .required_linear_history.enabled,
allow_force_pushes: .allow_force_pushes.enabled,
allow_deletions: .allow_deletions.enabled,
required_conversation_resolution: .required_conversation_resolution.enabled,
lock_branch: .lock_branch.enabled,
allow_fork_syncing: .allow_fork_syncing.enabled
}')
echo "$body"
if [[ "${1:-}" == --apply ]]; then
gh api -X PUT "$api" --input - <<< "$body" > /dev/null
set_now=$(gh api "$api" --jq '[.required_pull_request_reviews.require_code_owner_reviews,
.enforce_admins.enabled, ([.required_pull_request_reviews.bypass_pull_request_allowances.users[]?.login]
| index("ludovic111") != null), ([.required_status_checks.checks[].context] | index("verify") != null)]
| map(tostring) | join(" ")')
if [[ "$set_now" != "true true true true" ]]; then
echo "GitHub didn't keep everything (code owners, admins enforced, Ludovic's bypass, verify): $set_now" >&2
exit 1
fi
echo "main now requires code owners' reviews; Ludovic may bypass them; verify is required for everyone."
else
echo "(not applied: run with --apply)"
fi