Back to all articles
ExpoUpgradesReact Native
·5 min read

Expo SDK Upgrades: The Gotchas Nobody Warns You About

A battle-tested field guide to Expo SDK upgrades — what breaks, what quietly changes behavior, and how to test an upgrade without shipping a broken build.

Every Expo SDK upgrade comes with a migration guide. Every Expo SDK upgrade also comes with three things the migration guide doesn't mention. Here's what we've hit across the 52 → 53 → 54 → 55 → 56 cycle.

The category 1 landmine: peer-dep drift

Expo SDK pins React Native to a specific version. React Native pins React. React pins TypeScript's JSX transform. When you bump Expo, the entire pin tree shifts — and whatever non-Expo packages you've added (react-query, zod, react-hook-form) suddenly need minor bumps to stay compatible.

The giveaway: your app builds, runs once, then crashes on a second reload with an opaque useSyncExternalStore error.

The fix, in order:

npx expo install --fix
pnpm up
# Then delete node_modules + lockfile and start over if it still complains

Category 2: behavior changes that aren't in the changelog

These hurt more because your build is green:

  • SDK 54: Keyboard events shifted ~16ms earlier. If you were timing autoscroll to the keyboard show event, it now scrolls before the keyboard is actually visible.
  • SDK 55: The safe-area insets became reactive to orientation changes. Any layout that used useSafeAreaInsets().top in StyleSheet.create (computed once) silently broke on rotation.
  • SDK 56: expo-router's useLocalSearchParams started returning undefined during transitions instead of the previous-route's params. Fine unless you were relying on that.

None of these are in release notes as "breaking." They're "corrected behavior" that is nonetheless a breaking change for your app.

Category 3: native module incompatibilities

Third-party native modules — react-native-mmkv, react-native-reanimated, custom config plugins — lag Expo by a few days to a few weeks. The pattern:

  1. You bump Expo on a Friday.
  2. expo prebuild succeeds.
  3. The build fails in Xcode with a CocoaPods deprecation warning that reads like a fatal error.
  4. You discover the module's main branch already fixed it but the npm release hasn't shipped.

The defensive move: pin any native module that you depend on to a known-good version, and expo install with --fix after pinning.

How to test an upgrade before you ship it

Never merge an SDK upgrade from the same PR that changed anything else. The upgrade itself is the change.

# [!code ++] Clean branch, one responsibility
git checkout -b upgrade/expo-57
npx expo install expo@latest
npx expo install --fix
pnpm ios  # run the golden-path user flows
pnpm android

If your app has a setup checklist (ours does), run the full thing after upgrade. You'll catch 80% of the category-2 stuff inside 20 minutes.

The one thing that will save you an afternoon

Keep a running upgrade log per SDK bump: what broke, what you fixed, what you couldn't figure out. Past-you is your best resource. After three upgrades you'll have a personal field guide that's better than any release notes.


If you want to skip the first round of pain, our starter kit ships with pinned-and-tested versions for every SDK we support, and Evergreen subscribers get the patch notes and diffs the moment a new SDK drops.

Expo SDK Upgrades: The Gotchas Nobody Warns You About - TurboRocket