Skip to content

[Bug]: macOS control is cancelled near its 30-minute limit in full dispatch CI #4905

Closed

Description

@luvs01

Client or integration

Other

GitHub Actions — the macos-control job (macos control) in .github/workflows/ci.yml, not an installed client or a provider request.

Area

Platform (Windows / macOS / Linux)

Summary

The unsharded macOS control job does not produce a completed suite result in the reviewed full workflow_dispatch run: it is cancelled approximately 30 minutes after starting while test output is still being produced. The workflow configures timeout-minutes: 30 for this job. In the reviewed run, every other job succeeded, but the final ci aggregate failed.

This is a concrete CI reliability/evidence problem worth investigating. It is not a claim that every dispatch must fail, that normal pull-request runs execute this job, or that increasing the timeout alone is a proven fix. The record does not establish the suite's healthy full-run duration or rule out slow tests, process-lifecycle problems, or runner contention.

Expected behavior: the deliberately unsharded control should finish with a usable pass/fail result within an evidence-based, bounded budget. Genuine assertion failures and runtime crashes must remain failures; a green sharded run is not proof that the whole-pool control would pass.

Reproduction

  1. Inspect full dispatch run 35217283983, from luvs01/opencodex at commit aa67f23ac9bceeef5728ba23ffaa71e3b84dec6b on agent/reauth-cancellation-upstream-20260914. Its recorded event is workflow_dispatch.

  2. Open macos control, job 105188784487. Checkout, Bun setup, dependency installation, and GUI build succeeded. The Test step was cancelled and the subsequent CLI help smoke step was skipped.

  3. The control invokes the entire test tree without a shard argument:

    bun test --isolate --timeout 60000 tests
  4. Runner startup was 2026-09-17T11:55:44.8544970Z; cancellation was 2026-09-17T12:26:01.9485140Z (about 30 minutes 17 seconds). Test-file output continues immediately before cancellation, without a completed top-level suite result.

  5. Both macOS shards, all four Linux test shards, all nine Windows shards, and the other non-aggregate jobs succeeded. ci, job 105206728471, failed at Assert every job this event requested succeeded.

For a fresh reproduction, dispatch this recorded revision with lane=all and retain the control log and job annotations. Avoid a concurrent run on the same ref: the workflow also uses cancel-in-progress: true, so distinguish timeout from concurrency cancellation instead of inferring the cause from cancelled alone. No new CI run was launched for this issue-body review.

Version

Source checkout aa67f23ac9bceeef5728ba23ffaa71e3b84dec6b in luvs01/opencodex, run 35217283983, 2026-09-17. The job reports Bun 1.4.0 (34cbb9a40). This concerns repository CI, not an installed npm release.

Operating system

GitHub-hosted macos-latest; the reviewed job reports macOS 26.6.2 (build 25G83), runner image macos-26-arm64, image version 20260907.0351.1.

Provider and model

Not provider-specific — this is the repository's local Bun test suite in GitHub Actions. No model selection or account login is needed to identify this CI failure.

Logs or error output

2026-09-17T11:55:44.8544970Z Current runner version: '2.337.0'
2026-09-17T11:56:12.8117010Z bun test v1.4.0 (34cbb9a40)
...
2026-09-17T12:25:53.2421000Z ##[group]tests/routing/subagent-roster-retention.test.ts:
2026-09-17T12:26:01.9485140Z ##[error]The operation was canceled.

Observed conclusions: macos control = cancelled, Test = cancelled, CLI help smoke = skipped, aggregate ci = failure. The last printed test-file name is a location in the truncated log, not evidence that this file caused the problem.

Screenshots and supporting files

Primary evidence is the directly reviewed run and job logs above. The original report also linked fork run 35217224106, fork dev run 35214566277, and upstream run 35210400258 as additional occurrences. These remain comparison references, not proof that every other job passed in each run or that all cancellations share one cause.

Related: #3497 deliberately retained the unsharded whole-pool control when introducing sharded macOS jobs. This report concerns obtaining a completed result from that control, not removing its coverage. #4901 addresses separate Windows evidence/test-runner problems.

Redacted configuration

Relevant settings in the upstream CI workflow:

macos-control:
  name: macos control
  needs: changes
  if: github.event_name == 'workflow_dispatch'
  runs-on: macos-latest
  timeout-minutes: 30

The 30-minute budget covers the whole job, including setup/build, and differs from Bun's --timeout 60000 per-test limit. Pin workflow revisions and Bun versions when comparing runs; current branch contents may differ from the recorded revision.

Suggested investigation and acceptance criteria

  • Confirm the cancellation reason from Actions job annotations and compare completed control runs at pinned revisions, including setup time and runner/Bun versions. Identify slow or stalled tests before choosing a larger budget; this report does not establish a specific replacement timeout.
  • Preserve the unsharded whole-pool purpose and failure semantics. Sharding this control or making it non-blocking is not an equivalent fix and is not requested here.
  • Demonstrate a completed full-control result with the correction, retain genuine failures, and verify that the aggregate still rejects failed or cancelled required work. Do not weaken assertions or per-test deadlines merely to obtain a green run.

Checks

  • I searched existing issues and documentation.
  • I removed secrets, tokens, account details, request credentials, and personal data.

Activity

  1. added
    platformOS/service/tray/ACL (Windows-heavy, not Windows-only)
    on Sep 17, 2026
  2. github-actions commented on Sep 17, 2026

    @github-actions
    Contributor

    Issue reopened

    The report now contains the information required by the automated check. Thanks for updating it.

  3. changed the title [-]CI: macos control 30-minute cap cancels every workflow_dispatch run — full-suite signal can never go green[/-] [+][Bug]: macOS control is cancelled near its 30-minute limit in full dispatch CI[/+] on Sep 17, 2026
  4. added
    bugSomething isn't working
    account-poolOAuth, credentials, Codex pool, quota, failover, plans
    on Sep 17, 2026
  5. lidge-jun commented on Sep 17, 2026

    @lidge-jun
    Owner

    리뷰 · 우선순위 66 / 80

    이 이슈는 지금 dev HEAD fa26404d7(패키지 2.58.0, tip #4861) 기준 CI 워크플로에서, workflow_dispatch 전용 비샤드 macos-control 잡이 약 30분 만에 cancelled 되어 전체 suite 합격/불합격을 남기지 못하는 문제를 보고한다. 클라이언트·프로바이더 버그가 아니라 GitHub Actions evidence 신뢰성 문제다. 작성자가 포크 full dispatch run 35217283983의 macos control job을 직접 읽어, setup/GUI build까지는 성공하고 Test 단계가 취소되며 CLI help smoke가 skip된 기록을 남겼다. 같은 런에서 macOS 샤드·Linux 4샤드·Windows 9샤드 등은 성공했는데 aggregate ci만 실패했다.

    현재 upstream .github/workflows/ci.yml에도 macos-control job의 timeout-minutes: 30이 그대로 있다. 이 30분은 Bun --timeout 60000(테스트당)과 다르고, checkout·Bun 설치·의존성·GUI build까지 포함한 잡 전체 예산이다. #3497이 샤드 도입 때 일부러 전체 풀 control을 남긴 목적이므로, 샤드로 쪼개거나 non-blocking으로 바꾸는 것은 이 이슈가 원하는 수정이 아니다. #4901은 Windows evidence/runner 쪽 별건이다.

    보고 품질은 높다. cancel-in-progress concurrency와 timeout을 구분하라고 적었고, timeout만 올리는 것이 검증된 수정이라고 주장하지 않는다. 건강한 full-control 소요 시간도 아직 없다고 명시했다. 라벨은 bug/platform과 함께 account-pool이 붙어 있는데, 본문 내용은 OAuth/풀이 아니라 CI 잡 예산·러너 문제라서 라벨이 다소 어긋날 수 있다(라벨은 바꾸지 않는다).

    릴리스 트레인(2.58.0) 규칙상 hosted CI exact SHA만 게이트이고, cancelled job은 pass/fail이 아니다. 그래서 control이 cancelled로 끝나면 aggregate가 실패하는 현재 동작은 “증거가 없다”를 올바르게 반영한다. 다만 dispatch lane을 evidence로 쓰는 기여자·메인테이너에게는 반복 비용이 크다. PR #4910 본문도 같은 macos-control 30분 취소를 알려진 한계로 언급한다.

    다음 조사는 (1) Actions annotation으로 cancel 원인 확정, (2) 핀된 리비전에서 완료된 control 런과 setup 시간·Bun/러너 버전 비교, (3) 느린/멈춘 테스트를 예산 확대보다 먼저 찾는 순서여야 한다. 어서션·테스트당 timeout을 약화해 초록만 만드는 수정은 안 된다.

    .github/workflows/ci.yml macos-control - timeout-minutes: 30이 잡 전체 예산. Bun per-test 60s와 혼동하면 안 된다.
    aggregate ci job - cancelled control을 실패로 취급하는 현재 의미는 유지해야 한다(증거 없음 ≠ 통과).
    #3497 - 비샤드 control 목적 유지. 샤드화/non-blocking은 동등 수정이 아니다.
    label account-pool - 본문과 영역이 어긋날 수 있음. 플랫폼/CI 조사가 본체다.
    reproduction - cancel-in-progress:true 때문에 동시 런과 timeout을 구분해야 한다.

    메인테이너의 판단이 필요한 지점

    • 예산을 늘리기 전에 slow-test 목록을 뽑을지, 측정된 p95 기준으로만 timeout을 조정할지
    • macos-control을 2.58.0 열차의 필수 evidence로 둘지, dispatch 보조 신호로만 둘지
    • GUI build를 control 잡에서 빼 예산을 테스트에 돌려도 되는지(커버리지 의미 변경)

    너의 추천
    열린 버그로 두고, 핀된 SHA에서 control 완료 런·취소 런을 나란히 비교한 뒤 slow test를 먼저 고친다. timeout 상향은 측정값 다음에만 검토한다. 샤드화나 aggregate에서 control 무시로 초록을 만들지는 않는다.

    이 댓글은 grok-bot이 작성했습니다

  6. luvs01 commented on Sep 17, 2026

    @luvs01
    CollaboratorAuthor

    Author follow-up with the timing breakdown the review asked for.

    Cancelled macos control job, fork run 35217283983 (job 105188784487):

    Step Duration Result
    Set up job ~1s success
    Checkout 9s success
    Setup project Bun 4s success
    Install dependencies 2s success
    Build GUI 12s success
    Test 29m49s cancelled at the cap
    CLI help smoke — skipped (never reached)

    Job total: 11:55:43 → 12:26:09 UTC (~30m26s), matching timeout-minutes: 30.

    Findings:

    • The cancel cause is the job-level timeout-minutes cap, not concurrency cancel-in-progress — every other lane in the same run completed successfully, and the control job itself ran to ~30.4 minutes.
    • It is also not a hang: the Test step was still completing cases seconds before cancellation (last (pass) at 12:25:10, cancel at 12:26:01).
    • Setup + dependency + GUI build overhead is only ~29 seconds, so essentially the entire 30-minute budget is consumed by the unsharded test suite itself. The suite simply needs more than ~29.8 minutes on this runner class.
    • CLI help smoke never executes on this path, so the control currently provides no smoke signal either.
    • No completed macos control run exists in recent fork dispatch history to establish a healthy duration; upstream pull_request runs do not include this job, so there is no green baseline timing to compare against.

    This supports the review's ordering: the missing evidence is a measured completion time (or a slow-test list), not a budget bump. If a longer temporary cap on a pinned revision is acceptable as a measurement probe, a one-off dispatch with e.g. timeout-minutes: 90 on a fork branch would produce the healthy-duration figure without changing the committed workflow — happy to run that if it helps.

  7. luvs01 commented on Sep 17, 2026

    @luvs01
    CollaboratorAuthor

    Follow-up on the macos control lane: the 30-minute workflow cap is confirmed as the cancel source (job cancelled at 29m49s inside the Test step while still passing). Posting this as a write-path check after CreatePullRequest started returning FORBIDDEN for this account — if this comment lands, existing-resource writes still work while new-resource creation is blocked.

  8. lidge-jun commented on Sep 18, 2026

    @lidge-jun
    Owner

    Fixed on dev by #5028, squashed as 89b7d880d91f31ea0e40924090859f8c4d45713c. The budget is now 75 minutes.

    The number is measured, not chosen. An authorized one-off measurement let this lane finish for the first time: Test step 23:13:17Z to 00:03:56Z, 50 minutes 39 seconds wall, Bun reporting 3034.18s across 26526 tests in 1343 files, exiting on its own rather than being killed. So the completed duration is roughly fifty minutes against a thirty-minute budget, and 75 leaves about twenty-four minutes of growth room.

    What that means for the history here: every cancellation attributed to runner capacity was a job slightly past halfway. This lane had never once completed, so nothing it might have reported had ever been reachable.

    Two things this does not do, stated so they are not assumed.

    It does not fix anything the lane reports. The first complete run surfaced four tests exceeding their own timeouts under shared-process pressure — web-search heartbeat retry at 6233ms against 5000, image non-droppable at 60323 against 60000, imageTierBias at 91516 against 60000, and provider-option ownership spine at 31801 against 30000. Those are #4997 and remain open. Raising this budget is what made them observable.

    It does not resolve the separate class in #4956, where sharded macOS legs go silent for sixteen to eighteen minutes and spawned children produce nothing and never exit. That is a hang rather than a long run, and the two must not be conflated.

    Sharding this lane was considered and rejected: it is the only place the whole suite runs in one process, so it is the only oracle for cross-file ordering pressure — which is a strange thing to delete in the same round where order-dependent hangs are the open question.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    account-poolOAuth, credentials, Codex pool, quota, failover, plansbugSomething isn't workingplatformOS/service/tray/ACL (Windows-heavy, not Windows-only)

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions