Prod Release for pantos-io/servicenode - 1.7.1 #3
Workflow file for this run
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
name: Release Workflow | |
run-name: ${{ (github.event.release.prerelease && 'Beta') || 'Prod'}} Release for ${{ github.repository }} - ${{ github.event.release.tag_name }} | |
on: | |
release: | |
# Triggered on Pre-Releases and Releases | |
types: [released, prereleased] | |
# Only allow one release at the time | |
concurrency: | |
group: deploy-${{ github.repository }}-release-${{ github.event.release.prerelease }} | |
jobs: | |
define-environment: | |
name: Define Environment | |
runs-on: ubuntu-latest | |
if: (!github.event.release.draft) | |
outputs: | |
deployment_environment: ${{ steps.get-environment.outputs.deployment_environment }} | |
deployment_longname: ${{ steps.get-environment.outputs.deployment_longname }} | |
deployment_version: ${{ steps.get-environment.outputs.deployment_version }} | |
deployment_pypi_environment: ${{ steps.get-environment.outputs.deployment_pypi_environment }} | |
deployment_url: ${{ steps.get-environment.outputs.deployment_url }} | |
steps: | |
- uses: step-security/harden-runner@v2 | |
with: | |
disable-sudo: true | |
egress-policy: audit | |
- name: Configure Environment | |
id: get-environment | |
run: | | |
wget -O /usr/local/bin/semver https://raw.githubusercontent.com/fsaintjacques/semver-tool/master/src/semver | |
chmod +x /usr/local/bin/semver | |
if [[ $(semver validate ${{ github.event.release.tag_name }}) == "invalid" ]]; then | |
echo "::error title=Invalid Release::Release must be tagged with a valid SemVer version" | |
exit 1 | |
fi | |
TAG=${{ github.event.release.tag_name }} | |
echo "deployment_version=${TAG#v}" >> $GITHUB_OUTPUT | |
if [[ "${{ github.event.release.prerelease }}" == "true" ]]; then | |
echo "::notice title=Deployment Environment::Deployment for Test" | |
echo "deployment_environment=-rc" >> $GITHUB_OUTPUT | |
echo "deployment_longname=Beta" >> $GITHUB_OUTPUT | |
echo "deployment_pypi_environment=test-pypi" >> $GITHUB_OUTPUT | |
echo "deployment_url=https://test.pypi.org/p/pantos-service-node" >> $GITHUB_OUTPUT | |
else | |
echo "::notice title=Deployment Environment::Deployment for Prod" | |
echo "deployment_environment=" >> $GITHUB_OUTPUT | |
echo "deployment_longname=Prod" >> $GITHUB_OUTPUT | |
echo "deployment_pypi_environment=pypi" >> $GITHUB_OUTPUT | |
echo "deployment_url=https://pypi.org/p/pantos-service-node" >> $GITHUB_OUTPUT | |
fi | |
publish-docker: | |
name: Publish docker image for ${{ needs.define-environment.outputs.deployment_longname }} | |
needs: [define-environment, build] | |
environment: | |
name: dockerhub | |
url: ${{ steps.set-output-url.outputs.deployment_dockerhub_url }} | |
runs-on: ubuntu-latest | |
permissions: | |
id-token: write | |
steps: | |
- uses: step-security/harden-runner@v2 | |
with: | |
disable-sudo: true | |
egress-policy: audit | |
- uses: actions/checkout@v4 | |
- name: Set up QEMU | |
uses: docker/setup-qemu-action@v3 | |
- name: Set up Docker Buildx | |
uses: docker/setup-buildx-action@v3 | |
id: buildx | |
- name: Cache Docker layers | |
uses: actions/cache@v3 | |
with: | |
path: /tmp/.buildx-cache | |
key: ${{ runner.os }}-buildx-v1.0-service-node-${{ github.sha }} | |
restore-keys: | | |
${{ runner.os }}-buildx-v1.0-service-node- | |
- name: Login to Docker Hub | |
uses: docker/login-action@v3 | |
with: | |
username: ${{ secrets.DOCKERHUB_USERNAME }} | |
password: ${{ secrets.DOCKERHUB_TOKEN }} | |
- uses: actions/download-artifact@v4 | |
with: | |
name: build | |
path: dist | |
- name: Rename built artifacts | |
run: | | |
for file in dist/*.deb; do | |
mv "$file" "${file%.deb}-signed.deb" | |
done | |
- name: Build and push the images | |
run: | | |
docker buildx bake \ | |
--set "*.cache-from=type=local,src=/tmp/.buildx-cache" \ | |
--set "*.cache-to=type=local,dest=/tmp/.buildx-cache-new" \ | |
--set "*.platform=linux/amd64,linux/arm64" \ | |
--builder ${{ steps.buildx.outputs.name }} \ | |
--push \ | |
-f docker-compose.yml \ | |
app worker | |
env: | |
PANTOS_SERVICE_NODE_VERSION: ${{ needs.define-environment.outputs.deployment_version }} | |
PANTOS_SERVICE_NODE_REVISION: ${{ github.run_attempt }} | |
DOCKER_TAG: ${{ github.event.release.tag_name }}${{ needs.define-environment.outputs.deployment_environment }} | |
- name: Set output url | |
id: set-output-url | |
run: | | |
echo "deployment_dockerhub_url=https://hub.docker.com/r/pantosio/service-node/tags?name=${{ github.event.release.tag_name }}${{ needs.define-environment.outputs.deployment_environment }}" >> $GITHUB_OUTPUT | |
- uses: sigstore/cosign-installer@main | |
- name: Sign the images | |
run: | | |
for app in $(docker buildx bake -f docker-compose.yml --print --progress "plain" | jq -r '.target[].tags | add'); do | |
for image in $(docker buildx imagetools inspect $app --raw | jq -r '.manifests[].digest'); do | |
echo "Signing $image from $app"; | |
cosign sign --yes --verbose "${app%%:*}@$image"; | |
done; | |
done; | |
env: | |
DOCKER_TAG: ${{ github.event.release.tag_name }}${{ needs.define-environment.outputs.deployment_environment }} | |
COSIGN_EXPERIMENTAL: "true" | |
- name: Move cache | |
run: | | |
rm -rf /tmp/.buildx-cache | |
mv /tmp/.buildx-cache-new /tmp/.buildx-cache | |
build: | |
name: Build and attach .deb and .whl package | |
needs: [define-environment] | |
uses: ./.github/workflows/build.yml | |
secrets: 'inherit' | |
with: | |
# We need to use a semver that doesn't start with a v as debian will remove it anyways | |
version: ${{ needs.define-environment.outputs.deployment_version }} | |
revision: "${{ github.event.release.prerelease && 'rc' || '' }}${{ github.run_attempt }}" | |
environment: debian-release | |
add-assets: | |
name: Add Assets to the ${{ github.event.release.tag_name }} Release | |
needs: build | |
runs-on: ubuntu-latest | |
permissions: | |
contents: write | |
id-token: write | |
steps: | |
- uses: step-security/harden-runner@v2 | |
with: | |
disable-sudo: true | |
egress-policy: audit | |
- uses: actions/download-artifact@v4 | |
with: | |
name: build | |
path: dist | |
# We need to upload some artifacts, any, so that the download action works | |
- name: Upload release assets | |
uses: svenstaro/upload-release-action@v2 | |
with: | |
file: "./dist/*.deb" | |
file_glob: true | |
overwrite: true | |
repo_token: ${{ secrets.GITHUB_TOKEN }} | |
tag: ${{ github.event.release.tag_name }} | |
# We need to upload some artifacts, any, so that the download action works | |
- uses: robinraju/[email protected] | |
with: | |
tag: ${{ github.event.release.tag_name }} | |
tarBall: true | |
zipBall: true | |
fileName: '*' | |
out-file-path: release | |
preRelease: ${{ github.event.release.prerelease }} | |
token: ${{ secrets.GH_TOKEN }} | |
- name: List directory | |
run: | | |
cp dist/*.whl release/ | |
# Do not sign deb artifacts | |
rm release/*.deb | |
- uses: sigstore/[email protected] | |
with: | |
inputs: release/* | |
- uses: actions/upload-artifact@v4 | |
with: | |
name: signed-build | |
path: release/*.whl | |
- name: Merge with previous files | |
run: | | |
cp dist/*.deb release/ | |
ls -lha release | |
- name: Upload release assets | |
uses: svenstaro/upload-release-action@v2 | |
with: | |
file: "./release/*" | |
file_glob: true | |
overwrite: true | |
repo_token: ${{ secrets.GITHUB_TOKEN }} | |
tag: ${{ github.event.release.tag_name }} | |
publish-pypi: | |
name: Publish to ${{ needs.define-environment.outputs.deployment_pypi_environment }} | |
needs: [define-environment, add-assets] | |
runs-on: ubuntu-latest | |
environment: | |
name: ${{ needs.define-environment.outputs.deployment_pypi_environment }} | |
url: ${{ needs.define-environment.outputs.deployment_url }} | |
permissions: | |
id-token: write # IMPORTANT: this permission is mandatory for trusted publishing | |
steps: | |
- uses: step-security/harden-runner@v2 | |
with: | |
disable-sudo: true | |
egress-policy: audit | |
- uses: actions/checkout@v4 | |
- name: Set up Python | |
uses: actions/setup-python@v5 | |
with: | |
python-version: 3.8 | |
cache: 'pip' | |
- uses: actions/download-artifact@v4 | |
with: | |
name: signed-build | |
path: dist | |
- name: List directory | |
run: | | |
ls -lha . | |
ls -lha dist | |
- name: Publish package distributions to ${{ needs.define-environment.outputs.deployment_pypi_environment }} | |
uses: pypa/gh-action-pypi-publish@release/v1 | |
with: | |
repository-url: ${{ needs.define-environment.outputs.deployment_pypi_environment == 'test-pypi' && 'https://test.pypi.org/legacy/' || 'https://upload.pypi.org/legacy/' }} | |
publish-ppa: | |
name: Publishes assets to the PPA as ${{ github.event.release.tag_name }} | |
environment: | |
name: debian-release | |
url: ${{ steps.create-release.outputs.deployment_ppa_url }} | |
permissions: | |
contents: write | |
pages: write | |
needs: [add-assets] | |
# Disable the job for the moment being | |
runs-on: ubuntu-latest | |
steps: | |
- uses: step-security/harden-runner@v2 | |
with: | |
disable-sudo: true | |
egress-policy: audit | |
- uses: actions/download-artifact@v4 | |
with: | |
name: build | |
path: dist | |
- name: List directory | |
run: | | |
ls -lha . | |
ls -lha dist | |
mkdir -p release | |
mv dist/*.deb release/ | |
- name: Add index file | |
run: | | |
# Source: https://stackoverflow.com/questions/39048654/how-to-enable-directory-indexing-on-github-pages | |
cat > index.html<< 'EOF' | |
<!DOCTYPE html> | |
<html> | |
<body> | |
<script> | |
(async () => { | |
const response = await fetch('https://api.github.com/repos/pantos-io/servicenode/contents?ref=ppa'); | |
const data = await response.json(); | |
let htmlString = '<ul>'; | |
for (let file of data) { | |
htmlString += `<li><a href="${file.path}">${file.name}</a></li>`; | |
} | |
htmlString += '</ul>'; | |
document.getElementsByTagName('body')[0].innerHTML = htmlString; | |
})() | |
</script> | |
<body> | |
</html> | |
EOF | |
working-directory: release | |
- name: Import GPG key | |
uses: crazy-max/ghaction-import-gpg@v6 | |
with: | |
gpg_private_key: ${{ secrets.GPG_PRIVATE_KEY }} | |
passphrase: ${{ secrets.GPG_PASSPHRASE }} | |
- name: Prepare PPA | |
run: | | |
gpg --armor --export > ./KEY.gpg | |
dpkg-scanpackages --multiversion . > Packages | |
gzip -k -f Packages | |
working-directory: release | |
- name: Create Release files | |
id: create-release | |
run: | | |
apt-ftparchive release . > Release | |
gpg -abs -o - Release > Release.gpg | |
gpg --clearsign -o - Release > InRelease | |
url="$(gh api "repos/pantos-io/servicenode/pages" --jq '.html_url')" | |
echo "Using URL: $url" | |
echo "deployment_ppa_url=$url" >> $GITHUB_OUTPUT | |
echo "deb [signed-by=/etc/apt/trusted.gpg.d/servicenode.gpg] $url ./" > pantos-servicenode.list | |
working-directory: release | |
env: | |
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} | |
- name: Publish to GH Pages | |
uses: peaceiris/actions-gh-pages@v3 | |
with: | |
github_token: ${{ secrets.GITHUB_TOKEN }} | |
publish_dir: release | |
publish_branch: ppa | |
full_commit_message: "Publishing ${{ github.event.release.tag_name }} to the PPA" |