Skip to content

CI/CD

Workflows, runner routing, Discord notifications, auto-merge, and release pipeline.

Standard Workflow Set (legacy Stig-Johnny app repos — ARCHIVED)

The per-repo workflow set below is the legacy Stig-Johnny pattern and still lives in this orchestrator repo (Stig-Johnny/claude-3). The 6 consumer apps moved to dashecorp/dashe-* on 2026-06-09 and are now rig-managed: they do not use request-review.yml (review is dispatched push-based by rig-conductor via the Valkey assignments:review-e stream) and carry a different, larger workflow set (e.g. build-and-upload.yml, android-release.yml). Do not add these per-repo workflows to dashecorp repos.

The legacy app repos had these 7 workflows:

Workflow Trigger Purpose
request-review.yml pull_request opened/reopened/ready_for_review/synchronize/closed Request Review-E + Discord #tasks thread; re-request review when a stale CHANGES_REQUESTED is pushed over; notify on close/merge
pr-comments-to-discord.yml issue_comment Forward PR comments to Discord thread
forward-copilot-reviews.yml pull_request_review Forward Copilot review to Discord
build-status-to-discord.yml check_suite completed Post build status to Discord thread
auto-resolve-copilot-conversations.yml check_suite completed Resolve Copilot conversation threads
notify-failure.yml workflow_run completed Discord alert on CI failure
release-please.yml push to main Version bump, changelog, GitHub Release, auto-merge release PR

Known gaps: Nutri-E auto-merge on older version. Tracked in issue #309.

Review-E identity: Review-E reviews as the review-e-bot[bot] GitHub App; the legacy review-e-dashecorp user account is being retired. Workflows that key off Review-E's reviews must match both logins. request-review.yml was missed in the App migration — its synchronize re-review check only matched review-e-dashecorp, so a stale CHANGES_REQUESTED pushed over by the bot was never re-requested and the PR stalled (observed on #733; tracked in #745, fixed in #746).

Runner Routing

Job Type Runner Label Host
iOS SDK build (Xcode-required) macos-26 GitHub-hosted. cuti-e/ios-sdk CI runs on the org-standard macos-26 label — the same runner as the dashe-* app builds (build-and-upload.yml). Its release-please / pin-expiry-check workflows run on ubuntu-latest. (The self-hosted macOS runner was retired 2026-06-29 — see note below.)
Android build / publish ubuntu-latest GitHub-hosted. cuti-e/android-sdk publishes on ubuntu-latest. (The old [self-hosted, macOS, ios] MacBook Air "AAPT2 x86 via Rosetta" routing was retired 2026-06-29.)
Linux CI (linting, scripts, release-please, Docker actions) ubuntu-latest GitHub-hosted
Linux self-hosted (repo-scoped, orphaned) [self-hosted, Linux, X64, mcp-server-dotnet] 2 Dell systemd runners (/home/ubuntu/actions-runner-{1,2}/) registered to Stig-Johnny/mcp-server-dotnet only — orphaned (that repo's CI is 100% ubuntu-latest); decommission-flagged (infra#389)

ARC k3s runners were retired 2026-05-20 (operator-confirmed). All Linux CI uses GitHub-hosted ubuntu-latest. The cost is acceptable at current rig volume.

The self-hosted macOS CI runner was retired 2026-06-29 — there is no self-hosted macOS runner anywhere now (the Mac Mini runner stood up earlier that day was decommissioned the same day). Moving iOS/Android CI to GitHub-hosted runners removes the self-hosted-runner maintenance burden that caused a 24h queue-cancel outage. The Mac Mini M4 (Tailscale 100.92.170.124, user claude) hosts iBuild-E + iClaw-E only — no CI runner; the MacBook Air M4 hosts dev + Claude Code only — no runner. The only self-hosted runners are the 2 Dell Linux systemd runners (below) — and they are repo-scoped to Stig-Johnny/mcp-server-dotnet (not a general fallback), currently orphaned and flagged for decommission (infra#389).

PR Merge Flow

Note: There is no per-PR auto-merge.yml workflow in the app repos. Regular PRs are merged manually via gh pr merge once CI + Copilot pass. Automatic merging applies only to release PRs (see Release Pipeline below, handled by release-please.yml). Per-PR auto-merge is potential future work, not a current implementation.

claude-3 (orchestrator repo): its own per-PR auto-merge.yml was removed 2026-06-23 (#812). It had relied on the legacy classic GH_PAT, which expired and failed every merge with 401 Bad credentials. Per operator decision, claude-3 PRs now merge manually (orchestrator squash via gh pr merge --squash) — which is also rig-conductor's own documented fallback. The target is for rig-conductor (conductor-e) to own claude-3's merge gate, but per BRAIN the conductor MergeGate is scoped to dashecorp-org repos only, so that requires migrating claude-3 into dashecorp first (not yet scheduled).

Orchestrator cross-org reads (monitor-infra.yml, build-unified-docs.yml): the same expired GH_PAT was replaced by the codi-e-bot GitHub App (App ID 4127706, @dashecorp-owned, read-only). These workflows mint short-lived per-org tokens via actions/create-github-app-token from the ORCHESTRATOR_BOT_PEM repo secret. Currently RED: the PEM was uploaded as PKCS#1 but the action requires PKCS#8 (error:1E08010C:DECODER routines::unsupported), so both workflows fail until the operator re-sets the secret — runbook docs/runbooks/ops-e-reset-orchestrator-bot-pem.md (issue #765, deadline #24). App details + PKCS#8 conversion: .claude/skills/github-apps/SKILL.md.

  1. PR opened → request-review.yml creates Discord thread, tags Review-E
  2. CI runs on GitHub-hosted ubuntu-latest
  3. Copilot reviews automatically
  4. Maintainer checks CI status, Copilot review, and unresolved conversations
  5. Squash merge via gh pr merge
  6. Merge notification posted to Discord thread

Release Pipeline

  1. Conventional commits on main trigger release-please
  2. Release PR opened automatically with version bump + changelog
  3. Release PR auto-approved via RELEASE_PAT (Review-E classic PAT, EXPIRED 2026-05-30 — rotation pending, operator/Ops-E, deadline #23). An expired PAT surfaces as Release Please 'Bad credentials'. Live consumers are the dashecorp/dashe-* app repos + dashe-cutie, provisioned via OpenTofu in dashecorp/infra (TF_VAR_release_pat).
  4. Release PR auto-merged
  5. GitHub Release created with tag
  6. release-notes-to-discord.yml posts release notes to Discord

All actions SHA-pinned for security.

Discord Integration Flow

PR Created
  → request-review.yml → Discord #tasks thread (stores message ID in PR comment)
  → Review-E picks up from Discord notification

CI Runs
  → build-status-to-discord.yml → Updates Discord thread

Copilot Reviews
  → forward-copilot-reviews.yml → Posts to Discord thread

PR Merged/Closed
  → notify-closed job → Posts resolution to Discord thread (using stored message ID)

Key pattern: Discord message ID stored as HTML comment in PR (<!-- discord-review-msg-id:ID -->). This ID doubles as thread ID for webhook posts (?thread_id=ID).

iOS Build Pipeline (GitHub Actions)

Xcode Cloud was retired (claude-3 PR #776, merged 2026-06-16). iOS apps now build and ship to TestFlight via GitHub Actions: each dashecorp/dashe-* app repo has a build-and-upload.yml workflow on the macos-26 GitHub-hosted runner (fastlane match signing via dashecorp/ios-certs, ASC API upload to TestFlight internal; App Store submission stays human-gated). See iOS Build & Distribution for the full pipeline. The legacy account-wide Xcode Cloud GitHub App is no longer triggered.