Files
elizaos--eliza/.github/workflows/elizaos-os-full-release.yml
wehub-resource-sync 426e9eeabd
Benchmark Bridge Tests / benchmark (bunx @biomejs/biome check packages/lifeops-bench/src, benchmark-lint) (push) Waiting to run
Benchmark Bridge Tests / benchmark (bunx vitest run --config packages/lifeops-bench/vitest.config.ts --root packages/lifeops-bench --passWithNoTests, benchmark-tests) (push) Waiting to run
Build Agent Image / build-and-push (push) Waiting to run
Chat shell gestures / Chat shell gesture + parity e2e (push) Waiting to run
ci / test (push) Waiting to run
ci / lint-and-format (push) Waiting to run
ci / build (push) Waiting to run
ci / dev-startup (push) Waiting to run
Cloud Gateway Discord / Test (push) Waiting to run
Cloud Gateway Webhook / Test (push) Waiting to run
Cloud Tests / lint-and-types (push) Waiting to run
Cloud Tests / unit-tests (push) Waiting to run
Cloud Tests / integration-tests (push) Waiting to run
Cloud Tests / e2e-tests (push) Blocked by required conditions
CodeQL Advanced / Analyze (javascript-typescript) (push) Waiting to run
Deploy Apps Worker (Product 2) / Determine environment (push) Waiting to run
Deploy Apps Worker (Product 2) / Deploy apps worker to apps-control host (${{ needs.determine-env.outputs.environment }}) (push) Blocked by required conditions
Deploy Eliza Provisioning Worker / Determine environment (push) Waiting to run
Deploy Eliza Provisioning Worker / Deploy worker to Hetzner host (${{ needs.determine-env.outputs.environment }} @ ${{ needs.determine-env.outputs.deployment_sha }}) (push) Blocked by required conditions
Dev Smoke / Classify changed paths (push) Waiting to run
Dev Smoke / bun run dev onboarding chat (push) Blocked by required conditions
Dev Smoke / Vite HMR dependency-level smoke (push) Blocked by required conditions
Electrobun Submodule Guard / electrobun gitlink is fetchable (push) Waiting to run
gitleaks / gitleaks (push) Waiting to run
Markdown Links / Relative Markdown Links (push) Waiting to run
Publish @elizaos/example-code / check_npm (push) Waiting to run
Publish @elizaos/example-code / publish_npm (push) Blocked by required conditions
Publish @elizaos/plugin-elizacloud / verify_version (push) Waiting to run
Publish @elizaos/plugin-elizacloud / publish_npm (push) Blocked by required conditions
Quality (Extended) / Homepage Build (PR smoke) (push) Waiting to run
Quality (Extended) / Comment-only diff guard (push) Waiting to run
Quality (Extended) / Format + Type Safety Ratchet (push) Waiting to run
Quality (Extended) / Develop Gate (secret scan + UI determinism) (push) Waiting to run
Quality (Extended) / Develop Gate (lint) (push) Waiting to run
Sandbox Live Smoke / Sandbox live smoke (push) Waiting to run
Snap Build & Test / Build Snap (amd64) (push) Waiting to run
Snap Build & Test / Build Snap (arm64) (push) Waiting to run
supply-chain / sbom (push) Waiting to run
supply-chain / vulnerability-scan (push) Waiting to run
Build, Push & Deploy to Phala Cloud / build-and-push (push) Waiting to run
Test Packaging / Validate Packaging Configs (push) Waiting to run
Test Packaging / PyPI on Python ${{ matrix.python }} (push) Waiting to run
Test Packaging / Pack & Test JS Tarballs (push) Waiting to run
Test Packaging / elizaos CLI global-install smoke (node + bun) (push) Waiting to run
UI Fixture E2E / ui-fixture-e2e (push) Waiting to run
UI Fixture E2E / fixture-e2e (push) Waiting to run
UI Story Gate / story-gate (push) Waiting to run
vault-ci / test (macos-latest) (push) Waiting to run
vault-ci / test (ubuntu-latest) (push) Waiting to run
vault-ci / test (windows-latest) (push) Waiting to run
vault-ci / app-core wiring tests (push) Waiting to run
verify-patches / verify patches/CHECKSUMS.sha256 (push) Waiting to run
Voice Benchmark Smoke / voice-emotion fixture smoke (push) Waiting to run
Voice Benchmark Smoke / voiceagentbench fixture smoke (push) Waiting to run
Voice Benchmark Smoke / voicebench-quality unit smoke (push) Waiting to run
Voice Benchmark Smoke / voicebench TypeScript unit (no audio) (push) Waiting to run
Voice Benchmark Smoke / voice bench smoke summary (push) Blocked by required conditions
Windows CI / windows ([bun run --cwd packages/app-core test bun run --cwd packages/elizaos test bun run --cwd packages/cloud/shared test], app-and-cli) (push) Waiting to run
Windows CI / windows ([bun run --cwd packages/scenario-runner test bun run --cwd packages/vault test bun run --cwd packages/security test bun run --cwd plugins/plugin-coding-tools test], framework-packages) (push) Waiting to run
Windows CI / windows ([bun run --cwd plugins/plugin-elizacloud test bun run --cwd plugins/plugin-discord test bun run --cwd plugins/plugin-anthropic test bun run --cwd plugins/plugin-openai test bun run --cwd plugins/plugin-app-control test bun run --cwd plugins/pl… (push) Waiting to run
Windows CI / windows ([node packages/scripts/run-turbo.mjs run build --filter=@elizaos/core --filter=@elizaos/shared --filter=@elizaos/agent --concurrency=4 node packages/scripts/run-bash-linux-only.mjs scripts/verify-riscv64-buildpaths.sh node packages/scripts/run… (push) Waiting to run
Windows CI / windows ([node packages/scripts/run-turbo.mjs run typecheck --filter=@elizaos/core --filter=@elizaos/shared --filter=@elizaos/cloud-shared --concurrency=4 bun run --cwd packages/core test bun run --cwd packages/shared test], core-runtime, 75) (push) Waiting to run
Test Packaging / Build & Test PyPI Package (push) Waiting to run
Voice Workbench / headless workbench (mocked backends) (push) Has been cancelled
Voice Workbench / real acoustic lane (nightly, provisioned only) (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 12:43:05 +08:00

291 lines
13 KiB
YAML

name: elizaOS Full OS Release
on:
release:
types: [created]
workflow_dispatch:
inputs:
publish:
description: Upload artifacts to release
type: boolean
default: false
# Default to least privilege. Override per-job where needed.
permissions:
contents: read
jobs:
# Compute the bare semver version string (no leading 'v') from the ref name.
# On a 'release' event github.ref_name is the tag (e.g. v2.0.1); we strip
# the prefix here so downstream jobs get a clean version like '2.0.1'.
prepare:
runs-on: ${{ fromJSON(vars.HETZNER_FLEET_ONLINE == 'false' && '["ubuntu-24.04"]' || '["self-hosted","hetzner-robot"]') }}
outputs:
version: ${{ steps.parse.outputs.version }}
tag: ${{ steps.parse.outputs.tag }}
steps:
- name: Parse version from ref
id: parse
run: |
TAG="${{ github.ref_name }}"
VERSION="${TAG#v}"
echo "tag=$TAG" >> "$GITHUB_OUTPUT"
echo "version=$VERSION" >> "$GITHUB_OUTPUT"
echo "Resolved: tag=$TAG version=$VERSION"
trigger-linux-iso:
uses: ./.github/workflows/build-linux-iso.yml
with:
channel: stable
publish: ${{ github.event_name == 'release' || inputs.publish == true }}
secrets: inherit
trigger-debian-package:
uses: ./.github/workflows/build-debian-package.yml
secrets: inherit
trigger-vm-image:
uses: ./.github/workflows/build-vm-image.yml
with:
format: ova
publish: ${{ github.event_name == 'release' || inputs.publish == true }}
secrets: inherit
verify-artifacts:
name: Verify build artifacts exist and are non-empty
needs: [trigger-linux-iso, trigger-debian-package, trigger-vm-image]
runs-on: ${{ fromJSON(vars.HETZNER_FLEET_ONLINE == 'false' && '["ubuntu-24.04"]' || '["self-hosted","hetzner-robot"]') }}
timeout-minutes: 10
steps:
- name: Download Linux ISO artifact
uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c
with:
pattern: elizaos-live-iso-*
path: ./_verify/iso
merge-multiple: true
- name: Download Debian package artifact
uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c
with:
name: elizaos-debian-package
path: ./_verify/deb
- name: Download VM image artifact
uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c
with:
name: elizaos-vm-image
path: ./_verify/vm
- name: Assert artifacts present and non-empty
run: |
set -euo pipefail
fail=0
assert_nonempty() {
local pattern="$1"
local label="$2"
local match
match=$(find "$pattern" -type f \( -name "$3" \) -size +0c 2>/dev/null | head -1)
if [ -z "$match" ]; then
echo "ERROR: missing or empty $label artifact (pattern $3 under $pattern)"
fail=1
else
echo "OK: $label -> $match ($(stat --format=%s "$match") bytes)"
fi
}
assert_nonempty ./_verify/iso "Linux ISO" "*.iso"
assert_nonempty ./_verify/deb "Debian .deb" "*.deb"
assert_nonempty ./_verify/vm "VM image" "*.ova"
exit "$fail"
populate-and-validate-manifest:
name: Populate manifest checksums and gate on publishable validation
needs: [verify-artifacts]
runs-on: ${{ fromJSON(vars.HETZNER_FLEET_ONLINE == 'false' && '["ubuntu-24.04"]' || '["self-hosted","hetzner-robot"]') }}
timeout-minutes: 15
permissions:
# contents: write — required by softprops/action-gh-release to
# attach SHA256SUMS to the release asset list.
# id-token: write + attestations: write — required by
# actions/attest-build-provenance@v4 to mint a Sigstore-signed
# SLSA provenance attestation over SHA256SUMS via GitHub OIDC.
contents: write
id-token: write
attestations: write
steps:
- uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5
- uses: oven-sh/setup-bun@0c5077e51419868618aeaa5fe8019c62421857d6
with:
bun-version: "canary"
- name: Download all release artifacts
uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c
with:
path: ./_artifacts
merge-multiple: true
- name: Check manifest file exists
id: manifest_check
# The manifest file is hand-maintained per beta cycle. If it is
# missing (or got renamed without this workflow being updated)
# every downstream step would fail with ENOENT inside a Node
# readFileSync — a confusing 1-2 min failure with no clear call
# to action. Surface it explicitly so the maintainer either adds
# the manifest, updates this hardcoded path, or accepts the skip.
env:
MANIFEST_PATH: packages/os/release/beta-2026-05-16/manifest.json
run: |
if [ -f "$MANIFEST_PATH" ]; then
echo "can_validate_manifest=true" >> "$GITHUB_OUTPUT"
else
echo "::warning::Release manifest $MANIFEST_PATH not found. Manifest population + canonical SHA256SUMS + SLSA-over-SHA256SUMS attestation skipped. Per-artifact SLSA attestations from build-linux-iso.yml / build-debian-package.yml / build-vm-image.yml still mint correctly."
echo "can_validate_manifest=false" >> "$GITHUB_OUTPUT"
fi
- name: Populate manifest with real sha256 + sizes
if: steps.manifest_check.outputs.can_validate_manifest == 'true'
# Discovery is driven by the *manifest filename* — each entry's
# `filename` is searched verbatim under ./_artifacts. This keeps
# the workflow and manifest in lock-step: rename in the manifest,
# rename in the build, no workflow edits required.
#
# Build workflows that currently feed this step:
# - build-linux-iso.yml → *.iso (raw-linux-* entry)
# - build-vm-image.yml → *.qcow2, *.ova (vm-linux-* entry)
# Android (cf_x86_64, pixel-arm64) and macOS UTM bundles are NOT
# produced by any CI workflow today. They must be attached to the
# _artifacts staging dir out-of-band (release engineer uploads the
# built bundle as a workflow artifact via a prior manual job, or
# via release asset download) before this job runs. The strict
# gate at the end will fail loudly if any artifact is missing.
run: |
set -euo pipefail
MANIFEST=packages/os/release/beta-2026-05-16/manifest.json
ids=$(node -e '
const m = JSON.parse(require("node:fs").readFileSync(process.argv[1], "utf8"));
for (const a of m.artifacts) console.log(`${a.id}\t${a.filename}`);
' "$MANIFEST")
while IFS=$'\t' read -r id filename; do
path=$(find ./_artifacts -type f -name "$filename" | head -1 || true)
if [ -z "$path" ] || [ ! -f "$path" ]; then
echo "::warning::no artifact named $filename found for $id — strict gate will fail"
continue
fi
sha=$(sha256sum "$path" | cut -d' ' -f1)
size=$(stat --format=%s "$path")
node packages/os/scripts/update-release-manifest.mjs \
--manifest "$MANIFEST" \
--artifact "$id" \
--sha256 "$sha" \
--size "$size"
done <<< "$ids"
- name: Gate on publishable checksums (before status promotion)
if: steps.manifest_check.outputs.can_validate_manifest == 'true'
# Status promotion is gated on strict validation. If any artifact
# is missing a real checksum, the release stays "candidate" and
# this job fails — no half-published manifest.
run: |
node packages/os/scripts/validate-release-manifest.mjs \
--manifest packages/os/release/beta-2026-05-16/manifest.json \
--require-publishable-checksums
- name: Generate canonical SHA256SUMS via the in-repo tool
if: steps.manifest_check.outputs.can_validate_manifest == 'true'
# Runs BEFORE manifest promotion so that any failure here prevents
# the "available" status from being set and uploaded. SHA256SUMS
# generation is a hard prerequisite for promotion — closing the
# window where a promoted manifest could exist without a
# corresponding SHA256SUMS file or SLSA attestation.
#
# Calls packages/os/scripts/generate-release-checksums.mjs (which
# already exists, has unit tests under __tests__, and is the
# repo's canonical checksum tool) against the populated manifest
# + downloaded artifacts. Produces sha256sum -c compatible output
# mirroring the Debian / Fedora / Tails / Arch convention.
run: |
set -euo pipefail
node packages/os/scripts/generate-release-checksums.mjs \
--manifest packages/os/release/beta-2026-05-16/manifest.json \
--artifact-root ./_artifacts \
--output ./_artifacts/SHA256SUMS
echo "Generated SHA256SUMS:"
cat ./_artifacts/SHA256SUMS
- name: Attest SLSA build provenance over SHA256SUMS
if: steps.manifest_check.outputs.can_validate_manifest == 'true'
# Mints a single Sigstore-signed in-toto/SLSA provenance
# attestation that covers every release artifact via its hash,
# by attesting the canonical SHA256SUMS file generated above.
# Requires id-token: write + attestations: write (set in this
# job's permissions block). Users verify with:
#
# gh attestation verify SHA256SUMS --owner elizaOS
# sha256sum -c SHA256SUMS --ignore-missing
uses: actions/attest-build-provenance@0f67c3f4856b2e3261c31976d6725780e5e4c373
with:
subject-path: ./_artifacts/SHA256SUMS
- name: Upload SHA256SUMS artifact
if: steps.manifest_check.outputs.can_validate_manifest == 'true'
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a
with:
name: elizaos-release-checksums
path: ./_artifacts/SHA256SUMS
retention-days: 90
- name: Promote release status to available
if: steps.manifest_check.outputs.can_validate_manifest == 'true'
run: |
set -euo pipefail
node -e '
const fs = require("node:fs");
const p = "packages/os/release/beta-2026-05-16/manifest.json";
const m = JSON.parse(fs.readFileSync(p, "utf8"));
m.release.status = "available";
fs.writeFileSync(p, JSON.stringify(m, null, 2) + "\n");
'
- name: Upload populated manifest
if: steps.manifest_check.outputs.can_validate_manifest == 'true'
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a
with:
name: elizaos-os-release-manifest-published
path: packages/os/release/beta-2026-05-16/manifest.json
retention-days: 90
- name: Attach SHA256SUMS to release
if: github.event_name == 'release' && steps.manifest_check.outputs.can_validate_manifest == 'true'
uses: softprops/action-gh-release@718ea10b132b3b2eba29c1007bb80653f286566b
with:
files: ./_artifacts/SHA256SUMS
tag_name: ${{ github.event.release.tag_name || github.ref_name }}
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
publish-apt:
needs: [prepare, trigger-debian-package, verify-artifacts]
if: needs.trigger-debian-package.result == 'success' && needs.verify-artifacts.result == 'success'
uses: ./.github/workflows/publish-apt-repo.yml
with:
version: ${{ needs.prepare.outputs.version }}
tag: ${{ needs.prepare.outputs.tag }}
channel: stable
secrets: inherit
summary:
needs: [trigger-linux-iso, trigger-debian-package, trigger-vm-image, verify-artifacts, populate-and-validate-manifest, publish-apt]
runs-on: ${{ fromJSON(vars.HETZNER_FLEET_ONLINE == 'false' && '["ubuntu-24.04"]' || '["self-hosted","hetzner-robot"]') }}
if: always()
timeout-minutes: 5
steps:
- name: Release summary
run: |
{
echo "## elizaOS OS Release Summary"
echo "| Artifact | Status |"
echo "| -------- | ------ |"
echo "| Linux ISO | ${{ needs.trigger-linux-iso.result }} |"
echo "| Debian .deb | ${{ needs.trigger-debian-package.result }} |"
echo "| VM Image | ${{ needs.trigger-vm-image.result }} |"
echo "| Verify artifacts | ${{ needs.verify-artifacts.result }} |"
echo "| Populate + gate manifest | ${{ needs.populate-and-validate-manifest.result }} |"
echo "| apt Repo | ${{ needs.publish-apt.result }} |"
} >> "$GITHUB_STEP_SUMMARY"