chore: prepare v1.1.0 release #70
Workflow file for this run
This file contains hidden or 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 | |
| "on": | |
| push: | |
| tags: | |
| - "v*" | |
| release: | |
| types: | |
| - published | |
| workflow_dispatch: | |
| inputs: | |
| version: | |
| description: "Release version without the leading v" | |
| required: true | |
| type: string | |
| permissions: | |
| contents: write | |
| env: | |
| FORCE_JAVASCRIPT_ACTIONS_TO_NODE24: "true" | |
| concurrency: | |
| group: release-${{ github.ref }} | |
| cancel-in-progress: false | |
| jobs: | |
| metadata: | |
| name: Resolve Release Metadata | |
| runs-on: ubuntu-latest | |
| outputs: | |
| version: ${{ steps.meta.outputs.version }} | |
| raw_tag: ${{ steps.meta.outputs.raw_tag }} | |
| tag_name: ${{ steps.meta.outputs.tag_name }} | |
| archive_prefix: ${{ steps.meta.outputs.archive_prefix }} | |
| steps: | |
| - name: Checkout repository | |
| uses: actions/checkout@v6 | |
| - name: Resolve version | |
| id: meta | |
| run: | | |
| if [[ "${GITHUB_EVENT_NAME}" == "workflow_dispatch" ]]; then | |
| VERSION="${{ inputs.version }}" | |
| VERSION="${VERSION#v}" | |
| RAW_TAG="v${VERSION}" | |
| else | |
| RAW_TAG="${{ github.event.release.tag_name }}" | |
| if [[ -z "${RAW_TAG}" ]]; then | |
| RAW_TAG="${GITHUB_REF_NAME}" | |
| fi | |
| VERSION="${RAW_TAG#v}" | |
| fi | |
| if [[ -z "${VERSION}" ]]; then | |
| echo "Release version could not be determined." >&2 | |
| exit 1 | |
| fi | |
| PROJECT_VERSION="$(sed -n 's/^[[:space:]]*VERSION[[:space:]]\([0-9.][0-9.]*\)$/\1/p' CMakeLists.txt | head -n1)" | |
| SPEC_DEFAULT_VERSION="$(sed -n 's/^%global upstream_version %{!?upstream_version:\([0-9.][0-9.]*\)}%{?upstream_version}$/\1/p' packaging/rpm/ro-control.spec | head -n1)" | |
| echo "Resolved release metadata:" | |
| echo " event=${GITHUB_EVENT_NAME}" | |
| echo " ref_name=${GITHUB_REF_NAME}" | |
| echo " version=${VERSION}" | |
| echo " project_version=${PROJECT_VERSION}" | |
| echo " spec_default_version=${SPEC_DEFAULT_VERSION}" | |
| if [[ "${VERSION}" != "${PROJECT_VERSION}" ]]; then | |
| echo "Tag/workflow version (${VERSION}) does not match CMake project version (${PROJECT_VERSION})." >&2 | |
| exit 1 | |
| fi | |
| if [[ "${VERSION}" != "${SPEC_DEFAULT_VERSION}" ]]; then | |
| echo "Tag/workflow version (${VERSION}) does not match RPM spec default version (${SPEC_DEFAULT_VERSION})." >&2 | |
| exit 1 | |
| fi | |
| echo "raw_tag=${RAW_TAG}" >> "${GITHUB_OUTPUT}" | |
| echo "version=${VERSION}" >> "${GITHUB_OUTPUT}" | |
| echo "tag_name=${RAW_TAG}" >> "${GITHUB_OUTPUT}" | |
| echo "archive_prefix=ro-control-${VERSION}" >> "${GITHUB_OUTPUT}" | |
| source-archives: | |
| name: Build Source Archives | |
| runs-on: ubuntu-latest | |
| needs: metadata | |
| steps: | |
| - name: Checkout repository | |
| uses: actions/checkout@v6 | |
| - name: Create source archives | |
| env: | |
| ARCHIVE_PREFIX: ${{ needs.metadata.outputs.archive_prefix }} | |
| run: | | |
| git archive --format=tar.gz --prefix="${ARCHIVE_PREFIX}/" --output="${ARCHIVE_PREFIX}.tar.gz" "${GITHUB_SHA}" | |
| - name: Upload source archives | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: ro-control-source-${{ needs.metadata.outputs.version }} | |
| path: | | |
| ${{ needs.metadata.outputs.archive_prefix }}.tar.gz | |
| rpm: | |
| name: Build Fedora RPM (${{ matrix.arch }}) | |
| needs: [metadata, source-archives] | |
| runs-on: ${{ matrix.runs_on }} | |
| timeout-minutes: 60 | |
| strategy: | |
| fail-fast: false | |
| matrix: | |
| include: | |
| - arch: x86_64 | |
| runs_on: ubuntu-24.04 | |
| - arch: aarch64 | |
| runs_on: ubuntu-24.04-arm | |
| container: | |
| image: fedora:43 | |
| steps: | |
| - name: Checkout repository | |
| uses: actions/checkout@v6 | |
| - name: Download source archives | |
| uses: actions/download-artifact@v4 | |
| with: | |
| name: ro-control-source-${{ needs.metadata.outputs.version }} | |
| path: dist | |
| - name: Install packaging dependencies | |
| run: | | |
| dnf install -y \ | |
| git \ | |
| rpm-build \ | |
| cmake \ | |
| extra-cmake-modules \ | |
| gcc-c++ \ | |
| ninja-build \ | |
| qt6-qtbase-devel \ | |
| qt6-qtdeclarative-devel \ | |
| qt6-qttools-devel \ | |
| qt6-qtwayland-devel \ | |
| kf6-qqc2-desktop-style \ | |
| polkit-devel \ | |
| desktop-file-utils \ | |
| appstream | |
| - name: Build RPM artifacts | |
| env: | |
| VERSION: ${{ needs.metadata.outputs.version }} | |
| ARCHIVE_PREFIX: ${{ needs.metadata.outputs.archive_prefix }} | |
| RPM_ARCH: ${{ matrix.arch }} | |
| run: | | |
| mkdir -p ~/rpmbuild/SOURCES ~/rpmbuild/SPECS dist/rpm | |
| cp "dist/${ARCHIVE_PREFIX}.tar.gz" "${HOME}/rpmbuild/SOURCES/" | |
| cp packaging/rpm/ro-control.spec "${HOME}/rpmbuild/SPECS/ro-control.spec" | |
| FEDORA_VERSION=43 | |
| MAIN_RPM_PATTERN="ro-control-[0-9]*.${RPM_ARCH}.rpm" | |
| COMMON_RPM_PATTERN="ro-control-common-[0-9]*.noarch.rpm" | |
| rpmbuild -ba "${HOME}/rpmbuild/SPECS/ro-control.spec" \ | |
| --define "_topdir ${HOME}/rpmbuild" \ | |
| --define "upstream_version ${VERSION}" \ | |
| --define "dist .fc${FEDORA_VERSION}" | |
| MAIN_RPM_FILE="$(find ~/rpmbuild/RPMS -maxdepth 2 -type f -name "${MAIN_RPM_PATTERN}" | head -n1)" | |
| if [[ -z "${MAIN_RPM_FILE}" ]]; then | |
| echo "Failed to find built ${RPM_ARCH} main RPM." >&2 | |
| exit 1 | |
| fi | |
| cp "${MAIN_RPM_FILE}" "dist/rpm/ro-control-${RPM_ARCH}.rpm" | |
| COMMON_RPM_FILE="$(find ~/rpmbuild/RPMS -maxdepth 2 -type f -name "${COMMON_RPM_PATTERN}" | head -n1)" | |
| if [[ -n "${COMMON_RPM_FILE}" ]]; then | |
| cp "${COMMON_RPM_FILE}" "dist/rpm/ro-control-common-noarch.rpm" | |
| fi | |
| if [[ "${RPM_ARCH}" == "x86_64" ]]; then | |
| cp ~/rpmbuild/SRPMS/*.src.rpm dist/rpm/ | |
| fi | |
| - name: Verify package metadata | |
| env: | |
| VERSION: ${{ needs.metadata.outputs.version }} | |
| RPM_ARCH: ${{ matrix.arch }} | |
| run: | | |
| RPM_FILE="dist/rpm/ro-control-${RPM_ARCH}.rpm" | |
| if [[ ! -f "${RPM_FILE}" ]]; then | |
| echo "Failed to locate built ${RPM_ARCH} RPM." >&2 | |
| exit 1 | |
| fi | |
| rpm -qp --info "${RPM_FILE}" > "dist/rpm/ro-control-${VERSION}-${RPM_ARCH}-info.txt" | |
| rpm -qp --requires "${RPM_FILE}" | sort > "dist/rpm/ro-control-${VERSION}-${RPM_ARCH}-requires.txt" | |
| rpm -qlp "${RPM_FILE}" | sort > "dist/rpm/ro-control-${VERSION}-${RPM_ARCH}-files.txt" | |
| if grep -E 'Qt_6\.10|PRIVATE_API' "dist/rpm/ro-control-${VERSION}-${RPM_ARCH}-requires.txt"; then | |
| echo "Forbidden Qt private ABI dependency detected." >&2 | |
| exit 1 | |
| fi | |
| grep -Fx '/usr/bin/ro-control' "dist/rpm/ro-control-${VERSION}-${RPM_ARCH}-files.txt" | |
| - name: Verify main/common package split | |
| env: | |
| RPM_ARCH: ${{ matrix.arch }} | |
| run: | | |
| MAIN_RPM_FILE="dist/rpm/ro-control-${RPM_ARCH}.rpm" | |
| COMMON_RPM_FILE="dist/rpm/ro-control-common-noarch.rpm" | |
| if [[ ! -f "${MAIN_RPM_FILE}" ]]; then | |
| echo "Main ro-control RPM is missing." >&2 | |
| exit 1 | |
| fi | |
| if [[ ! -f "${COMMON_RPM_FILE}" ]]; then | |
| echo "ro-control-common noarch RPM is missing." >&2 | |
| exit 1 | |
| fi | |
| if rpm -qpl "${COMMON_RPM_FILE}" | grep -Fx '/usr/bin/ro-control'; then | |
| echo "/usr/bin/ro-control must not be shipped by ro-control-common." >&2 | |
| exit 1 | |
| fi | |
| - name: Validate desktop metadata | |
| run: | | |
| desktop-file-validate data/icons/io.github.projectroasd.rocontrol.desktop | |
| appstreamcli validate --no-net data/icons/io.github.projectroasd.rocontrol.metainfo.xml | |
| - name: Install and smoke-test RPM | |
| if: matrix.arch == 'x86_64' | |
| env: | |
| VERSION: ${{ needs.metadata.outputs.version }} | |
| RPM_ARCH: ${{ matrix.arch }} | |
| run: | | |
| RPM_FILE="dist/rpm/ro-control-${RPM_ARCH}.rpm" | |
| NOARCH_FILE="dist/rpm/ro-control-common-noarch.rpm" | |
| if [[ ! -f "${RPM_FILE}" ]]; then | |
| echo "Failed to locate built ${RPM_ARCH} RPM for smoke testing." >&2 | |
| exit 1 | |
| fi | |
| if [[ ! -f "${NOARCH_FILE}" ]]; then | |
| echo "Failed to locate ro-control-common noarch RPM for smoke testing." >&2 | |
| exit 1 | |
| fi | |
| dnf install -y --nogpgcheck "${RPM_FILE}" "${NOARCH_FILE}" | |
| INSTALLED_VERSION="$(ro-control --version | tr -d '\n')" | |
| if [[ "${INSTALLED_VERSION}" != "${VERSION}" ]]; then | |
| echo "Installed CLI version (${INSTALLED_VERSION}) does not match release version (${VERSION})." >&2 | |
| exit 1 | |
| fi | |
| rpm -q ro-control | |
| command -v ro-control | |
| rpm -q --whatprovides /usr/bin/ro-control | grep -Fx 'ro-control' | |
| ldd -r /usr/bin/ro-control | |
| ro-control --help > /dev/null | |
| - name: Generate per-arch checksums | |
| env: | |
| VERSION: ${{ needs.metadata.outputs.version }} | |
| RPM_ARCH: ${{ matrix.arch }} | |
| run: | | |
| ( | |
| cd dist/rpm | |
| sha256sum * > "ro-control-${VERSION}-${RPM_ARCH}-SHA256SUMS.txt" | |
| ) | |
| - name: Upload RPM artifacts | |
| uses: actions/upload-artifact@v4 | |
| with: | |
| name: ro-control-rpm-${{ matrix.arch }}-${{ needs.metadata.outputs.version }} | |
| path: | | |
| dist/rpm/* | |
| release: | |
| name: Create GitHub Release | |
| runs-on: ubuntu-latest | |
| needs: [metadata, source-archives, rpm] | |
| steps: | |
| - name: Download all release artifacts | |
| uses: actions/download-artifact@v4 | |
| with: | |
| pattern: ro-control-* | |
| path: dist | |
| merge-multiple: true | |
| - name: Publish release | |
| uses: softprops/action-gh-release@v2 | |
| with: | |
| tag_name: ${{ needs.metadata.outputs.tag_name }} | |
| target_commitish: ${{ github.sha }} | |
| generate_release_notes: true | |
| files: | | |
| dist/*.x86_64.rpm | |
| dist/*.aarch64.rpm | |
| dist/*.noarch.rpm | |
| dist/*.src.rpm | |
| dist/*SHA256SUMS.txt | |
| dist/*-requires.txt | |
| dist/*-info.txt | |
| dist/*-files.txt |