Skip to content

test(expo): send uncommitted changes to a borrowed device and start it from a kept native build - #10230

Closed
mikepitre wants to merge 7 commits into
mike/expo-verify-parity-skillfrom
mike/expo-verify-port-sessions
Closed

mikepitre wants to merge 7 commits into
mike/expo-verify-parity-skillfrom
mike/expo-verify-port-sessions

Conversation

@mikepitre

@mikepitre mikepitre commented Oct 14, 2026 •

Copy link
Copy Markdown
Contributor

Description

This PR sits on #10228 and must merge after it. It brings the Expo borrowed device level with four clerk-ios changes: clerk/clerk-ios#695, #698, #700 and #701.

An agent with no Mac or no emulator borrows a device on a GitHub Actions runner. Before this PR, every change cost a commit, a push and a session build, and every session built the test app natively, about 21 minutes on iOS. After it:

  • up and run send uncommitted changes to the app sources as one patch. The session applies it over a clean checkout of the commit and builds. A run on such a build is not tied to a commit, so attach refuses it.
  • Before its agent starts, a session downloads the native builds that the newest Verify end-to-end tests runs of the same branch kept, each named by its native fingerprint. When one matches the tree, up only exports the JS and puts it in that app. A JS-only patch does the same. A patch to a native input changes the fingerprint, and the session builds natively.
  • From clerk-ios's cold-run fixes: the fallback screenshot of a borrowed device stays out of the checkout, attach fills an empty pair of evidence markers, and doctor checks that gh can use the GraphQL API.

The commits are separate, so the stack can be regrouped. The first copies the shared files byte for byte from clerk-ios main and adds the Expo glue. The session device names the paths a patch may change, and the workflow passes the default branch, on which the session refuses every patch. The second fixes a stale build that the patch would expose. The session's native project was keyed on the native inputs at HEAD, so a patch to a native input kept the old project. The third and fifth are the kept native build. The fifth replaces the third's install before the agent, which took too long on a Mac runner, with a download by name. The fourth and sixth are the skill text, and the last gives a test a git identity.

What is different from clerk-ios, and why:

  • clerk-ios stores its app in the Actions cache from a job on main. Expo already stores native builds as artifacts from its device suite, so the session reuses that store and its rule, which takes a build only from a run of the same branch of this repository. The fetch moved into bin/fetch-native-build.sh so both workflows apply the same rule.
  • The session cannot fetch inside its build, because the agent removes the GitHub token before it runs build commands that a patch can change. It cannot learn its fingerprint before the agent starts without installing the workspace and the fixture first. So it downloads up to three kept builds by name and lets the build pick.
  • A session stores no native build. Artifacts of this repository are public, and the shared contract test allows a session one upload, the evidence. So a branch with no device suite run builds natively once per session.
  • chore(clerk-react,shared): Eliminate missing frontendApi error message #701 restores build state in every session. Expo stores none. The repository's Actions cache is at its 10 GB limit, and expo prebuild --clean removes the iOS build directory anyway. A patch to a native input therefore builds natively from nothing.

Measured on three sessions of this branch, one run each. An iOS up that took the kept native build was ready in 1069 s; the native build it skipped took 676 s in the same session. Its limiter is now pnpm install and turbo build on a cold Mac, 580 s. An Android up was ready in 178 s with the kept build and in 672 s without one. A JS-only uncommitted change reached a spec in 64 s on iOS and 28 s on Android. An uncommitted change to a native Swift file built natively in 716 s on iOS. attach refused the patched run with EVIDENCE_UNSAFE. The device suite passed on both platforms at the head.

Not proven: a patch that does not apply, on a real runner (unit tests only); an Android session after a native patch. A kept build is found only while no Expo package with native code has been published since the device suite run, because the fixture resolves expo by a range with no lockfile.

The changeset is empty, as in the other PRs of the stack.

Checklist

  • pnpm test runs as expected.
  • pnpm build runs as expected.
  • (If applicable) JSDoc comments have been added or updated for any package exports
  • (If applicable) Documentation has been updated

Type of change

  • 🐛 Bug fix
  • 🌟 New feature
  • 🔨 Breaking change
  • 📖 Refactoring / dependency upgrade / documentation
  • other:

🤖 Generated with Claude Code

mikepitre and others added 4 commits October 14, 2026 11:27
…-ios

Copy the shared files from clerk/clerk-ios main (1ac144cb8): a remote
run sends the uncommitted changes to the build inputs as a patch, the
session applies it over a clean checkout and builds, and attach refuses
a run on such a build. The same copy brings three fixes from a cloud
agent's cold run: the fallback screenshot of a borrowed device stays out
of the checkout, attach fills an empty pair of evidence markers, and
doctor checks that gh can use the GraphQL API.

The Expo session device names the paths a patch may change (the
standalone build inputs, which the CLI sends), and the session workflow
passes the default branch, on which the agent refuses every patch.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…changes a native input

A remote session builds with a key for the native project. The key
hashed the native inputs at HEAD, so after the session applied
uncommitted changes to a native input it kept the old project and
skipped expo prebuild. The key now hashes the files as they are on
disk, tracked or not, the same way the native fingerprint reads them.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… the commit

