Files
filip131311 18974cab93 fix(release): ship ax-service in bin/darwin/ so describe works in published packages (#303)
## Summary

`describe` is broken in every published package since **0.9.0**: on a
normally-booted simulator it returns only a bare `ROOT AXGroup` (empty
tree) or silently falls back to native-devtools, always accompanied by
the misleading hint *"this simulator was not booted through argent …
call boot-device with force=true"* — even right after a forced argent
boot, so there is no recovery.

**Root cause:** the published npm package is **missing the `ax-service`
binary** entirely.

## Bisect

| Release | `ax-service` in tarball | `describe` |
|---|---|---|
| 0.7.1 | `bin/ax-service` (flat) ✅ | works |
| 0.8.1 | `bin/ax-service` (flat) ✅ | works |
| **0.9.0** | **absent** ❌ | **broken** |
| 0.10.0 | **absent** ❌ | **broken** |

- **Last good release:** 0.8.1
- **First broken release:** 0.9.0
- **Breaking commit:** `80661fad` — *feat: Linux support (#249)*

## Why it broke

#249 migrated native binaries to a per-platform `bin/<platform>/` layout
and updated **two of the three** places that touch the ax-service path:

- `packages/native-devtools-ios/src/index.ts` — `axServiceBinaryPath()`
now resolves `bin/darwin/ax-service` (was flat `bin/ax-service`).
- `packages/argent/scripts/bundle-tools.cjs` — copies the published
binary **from** `bin/darwin/ax-service`.

…but it **did not** update `scripts/download-native-binaries.sh` — the
script the standard `pack` / CI release path runs — which kept
downloading ax-service to the **flat `bin/` root**.

Producer (download script) and consumer (bundler/resolver) disagreed.
During `pack`, the bundler looked under `bin/darwin/`, found nothing,
**warned and skipped the copy**, and the tarball shipped with no
ax-service. At runtime the ax-service factory throws *(binary not
found)* → `describe` catches it → empty tree + degraded hint →
native-devtools fallback (which itself fails on plain screens like
SpringBoard).

`pack:mcp:local` (which runs `build:ios-binaries` → `build.sh`, already
writing to `bin/darwin/`) was unaffected — only released/downloaded
builds were broken, which is why it wasn't caught locally.

## Fix

`download-native-binaries.sh` now downloads ax-service into
`bin/darwin/`, matching the resolver and the bundler. Plus a regression
test (`package-manifest.test.ts`) that pins the producer→consumer path
agreement so the two scripts can't silently drift again (verified it
fails on the pre-fix path and passes after).

## Verification

Rebuilt via **`npm run pack:mcp`** → tarball now contains
`package/bin/darwin/ax-service` (byte-identical, signed Mach-O). Drove
the **packaged** binary's `describe` RPC directly and via the full MCP
`describe` tool:

- iPhone 17 Pro — iOS 26.4 → `source: ax-service`, full tree (32
elements), no degraded hint ✅
- iPhone Air — iOS 26.4 → `source: ax-service`, full tree ✅
- iPhone 16 Pro — iOS 18.5 → `source: ax-service`, full tree (33
elements) ✅

Before the fix all three returned a bare `ROOT AXGroup` (or
native-devtools fallback) + the degraded hint.

Tests: `packages/tool-server` ax-service/describe suites (40) green;
`packages/argent` suite (12, incl. new guard) green.

## Notes
- Script-only change to release tooling + one test; no runtime TS
changes. The bundled `bin/` artifacts are gitignored (produced by
`pack`), so the diff is just the script and the test.
- Independent of `fix/boot-device-refresh-stale-services` (stale-service
eviction after reboot) — that fix can't help while the binary is absent
from the package; both are needed for fully healthy `describe`.
2026-06-03 22:28:22 +02:00
..
2026-06-03 15:57:42 +02:00