Skip to content

chore(v6): upgrade to Expo SDK 56#4944

Merged
satya164 merged 16 commits into
callstack:v6from
azizbecha:@azizbecha/chore/expo-sdk-56
May 15, 2026
Merged

chore(v6): upgrade to Expo SDK 56#4944
satya164 merged 16 commits into
callstack:v6from
azizbecha:@azizbecha/chore/expo-sdk-56

Conversation

@azizbecha
Copy link
Copy Markdown
Collaborator

Motivation

  • Example: Expo ~56.0.0-preview.10, RN 0.85.3, React 19.2.3, expo-* aligned via expo install --fix.
  • Core devDeps aligned to match; added @react-native/jest-preset (extracted from RN in 0.85).
  • Deleted example/android / example/ios, gitignored. expo run:* regenerates them via prebuild.
  • Dropped @expo/webpack-config; web served by Metro (config aliases for vector icons + crypto preserved).
  • app.json cleanup (deprecated privacy/packagerOpts/splash/newArchEnabled removed, splash moved into the plugin). expo-doctor 18/18.
  • Fixed deprecations surfaced by RN 0.85 / React 19.2:
    • absoluteFillObjectabsoluteFill
    • Image style.tintColor/resizeMode → props
    • shadow*boxShadow (token still sourced from Palette.primary0)
  • Fixed React 19.2 hydration error in CustomFABControls (nested <button>).
  • Fixed pre-existing typo in DrawerItems (Dynamic Theme row used a JS comma expression instead of a style array).

Test plan

  • yarn typescript, yarn lint, yarn test all green (55 suites / 726 tests / 161 snapshots).
  • cd example && npx expo-doctor → 18/18 ✓.
  • cd example && yarn ios, yarn android, yarn web all boot.
  • All components render correctly on all platforms.

@callstack-bot
Copy link
Copy Markdown

callstack-bot commented May 13, 2026

Hey @azizbecha, thank you for your pull request 🤗. The documentation from this branch can be viewed here.

Copy link
Copy Markdown
Member

@satya164 satya164 left a comment

Choose a reason for hiding this comment

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

Thanks for the PR. I left some comments. Also, please revert any changes that aren't necessary in the library's code.

Comment thread example/app.json Outdated
Comment thread example/metro.config.js Outdated
Comment thread example/metro.config.js
Comment thread example/package.json Outdated
Comment thread example/package.json Outdated
Comment thread src/components/Appbar/AppbarBackIcon.tsx Outdated
Comment thread src/components/Icon.tsx Outdated
Comment thread src/theme/shadow.tsx Outdated
Comment thread example/metro.config.js Outdated
@azizbecha azizbecha added the v6 label May 14, 2026
azizbecha and others added 15 commits May 14, 2026 19:57
Example app:
- expo ^56.0.0-preview.10
- react/react-dom 19.2.3, react-native 0.85.3
- expo-* aligned via 'npx expo install --fix'
- react-native-reanimated 4.3.1, react-native-worklets 0.8.3
- react-native-gesture-handler ~2.31.1, safe-area-context ~5.7.0
- react-native-screens 4.25.0
- babel-preset-expo ~56.0.0, @babel/core ^7.29.0
- app.json: add expo-splash-screen config plugin (now required)

Core (root devDependencies):
- react/react-dom 19.2.3, react-native 0.85.3, react-test-renderer 19.2.3
- @react-native/babel-preset ^0.85.3
- react-native-safe-area-context 5.7.0
- @babel/core ^7.29.0, @babel/runtime ^7.29.0
- add @react-native/jest-preset ^0.85.3 (RN 0.85 moved jest-preset to
  a separate package) and point jest.preset at it

Other fixes required by the new typedefs:
- replace removed StyleSheet.absoluteFillObject with StyleSheet.absoluteFill
  in Modal and TouchableRipple.native
- TeamDetails example: handle 'unspecified' from useColorScheme

v6 needs the newer react-native-reanimated bundled with SDK 56, and v6 is
not shipping imminently, so the SDK 56 preview is acceptable.
Delete example/android/ and example/ios/ so Expo Continuous Native
Generation regenerates them from app.json + config plugins at build
time. The committed Android project was stale at SDK 52 and was the
reason runtimeVersion was pinned to exposdk:52.0.0.

example/ios/ was not tracked in git.

Update example scripts to use --dev-client (Expo Go does not support
the dev-client-only modules and we'll use development builds going
forward).
@expo/webpack-config has been deprecated since Expo SDK 50; Metro is
the supported web bundler going forward.

example/package.json
- remove @expo/webpack-config, file-loader, url-loader, typeface-roboto

example/webpack.config.js — deleted

