Skip to content

Publishing and promoting #68

Publishing and promoting

Publishing and promoting #68

Workflow file for this run

# Copyright 2024 Canonical Ltd.
# See LICENSE file for licensing details.
name: Publish charm
on:
push:
branches:
- main
pull_request:
env:
OWNER: ${{ github.repository_owner }}
REGISTRY: ghcr.io
channel: latest/edge
charm_directory: "charm"
charmcraft_ref: feat-12f-django
charmcraft_repository: weiiwang01/charmcraft
paas_app_charmer_oci_name: django-app-image
tag_prefix:
working_directory: "./"
jobs:
branch-up-to-date-check-enabled:
runs-on: ubuntu-22.04
steps:
- uses: octokit/[email protected]
id: get-branch-protection
env:
GITHUB_TOKEN: ${{ secrets.REPO_ACCESS_TOKEN }}
with:
route: GET /repos/{owner}/{repo}/branches/{branch}/protection/required_status_checks
repo: ${{ github.event.repository.name }}
owner: ${{ github.event.repository.owner.login }}
branch: main
- run: |
if [ ${{ fromJson(steps.get-branch-protection.outputs.data).strict }} != "true" ]; then
echo "::error::Strict checks are not enabled for this repository"
exit 1
fi
draft-publish-docs:
name: Draft publish docs
needs: [ branch-up-to-date-check-enabled ]
runs-on: ubuntu-22.04
defaults:
run:
working-directory: ${{ env.working_directory }}/${{ env.charm_directory }}
steps:
- uses: actions/[email protected]
- name: Search for docs folder
id: docs-exist
run: echo "docs_exist=$([[ -d docs ]] && echo 'True' || echo 'False')" >> $GITHUB_OUTPUT
- name: Publish documentation
if: steps.docs-exist.outputs.docs_exist == 'True'
uses: canonical/discourse-gatekeeper@stable
with:
discourse_host: discourse.charmhub.io
discourse_api_username: ${{ secrets.DISCOURSE_API_USERNAME }}
discourse_api_key: ${{ secrets.DISCOURSE_API_KEY }}
dry_run: true
github_token: ${{ secrets.GITHUB_TOKEN }}
charm_dir: ${{ env.working_directory }}/${{ env.charm_directory }}
get-runner-image:
name: Get runner image
uses: canonical/operator-workflows/.github/workflows/get_runner_image.yaml@test-netbox
with:
working-directory: ${{ env.working_directory }}/${{ env.charm_directory }}

Check failure on line 67 in .github/workflows/publish_charm.yaml

View workflow run for this annotation

GitHub Actions / Publish charm

Invalid workflow file

