DEV Community

Dainy Jose
Dainy Jose

Posted on

Android System Back Button Closes the App After Upgrading to Target SDK 36 — React Native Fix

If you're maintaining a React Native Android application and recently upgraded your project to target SDK 36 (Android 16), you may encounter an unexpected navigation issue:

Pressing the Android system back button closes the app instead of navigating to the previous screen.

This can be particularly confusing when React Navigation is already configured correctly and the same navigation flow works perfectly on older Android target SDK versions.

This article explains what changed, how to identify the issue, the workaround I used, and what you should consider for a proper Android 16 migration.


The Problem

After upgrading the Android project from an older target SDK to:

targetSdkVersion = 36
Enter fullscreen mode Exit fullscreen mode

the app started behaving differently when using the Android system back button.

For example, suppose the navigation stack is:

Home
  ↓
Products
  ↓
Product Details
Enter fullscreen mode Exit fullscreen mode

When the user presses the Android system back button from Product Details, the expected behavior is:

Product Details
        ↓
    Products
Enter fullscreen mode Exit fullscreen mode

Instead, the application could close.

Interestingly, navigation using React Navigation itself continued to work:

navigation.goBack();
Enter fullscreen mode Exit fullscreen mode

The issue was specifically related to the Android system back event.


Environment

The issue was observed in a React Native application with a setup similar to:

React Native
React Navigation
Android SDK 36
Target SDK 36
Enter fullscreen mode Exit fullscreen mode

The important change was upgrading the Android target SDK to API level 36, corresponding to Android 16.


Why Does This Happen?

The important part of the migration is the Android back-navigation change.

Android has been moving away from the older:

onBackPressed()
Enter fullscreen mode Exit fullscreen mode

mechanism toward the newer:

OnBackInvokedDispatcher
Enter fullscreen mode Exit fullscreen mode

and predictive back navigation APIs.

With newer Android versions and target SDK requirements, applications need to properly participate in the newer back-navigation system.

This can expose compatibility issues in applications or libraries that still rely on the older back handling mechanism.

In a React Native application, the Android system back event eventually needs to be correctly propagated into the React Native / React Navigation layer.

If that doesn't happen, Android may interpret the back action as:

No navigation handler
        ↓
Finish current Activity
        ↓
App closes
Enter fullscreen mode Exit fullscreen mode

instead of:

System Back
     ↓
React Native Back Handler
     ↓
React Navigation
     ↓
Previous screen
Enter fullscreen mode Exit fullscreen mode

How I Identified the Problem

The first thing I checked was whether React Navigation itself was working.

Navigation from the application was working correctly:

navigation.navigate("ProductDetails");
Enter fullscreen mode Exit fullscreen mode

and programmatic back navigation also worked:

navigation.goBack();
Enter fullscreen mode Exit fullscreen mode

The problem only occurred when pressing the physical/system Android back button.

I also checked whether the application was closing directly from the Home screen.

That behavior is expected:

Home
 ↓
Android Back
 ↓
App exits
Enter fullscreen mode Exit fullscreen mode

The actual problem was:

Home
 ↓
Product List
 ↓
Product Details
 ↓
Android Back
 ↓
App exits ❌
Enter fullscreen mode Exit fullscreen mode

instead of:

Home
 ↓
Product List
 ↓
Product Details
 ↓
Android Back
 ↓
Product List ✅
Enter fullscreen mode Exit fullscreen mode

This distinction is important when debugging Android back navigation.


The AndroidManifest Configuration

The Android application can control the behavior of the newer back system using:

android:enableOnBackInvokedCallback
Enter fullscreen mode Exit fullscreen mode

For example:

<application
    android:name=".MainApplication"
    android:label="@string/app_name"
    android:icon="@mipmap/ic_launcher"
    android:enableOnBackInvokedCallback="false">
Enter fullscreen mode Exit fullscreen mode

In my case, setting:

android:enableOnBackInvokedCallback="false"
Enter fullscreen mode Exit fullscreen mode

worked as a temporary workaround.

After adding this configuration, the Android system back button once again started navigating to the previous React Navigation screen instead of immediately closing the application.


Why Does false Work?

Setting:

android:enableOnBackInvokedCallback="false"
Enter fullscreen mode Exit fullscreen mode

essentially disables the application's participation in the newer OnBackInvokedDispatcher behavior.

This allows the application to continue using the older back handling path.

Conceptually:

Without the workaround

Android System Back
        ↓
OnBackInvokedDispatcher
        ↓
React Native / Navigation handler
        ↓
❌ Handler not properly triggered
        ↓
Activity finishes
        ↓
App closes
Enter fullscreen mode Exit fullscreen mode

With the temporary workaround

Android System Back
        ↓
Legacy back handling
        ↓
React Native BackHandler
        ↓
React Navigation
        ↓
Previous screen
Enter fullscreen mode Exit fullscreen mode

So the workaround doesn't really "fix" predictive back support.

It tells Android to avoid the newer callback behavior for this application.


Is enableOnBackInvokedCallback="false" the Permanent Fix?

Not necessarily.

This is an important distinction.

