From 3e968d9efd21bbd34d77f764cc9b470653774953 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Mon, 20 Apr 2026 19:35:39 +0000 Subject: [PATCH] chore: split ios release dispatch from desktop release Agent-Logs-Url: https://github.com/OpenKnots/okcode/sessions/ce03574c-94be-42d0-9506-81fdce257c40 Co-authored-by: BunsDev <68980965+BunsDev@users.noreply.github.com> --- .github/workflows/release-ios.yml | 39 ++++++++++++++++++---- README.md | 4 +-- docs/release.md | 13 ++++---- docs/releases/v0.26.0.md | 6 ++-- docs/releases/v0.26.0/assets.md | 2 +- docs/releases/v0.26.0/rollout-checklist.md | 2 +- scripts/prepare-release.ts | 10 +++--- 7 files changed, 52 insertions(+), 24 deletions(-) diff --git a/.github/workflows/release-ios.yml b/.github/workflows/release-ios.yml index 33fff9e9..c1e669e7 100644 --- a/.github/workflows/release-ios.yml +++ b/.github/workflows/release-ios.yml @@ -1,15 +1,16 @@ name: Release iOS on: - push: - tags: - - "v*.*.*" workflow_dispatch: inputs: version: description: "Release version (for example 1.2.3 or v1.2.3)" required: true type: string + ref: + description: "Git ref to build (defaults to refs/tags/v; may also be a branch or SHA)" + required: false + type: string permissions: contents: read @@ -23,7 +24,8 @@ jobs: tag: ${{ steps.release_meta.outputs.tag }} release_channel: ${{ steps.release_meta.outputs.release_channel }} build_timestamp: ${{ steps.release_meta.outputs.build_timestamp }} - ref: ${{ github.sha }} + ref: ${{ steps.release_meta.outputs.ref }} + commit_sha: ${{ steps.resolved_commit.outputs.sha }} steps: - id: release_meta name: Resolve release version @@ -33,8 +35,10 @@ jobs: if [[ "${GITHUB_EVENT_NAME}" == "workflow_dispatch" ]]; then raw="${{ github.event.inputs.version }}" + requested_ref="${{ github.event.inputs.ref }}" else raw="${GITHUB_REF_NAME}" + requested_ref="${GITHUB_REF}" fi version="${raw#v}" @@ -43,11 +47,23 @@ jobs: exit 1 fi + tag="v$version" + if [[ "${GITHUB_EVENT_NAME}" == "workflow_dispatch" ]]; then + if [[ -n "$requested_ref" ]]; then + resolved_ref="$requested_ref" + else + resolved_ref="refs/tags/$tag" + fi + else + resolved_ref="$requested_ref" + fi + build_timestamp="$(date -u +"%Y-%m-%dT%H:%M:%SZ")" echo "version=$version" >> "$GITHUB_OUTPUT" - echo "tag=v$version" >> "$GITHUB_OUTPUT" + echo "tag=$tag" >> "$GITHUB_OUTPUT" echo "build_timestamp=$build_timestamp" >> "$GITHUB_OUTPUT" + echo "ref=$resolved_ref" >> "$GITHUB_OUTPUT" if [[ "$version" =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then echo "release_channel=stable" >> "$GITHUB_OUTPUT" @@ -55,6 +71,17 @@ jobs: echo "release_channel=prerelease" >> "$GITHUB_OUTPUT" fi + - name: Checkout release ref + uses: actions/checkout@v6 + with: + ref: ${{ steps.release_meta.outputs.ref }} + fetch-depth: 0 + + - id: resolved_commit + name: Resolve release commit + shell: bash + run: echo "sha=$(git rev-parse HEAD)" >> "$GITHUB_OUTPUT" + ios_signing_preflight: name: iOS signing preflight needs: [preflight] @@ -102,7 +129,7 @@ jobs: runs-on: macos-14 env: RELEASE_VERSION: ${{ needs.preflight.outputs.version }} - OKCODE_COMMIT_HASH: ${{ github.sha }} + OKCODE_COMMIT_HASH: ${{ needs.preflight.outputs.commit_sha }} OKCODE_BUILD_TIMESTAMP: ${{ needs.preflight.outputs.build_timestamp }} OKCODE_RELEASE_CHANNEL: ${{ needs.preflight.outputs.release_channel }} steps: diff --git a/README.md b/README.md index 3029afd5..ecfacc47 100644 --- a/README.md +++ b/README.md @@ -188,7 +188,7 @@ Notes: Release is driven by `.github/workflows/release.yml` and the canonical runbook in [`docs/release.md`](/Users/buns/.okcode/worktrees/okcode/okcode-1c7a5554/docs/release.md). -- Release tags publish desktop artifacts and `okcodes` from `release.yml`, while `release-ios.yml` uploads the matching iOS TestFlight build separately. +- Release tags publish desktop artifacts and `okcodes` from `release.yml`, while `release-ios.yml` is dispatched separately for the matching iOS TestFlight build. - Preflight runs format, lint, typecheck, tests, browser tests, desktop smoke, and release smoke. - The separate Intel mac workflow is compatibility-only and non-blocking. - Publishing still requires release notes and an asset manifest for the tagged version. @@ -236,7 +236,7 @@ Release is driven by `.github/workflows/release.yml` and the canonical runbook i 2. Confirm macOS, Windows, Linux, iOS TestFlight, and CLI release inputs are ready. 3. Confirm signing secrets availability for macOS/Windows targets. 4. Confirm `docs/releases/v.md` and `docs/releases/v/assets.md` exist. -5. Trigger the desktop/CLI release and monitor both the desktop/CLI and iOS workflows. +5. Trigger the desktop/CLI release, then dispatch and monitor the separate iOS workflow for the same version when needed. ## 12) Contributing expectations diff --git a/docs/release.md b/docs/release.md index 0b224ba2..a04ea778 100644 --- a/docs/release.md +++ b/docs/release.md @@ -11,7 +11,7 @@ The next stable train ships one semver across desktop, CLI, and iOS surfaces: - macOS arm64 desktop DMG plus updater metadata - Windows x64 signed NSIS installer - Linux x64 AppImage -- iOS TestFlight build from the same tag +- iOS TestFlight build from the same release tag, dispatched separately - `okcodes` npm package from the same tag `docs/release.md` is the source of truth for release policy, release gates, and the platform matrix. Treat `docs/releases/README.md` and README release references as pointers only. @@ -32,10 +32,10 @@ The next stable train ships one semver across desktop, CLI, and iOS surfaces: ## Release workflows -Official release tags now fan out into two workflows: +Official release tags and follow-up mobile promotion now use two workflows: -- [`release.yml`](../.github/workflows/release.yml) for desktop artifacts, npm publish, GitHub Release publication, and finalize. -- [`release-ios.yml`](../.github/workflows/release-ios.yml) for the matching TestFlight upload from the same tag. +- [`release.yml`](../.github/workflows/release.yml) runs automatically on release tags for desktop artifacts, npm publish, GitHub Release publication, and finalize. +- [`release-ios.yml`](../.github/workflows/release-ios.yml) is dispatched manually for the matching version/ref when we want the TestFlight upload. `release.yml` job order: @@ -114,6 +114,7 @@ Non-blocking compatibility lane: - Build the mobile web bundle and sync Capacitor before archiving. - Run a simulator build in CI before archive/upload. - Upload the archive to TestFlight from the dedicated `release-ios.yml` workflow. +- Dispatch `release-ios.yml` with the release version and matching tag/ref (defaults to `refs/tags/vX.Y.Z`). - During RC soak, manually verify on: - one current supported iPhone/iOS - one older supported iPhone/iOS @@ -175,12 +176,12 @@ If any blocker fails, cut a new RC and repeat the soak. ## Post-release expectations - The GitHub release includes desktop artifacts plus release notes and asset manifest. -- iOS is distributed through TestFlight by `release-ios.yml`, not attached to the GitHub release. +- iOS is distributed through TestFlight by a separate `release-ios.yml` dispatch against the release tag, not attached to the GitHub release. - `finalize` updates version strings and pushes the post-release bump to `main`. ## Troubleshooting - If `preflight` fails, reproduce locally with the exact failing command before retriggering the workflow. - If `desktop_build` fails, inspect the target-specific signing secrets first. -- If `ios_testflight` fails, re-check provisioning, App Store Connect API key setup, and archive/export logs in `release-ios.yml`. +- If `ios_testflight` fails, re-check provisioning, App Store Connect API key setup, the dispatched ref, and archive/export logs in `release-ios.yml`. - If `publish_cli` fails, do not continue the train. Fix the publish issue so the app and CLI do not drift. diff --git a/docs/releases/v0.26.0.md b/docs/releases/v0.26.0.md index be4fad68..028feb18 100644 --- a/docs/releases/v0.26.0.md +++ b/docs/releases/v0.26.0.md @@ -21,9 +21,9 @@ File-content search, desktop terminal docking, transport snapshot fixes, updated ## Upgrade and install -- **CLI:** `npm install -g okcodes@0.26.0` once the coordinated release workflow finishes. +- **CLI:** `npm install -g okcodes@0.26.0` once the desktop/CLI release workflow finishes. - **Desktop:** Download from [GitHub Releases](https://github.com/OpenKnots/okcode/releases/tag/v0.26.0). Filenames are listed in [assets.md](v0.26.0/assets.md). -- **iOS:** Available via TestFlight (uploaded automatically by the Release iOS workflow). +- **iOS:** Available via TestFlight after the separate Release iOS workflow is dispatched for this tag. ## Known limitations @@ -32,5 +32,5 @@ OK Code remains early work in progress. Expect rough edges around session recove ## Release operations - Review the [asset manifest](v0.26.0/assets.md) to confirm every expected GitHub Release attachment is present. -- Use the [rollout checklist](v0.26.0/rollout-checklist.md) to walk the coordinated release from preflight through post-release verification. +- Use the [rollout checklist](v0.26.0/rollout-checklist.md) to walk the desktop/CLI release plus the separate iOS TestFlight dispatch through post-release verification. - Use the [soak test plan](v0.26.0/soak-test-plan.md) to validate the highest-risk surfaces after the tag is live. diff --git a/docs/releases/v0.26.0/assets.md b/docs/releases/v0.26.0/assets.md index 1ada6753..3338e4a5 100644 --- a/docs/releases/v0.26.0/assets.md +++ b/docs/releases/v0.26.0/assets.md @@ -37,7 +37,7 @@ All macOS DMG and ZIP payloads are **code-signed** with an Apple Developer ID ce ## iOS (TestFlight) -The iOS build is uploaded directly to App Store Connect / TestFlight by the [Release iOS workflow](../../.github/workflows/release-ios.yml). No IPA artifact is attached to the GitHub Release. +The iOS build is uploaded directly to App Store Connect / TestFlight by the separately dispatched [Release iOS workflow](../../.github/workflows/release-ios.yml). No IPA artifact is attached to the GitHub Release. | Detail | Value | | ----------------- | ------------------------------------------ | diff --git a/docs/releases/v0.26.0/rollout-checklist.md b/docs/releases/v0.26.0/rollout-checklist.md index 7bf8df04..e30c1cc8 100644 --- a/docs/releases/v0.26.0/rollout-checklist.md +++ b/docs/releases/v0.26.0/rollout-checklist.md @@ -35,7 +35,7 @@ Step-by-step playbook for the v0.26.0 release. Each phase must complete before a - [ ] Push the release-prep commit to `main`. - [ ] Create and push tag `v0.26.0`. - [ ] Verify the coordinated `release.yml` workflow starts. -- [ ] Verify the separate `release-ios.yml` workflow starts for `v0.26.0`, or trigger it manually with the same version if needed. +- [ ] Trigger `release-ios.yml` manually for `v0.26.0` (or the matching release ref if the tag is unavailable). - [ ] Monitor `release.yml` through Preflight, Desktop builds, Publish CLI, Publish GitHub Release, and Finalize release. - [ ] Monitor `release-ios.yml` through Preflight, iOS signing preflight, and iOS TestFlight. diff --git a/scripts/prepare-release.ts b/scripts/prepare-release.ts index c6d84af0..72fd8d56 100644 --- a/scripts/prepare-release.ts +++ b/scripts/prepare-release.ts @@ -265,7 +265,7 @@ ${highlights || "- See changelog for detailed changes."} - **CLI:** \`npm install -g okcodes@${version}\` once the desktop/CLI release workflow finishes. - **Desktop:** Download from [GitHub Releases](${REPO_URL}/releases/tag/v${version}). Filenames are listed in [assets.md](v${version}/assets.md). -- **iOS:** Available via TestFlight (uploaded automatically by the Release iOS workflow). +- **iOS:** Available via TestFlight after the separate Release iOS workflow is dispatched for this tag. ## Known limitations @@ -274,7 +274,7 @@ OK Code remains early work in progress. Expect rough edges around session recove ## Release operations - Review the [asset manifest](v${version}/assets.md) to confirm every expected GitHub Release attachment is present. -- Use the [rollout checklist](v${version}/rollout-checklist.md) to walk the desktop/CLI release plus the matching iOS TestFlight workflow through post-release verification. +- Use the [rollout checklist](v${version}/rollout-checklist.md) to walk the desktop/CLI release plus the separate iOS TestFlight dispatch through post-release verification. - Use the [soak test plan](v${version}/soak-test-plan.md) to validate the highest-risk surfaces after the tag is live. `; } @@ -319,7 +319,7 @@ All macOS DMG and ZIP payloads are **code-signed** with an Apple Developer ID ce ## iOS (TestFlight) -The iOS build is uploaded directly to App Store Connect / TestFlight by the [Release iOS workflow](../../.github/workflows/release-ios.yml). No IPA artifact is attached to the GitHub Release. +The iOS build is uploaded directly to App Store Connect / TestFlight by the separately dispatched [Release iOS workflow](../../.github/workflows/release-ios.yml). No IPA artifact is attached to the GitHub Release. | Detail | Value | | ----------------- | ------------------------------------------ | @@ -378,7 +378,7 @@ Step-by-step playbook for the v${version} release. Each phase must complete befo - [ ] Push the release-prep commit to \`main\`. - [ ] Create and push tag \`v${version}\`. - [ ] Verify the coordinated \`release.yml\` workflow starts. -- [ ] Verify the separate \`release-ios.yml\` workflow starts for the same tag or trigger it manually with the same version if needed. +- [ ] Trigger \`release-ios.yml\` manually for \`v${version}\` (or the matching release ref if the tag is unavailable). - [ ] Monitor \`release.yml\` through Preflight, Desktop builds, Publish CLI, Publish GitHub Release, and Finalize release. - [ ] Monitor \`release-ios.yml\` through Preflight, iOS signing preflight, and iOS TestFlight. @@ -948,7 +948,7 @@ async function main(): Promise { ` 1. Monitor the desktop release workflow: ${REPO_URL}/actions/workflows/release.yml`, ); console.log( - ` 2. Monitor the iOS TestFlight workflow: ${REPO_URL}/actions/workflows/release-ios.yml`, + ` 2. Trigger and monitor the iOS TestFlight workflow: ${REPO_URL}/actions/workflows/release-ios.yml`, ); console.log(` 3. Verify the GitHub Release: ${REPO_URL}/releases/tag/${tag}`); console.log(" 4. Test downloaded installers on each platform.");