The workflow is not valid. .github/workflows/publish_charm.yaml (Line: 67, Col: 26): Unrecognized named-value: 'env'. Located at position 1 within expression: env.working_directory
secrets: inherit
release-charm-libs:
name: Release charm libs
needs: [ branch-up-to-date-check-enabled ]
runs-on: ubuntu-22.04
steps:
- uses: actions/[email protected]
- if: ${{ env.working_directory }}/${{ env.charm_directory }} != './/.'
name: Change directory
run: |
TEMP_DIR=$(mktemp -d)
cp -rp ./${{ env.working_directory }}/${{ env.charm_directory }}/. $TEMP_DIR
rm -rf .* * || :
cp -rp $TEMP_DIR/. .
rm -rf $TEMP_DIR
- uses: canonical/charming-actions/[email protected]
name: Release libs
with:
credentials: ${{ secrets.CHARMHUB_TOKEN }}
github-token: ${{ secrets.GITHUB_TOKEN }}
get-run-id:
name: Get workflow run id
needs: [ branch-up-to-date-check-enabled ]
runs-on: ubuntu-22.04
outputs:
run-id: ${{ env.RUN_ID }}
steps:
- name: Get workflow run id
if: ${{ github.event_name == 'push' }}
shell: bash
run: |
# Get commit info
TREE_SHA=$(gh api \
-H "Accept: application/vnd.github+json" \
-H "X-GitHub-Api-Version: 2022-11-28" \
/repos/${{ github.repository }}/commits/${GITHUB_SHA} \
--jq '.commit.tree.sha')
# Get workflow run id from this specific tree id, paginate until found
TOTAL_COUNT=$(gh api \
--method GET \
-H "Accept: application/vnd.github+json" \
-H "X-GitHub-Api-Version: 2022-11-28" \
/repos/${{ github.repository }}/actions/runs \
-f status=completed \
-f event=pull_request | jq ".total_count")
PER_PAGE=100
MAX_PAGES=$(( (TOTAL_COUNT + 99) / $PER_PAGE ))
PAGE=1
while true; do
RESULT=$( gh api \
--method GET \
-H "Accept: application/vnd.github+json" \
-H "X-GitHub-Api-Version: 2022-11-28" \
/repos/${{ github.repository }}/actions/runs \
-f page=$PAGE \
-f per_page=$PER_PAGE \
-f status=completed \
-f event=pull_request \
--jq "[
.workflow_runs[]
| select(.path == \".github/workflows/integration_test.yaml\")
| select(.head_commit.tree_id == \"$TREE_SHA\")
] | max_by(.updated_at) | .id"
)
if [[ -n $RESULT ]]; then
RUN_ID=$RESULT
break
fi
if [[ "PAGE" -eq "$MAX_PAGES" ]]; then
echo "::error::No workflow run id found for specific tree id"
exit 1
fi
((PAGE++))
done
echo "RUN_ID=$RUN_ID" >> $GITHUB_ENV
env:
GITHUB_TOKEN: ${{ secrets.REPO_ACCESS_TOKEN }}
- name: Get current run id
if: ${{ github.event_name == 'pull_request' }}
shell: bash
run: |
echo "RUN_ID=${{ github.run_id }}" >> $GITHUB_ENV
get-images:
name: Get images
runs-on: ubuntu-22.04
outputs:
images: ${{ env.IMAGES }}
steps:
- uses: actions/[email protected]
- name: Get images
working-directory: ${{ env.working_directory }}
run: |
lines=$(find . -type f -name rockcraft.yaml | wc -l)
if [ $lines -ne 0 ]; then
IMAGES=$(find . -type f -name rockcraft.yaml | xargs -l yq '.name' | jq -Rsc '. / "\n" - [""]')
else
IMAGES=$(ls *.Dockerfile 2> /dev/null | sed s/\.Dockerfile// | jq -Rsc '. / "\n" - [""]')
fi
echo "IMAGES=$IMAGES" >> $GITHUB_ENV
publish-images:
name: Publish images to charmhub
runs-on: ${{ needs.get-runner-image.outputs.runs-on }}
needs: [ get-images, get-run-id, get-runner-image]
if: ${{ needs.get-images.outputs.images != '[]' }}
steps:
- uses: actions/checkout@v4
if: env.charmcraft_repository != ''
with:
repository: ${{ env.charmcraft_repository }}
ref: ${{ env.charmcraft_ref }}
path: ./charmcraft
fetch-depth: 0
- name: Get Charmcraft SHA
if: env.charmcraft_repository != ''
id: charmcraft-sha
working-directory: ./charmcraft
run: echo "sha=$(git rev-parse HEAD)" >> $GITHUB_OUTPUT
- name: Restore Charmcraft Cache
if: env.charmcraft_repository != ''
id: restore-charmcraft
uses: actions/cache/restore@v4
with:
path: ./charmcraft*.snap
key: charmcraft-${{ steps.charmcraft-sha.outputs.sha }}
- name: Install Snapcraft
if: steps.restore-charmcraft.outputs.cache-hit != 'true' && env.charmcraft_repository != ''
run: sudo snap install snapcraft --classic
- name: Build Charmcraft
if: steps.restore-charmcraft.outputs.cache-hit != 'true' && env.charmcraft_repository != ''
working-directory: ./charmcraft
run: |
snapcraft --use-lxd
cp charmcraft*.snap ../
- name: Save Charmcraft Cache
uses: actions/cache/save@v4
if: steps.restore-charmcraft.outputs.cache-hit != 'true' && env.charmcraft_repository != ''
with:
path: ./charmcraft*.snap
key: ${{ steps.restore-charmcraft.outputs.cache-primary-key }}
- name: Install charmcraft
if: env.charmcraft_repository != ''
run: sudo snap install --dangerous --classic charmcraft*.snap
- name: Clean up
if: env.charmcraft_repository != ''
run: rm -rf *
- name: Install charmcraft
if: env.charmcraft_repository == ''
run: |
sudo snap install charmcraft --classic --channel ${{ env.charmcraft_channel }}
- uses: actions/[email protected]
- if: ${{ env.working_directory }}/${{ env.charm_directory }} != './/.'
name: Change directory
run: |
TEMP_DIR=$(mktemp -d)
cp -rp ./${{ env.working_directory }}/${{ env.charm_directory }}/. $TEMP_DIR
rm -rf .* * || :
cp -rp $TEMP_DIR/. .
rm -rf $TEMP_DIR
- name: Get charm name
id: get-charm-name
run: |
CHARM_NAME="$([ -f metadata.yaml ] && yq '.name' metadata.yaml || echo UNKNOWN)"
if [ "$CHARM_NAME" == "UNKNOWN" ]; then
CHARM_NAME="$([ -f charmcraft.yaml ] && yq '.name' charmcraft.yaml || echo UNKNOWN)"
fi
echo "CHARM_NAME=$CHARM_NAME">> $GITHUB_ENV
- name: Log in to the Container registry
uses: docker/login-action@v3
with:
registry: ${{ env.REGISTRY }}
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Download images artifact
if: ${{ github.event_name == 'push' }}
run: |
gh run download ${{ needs.get-run-id.outputs.run-id }} -R ${{ github.repository }} -n ${{ env.CHARM_NAME }}-images
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- name: Download images artifact (for testing)
uses: actions/download-artifact@v4
if: ${{ github.event_name == 'pull_request' }}
with:
name: ${{ env.CHARM_NAME }}-images
- name: Publish image
env:
CHARMCRAFT_ENABLE_EXPERIMENTAL_EXTENSIONS: "true"
CHARMCRAFT_AUTH: ${{ secrets.CHARMHUB_TOKEN }}
run: |
charm=${{ env.CHARM_NAME }}
declare -a resources
declare -a images
if [ -f metadata.yaml ]; then
for resource in $(yq -er '.resources | with_entries(select(.value.type=="oci-image")) | keys | join(" ")' metadata.yaml); do
resources+=("$resource")
done
else
for resource in $(yq -er '.resources | with_entries(select(.value.type=="oci-image")) | keys | join(" ")' <(charmcraft expand-extensions)); do
resources+=("$resource")
done
fi
for image in $(cat ${{ env.CHARM_NAME }}-images); do
images+=("$image")
done
echo resources: -"${resources[@]}"-
echo images: -"${images[@]}"-
for image in "${images[@]}"; do
if [[ "${{ env.paas_app_charmer_oci_name }}" != "" ]]; then
# This is for paas-app-charmer . The main image name (resource oci in charmcraft.yaml) is
# defined with the env variable paas-app-charmer-oci-name, and corresponds to the main
# image in rockcraft.yaml.
resource_name="{{ env.paas_app_charmer_oci_name }}"
else
resource_name=$(echo $image | awk -F '/' '{print $NF}' | cut -d ':' -f 1)-image
fi
if [[ " ${resources[@]} " =~ " $resource " ]]; then
docker pull $image
image_id=$(docker images $image --format "{{.ID}}")
charmcraft upload-resource $charm $resource --image=$image_id --verbosity=brief
fi
done
publish-charm:
name: Publish charm
runs-on: ${{ needs.get-runner-image.outputs.runs-on }}
needs: [get-run-id, get-runner-image, publish-images]
if: ${{ !failure() }}
steps:
- uses: actions/checkout@v4
if: env.charmcraft_repository != ''
with:
repository: ${{ env.charmcraft_repository }}
ref: ${{ env.charmcraft_ref }}
path: ./charmcraft
fetch-depth: 0
- name: Get Charmcraft SHA
if: env.charmcraft_repository != ''
id: charmcraft-sha
working-directory: ./charmcraft
run: echo "sha=$(git rev-parse HEAD)" >> $GITHUB_OUTPUT
- name: Restore Charmcraft Cache
if: env.charmcraft_repository != ''
id: restore-charmcraft
uses: actions/cache/restore@v4
with:
path: ./charmcraft*.snap
key: charmcraft-${{ steps.charmcraft-sha.outputs.sha }}
- name: Install Snapcraft
if: steps.restore-charmcraft.outputs.cache-hit != 'true' && env.charmcraft_repository != ''
run: sudo snap install snapcraft --classic
- name: Build Charmcraft
if: steps.restore-charmcraft.outputs.cache-hit != 'true' && env.charmcraft_repository != ''
working-directory: ./charmcraft
run: |
snapcraft --use-lxd
cp charmcraft*.snap ../
- name: Save Charmcraft Cache
uses: actions/cache/save@v4
if: steps.restore-charmcraft.outputs.cache-hit != 'true' && env.charmcraft_repository != ''
with:
path: ./charmcraft*.snap
key: ${{ steps.restore-charmcraft.outputs.cache-primary-key }}
- name: Install charmcraft
if: env.charmcraft_repository != ''
run: sudo snap install --dangerous --classic charmcraft*.snap
- name: Clean up
if: env.charmcraft_repository != ''
run: rm -rf *
- name: Install charmcraft
if: env.charmcraft_repository == ''
run: |
sudo snap install charmcraft --classic --channel ${{ env.charmcraft_channel }}
- uses: actions/[email protected]
- if: ${{ env.working_directory }}/${{ env.charm_directory }} != './/.'
name: Change directory
run: |
set -x
ls
TEMP_DIR=$(mktemp -d)
cp -rp ./${{ env.working_directory }}/${{ env.charm_directory }}/. $TEMP_DIR
rm -rf .* * || :
cp -rp $TEMP_DIR/. .
rm -rf $TEMP_DIR
ls
- name: Get charm name
id: get-charm-name
run: |
set -x
CHARM_NAME="$([ -f metadata.yaml ] && yq '.name' metadata.yaml || echo UNKNOWN)"
if [ "$CHARM_NAME" == "UNKNOWN" ]; then
CHARM_NAME="$([ -f charmcraft.yaml ] && yq '.name' charmcraft.yaml || echo UNKNOWN)"
fi
echo "CHARM_NAME=$CHARM_NAME">> $GITHUB_ENV
- name: Download charm artifact
if: ${{ github.event_name == 'push' }}
run: |
gh run download ${{ needs.get-run-id.outputs.run-id }} -R ${{ github.repository }} -n ${{ env.CHARM_NAME }}-charm
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- name: Download charm artifact (for testing)
uses: actions/download-artifact@v4
if: ${{ github.event_name == 'pull_request' }}
with:
name: ${{ env.CHARM_NAME }}-charm
path: ${{ env.working_directory }}
- name: Get charm file
id: get-charm-file
run: |
echo "CHARM_FILE=$(ls ${{ env.CHARM_NAME }}_*.charm)" >> $GITHUB_OUTPUT
- name: Upload charm to charmhub
env:
CHARMCRAFT_ENABLE_EXPERIMENTAL_EXTENSIONS: "true"
CHARMCRAFT_AUTH: ${{ secrets.CHARMHUB_TOKEN }}
CHARM_FILE: ${{ steps.get-charm-file.outputs.CHARM_FILE }}
run: |
charmcraft resource-revisions netbox django-app-image
# it looks like this is not necessary, but it is what the canonical/charming-actions/upload-charm does.
MAX_REV=$(charmcraft resource-revisions netbox django-app-image --format=json | jq 'map( .revision) | max')
echo max_rev ${MAX_REV}
charmcraft upload --format json --release ${channel} ${CHARM_FILE} --resource=django-app-image:${MAX_REV}