A session built the test app natively on every up, about 21 minutes on
iOS. Before its agent starts, the session now names the native build by
the fingerprint, takes the newest artifact a run of the same branch kept
under that name, and points VERIFY_NATIVE_CACHE at it. The build then
exports the JS and embeds it in that app, and runs no expo prebuild,
xcodebuild or Gradle. With no kept build it builds natively as before.
Uncommitted JS changes sent to the session take the same path; a change
to a native input changes the fingerprint and builds natively.

The fetch moves into bin/fetch-native-build.sh so the device suite and
the session take a kept build by one rule. A session stores no native
build: the artifacts of this repository are public, and the shared
contract test allows a session one upload, the evidence.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…pt native builds

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@changeset-bot

changeset-bot Bot commented Oct 14, 2026 •

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 1f33517

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 0 packages

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercel Bot commented Oct 14, 2026 •

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
clerk-js-sandbox Ready Ready Preview Oct 14, 2026 4:39pm UTC
swingset Ready Ready Preview Oct 14, 2026 4:39pm UTC

Request Review

@coderabbitai

coderabbitai Bot commented Oct 14, 2026

Copy link
Copy Markdown
Contributor

Important

Draft PR not reviewed

Draft PRs are not automatically reviewed by default.

  • Trigger a manual review

To automatically review draft PRs, update your CodeRabbit configuration:

reviews:
  auto_review:
    drafts: true
  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Comment @coderabbitai help to get the list of available commands.

mikepitre and others added 2 commits October 14, 2026 11:54
…l, not after it

The previous commit installed the workspace and the fixture before the
session agent started, to learn the fingerprint. On a macos-26 runner
that install took 631 seconds in the device suite, and the tunnel step
that runs after it must come up within the 20 minutes up waits. The
build cannot fetch for itself, because the agent removes GITHUB_TOKEN
before it runs build commands that a patch may change.

The session now downloads the native builds of its platform that the
newest device suite runs of the same branch kept, at most three, each
under the fingerprint in its name, and starts the agent at once. The
build uses one only when its own fingerprint matches.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…t it saves

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@pkg-pr-new

pkg-pr-new Bot commented Oct 14, 2026 •

Copy link
Copy Markdown

Open in StackBlitz

@clerk/astro

npm i https://pkg.pr.new/@clerk/astro@10230

@clerk/backend

npm i https://pkg.pr.new/@clerk/backend@10230

@clerk/chrome-extension

npm i https://pkg.pr.new/@clerk/chrome-extension@10230

@clerk/clerk-js

npm i https://pkg.pr.new/@clerk/clerk-js@10230

@clerk/electron

npm i https://pkg.pr.new/@clerk/electron@10230

@clerk/electron-passkeys

npm i https://pkg.pr.new/@clerk/electron-passkeys@10230

@clerk/eslint-plugin

npm i https://pkg.pr.new/@clerk/eslint-plugin@10230

@clerk/expo

npm i https://pkg.pr.new/@clerk/expo@10230

@clerk/expo-biometrics

npm i https://pkg.pr.new/@clerk/expo-biometrics@10230

@clerk/expo-google-signin

npm i https://pkg.pr.new/@clerk/expo-google-signin@10230

@clerk/expo-native-components

npm i https://pkg.pr.new/@clerk/expo-native-components@10230

@clerk/expo-passkeys

npm i https://pkg.pr.new/@clerk/expo-passkeys@10230

@clerk/express

npm i https://pkg.pr.new/@clerk/express@10230

@clerk/fastify

npm i https://pkg.pr.new/@clerk/fastify@10230

@clerk/hono

npm i https://pkg.pr.new/@clerk/hono@10230

@clerk/localizations

npm i https://pkg.pr.new/@clerk/localizations@10230

@clerk/mosaic

npm i https://pkg.pr.new/@clerk/mosaic@10230

@clerk/nextjs

npm i https://pkg.pr.new/@clerk/nextjs@10230

@clerk/nuxt

npm i https://pkg.pr.new/@clerk/nuxt@10230

@clerk/react

npm i https://pkg.pr.new/@clerk/react@10230

@clerk/react-router

npm i https://pkg.pr.new/@clerk/react-router@10230

@clerk/shared

npm i https://pkg.pr.new/@clerk/shared@10230

@clerk/tanstack-react-start

npm i https://pkg.pr.new/@clerk/tanstack-react-start@10230

@clerk/testing

npm i https://pkg.pr.new/@clerk/testing@10230

@clerk/ui

npm i https://pkg.pr.new/@clerk/ui@10230

@clerk/upgrade

npm i https://pkg.pr.new/@clerk/upgrade@10230

@clerk/vue

npm i https://pkg.pr.new/@clerk/vue@10230

commit: 1f33517

The test committed with the machine's git identity, which a Linux CI
runner does not have, so the commit failed there. It now passes the
author on the command line, as the other tests in this package do.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@mikepitre

Copy link
Copy Markdown
Contributor Author

Replaced by the regrouped stack #10235, #10236, #10237 and #10238, which ends on the same code (tree c2fc7c19). The old stack grew one PR per port from clerk-ios and clerk-android; the new one groups what a reviewer reads together.

@mikepitre mikepitre closed this Oct 14, 2026

This branch was successfully deployed

2 active deployments
Preview – swingset — 1f335171 Deployed Oct 14, 2026 by vercel[bot]
Preview – clerk-js-sandbox — 1f335171 Deployed Oct 14, 2026 by vercel[bot]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant