Skip to content

Desktop core E2E harness, tiered testing, and release blessing gate#9168

Merged
Git-on-my-level merged 24 commits into
mainfrom
cursor/1eaeca88
Jul 7, 2026
Merged

Desktop core E2E harness, tiered testing, and release blessing gate#9168
Git-on-my-level merged 24 commits into
mainfrom
cursor/1eaeca88

Conversation

@Git-on-my-level

@Git-on-my-level Git-on-my-level commented Jul 6, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • Adds a tiered desktop core E2E harness (desktop-core-harness.sh, CORE_E2E.md, flow lint, T0 CI self-check) so agents can validate real app behavior via the automation bridge — not just compile/unit tests.
  • Introduces hermetic T2 testing with PROVIDER_MODE=offline, Rust OMI_LLM_STUB, capture/chat/memories/tasks bridge seams, and falsifiable YAML flow assertions (12 flows + spatial overlay verified green locally).
  • Adds release blessing: bless-release.sh runs T2 against a rebuild tag, writes blessed metadata to GitHub release KEY_VALUE blocks; prod promotion (desktop_promote_prod) is gated unless --override-unblessed + confirmation string; admin Releases page shows blessing status.

Test plan

  • ./scripts/desktop-core-harness.sh --self-check --skip-backend-contracts (T0)
  • PROVIDER_MODE=offline make dev-up + make desktop-run-local DESKTOP_APP_NAME=omi-core-e2e DESKTOP_USER=alice
  • ./scripts/desktop-core-harness.sh --tier 2 --bundle omi-core-e2e --port <automation-port> --keep-stackpassed: true, provider_mode: offline
  • python3 scripts/release-keyvalue.py check-manifest accepts good manifest, rejects missing provider_mode: offline
  • python3 .github/scripts/test_check_desktop_release_promotion.py (bless gate unit tests)
  • Pre-push hooks: Swift compile, Rust compile, changelog validation, prod promotion policy check

Notes

  • T2 requires Docker/OrbStack for Typesense; dev-up now restarts Typesense when the container dies but manifest PID lingers.
  • Bless runs are intended 1–2×/day on agent-local macOS runners, not per-PR.
  • Prod override requires override_unblessed=true and override_confirm=I-ACCEPT-UNBLESSED-PROD-RISK.

Made with Cursor

Review in cubic

Git-on-my-level and others added 17 commits July 6, 2026 03:05
Introduces the tiered desktop-core-harness dispatcher, YAML flow lint against registered bridge actions, CORE_E2E.md, and a Linux self-check job so desktop PRs get a fast static confidence gate.

Verification: ./desktop/macos/scripts/desktop-core-harness.sh --self-check
Co-authored-by: Cursor <cursoragent@cursor.com>
Adds capture_test_transcript plus conversation/memories/tasks snapshot actions and last_assistant_text in main_chat_snapshot for deterministic harness assertions.

Verification: desktop-flow-lint.py (action names registered in bridge source)
Co-authored-by: Cursor <cursoragent@cursor.com>
Adds bless-release.sh for agent-local T2 blessing, requires blessedSha metadata in check-desktop-release-promotion.py with typed override escape hatch, and extends the promotion workflow/policy enforcement.

Verification: python3 .github/scripts/test_check_desktop_release_promotion.py
Co-authored-by: Cursor <cursoragent@cursor.com>
Parses bless keys from GitHub release KEY_VALUE metadata, fixes parseVersion for two-part macOS tags, and adds a Blessed column plus deployable banner on the releases dashboard.

Verification: parseVersion regex accepts v11.0+11000-macos
Co-authored-by: Cursor <cursoragent@cursor.com>
open_ask_omi returns focused timing fields, not askOmiOpen in action detail; state.expect still covers askOmiOpen on step 3.

Co-authored-by: Cursor <cursoragent@cursor.com>
Wire capture_test_transcript through TranscriptionStorage with real session IDs,
assert conversation_count_increased in the flow, strengthen chat marker checks,
and document hermetic vs Omi Dev auth bootstrap in CORE_E2E.md.

