Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
55 changes: 45 additions & 10 deletions .github/workflows/linux_amd64_build.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -349,21 +349,35 @@ jobs:
if [[ "${GITHUB_REF:-}" == refs/tags/v* ]]; then
bash ../.github/scripts/assert-system-contract-build.sh .
fi
cpack
../tools/tweak-deb.sh wire-sysio_*.deb
cpack -G DEB
../tools/packaging/scripts/deb-postprocess.sh wire-sysio_*.deb

- name: Install dev package
- name: Install base package
if: ${{ steps.build.outcome == 'success' && !cancelled() }}
run: |
apt-get update
apt-get install -y ./build/wire-sysio_*.deb

- name: Upload dev package
if: ${{ steps.build.outcome == 'success' && !cancelled() }}
- name: Assemble release package set (tgz + deb + rpm, base + dev)
if: ${{ steps.build.outcome == 'success' && matrix.platform == 'ubuntu24' && !cancelled() }}
run: |
# The RPM generator needs rpmbuild; the Debian-based platform image does not ship it.
command -v rpmbuild >/dev/null || { apt-get update && apt-get install -y rpm; }
cd build
cpack -G RPM
cmake --build . --target package-tgz

- name: Upload release package set
if: ${{ steps.build.outcome == 'success' && matrix.platform == 'ubuntu24' && !cancelled() }}
uses: actions/upload-artifact@b7c566a772e6b6bfb58ed0dc250532a479d7789f # actions/upload-artifact@v6
with:
name: wire-sysio-dev-${{matrix.platform}}-amd64
path: build/wire-sysio_*.deb
name: wire-sysio-packages-amd64
if-no-files-found: error
path: |
build/wire-sysio_*.deb
build/wire-sysio-dev_*.deb
build/wire-sysio-*.rpm
build/wire-sysio-*.tar.gz

v:
name: Discover Versions
Expand Down Expand Up @@ -504,9 +518,30 @@ jobs:
echo "::error::Timed out waiting for Wire CDT package artifact for ${cdt_sha}" >&2
exit 1

verify-packages:
name: Verify packages (S1-S6)
needs: [build-test-package]
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # actions/checkout@v5

- uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # actions/[email protected]
with:
name: wire-sysio-packages-amd64
path: artifacts

- name: Run packaging verification suite
run: |
ls -la artifacts/
tools/packaging/tests/verify-scripts.sh
tools/packaging/tests/verify-tgz.sh artifacts/wire-sysio-*.tar.gz
tools/packaging/tests/verify-deb.sh artifacts/wire-sysio_*.deb artifacts/wire-sysio-dev_*.deb
# wire-sysio-[0-9]* matches the base rpm only (the dev rpm is wire-sysio-dev-*).
tools/packaging/tests/verify-rpm.sh artifacts/wire-sysio-[0-9]*.rpm artifacts/wire-sysio-dev-*.rpm

all-passing:
name: All Required Tests Passed
needs: [ build-test-package, root-node-tooling ]
needs: [ build-test-package, root-node-tooling, verify-packages ]
if: always()
runs-on: ubuntu-latest
steps:
Expand All @@ -517,8 +552,8 @@ jobs:
webhook-url: ${{ secrets.WEBHOOK_URL }}
notification-type: 1
workflow-name: "Build & Test Workflow"
job-results: "build-test-package:${{ needs.build-test-package.result }},root-node-tooling:${{ needs.root-node-tooling.result }}"
job-results: "build-test-package:${{ needs.build-test-package.result }},root-node-tooling:${{ needs.root-node-tooling.result }},verify-packages:${{ needs.verify-packages.result }}"
github-context: ${{ toJSON(github) }}

- if: needs.build-test-package.result != 'success' || needs.root-node-tooling.result != 'success'
- if: needs.build-test-package.result != 'success' || needs.root-node-tooling.result != 'success' || needs.verify-packages.result != 'success'
run: false
53 changes: 0 additions & 53 deletions .github/workflows/noop/release.yaml

This file was deleted.

15 changes: 15 additions & 0 deletions .github/workflows/opp-bundles.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,10 @@ on:

permissions:
contents: read
# Required for the publish step's OIDC role assumption (CodeArtifact cargo
# publish). PR validation never requests a token — the credentials step is
# gated to push/workflow_dispatch below.
id-token: write

jobs:
opp-bundles:
Expand Down Expand Up @@ -47,6 +51,17 @@ jobs:
cd ./libraries/opp/tools
pnpm audit --audit-level=moderate

- name: Configure AWS credentials (CodeArtifact cargo publish)
if: github.event_name == 'push' || github.event_name == 'workflow_dispatch'
uses: aws-actions/configure-aws-credentials@517a711dbcd0e402f90c77e7e2f81e849156e31d # aws-actions/[email protected]
with:
# wire-infra ArtifactManagementStack — the role trusts ONLY
# repo:Wire-Network/wire-sysio:ref:refs/heads/master via GitHub OIDC.
# generate-opp-bundles.sh --publish mints the CodeArtifact token from
# these credentials and exports CARGO_REGISTRIES_WIRE_INDEX/_TOKEN.
role-to-assume: arn:aws:iam::619322354039:role/wire-pkg-cargo-publisher
aws-region: us-east-1

- name: Generate & Publish OPP Bundles
if: github.event_name == 'push' || github.event_name == 'workflow_dispatch'
env:
Expand Down
120 changes: 120 additions & 0 deletions .github/workflows/release.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
name: "Release Actions"

on:
release:
types: [published]
# Validation path: release-published events always run the DEFAULT branch's
# workflow file, so pre-merge testing (and re-runs against an existing
# release) go through manual dispatch with the tag as input.
workflow_dispatch:
inputs:
tag:
description: "Existing release tag to verify and populate (e.g. v1.0.0-rc1)"
type: string
required: true

permissions:
contents: write
packages: write
actions: read

defaults:
run:
shell: bash

jobs:
publish-assets:
name: Verify & attach release artifacts
runs-on: ubuntu-latest
outputs:
run-id: ${{ steps.run.outputs.run-id }}
env:
GH_TOKEN: ${{ github.token }}
TAG: ${{ inputs.tag || github.ref_name }}
steps:
- uses: actions/checkout@93cb6efe18208431cddfb8368fd83d5badbf9bfd # actions/checkout@v5

- name: Resolve build run for the released commit
id: run
run: |
# The release points at a tag; the tag build (linux_amd64_build.yaml,
# push: tags v*) produced wire-sysio-packages-amd64 for exactly this
# commit. Same resolution pattern as the wire-cdt artifact lookup.
sha=$(gh api "repos/${GITHUB_REPOSITORY}/commits/${TAG}" --jq .sha)
run_id=""
for attempt in {1..30}; do
run_id=$(gh api "repos/${GITHUB_REPOSITORY}/actions/workflows/linux_amd64_build.yaml/runs?head_sha=${sha}&event=push&per_page=10" \
--jq '[.workflow_runs[] | select(.status=="completed" and .conclusion=="success")][0].id // empty')
[[ -n "$run_id" ]] && break
echo "Waiting for successful tag build of ${sha} (attempt ${attempt}/30)"
sleep 60
done
[[ -n "$run_id" ]] || { echo "::error::No successful build run found for ${sha}"; exit 1; }
echo "run-id=$run_id" >> "$GITHUB_OUTPUT"

- uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # actions/[email protected]
with:
name: wire-sysio-packages-amd64
path: dist
run-id: ${{ steps.run.outputs.run-id }}
github-token: ${{ github.token }}

- name: Guard release tag matches artifact version
run: |
tag="${GITHUB_REF_NAME#v}"
ls -la dist/
[[ -f "dist/wire-sysio_${tag}_amd64.deb" ]] \
|| { echo "::error::Release tag v${tag} does not match the artifact version (bump VERSION_* in CMakeLists.txt to match the tag before tagging)"; exit 1; }

- name: Verify packages (S1-S6)
run: |
tools/packaging/tests/verify-tgz.sh dist/wire-sysio-*.tar.gz
tools/packaging/tests/verify-deb.sh dist/wire-sysio_*.deb dist/wire-sysio-dev_*.deb
# wire-sysio-[0-9]* matches the base rpm only (the dev rpm is wire-sysio-dev-*).
tools/packaging/tests/verify-rpm.sh dist/wire-sysio-[0-9]*.rpm dist/wire-sysio-dev-*.rpm