If your application is targeting Android 16, you should ideally investigate whether your React Native version and navigation dependencies properly support Android's newer back-navigation behavior.

Using:

android:enableOnBackInvokedCallback="false"
Enter fullscreen mode Exit fullscreen mode

can be useful as a compatibility workaround while migrating, but it should not automatically be considered the final Android 16 solution.

The long-term goal should be:

Android 16
      ↓
Predictive Back
      ↓
OnBackInvokedDispatcher
      ↓
React Native
      ↓
React Navigation
Enter fullscreen mode Exit fullscreen mode

working correctly.


Check Your React Native Version

Before adding application-level workarounds, check the React Native version:

npm list react-native
Enter fullscreen mode Exit fullscreen mode

or:

yarn why react-native
Enter fullscreen mode Exit fullscreen mode

Also check React Navigation:

npm list @react-navigation/native
Enter fullscreen mode Exit fullscreen mode

For example:

react-native
@react-navigation/native
@react-navigation/native-stack
@react-navigation/bottom-tabs
Enter fullscreen mode Exit fullscreen mode

Older combinations may have different levels of Android predictive-back support.

It's important to evaluate the complete dependency chain rather than changing only the AndroidManifest.


Check Your MainActivity

Also inspect your Android MainActivity.

A typical React Native application may have something similar to:

public class MainActivity extends ReactActivity {

    @Override
    protected String getMainComponentName() {
        return "MyApp";
    }
}
Enter fullscreen mode Exit fullscreen mode

If your application has custom back handling, search the Android project for:

onBackPressed
Enter fullscreen mode Exit fullscreen mode

For example:

grep -R "onBackPressed" android/
Enter fullscreen mode Exit fullscreen mode

Also search for:

OnBackInvokedDispatcher
Enter fullscreen mode Exit fullscreen mode

and:

OnBackInvokedCallback
Enter fullscreen mode Exit fullscreen mode

This helps identify whether custom native code is interfering with the new Android back-navigation mechanism.


Check React Native BackHandler

React Native applications can listen for Android back events using:

import { BackHandler } from "react-native";
Enter fullscreen mode Exit fullscreen mode

For example:

useEffect(() => {
  const subscription = BackHandler.addEventListener(
    "hardwareBackPress",
    () => {
      navigation.goBack();
      return true;
    }
  );

  return () => subscription.remove();
}, [navigation]);
Enter fullscreen mode Exit fullscreen mode

However, don't add this globally just to hide the problem.

React Navigation normally handles Android back navigation for its navigation stack.

Adding multiple global BackHandler listeners can introduce new problems such as:

  • Back event being consumed too early
  • Incorrect navigation
  • Screens being popped multiple times
  • Modals not closing correctly
  • Navigation stack becoming inconsistent

So first determine whether the underlying Android back event is reaching React Native correctly.


A Useful Debugging Test

You can temporarily add a BackHandler listener to determine whether React Native receives the system back event:

useEffect(() => {
  const subscription = BackHandler.addEventListener(
    "hardwareBackPress",
    () => {
      console.log("ANDROID BACK EVENT RECEIVED");

      return false;
    }
  );

  return () => subscription.remove();
}, []);
Enter fullscreen mode Exit fullscreen mode

Then navigate to a screen and press the Android system back button.

If you see:

ANDROID BACK EVENT RECEIVED
Enter fullscreen mode Exit fullscreen mode

then the event is reaching React Native.

If the app closes without the event reaching your JavaScript handler, the problem is likely further down in the Android back-dispatching path.

This is a useful way to separate:

Android back event problem
Enter fullscreen mode Exit fullscreen mode

from:

React Navigation configuration problem
Enter fullscreen mode Exit fullscreen mode

Don't Confuse Home Screen Behavior With a Bug

One important testing detail:

If the user is already on the root screen:

Home
Enter fullscreen mode Exit fullscreen mode

pressing Android Back is normally expected to exit the application.

For example:

Home
 ↓
Android Back
 ↓
App closes
Enter fullscreen mode Exit fullscreen mode

That alone isn't evidence of a problem.

The important test is:

Home
 ↓
Screen A
 ↓
Screen B
 ↓
Android Back
Enter fullscreen mode Exit fullscreen mode

Expected:

Screen B
 ↓
Screen A
Enter fullscreen mode Exit fullscreen mode

If instead:

Screen B
 ↓
App closes
Enter fullscreen mode Exit fullscreen mode

then back navigation is not being handled correctly.


Testing Checklist After Target SDK 36 Upgrade

After upgrading to API 36, I recommend testing all of these scenarios.

1. Normal navigation

Home → List → Details
Enter fullscreen mode Exit fullscreen mode

Press system Back.

Expected:

Details → List
Enter fullscreen mode Exit fullscreen mode

2. Multiple navigation levels

Home → A → B → C
Enter fullscreen mode Exit fullscreen mode

Press Back repeatedly.

Expected:

C → B → A → Home
Enter fullscreen mode Exit fullscreen mode

3. Root screen

Home
Enter fullscreen mode Exit fullscreen mode

Press Back.

Expected:

App exits
Enter fullscreen mode Exit fullscreen mode

4. Modal

Open a modal and press Back.