example/metro.config.js
- port the web-only aliases from the old webpack config via
  resolver.resolveRequest:
  - @react-native-vector-icons/material-design-icons -> @expo/vector-icons
  - crypto -> expo-crypto

example/index.web.js
- call registerRootComponent so Metro web actually mounts the app
  (webpack used to bootstrap this implicitly)

example/public/index.html
- remove the static <script src="app.bundle.js"> tag (Metro injects
  its own bundle URL)
- load Roboto from Google Fonts CDN

example/assets/styles/fonts.css
- map the legacy 'Roboto-<Weight>' family names to the CDN-loaded
  Roboto via local() so the existing app code keeps working
- runtimeVersion: switch from the hardcoded 'exposdk:52.0.0' (which was
  pinned to the deleted Android project) to { policy: 'sdkVersion' } so
  EAS Update tracks the installed SDK automatically.
- newArchEnabled: removed; new architecture has been the default since
  Expo SDK 53.
app.json
- remove deprecated fields: privacy, packagerOpts, splash
- migrate splash settings into the expo-splash-screen plugin entry

metro.config.js
- inline monorepo setup (drop react-native-monorepo-config); append
  to Expo's default watchFolders instead of replacing them, which fixes
  the expo-doctor "watchFolders does not contain all entries from
  Expo's defaults" check
- use the canonical 'expo/metro-config' entry

package.json
- remove react-native-monorepo-config (no longer needed)

expo-doctor: 18/18 checks pass.
Once we delete the committed ios/android folders and rely on
'expo run:*' to prebuild them locally, EAS Update treats the resulting
build as bare-workflow and rejects policy-style runtimeVersion values
at startup ("You're currently using the bare workflow, where runtime
version policies are not supported"). Set it to the literal "56.0.0"
to match the installed SDK.

Also add the CNG-generated /android and /ios paths to .gitignore so
they're not accidentally committed, which also clears the related
expo-doctor warning about app.json fields not being synced when
native folders are present.
The outer TouchableOpacity (from react-native-gesture-handler) rendered
a <button> on web because of accessibilityRole='button'. Inside it,
Paper's RadioButton also renders a <button>. Under React 19.2 this
turns from a tolerated warning into a hard hydration error
("<button> cannot contain a nested <button>").

Drop the redundant accessibilityRole on the outer TouchableOpacity;
its Pressable semantics are enough and RadioButton remains the
announced button.
React Native deprecates the style-form of these properties on Image:
"Image: style.resizeMode is deprecated. Please use props.resizeMode."
"Image: style.tintColor is deprecated. Please use props.tintColor."

- Icon (image source variant): tintColor / resizeMode lifted out of the
  style array onto the <Image> props.
- AppbarBackIcon (iOS back chevron): same migration; drop the now-empty
  styles.icon entry.

Snapshot in Appbar.test.tsx updated to reflect the new prop placement.
The Use Dynamic Theme row in the Preferences drawer section had
style={(styles.preference, styles.v3Preference)} — a JS comma
expression that evaluates to only styles.v3Preference. That dropped
the row's flexDirection: 'row' / justifyContent: 'space-between'
layout, so the trailing Switch overflowed the drawer on Android.

Match the array form used by every other preference row:
style={[styles.preference, styles.v3Preference]}.
Reapply the policy form (originally introduced in 5454f04 and reverted
in facf497). 'expo prebuild' resolves it at native-build time and
writes the literal 'exposdk:56.0.0' to ios Expo.plist (and the Android
equivalent), so EAS Update sees a literal string at runtime — there's
no bare-workflow rejection.

The earlier failure was from a stale build that hadn't re-prebuilt
after the policy was first applied.
Track the latest SDK 56 preview tag.
Per review: drop android:native, ios:native, and web. Replace
android/ios start variants with the run: form so they prebuild
and build natively. Web can be opened by pressing w in the terminal
during expo start.
Per review: Expo SDK 56 resolves
@react-native-vector-icons/material-design-icons directly, so the
@expo/vector-icons shim and the metro resolver alias are unnecessary.

- Replace four example imports of
  '@expo/vector-icons/MaterialCommunityIcons' with
  '@react-native-vector-icons/material-design-icons'.
- Drop @expo/vector-icons from example/package.json.
- Remove the resolver.resolveRequest web-aliases block (vector-icons
  and crypto) from example/metro.config.js. The metro config now only
  carries the monorepo-specific setup.
@azizbecha azizbecha force-pushed the @azizbecha/chore/expo-sdk-56 branch from 3f122bb to 0ca6967 Compare May 14, 2026 18:58
Copy link
Copy Markdown
Member

@satya164 satya164 left a comment

Choose a reason for hiding this comment

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

thank you

@satya164 satya164 merged commit f5b5d75 into callstack:v6 May 15, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants