This runbook documents how Flow CI/CD is wired today and how to debug it quickly when jobs fail.
- Workflows:
.github/workflows/pr-fast.yml: fast PR gate (Linux) using vendored hydrate +cargo check..github/workflows/canary.yml: runs on every push tomain, publishes/updates thecanaryrelease/tag..github/workflows/nightly-validation.yml: scheduled full cross-target validation (plus host SIMD) without publishing..github/workflows/release.yml: runs on tag pushes matchingv*, publishes stable releases.
- Trigger optimization:
- Canary
pushskips docs-only changes (docs/**,**/*.md). - Use
workflow_dispatchto force a Canary run when needed after docs-only changes.
- Canary
- Vendored deps bootstrap:
- Both workflows run
scripts/vendor/vendor-repo.sh hydrateimmediately after checkout in each build job. - This materializes
lib/vendor/*from the pinned commit invendor.lock.tomlbefore Cargo builds. - Build jobs cache vendor checkout/materialization (
.vendor/flow-vendor,lib/vendor,lib/vendor-manifest) keyed byvendor.lock.toml.
- Both workflows run
- Repository policy checks:
- CI enforces lowercase
readme.mdnaming viascripts/ci/check-readme-case.sh.
- CI enforces lowercase
- Build jobs in both workflows:
- Matrix build: macOS + Linux targets.
- SIMD build:
build-linux-host-simd(Linux x64 with--features linux-host-simd-json). - CI builds
--bin fonly (release artifacts packagef; avoids duplicateflowalias build cost).
- Release jobs:
- Gather all build artifacts.
- Publish release assets (and in Canary, force-move
canarytag to currentmaincommit). releasewaits for bothbuildandbuild-linux-host-simd.
Flow uses task-driven mode switching (not manual workflow edits):
githubmode:- Standard Linux lanes on
ubuntu-latest. - SIMD lane disabled.
- Standard Linux lanes on
blacksmithmode:- Linux lanes on Blacksmith runners.
- SIMD lane enabled on Blacksmith.
hostmode:- Standard Linux lanes stay on GitHub-hosted runners.
- SIMD lane runs on self-hosted label:
[self-hosted, linux, x64, ci-1focus].
Check/switch mode:
f ci-blacksmith-status
f ci-blacksmith-enable
f ci-blacksmith-enable-apply
f ci-host-enable
f ci-host-enable-apply
f ci-blacksmith-disable
f ci-blacksmith-disable-applyPreferred path (painless, idempotent):
f ci-host-setupIf infra host is not configured yet:
f ci-host-setup <user@ip>What f ci-host-setup does:
- Validates
ghauth andinfrahost config. - Installs/registers the
ci-1focusself-hosted runner on the Linux host. - Waits for runner to report online.
- Switches workflows to
hostmode with commit + push. - Prints final runner health/status.
- Check current mode:
f ci-blacksmith-status - Check runner service + GitHub registration:
f ci-host-runner-status - Reinstall runner if needed:
f ci-host-runner-install - Remove runner:
f ci-host-runner-remove
Stable release flow:
- Merge version bump to
main. - Push tag
vX.Y.Z. - Watch
Releaseworkflow.
Canary flow:
- Push to
main. - Watch
Canaryworkflow. - Confirm
canarytag moved and release assets updated.
PR flow:
- Open/refresh PR to
main. - Watch
PR Fast Check(cargo check+cargo test --no-runshard). - Merge only after fast check passes.
gh run list --workflow Canary --limit 10
gh run list --workflow Release --limit 10
gh run view <run-id> --log-failed
gh run watch <run-id>If failure shows:
failed to load source for dependency 'axum'Unable to update .../lib/vendor/axumNo such file or directory (os error 2)
then vendored deps were not hydrated before build.
Usually means self-hosted runner routing issue.
f ci-blacksmith-status
f ci-host-runner-status
python3 ./scripts/ci_host_runner.py health --repo nikivdev/flowExpected healthy state is:
- Host service:
active - GitHub runner status:
online - Runner has label
ci-1focus
If not healthy, run:
f ci-host-runner-install
python3 ./scripts/ci_host_runner.py wait-online --repo nikivdev/flow --timeout-secs 120 --interval-secs 5f ci-blacksmith-statusIf wrong:
f ci-host-enable-apply
# or:
f ci-blacksmith-enable-apply
# or:
f ci-blacksmith-disable-applyHydration depends on vendor.lock.toml pin and vendor repo availability.
Quick checks:
scripts/vendor/vendor-repo.sh status
scripts/vendor/vendor-repo.sh hydrateExpected:
- pinned commit in
vendor.lock.tomlis non-empty, - hydrate logs
hydrated <crate> -> lib/vendor/<crate>, lib/vendor/axum/Cargo.tomlandlib/vendor/reqwest/Cargo.tomlexist after hydrate.
If CI cannot clone SSH URL from lock, vendor-repo.sh now falls back to HTTPS clone for GitHub URLs.
Flow installer defaults to canary unless FLOW_VERSION is set differently. Check if canary moved:
git ls-remote --tags origin canaryThen verify in sandbox (recommended) using:
docs/rise-sandbox-feature-test-runbook.md
That runbook gives an isolated rise sandbox smoke test for:
curl -fsSL https://myflow.sh/install.sh | sh
~/.flow/bin/f --versionRe-run:
f ci-host-setupThe installer path is idempotent (it removes old service/config before re-registering). If failure persists, inspect:
f ci-host-runner-status
gh api repos/nikivdev/flow/actions/runners- CI/CD execution is defined in repo workflows; GitHub UI is control plane/visibility (runs, logs, runner state), not the source of truth for pipeline logic.
- Current performance balance: keep general Linux matrix jobs on GitHub-hosted runners, offload expensive SIMD build to the Linux host.