- name: Attach artifacts to the release
run: |
sha256sum dist/* > "wire-sysio-${GITHUB_REF_NAME#v}-checksums.txt"
mv "wire-sysio-${GITHUB_REF_NAME#v}-checksums.txt" dist/
gh release upload "$GITHUB_REF_NAME" dist/* --clobber

experimental-binaries:
name: experimental-binaries (ghcr mirror)
needs: [publish-assets]
runs-on: ubuntu-latest
permissions:
contents: read
packages: write
actions: read
steps:
- uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # actions/[email protected]
with:
name: wire-sysio-packages-amd64
path: .
run-id: ${{ needs.publish-assets.outputs.run-id }}
github-token: ${{ github.token }}

- name: Create Dockerfile
run: |
cat <<DOCKEREOF > Dockerfile
FROM scratch
LABEL org.opencontainers.image.description="A collection of experimental Wire binary packages"
COPY *.deb /
DOCKEREOF

- name: Login to ghcr
uses: docker/login-action@c94ce9fb468520275223c153574b00df6fe4bcc9 # docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ github.token }}

- run: echo "REPOSITORY_OWNER_LOWER=${GITHUB_REPOSITORY_OWNER,,}" >> "${GITHUB_ENV}"

- name: Build and push wire-sysio-experimental-binaries
uses: docker/build-push-action@10e90e3645eae34f1e60eeb005ba3a3d33f178e8 # docker/build-push-action@v6
with:
push: true
tags: ghcr.io/${{ env.REPOSITORY_OWNER_LOWER }}/wire-sysio-experimental-binaries:${{ inputs.tag || github.ref_name }}
context: .
39 changes: 39 additions & 0 deletions BUILD.md
Original file line number Diff line number Diff line change
Expand Up @@ -258,3 +258,42 @@ After the script finishes, you will have a Docker image with Wire Sysio built in
Using the Docker build is particularly useful if you are on a host that is not Ubuntu 24/25 or if you want to avoid installing compilers and dependencies on your system. The Docker environment ensures a consistent, reproducible build.

---

## Packaging

From a configured Release build tree (any install prefix — packages are
prefix-independent):

cd $BUILD_DIR
cpack -G TGZ # portable tarball wire-sysio.tar.gz: top-level wire-sysio/, extract to /opt
cmake --build . --target package-tgz # same tarball, versioned artifact name
cpack -G DEB # Debian/Ubuntu package (requires dpkg); installs under /usr
cpack -G RPM # RHEL/Fedora package (requires rpmbuild); installs under /usr

The DEB asks (via debconf) whether to register the wire-sysio-nodeop systemd
service and whether to enable it; enabling also starts it immediately.
Noninteractive installs default to yes/yes (register + enable + start). The
RPM registers, enables, and starts the service on fresh install. Log rotation
is 5 x 1G via /etc/logrotate.d/wire-sysio-nodeop (a conffile — edit the
installed copy to change thresholds). Chain data (/var/lib/wire/sysio) and
logs (/var/log/wire/sysio) are never removed by package removal or purge.

Verification: `tools/packaging/tests/` contains the packaging gate scripts —
`verify-tgz.sh` (tarball layout), `verify-deb.sh` / `verify-rpm.sh` (payload,
control files, containerized install, plus a systemd-in-container runtime
stage proving the service enables, starts, and stays up),
`verify-install-manifest.sh` (install regression vs a baseline), and
`verify-scripts.sh` (static lint). The deb/rpm verifiers require docker; the
runtime stage builds a cached systemd-enabled test image on first use.

### Release flow

1. Bump `VERSION_MAJOR/MINOR/PATCH/SUFFIX` in `CMakeLists.txt` (PR to master).
2. Push tag `v<version>` — the tag build installs the Wire CDT package, builds
and asserts system contracts, assembles the full package set, and verifies
it (S1-S6, including the systemd service-start gate).
3. Publish the GitHub Release for the tag — the `Release Actions` workflow
locates the successful tag build, re-verifies the artifacts, fails fast if
the tag does not match the artifact version, attaches the packages plus a
sha256 checksums file to the release, and refreshes the
`wire-sysio-experimental-binaries` ghcr image.
20 changes: 10 additions & 10 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -150,34 +150,34 @@ add_subdirectory(contracts)
add_subdirectory(contracts/tests)

configure_file(${CMAKE_CURRENT_SOURCE_DIR}/sysio.version.in ${CMAKE_CURRENT_BINARY_DIR}/sysio.version.hpp)
install(FILES ${CMAKE_CURRENT_BINARY_DIR}/sysio.version.hpp DESTINATION ${CMAKE_INSTALL_FULL_INCLUDEDIR})
install(FILES ${CMAKE_CURRENT_BINARY_DIR}/sysio.version.hpp DESTINATION ${CMAKE_INSTALL_INCLUDEDIR} COMPONENT dev)

set(SYSIO_ROOT_DIR "${CMAKE_INSTALL_FULL_LIBDIR}")
configure_file(${CMAKE_SOURCE_DIR}/cmake/sysio-config.cmake.in ${CMAKE_BINARY_DIR}/lib/cmake/sysio/sysio-config.cmake @ONLY)
configure_file(${CMAKE_SOURCE_DIR}/cmake/SysioTester.cmake.in ${CMAKE_BINARY_DIR}/lib/cmake/sysio/SysioTester.cmake @ONLY)
configure_file(${CMAKE_SOURCE_DIR}/cmake/SysioCheckVersion.cmake ${CMAKE_BINARY_DIR}/lib/cmake/sysio/SysioCheckVersion.cmake COPYONLY)

install(FILES ${CMAKE_BINARY_DIR}/lib/cmake/sysio/sysio-config.cmake DESTINATION ${CMAKE_INSTALL_FULL_LIBDIR}/cmake/sysio)
install(FILES ${CMAKE_BINARY_DIR}/lib/cmake/sysio/SysioTester.cmake DESTINATION ${CMAKE_INSTALL_FULL_LIBDIR}/cmake/sysio)
install(FILES ${CMAKE_BINARY_DIR}/lib/cmake/sysio/SysioCheckVersion.cmake DESTINATION ${CMAKE_INSTALL_FULL_LIBDIR}/cmake/sysio)
install(FILES ${CMAKE_BINARY_DIR}/lib/cmake/sysio/sysio-config.cmake DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/sysio COMPONENT dev)
install(FILES ${CMAKE_BINARY_DIR}/lib/cmake/sysio/SysioTester.cmake DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/sysio COMPONENT dev)
install(FILES ${CMAKE_BINARY_DIR}/lib/cmake/sysio/SysioCheckVersion.cmake DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/sysio COMPONENT dev)

include(cmake/licenses.cmake)

# Merge compile_commands.json from ExternalProject contract builds with the root
# project's database so that IDEs (CLion, clangd) can navigate contract sources.
add_merged_compile_commands_target()

install(DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}/licenses/sysio" DESTINATION "${CMAKE_INSTALL_FULL_DATAROOTDIR}/licenses/")
install(DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}/licenses/sysio" DESTINATION "${CMAKE_INSTALL_DATAROOTDIR}/licenses/" COMPONENT base)

install(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/libraries/testing/contracts DESTINATION ${CMAKE_INSTALL_FULL_DATAROOTDIR}/sysio_testing/libraries/testing COMPONENT dev EXCLUDE_FROM_ALL
install(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/libraries/testing/contracts DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/sysio_testing/libraries/testing OPTIONAL COMPONENT dev EXCLUDE_FROM_ALL
PATTERN "CMakeFiles" EXCLUDE
PATTERN "*.cmake" EXCLUDE
PATTERN "Makefile" EXCLUDE)
install(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/unittests/system-test-contracts DESTINATION ${CMAKE_INSTALL_FULL_DATAROOTDIR}/sysio_testing/unittests COMPONENT dev EXCLUDE_FROM_ALL
install(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/unittests/system-test-contracts DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/sysio_testing/unittests OPTIONAL COMPONENT dev EXCLUDE_FROM_ALL
PATTERN "CMakeFiles" EXCLUDE
PATTERN "*.cmake" EXCLUDE
PATTERN "Makefile" EXCLUDE)
install(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/tests/TestHarness DESTINATION ${CMAKE_INSTALL_FULL_DATAROOTDIR}/sysio_testing/tests COMPONENT dev EXCLUDE_FROM_ALL
install(DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/tests/TestHarness DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/sysio_testing/tests OPTIONAL COMPONENT dev EXCLUDE_FROM_ALL
FILES_MATCHING
PATTERN "*.py"
PATTERN "*.json"
Expand All @@ -196,14 +196,14 @@ if(CMAKE_VERSION VERSION_GREATER_EQUAL 3.21)
COMMAND ${CMAKE_COMMAND} -E make_directory share/sysio_testing
COMMAND ${CMAKE_COMMAND} -E create_symlink ../../bin share/sysio_testing/bin)

install(FILES ${CMAKE_CURRENT_BINARY_DIR}/lib/python3/dist-packages/TestHarness DESTINATION ${CMAKE_INSTALL_FULL_LIBDIR}/python3/dist-packages COMPONENT dev EXCLUDE_FROM_ALL)
install(FILES ${CMAKE_CURRENT_BINARY_DIR}/lib/python3/dist-packages/TestHarness DESTINATION ${CMAKE_INSTALL_LIBDIR}/python3/dist-packages COMPONENT dev EXCLUDE_FROM_ALL)
install(PROGRAMS
${CMAKE_CURRENT_BINARY_DIR}/bin/clio
${CMAKE_CURRENT_BINARY_DIR}/bin/kiod
${CMAKE_CURRENT_BINARY_DIR}/bin/nodeop
${CMAKE_CURRENT_BINARY_DIR}/bin/sys-util
${CMAKE_CURRENT_BINARY_DIR}/bin/trace_api_util
DESTINATION ${CMAKE_INSTALL_FULL_DATAROOTDIR}/sysio_testing/bin
DESTINATION ${CMAKE_INSTALL_DATAROOTDIR}/sysio_testing/bin
COMPONENT dev
EXCLUDE_FROM_ALL)
else()
Expand Down
Loading
Loading