Skip to content

fix: use python 3.13 to build 26.04 and fix post deply checks #301

fix: use python 3.13 to build 26.04 and fix post deply checks

fix: use python 3.13 to build 26.04 and fix post deply checks #301

Workflow file for this run

name: "CI"
# We don't run this workflow on 'pull_request', because we require secrets to
# upload the charm to Charmhub, and pull_request runs can't access secrets.
# PRs should be opened from a branch on the main juju/juju-controller repo,
# not from a fork.
on:
push:
workflow_dispatch:
env:
CHARM_NAME: ${{ vars.CHARM_NAME }}
jobs:
unit-tests:
name: Unit tests
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Set up Python
uses: actions/setup-python@v4
with:
python-version: '3.10'
- name: Install uv
run: pip install uv
- name: Create uv virtualenv
run: uv venv
- name: Install dependencies for testing
run: |
source .venv/bin/activate
uv pip install ".[dev]"
- name: Run tests
run: |
source .venv/bin/activate
./run_tests
build:
name: Build charm (${{ matrix.platform }})
needs: unit-tests
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
include:
- platform: ubuntu@20.04:amd64
uv_python: "3.8"
artifact_name: charm-ubuntu-20.04-amd64
- platform: ubuntu@22.04:amd64
uv_python: "3.10"
artifact_name: charm-ubuntu-22.04-amd64
- platform: ubuntu@24.04:amd64
uv_python: "3.12"
artifact_name: charm-ubuntu-24.04-amd64
- platform: ubuntu@26.04:amd64
uv_python: "3.13"
artifact_name: charm-ubuntu-26.04-amd64
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Set up Python
uses: actions/setup-python@v4
with:
python-version: ${{ matrix.uv_python }}
- name: Install uv
run: pip install uv
- name: Set up LXD
uses: canonical/setup-lxd@90d76101915da56a42a562ba766b1a77019242fd
- name: Add runner to lxd group
run: |
sudo usermod -a -G lxd $USER
newgrp lxd
- name: Install charmcraft
# We use latest because there's no 4.x track yet.
run: sudo snap install charmcraft --classic --channel=latest/stable
- name: Pack charm
run: sg lxd -c "UV_PYTHON=${{ matrix.uv_python }} charmcraft pack --platform='${{ matrix.platform }}'"
- name: Upload charm artifact
uses: actions/upload-artifact@v4
with:
name: ${{ matrix.artifact_name }}
path: "*.charm"
channel:
name: Select Charmhub channel
runs-on: ubuntu-latest
outputs:
test: ${{ steps.channel.outputs.test }}
release: ${{ steps.channel.outputs.release }}
steps:
- name: Select Charmhub channel
id: channel
shell: bash
run: |
set -eux
case ${{ github.ref_name }} in
3.* | 4.*)
TRACK=$(echo "${{ github.ref_name }}" | awk -F "-" '{print $1}')
DO_RELEASE=true
;;
main)
TRACK="latest"
DO_RELEASE=true
;;
*)
TRACK="latest"
DO_RELEASE=false # Don't release feature branches
;;
esac
# Feature branches will be released to the 'latest' track, so we need
# to include the branch name to disambiguate.
BRANCH="${{ github.ref_name }}-${{ github.sha }}"
echo "test=$TRACK/edge/$BRANCH" >> "$GITHUB_OUTPUT"
if [[ "$DO_RELEASE" == 'true' ]]; then
echo "release=$TRACK/edge" >> "$GITHUB_OUTPUT"
fi
upload:
name: Upload to Charmhub
needs: [build, channel]
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Download packed charm
id: download
uses: actions/download-artifact@v4
with:
pattern: charm-ubuntu-*
merge-multiple: true
path: charms
- name: Upload charms to Charmhub
env:
CHARMCRAFT_AUTH: ${{ secrets.CHARMCRAFT_AUTH }}
run: |
# We use latest because there's no 4.x track yet.
sudo snap install charmcraft --channel latest/stable --classic
for FILE in charms/*.charm; do
echo "Uploading: $FILE"
charmcraft upload --name "$CHARM_NAME" --release "${{ needs.channel.outputs.test }}" "$FILE"
done
integration:
name: "Integration tests"
runs-on: ubuntu-latest
needs: [build, upload, channel]
strategy:
fail-fast: false
matrix:
cloud: ["lxd", "microk8s"]
steps:
- name: Save charmcraft logs as artifact
if: always() && steps.charmcraft.outcome != 'skipped'
uses: actions/upload-artifact@v4
with:
name: charmcraft-upload-logs
path: ~/.local/state/charmcraft/log/
continue-on-error: true
- name: Setup LXD
if: matrix.cloud == 'lxd'
uses: canonical/setup-lxd@2fa6235ef2dfd3288e0de09edac03f2ebf922968
- name: Set up MicroK8s
if: matrix.cloud == 'microk8s'
uses: balchua/microk8s-actions@v0.4.2
with:
channel: "1.36-strict/stable"
addons: '["dns", "hostpath-storage"]'
- name: Install Juju
run: |
sudo snap install juju --channel 3/stable
- name: Bootstrap on LXD
if: matrix.cloud == 'lxd'
run: |
juju bootstrap lxd c \
--controller-charm-channel=${{ needs.channel.outputs.test }}
- name: Bootstrap on MicroK8s
if: matrix.cloud == 'microk8s'
run: |
sg snap_microk8s <<EOF
juju bootstrap microk8s c \
--controller-charm-channel=${{ needs.channel.outputs.test }}
EOF
- name: Check charm status
run: |
juju switch controller
juju status
start_time="$(date -u +%s)"
timeout=600
while true; do
status_json="$(juju status --format=json 2>/dev/null || echo '{}')"
app_status="$(
jq -r \
'.applications.controller["application-status"].current // "unknown"' \
<<<"${status_json}"
)"
if jq -e '
(.applications.controller.units // {})
| to_entries
| any(
.[];
.value["workload-status"].current == "error"
or .value["juju-status"].current == "error"
)
' >/dev/null <<<"${status_json}"; then
echo "Controller unit entered error state"
juju status
exit 1
fi
if [[ "${app_status}" == "active" ]] && jq -e '
(.applications.controller.units // {})
| to_entries
| length > 0
and all(
.[];
.value["workload-status"].current == "active"
and .value["juju-status"].current == "idle"
)
' >/dev/null <<<"${status_json}"; then
break
fi
echo "Waiting for controller to become ready..."
juju status
sleep 10
elapsed=$(( $(date -u +%s) - start_time ))
if [[ ${elapsed} -ge ${timeout} ]]; then
echo "Timed out waiting for controller to become ready"
juju status
exit 1
fi
done
- name: Get some info for debugging
if: failure()
run: |
set -x
set +e
juju status -m controller
juju debug-log -m controller --replay
sg snap_microk8s <<EOF
microk8s.kubectl -n controller-c get all
microk8s.kubectl -n controller-c get -o yaml pod/controller-0
EOF
# TODO: test integration with dashboard / ha-proxy