Expected:

Modal closes
Enter fullscreen mode Exit fullscreen mode

instead of:

App exits
Enter fullscreen mode Exit fullscreen mode

5. Bottom tabs

Test:

Tab A → Tab B → Screen
Enter fullscreen mode Exit fullscreen mode

and verify that system Back behaves consistently with your navigation design.


6. Authentication flow

Test:

Login → OTP → Home
Enter fullscreen mode Exit fullscreen mode

and make sure Back doesn't allow users to incorrectly return to authentication screens.


7. Deep links

Test:

Deep Link → Details
Enter fullscreen mode Exit fullscreen mode

and verify the back stack behaves as expected.


8. Android gesture navigation

Test using:

  • 3-button navigation
  • Gesture navigation

Predictive back behavior can differ from traditional button-based testing, so both should be tested.


Temporary Workaround

If your application is currently affected and you need to stabilize the release, one possible temporary configuration is:

<application
    ...
    android:enableOnBackInvokedCallback="false">
Enter fullscreen mode Exit fullscreen mode

After rebuilding the application:

cd android
./gradlew clean
cd ..
Enter fullscreen mode Exit fullscreen mode

Then rebuild:

npx react-native run-android
Enter fullscreen mode Exit fullscreen mode

or use your normal release build process.

For an Expo bare/prebuild project, make sure the generated Android configuration is also correctly reflected in the source configuration you use for builds, rather than relying on a manual change that can be overwritten.


Recommended Migration Approach

Instead of treating the manifest flag as the final solution, I recommend approaching the migration in this order:

1. Upgrade target SDK → 36
          ↓
2. Test system Back
          ↓
3. Check React Native version
          ↓
4. Check React Navigation versions
          ↓
5. Search for custom Android back handling
          ↓
6. Search for BackHandler overrides
          ↓
7. Test predictive back
          ↓
8. Update incompatible dependencies
          ↓
9. Use manifest workaround if required
          ↓
10. Remove workaround after proper migration
Enter fullscreen mode Exit fullscreen mode

This approach makes it easier to identify the actual compatibility problem.


Important Takeaway

Upgrading:

targetSdkVersion
Enter fullscreen mode Exit fullscreen mode

is not always just a build configuration change.

A target SDK upgrade can activate or expose new Android platform behavior.

For Android 16 / API 36, back navigation and predictive back behavior are especially important areas to test.

If your React Native app suddenly starts closing when the Android system back button is pressed after moving to target SDK 36, don't immediately assume that your React Navigation stack is broken.

First determine whether:

Android
   ↓
Back Dispatcher
   ↓
React Native
   ↓
React Navigation
Enter fullscreen mode Exit fullscreen mode

is working correctly.

The following configuration can serve as a temporary compatibility workaround:

android:enableOnBackInvokedCallback="false"
Enter fullscreen mode Exit fullscreen mode

but the preferred long-term solution is to ensure that the React Native and navigation stack properly supports Android's modern back-navigation APIs.


Final Checklist

Before releasing a target SDK 36 build, verify:

  • [ ] Android system Back navigates correctly
  • [ ] Root screen exits correctly
  • [ ] Nested navigation works
  • [ ] Modals handle Back correctly
  • [ ] Bottom tabs behave correctly
  • [ ] Authentication screens behave correctly
  • [ ] Deep links create the expected back stack
  • [ ] Gesture navigation works
  • [ ] 3-button navigation works
  • [ ] Predictive back behavior has been tested
  • [ ] React Native version is compatible
  • [ ] React Navigation dependencies are compatible
  • [ ] Custom BackHandler logic has been reviewed
  • [ ] Native onBackPressed() implementations have been reviewed
  • [ ] OnBackInvokedDispatcher usage has been reviewed
  • [ ] Any temporary enableOnBackInvokedCallback workaround is documented

Conclusion

Android 16 introduces another step in the evolution of Android back navigation. For React Native applications, upgrading to target SDK 36 can expose problems where the system Back button no longer reaches the JavaScript navigation layer as expected.

If your app starts closing instead of navigating backward, investigate the new Android back-dispatching behavior before modifying your navigation stack.

A manifest-level workaround such as:

android:enableOnBackInvokedCallback="false"
Enter fullscreen mode Exit fullscreen mode

may restore the previous behavior temporarily, but dependency compatibility and proper predictive-back support should be addressed as part of the complete migration.

Target SDK upgrades should always be followed by dedicated navigation regression testing—not just build and installation testing.


✍️ Written by Dainy Jose — React Native Mobile Application Developer with 3+ years of experience building cross-platform mobile apps using React Native (Expo, TypeScript, Redux).
Currently expanding backend knowledge through the MERN Stack (MongoDB, Express.js, React.js, Node.js) to create more efficient, full-stack mobile experiences.

💼 Tech Stack: React Native · TypeScript · Redux · Expo · Firebase · Node.js · Express.js · MongoDB · REST API · JWT · Jest · Google Maps · Razorpay · PayU · Agile · SDLC · Git · Bitbucket · Jira

📬 Connect with me:
🌐 Portfolio
🔗 LinkedIn
💻 GitHub

Top comments (0)