From 10d36643365bb95005f67a7504d1c99caf026ac2 Mon Sep 17 00:00:00 2001 From: Chris Porter Date: Thu, 26 Sep 2024 04:16:54 +0000 Subject: [PATCH 1/3] Release: Fix docker-manifest-create for latest tag The `docker manifest create` command for creating the latest tag had a typo which needed amending. Also, the way the loops and associative arrays are written, this `docker manifest create` command would have run more than once for the same `latest` package. This was probably not intended, because ghcr will only accept 1 latest tag for the same package anyway. So, this change also moves the `docker manifest create` command outside of the loop to avoid this ambiguity and chooses the release package name without any prefix to be the latest version (e.g. opting for key-broker-service:v0.10.0 for the latest tag instead of key-broker-service:built-in-as-v0.10.0). Signed-off-by: Chris Porter --- hack/release-helper.sh | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-) diff --git a/hack/release-helper.sh b/hack/release-helper.sh index 94fc32329..02932b2ee 100755 --- a/hack/release-helper.sh +++ b/hack/release-helper.sh @@ -8,6 +8,11 @@ declare -g release_candidate_sha declare -g release_tag # Output naming convention along with release guide can be found in release-guide.md +declare -a release_pkg_names=( + "key-broker-service" + "reference-value-provider-service" + "attestation-service" +) declare -A staged_to_release=( ["staged-images/kbs"]="key-broker-service" ["staged-images/kbs-grpc-as"]="key-broker-service" @@ -36,7 +41,7 @@ function usage_and_exit() { echo " Example: v0.8.2" echo echo "Example usage:" - echo " ./release-helper.sh -u \${gh_username} -k \${gh_token} -c dc01f454264fb4350e5f69eba05683a9a1882c41 -n v0.8.2" + echo " ./release-helper.sh -u \${gh_username} -k \${gh_token} -c dc01f454264fb4350e5f69eba05683a9a1882c41 -r v0.8.2" echo exit 1 } @@ -106,10 +111,14 @@ function tag_and_push_packages() { --amend ${ghcr_repo}/${release_pkg_name}:${release_tag_full}-x86_64 \ --amend ${ghcr_repo}/${release_pkg_name}:${release_tag_full}-s390x docker manifest push ${ghcr_repo}/${release_pkg_name}:${release_tag_full} + done - docker manifest create ${ghcr_repo}/${release_pkg_name}:${release_tag_full} \ - --amend ${ghcr_repo}/${release_pkg_name}:${release_tag_full}-x86_64 \ - --amend ${ghcr_repo}/${release_pkg_name}:${release_tag_full}-s390x + # Publish a latest tag. Note this will be applied to only the non-prefixed + # packages (e.g. the "built-in-as" kbs package won't have a latest tag). + for release_pkg_name in ${release_pkg_names[@]}; do + docker manifest create ${ghcr_repo}/${release_pkg_name}:latest \ + --amend ${ghcr_repo}/${release_pkg_name}:${release_tag}-x86_64 \ + --amend ${ghcr_repo}/${release_pkg_name}:${release_tag}-s390x docker manifest push ${ghcr_repo}/${release_pkg_name}:latest done From 805c0d68cad08f2480c84b2f7d0f18401adc2293 Mon Sep 17 00:00:00 2001 From: Chris Porter Date: Thu, 26 Sep 2024 05:45:31 +0000 Subject: [PATCH 2/3] Release: Split the release-helper script in two The release-helper script did two things: bump the version in the kustomization file, and update the ghcr packages with release tags. The latter step should be triggered by a github action on release and should not require a user to manually run it. Thus, it makes sense to separate this into its own script. Signed-off-by: Chris Porter --- ...lease-helper.sh => release-helper-ghcr.sh} | 86 ++--------- hack/release-helper-kustfile.sh | 136 ++++++++++++++++++ 2 files changed, 147 insertions(+), 75 deletions(-) rename hack/{release-helper.sh => release-helper-ghcr.sh} (66%) create mode 100755 hack/release-helper-kustfile.sh diff --git a/hack/release-helper.sh b/hack/release-helper-ghcr.sh similarity index 66% rename from hack/release-helper.sh rename to hack/release-helper-ghcr.sh index 02932b2ee..bf49e97b7 100755 --- a/hack/release-helper.sh +++ b/hack/release-helper-ghcr.sh @@ -1,6 +1,16 @@ #!/bin/bash set -euo pipefail +# +# This release helper script creates the ghcr packages and associated tags for +# a trustee release. +# This is done by pulling the candidate ghcr packages in "staged-images/", +# tagging them with the appropriate release tags, and then pushing the new +# release tags back to ghcr. +# +# XXX This script is meant to be running "on: release" by a github action +# runner and should rarely require a user to manually run it. +# declare -g gh_username declare -g gh_token @@ -41,7 +51,7 @@ function usage_and_exit() { echo " Example: v0.8.2" echo echo "Example usage:" - echo " ./release-helper.sh -u \${gh_username} -k \${gh_token} -c dc01f454264fb4350e5f69eba05683a9a1882c41 -r v0.8.2" + echo " $0 -u \${gh_username} -k \${gh_token} -c dc01f454264fb4350e5f69eba05683a9a1882c41 -r v0.8.2" echo exit 1 } @@ -133,83 +143,9 @@ function tag_and_push_packages() { } -function bump_kustomization_with_pr() { - local kust_file="kbs/config/kubernetes/base/kustomization.yaml" - local update_branch="updates-for-release-${release_tag}" - tmp_dir=$(mktemp -d) - trap teardown EXIT - - echo - echo "Bumping kustomization and opening PR" - echo - - # clone user's trustee - git clone git@github.com:${gh_username}/trustee ${tmp_dir}/trustee - pushd ${tmp_dir}/trustee - - # bail if the (remote) origin already has the branch we need to use - rv=$(git ls-remote --heads origin ${update_branch}) - if [[ "${rv}" =~ "refs/heads/${update_branch}" ]]; then - echo "Error: origin/${update_branch} already exists, but this script" - echo "expects to be able to push to a fresh ${update_branch} branch." - echo "Please manually delete the branch or otherwise handle this" - echo "before proceeding." - exit 1 - fi - - # switch to a new branch that's tracking (upstream) main - git remote add upstream git@github.com:confidential-containers/trustee - git fetch upstream - git checkout -b ${update_branch} upstream/main - - # update kustomization.yaml - sed \ - -Ei \ - "s;newTag: built-in-as-v[0-9]+\.[0-9]+\.[0-9]+;newTag: built-in-as-${release_tag};g" \ - ${kust_file} - - # commit and push - git add ${kust_file} - git commit -sm 'Release: Update kbs kustomization.yaml for '${release_tag} - git push --set-upstream origin ${update_branch} - - # open PR - rv=$(curl \ - -L \ - -s \ - -i \ - -X POST \ - -H "Accept: application/vnd.github+json" \ - -H "Authorization: Bearer ${gh_token}" \ - -H "X-GitHub-Api-Version: 2022-11-28" \ - https://api.github.com/repos/confidential-containers/trustee/pulls \ - -d '{"title":"Release: Update KBS for '${release_tag}'", - "body":"Updates kustomization.yaml for next release.", - "head":"'${gh_username}':'${update_branch}'", - "base":"main"}') - rc=$(echo ${rv} | head -n 1 | cut -d' ' -f2) - if ! [[ "${rc}" =~ 2[0-9][0-9] ]]; then - echo "Error: POST to open a PR received a non-2xx response from github" - echo "(${rc}). Dumping full response..." - echo ${rv} - echo "Attempting to delete origin/${update_branch}" - git push origin :${update_branch} - exit 1 - fi - - popd -} - - -function teardown() { - rm -rf ${tmp_dir} -} - - function main() { parse_args "$@" tag_and_push_packages - bump_kustomization_with_pr echo "Success. Exiting..." } diff --git a/hack/release-helper-kustfile.sh b/hack/release-helper-kustfile.sh new file mode 100755 index 000000000..a06e97f04 --- /dev/null +++ b/hack/release-helper-kustfile.sh @@ -0,0 +1,136 @@ +#!/bin/bash +set -euo pipefail + +# +# This release helper script updates the kustomization.yaml file for a new +# release and automatically opens a PR with the change. +# + + +declare -g gh_username +declare -g gh_token +declare -g release_tag + + +function usage_and_exit() { + echo + echo "Usage:" + echo " $0 -u github-username -k github-token -r release-tag" + echo + echo " -u Your github username. You'll be opening a PR against " + echo " confidential-container's trustee/main." + echo " -k A github token with permissions on trustee to open a PR." + echo " -r This is the new version tag that the release will have." + echo " Example: v0.8.2" + echo + echo "Example usage:" + echo " $0 -u \${gh_username} -k \${gh_token} -r v0.8.2" + echo + exit 1 +} + + +function parse_args() { + while getopts ":u:k:r:" opt; do + case "${opt}" in + u) + gh_username=${OPTARG} + ;; + k) + gh_token=${OPTARG} + ;; + r) + release_tag=${OPTARG} + ;; + *) + usage_and_exit + ;; + esac + done + if [[ ! -v gh_username ]] || [[ ! -v gh_token ]] || [[ ! -v release_tag ]]; then + usage_and_exit + fi +} + + +function bump_kustomization_with_pr() { + local kust_file="kbs/config/kubernetes/base/kustomization.yaml" + local update_branch="updates-for-release-${release_tag}" + tmp_dir=$(mktemp -d) + trap teardown EXIT + + echo + echo "Bumping kustomization and opening PR" + echo + + # clone user's trustee + git clone git@github.com:${gh_username}/trustee ${tmp_dir}/trustee + pushd ${tmp_dir}/trustee + + # bail if the (remote) origin already has the branch we need to use + rv=$(git ls-remote --heads origin ${update_branch}) + if [[ "${rv}" =~ "refs/heads/${update_branch}" ]]; then + echo "Error: origin/${update_branch} already exists, but this script" + echo "expects to be able to push to a fresh ${update_branch} branch." + echo "Please manually delete the branch or otherwise handle this" + echo "before proceeding." + exit 1 + fi + + # switch to a new branch that's tracking (upstream) main + git remote add upstream git@github.com:confidential-containers/trustee + git fetch upstream + git checkout -b ${update_branch} upstream/main + + # update kustomization.yaml + sed \ + -Ei \ + "s;newTag: built-in-as-v[0-9]+\.[0-9]+\.[0-9]+;newTag: built-in-as-${release_tag};g" \ + ${kust_file} + + # commit and push + git add ${kust_file} + git commit -sm 'Release: Update kbs kustomization.yaml for '${release_tag} + git push --set-upstream origin ${update_branch} + + # open PR + rv=$(curl \ + -L \ + -s \ + -i \ + -X POST \ + -H "Accept: application/vnd.github+json" \ + -H "Authorization: Bearer ${gh_token}" \ + -H "X-GitHub-Api-Version: 2022-11-28" \ + https://api.github.com/repos/confidential-containers/trustee/pulls \ + -d '{"title":"Release: Update KBS for '${release_tag}'", + "body":"Updates kustomization.yaml for next release.", + "head":"'${gh_username}':'${update_branch}'", + "base":"main"}') + rc=$(echo ${rv} | head -n 1 | cut -d' ' -f2) + if ! [[ "${rc}" =~ 2[0-9][0-9] ]]; then + echo "Error: POST to open a PR received a non-2xx response from github" + echo "(${rc}). Dumping full response..." + echo ${rv} + echo "Attempting to delete origin/${update_branch}" + git push origin :${update_branch} + exit 1 + fi + + popd +} + + +function teardown() { + rm -rf ${tmp_dir} +} + + +function main() { + parse_args "$@" + bump_kustomization_with_pr + echo "Success. Exiting..." +} + + +main "$@" From c38a095ef09062855c83615b360b1980676f8318 Mon Sep 17 00:00:00 2001 From: Chris Porter Date: Thu, 26 Sep 2024 06:03:16 +0000 Subject: [PATCH 3/3] Release: Add an on-release GHA to tag ghcr pkgs Rather than manuallyu execute a script for tagging ghcr packages at release time, this can be more reliably automated in a github action that's triggered on release. This new github action simply calls the previous release-helper script support that is in place. Signed-off-by: Chris Porter --- .../publish-ghcr-pkgs-on-release.yml | 22 +++++++++++++++++++ 1 file changed, 22 insertions(+) create mode 100644 .github/workflows/publish-ghcr-pkgs-on-release.yml diff --git a/.github/workflows/publish-ghcr-pkgs-on-release.yml b/.github/workflows/publish-ghcr-pkgs-on-release.yml new file mode 100644 index 000000000..ed8758a83 --- /dev/null +++ b/.github/workflows/publish-ghcr-pkgs-on-release.yml @@ -0,0 +1,22 @@ +name: Publish ghcr packages on trustee release + +on: + release: + types: [published] + +jobs: + publish-ghcr-packages: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v4 + + - name: Run release-helper-ghcr to tag ghcr release packages + env: + GH_TOKEN: ${{ github.token }} + GH_USERNAME: ${{ github.actor }} + GH_SHA: ${{ github.sha }} + run: | + tag=$(echo $GITHUB_REF | sed 's|refs/tags/||') + cd hack + ./release-helper-ghcr.sh -u $GH_USERNAME -k $GH_TOKEN -c $GH_SHA -r $tag