Verified: swift build, desktop-core-harness --self-check.
Co-authored-by: Cursor <cursoragent@cursor.com>
The manifest pass-check used `raise (X if cond else None)`, which raised
TypeError on success; background desktop-run-local and wait for the
worktree automation bridge; use make desktop-run-local (alice) instead of
omi-auth-seed; discover --port via dev-instance.sh; consolidate KEY_VALUE
edits into release-keyvalue.py; add cleanup trap.

Verified: bash -n scripts/bless-release.sh; release-keyvalue.py self-test
(pass manifest exit 0, fail exit 1, old pattern TypeError on pass).

Co-authored-by: Cursor <cursoragent@cursor.com>
Split T0 CI to desktop-only static checks (--skip-backend-contracts) so the
job no longer duplicates backend pytest; enforce offline dev-stack via config
digest + health probes; derive flow lists from tier metadata; record
provider_mode in manifests.

Verified: bash -n; --self-check (8 pytest contracts); --self-check
--skip-backend-contracts; workflow YAML parse; tier-1 metadata = harness-smoke
+ navigation; probe exits 0 on healthy offline stack and 2 on non-offline digest.

Co-authored-by: Cursor <cursoragent@cursor.com>
memories_snapshot and tasks_snapshot now await real API/store loads and return
falsifiable load_state/count-valid fields; flows assert those instead of vacuous
ok/refreshed. floating-bar-functional waits for chat idle and asserts the stub
marker echo via main_chat_snapshot (shared ChatProvider). Document
automationStopCaptureTestSession sync with stopTranscription().

Verified: xcrun swift build -c debug --package-path Desktop (pass);
python3 scripts/desktop-flow-lint.py (pass, 22 flows). Live omi-harness runs
blocked by concurrent ./run.sh lock contention; manual binary swap breaks Sparkle
rpaths so full bundle rebuild needed for live flow runs.

Co-authored-by: Cursor <cursoragent@cursor.com>
Local profile no longer crashes on Auth.auth() or signs out when pi-mono
requests a token refresh against the Auth emulator; skip RealtimeHub warm-up
and Omi Dev auth seed for desktop-run-local. Replace mapfile (bash 4+) in
desktop-core-harness.sh for macOS default bash.

Verified: omi-core-e2e boots signed-in as alice on bridge :47956; tier-2
harness runs 9/13 flows pass (capture-lifecycle, chat*, floating-bar still fail).

Co-authored-by: Cursor <cursoragent@cursor.com>
Terminate omi-bless-* app and run.sh process tree on bless cleanup instead of
only killing the launch subshell; require harness sentinel + alive owned PIDs
before T2 accepts a dev stack; require provider_mode=offline in check-manifest
and fail update-blessed when KEY_VALUE block is missing.

Verified: bash -n bless-release.sh desktop-core-harness.sh; release-keyvalue.py
self-test; probe fixtures (stale PIDs, foreign/absent sentinel → exit 1);
cleanup process-tree simulation OK.

Co-authored-by: Cursor <cursoragent@cursor.com>
Dedupe repeated markers in one message and add a regression test so hermetic
chat assertions see a single stub echo per turn. Verified: cargo test in
Backend-Rust (301 passed).

Co-authored-by: Cursor <cursoragent@cursor.com>
Clear kernel main_chat surface state and UI messages before each chat flow
so stub marker assertions are not polluted by prior turns in the same session.
Verified: chat-hermetic + chat flows pass on bridge port 47956.

Co-authored-by: Cursor <cursoragent@cursor.com>
Report askOmiOpen for any open AI conversation (including response view),
reset floating-bar kernel/chat on open_ask_omi reset, and use floating-bar
snapshot/wait actions so assertions target the correct provider. Verified:
floating-bar-functional flow pass on bridge port 47956.

Co-authored-by: Cursor <cursoragent@cursor.com>
Await segment persistence in the automation inject seam and guarantee
finishedAt is at least one second after startedAt so from-segments uploads
pass backend validation. Verified: capture-lifecycle flow pass on bridge
port 47956.

Co-authored-by: Cursor <cursoragent@cursor.com>
…gers.

Restart unhealthy harness services before dev-up skips them, verify the Typesense Docker container in probe_dev_stack, and retry stack probes after dev-up so tier-2 dispatch passes reliably.

Verified: PROVIDER_MODE=offline make dev-up; ./scripts/desktop-core-harness.sh --tier 2 --bundle omi-core-e2e --port 47956 --keep-stack (manifest passed=true, provider_mode=offline); release-keyvalue.py self-test; desktop-core-harness --self-check.
Co-authored-by: Cursor <cursoragent@cursor.com>
Co-authored-by: Cursor <cursoragent@cursor.com>

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: a9cc72e705

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +94 to +96
pub fn stub_chat_completions_response(req: &ChatCompletionRequest) -> Response {
let user_text = extract_latest_user_text(req);
let lines = fixture_lines(&user_text, DEFAULT_FIXTURE);

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Honor non-stream chat completion requests in the stub

When OMI_LLM_STUB=1, this stub always returns text/event-stream, even when req.stream is false. Non-stream desktop callers such as AgentDelegationResolver.swift and AgentPill.swift send "stream": false and parse a JSON choices[0].message.content response, so the offline/T3 harness paths that exercise those callers will get HTTP 200 with an SSE body and fail with an unexpected response shape. Return an OpenAI-compatible JSON completion for non-stream requests.

Useful? React with 👍 / 👎.

fi
if [[ "$TIER" -eq 3 ]]; then
set +e
OMI_AUTOMATION_PORT="$PORT" "$SCRIPT_DIR/agent-continuity-gauntlet.sh" --bundle-id "com.omi.${BUNDLE#omi-}"

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Use the actual named-bundle id for T3 gauntlet

For any required omi-* bundle, the app-config logic derives the bundle id as com.omi.<full slug> (for example omi-core-e2e becomes com.omi.omi-core-e2e). Stripping the omi- prefix here makes the T3 gauntlet target com.omi.core-e2e, which will not match the running named bundle, so tier-3 harness runs fail to connect to the app even though the bridge is healthy.

Useful? React with 👍 / 👎.

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

22 issues found across 56 files

Confidence score: 2/5

  • desktop/macos/Desktop/Sources/DesktopAutomationBridge.swift (reset_main_chat) can erase a signed-in user’s main chat when automation bridge is enabled on a production bundle, which is a direct user-data loss risk if merged as-is — add the same non-prod gating used by adjacent harness-only actions before allowing reset.
  • desktop/macos/Desktop/Sources/AppState/AppState+Transcription.swift allows already_recording to proceed through inject/stop, so harness capture can interfere with a real in-progress recording and tear it down unexpectedly — track harness-owned sessions (or hard-stop on preexisting recordings) before merge.
  • Release promotion integrity is currently weak across desktop/macos/scripts/release-keyvalue.py and .github/workflows/desktop_promote_prod.yml: blessing can accept non-T2 manifests, malformed metadata blocks can appear successful, and blessed_override=true can bypass blessedSha commit mismatch checks — tighten these validations so only correctly tiered, well-formed metadata tied to the target commit can be promoted.
  • desktop/macos/scripts/desktop-flow-lint.py checks for a non-existent do: key, so typed flows can silently include legacy do steps and pass lint, reducing confidence in flow correctness — fix the key detection to do and re-run lint on typed flows before merging.
Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="desktop/macos/Backend-Rust/src/routes/chat_completions.rs">

<violation number="1" location="desktop/macos/Backend-Rust/src/routes/chat_completions.rs:616">
P2: Stub always returns SSE even for non-streaming requests — `req.stream` is ignored. A client sending `stream: false` or omitting `stream` gets `Content-Type: text/event-stream` with SSE line events instead of the expected JSON `ChatCompletionResponse`. Consider checking `req.stream` in the stub: when `false`, return a single-chunk JSON response matching the real handler's non-streaming shape.</violation>
</file>

Reply with feedback, questions, or to request a fix.

Re-trigger cubic

Comment thread desktop/macos/Desktop/Sources/DesktopAutomationBridge.swift
Comment thread desktop/macos/Desktop/Sources/AppState/AppState+Transcription.swift Outdated
Comment thread web/admin/app/api/omi/releases/route.ts Outdated
Comment thread desktop/macos/changelog/unreleased/20260706-desktop-core-e2e-harness.json Outdated
Comment thread desktop/macos/e2e/flows/chat.yaml Outdated
Comment thread desktop/macos/Backend-Rust/src/routes/llm_stub.rs
Comment thread desktop/macos/scripts/desktop-core-harness.sh Outdated
Comment thread desktop/macos/changelog/unreleased/20260706-desktop-core-e2e-harness.json Outdated
Comment thread desktop/macos/Backend-Rust/src/routes/llm_stub.rs Outdated
Comment thread .github/workflows/desktop_promote_prod.yml
…delity.

Gate harness-only chat/capture actions on non-prod bundles, reject bless manifests without tier-2 offline evidence, fix promotion override semantics, and tighten admin blessed parsing.

Co-authored-by: Cursor <cursoragent@cursor.com>

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

4 issues found across 19 files (changes from recent commits).

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="desktop/macos/Backend-Rust/src/routes/chat_completions.rs">

<violation number="1" location="desktop/macos/Backend-Rust/src/routes/chat_completions.rs:616">
P2: Stub always returns SSE even for non-streaming requests — `req.stream` is ignored. A client sending `stream: false` or omitting `stream` gets `Content-Type: text/event-stream` with SSE line events instead of the expected JSON `ChatCompletionResponse`. Consider checking `req.stream` in the stub: when `false`, return a single-chunk JSON response matching the real handler's non-streaming shape.</violation>
</file>

Reply with feedback, questions, or to request a fix.

Re-trigger cubic

Comment thread desktop/macos/Backend-Rust/src/routes/llm_stub.rs Outdated
Comment thread desktop/macos/Desktop/Sources/AppState/AppState+Transcription.swift
Comment thread desktop/macos/Desktop/Sources/Providers/ChatProvider.swift
Comment thread desktop/macos/Backend-Rust/src/routes/llm_stub.rs
Git-on-my-level and others added 2 commits July 6, 2026 23:13
Resolve DesktopAutomationBridge conflict by keeping both the PR's
hermetic capture/snapshot actions and main's ptt_start/ptt_stop hooks.

Co-authored-by: Cursor <cursoragent@cursor.com>
…down.

- Parse Gemini stub markers from latest user content only; assert in test
- Propagate harness chat-reset deletion failures to automation bridge
- Clear capture-test state after finalize errors so retries can recover
- Share release metadata parsing; restore override_unblessed blessedSha warning
- Fix flow-lint typed-flow do-key detection; add promotion gate to lint CI

Co-authored-by: Cursor <cursoragent@cursor.com>

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

1 issue found across 10 files (changes from recent commits).

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name=".github/workflows/lint.yml">

<violation number="1" location=".github/workflows/lint.yml:92">
P3: Two assertions in `test_unblessed_release_fails` lack failure context, making CI failures harder to debug. If the check script's output format or exit code changes, the failed assertion produces only `AssertionError` without showing what the actual stdout/stderr contained. The other two test functions already include `result.stderr` in their assertions for this reason.</violation>
</file>

Tip: Review your code locally with the cubic CLI to iterate faster.

Re-trigger cubic

@@ -89,6 +89,9 @@ jobs:
- name: Check desktop prod promotion policy

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P3: Two assertions in test_unblessed_release_fails lack failure context, making CI failures harder to debug. If the check script's output format or exit code changes, the failed assertion produces only AssertionError without showing what the actual stdout/stderr contained. The other two test functions already include result.stderr in their assertions for this reason.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At .github/workflows/lint.yml, line 92:

<comment>Two assertions in `test_unblessed_release_fails` lack failure context, making CI failures harder to debug. If the check script's output format or exit code changes, the failed assertion produces only `AssertionError` without showing what the actual stdout/stderr contained. The other two test functions already include `result.stderr` in their assertions for this reason.</comment>

<file context>
@@ -89,6 +89,9 @@ jobs:
       - name: Check desktop prod promotion policy
         run: python3 .github/scripts/check-desktop-prod-promotion-policy.py
 
+      - name: Test desktop release promotion gate
+        run: python3 .github/scripts/test_check_desktop_release_promotion.py
+
</file context>

Git-on-my-level and others added 2 commits July 7, 2026 00:04
Restore DesktopLocalProfile visibility for harness-gated code paths,
replace Response::builder unwraps with response_or_500, and add stderr
context to unblessed release promotion test assertions.

Co-authored-by: Cursor <cursoragent@cursor.com>
Map changed AuthService, agent runtime, floating bar, and transcription
files to tier-2 harness flows, restore check-e2e-flow-coverage.py, and
align lint.yml with main's strict coverage gate.

Co-authored-by: Cursor <cursoragent@cursor.com>

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

1 issue found across 6 files (changes from recent commits).

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="desktop/macos/Backend-Rust/src/routes/chat_completions.rs">

<violation number="1" location="desktop/macos/Backend-Rust/src/routes/chat_completions.rs:616">
P2: Stub always returns SSE even for non-streaming requests — `req.stream` is ignored. A client sending `stream: false` or omitting `stream` gets `Content-Type: text/event-stream` with SSE line events instead of the expected JSON `ChatCompletionResponse`. Consider checking `req.stream` in the stub: when `false`, return a single-chunk JSON response matching the real handler's non-streaming shape.</violation>
</file>

<file name=".github/workflows/lint.yml">

<violation number="1" location=".github/workflows/lint.yml:92">
P3: Two assertions in `test_unblessed_release_fails` lack failure context, making CI failures harder to debug. If the check script's output format or exit code changes, the failed assertion produces only `AssertionError` without showing what the actual stdout/stderr contained. The other two test functions already include `result.stderr` in their assertions for this reason.</violation>
</file>

<file name="desktop/macos/scripts/check-e2e-flow-coverage.py">

<violation number="1" location="desktop/macos/scripts/check-e2e-flow-coverage.py:181">
P2: The harness recommendation in `check-e2e-flow-coverage.py` prints a command that uses the old `omi-harness` runner and the old app name `omi-e2e`, but this PR introduces the `desktop-core-harness.sh` tiered harness and the `omi-core-e2e` bundle name. Developers relying on the coverage report will get stale or incorrect invocation instructions that don't align with the new desktop core E2E contract. Consider updating `harness_command` to generate a command that matches the new harness interface (e.g., `desktop-core-harness.sh` with `--bundle omi-core-e2e` or the appropriate tier/port).</violation>
</file>

Tip: Review your code locally with the cubic CLI to iterate faster.

Re-trigger cubic

Comment thread desktop/macos/scripts/check-e2e-flow-coverage.py Outdated
@Git-on-my-level

Copy link
Copy Markdown
Collaborator Author

@cursor address merge conflict

@cursor

cursor Bot commented Jul 7, 2026

Copy link
Copy Markdown

Merge conflict resolved and pushed.

Conflict: desktop/macos/e2e/flows/harness-smoke.yaml

main dropped the AuthService.swift covers entry; this branch added tier: 1 and kept that coverage. Resolution keeps both:

  • tier: 1
  • covers for DesktopAutomationBridge.swift and AuthService.swift

Also fixed the stale harness recommendation in check-e2e-flow-coverage.py (cubic review): it now suggests desktop-core-harness.sh --tier N --bundle omi-core-e2e instead of the legacy omi-harness / omi-e2e command. The coverage test was updated to match.

Verification: bash desktop/macos/tests/test-e2e-flow-coverage.sh passed.

Commit: 2986c1faa on cursor/1eaeca88, pushed to origin. The PR should be mergeable with main now.

Open in Web Open in Cursor 

Resolve harness-smoke.yaml conflict: keep tier: 1 and AuthService.swift
coverage from the desktop core E2E harness branch.

Update check-e2e-flow-coverage.py to recommend desktop-core-harness.sh
with omi-core-e2e bundle instead of the legacy omi-harness command.

Co-authored-by: David Zhang <Git-on-my-level@users.noreply.github.com>
Move the macOS Swift build/test job out of lint.yml into desktop-swift-ci.yml
so PR checks no longer show two unrelated jobs under "Lint Check". Update
AgentRuntimeProcessTests source-inspection assertions for the merged main
auth refresh guard (forceRefreshToken + DesktopLocalProfile).

Co-authored-by: Cursor <cursoragent@cursor.com>

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

2 issues found across 3 files (changes from recent commits).

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name=".github/workflows/desktop-swift-ci.yml">

<violation number="1" location=".github/workflows/desktop-swift-ci.yml:25">
P2: For push events to `main`, the diff base is hard-coded to `HEAD~1` in both the path gate and the e2e coverage check. On a multi-commit push, this only looks at the last commit, so desktop changes in earlier pushed commits can be missed and the Swift build, tests, and e2e coverage validation will be skipped.

Use `github.event.before` as the diff base for push events so the full pushed range is evaluated.</violation>

<violation number="2" location=".github/workflows/desktop-swift-ci.yml:63">
P2: The CI build only validates `arm64-apple-macosx`, while the Codemagic release pipeline builds both `arm64` and `x86_64` and merges them into a universal binary. This means x86_64-specific compile or link failures won't be caught in CI and will only surface during the release build, which has historically caused issues (see the "Burned a build in May 2026" comment in the release pipeline). Consider adding an x86_64 build step or using the same build matrix the release pipeline uses.</violation>
</file>

Tip: Review your code locally with the cubic CLI to iterate faster.

Re-trigger cubic

- name: Build desktop Swift app
if: steps.changed.outputs.should_run == 'true'
working-directory: desktop/macos
run: xcrun swift build -c release --package-path Desktop --triple arm64-apple-macosx

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: The CI build only validates arm64-apple-macosx, while the Codemagic release pipeline builds both arm64 and x86_64 and merges them into a universal binary. This means x86_64-specific compile or link failures won't be caught in CI and will only surface during the release build, which has historically caused issues (see the "Burned a build in May 2026" comment in the release pipeline). Consider adding an x86_64 build step or using the same build matrix the release pipeline uses.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At .github/workflows/desktop-swift-ci.yml, line 63:

<comment>The CI build only validates `arm64-apple-macosx`, while the Codemagic release pipeline builds both `arm64` and `x86_64` and merges them into a universal binary. This means x86_64-specific compile or link failures won't be caught in CI and will only surface during the release build, which has historically caused issues (see the "Burned a build in May 2026" comment in the release pipeline). Consider adding an x86_64 build step or using the same build matrix the release pipeline uses.</comment>

<file context>
@@ -0,0 +1,68 @@
+      - name: Build desktop Swift app
+        if: steps.changed.outputs.should_run == 'true'
+        working-directory: desktop/macos
+        run: xcrun swift build -c release --package-path Desktop --triple arm64-apple-macosx
+
+      - name: Test desktop Swift app
</file context>

if [ "${{ github.event_name }}" = "pull_request" ]; then
DIFF_BASE="origin/${{ github.base_ref }}"
else
DIFF_BASE="HEAD~1"

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: For push events to main, the diff base is hard-coded to HEAD~1 in both the path gate and the e2e coverage check. On a multi-commit push, this only looks at the last commit, so desktop changes in earlier pushed commits can be missed and the Swift build, tests, and e2e coverage validation will be skipped.

Use github.event.before as the diff base for push events so the full pushed range is evaluated.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At .github/workflows/desktop-swift-ci.yml, line 25:

<comment>For push events to `main`, the diff base is hard-coded to `HEAD~1` in both the path gate and the e2e coverage check. On a multi-commit push, this only looks at the last commit, so desktop changes in earlier pushed commits can be missed and the Swift build, tests, and e2e coverage validation will be skipped.

Use `github.event.before` as the diff base for push events so the full pushed range is evaluated.</comment>

<file context>
@@ -0,0 +1,68 @@
+          if [ "${{ github.event_name }}" = "pull_request" ]; then
+            DIFF_BASE="origin/${{ github.base_ref }}"
+          else
+            DIFF_BASE="HEAD~1"
+          fi
+          FILES=$(git diff --name-only --diff-filter=ACMRD "$DIFF_BASE"...HEAD)
</file context>

@Git-on-my-level Git-on-my-level merged commit 9e7964e into main Jul 7, 2026
7 checks passed
@Git-on-my-level Git-on-my-level deleted the cursor/1eaeca88 branch July 7, 2026 06:36
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants