You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React Native Android切换网络后Fetch API请求失败排查求助

React Native Fetch API "Network request failed" After Switching Networks (WiFi ↔ Mobile Data)

Problem Description

I've built a React Native Android app that lets users log in and view information. Everything works fine initially—users can log in, view content, and log out multiple times without issues. But after switching between WiFi and mobile data, any attempt to log in or fetch data throws this error:

Network request failed at XMLHttpRequest.xhr.onerror (fetch.js:441)

I'm using the Fetch API for network calls. Here's my request implementation:

export const request = async function request(path, body = null, method = 'GET') { 
  try { 
    const headers = { 
      'Content-Type': body instanceof FormData ? 'multipart/form-data' : 'application/json', 
    }; 
    const token = await AsyncStorage.getItem('authToken'); 
    if (token) { 
      headers.Authorization = token; 
    } 
    const config = { 
      method, 
      url: Config.API_URL + path, 
      headers, 
    }; 
    if (!['HEAD', 'GET'].includes(method.toUpperCase())) { 
      config.body = body instanceof FormData ? body : JSON.stringify(body); 
    } 
    const response = await fetch(Config.API_URL + path, config); 
    const data = await response.json(); 
    if (response.status >= 400) { 
      throw data.error; 
    } 
    return data; 
  } catch (e) { 
    console.log('Error', path, e); 
    return Promise.reject(e); 
  } 
};

Full error stack trace:

Network request failed at XMLHttpRequest.xhr.onerror (fetch.js:441) 
at XMLHttpRequest.dispatchEvent (event-target.js:172) 
at XMLHttpRequest.setReadyState (XMLHttpRequest.js:567) 
at XMLHttpRequest.__didCompleteResponse (XMLHttpRequest.js:397) 
at XMLHttpRequest.js:503 
at RCTDeviceEventEmitter.emit (EventEmitter.js:179) 
at MessageQueue.__callFunction (MessageQueue.js:351) 
at MessageQueue.js:116 
at MessageQueue.__guardSafe (MessageQueue.js:314)

My Android SDK versions:

  • compileSdkVersion: 25
  • buildToolsVersion: "25.0.2"
  • minSdkVersion: 16
  • targetSdkVersion: 25

I'm new to React Native and can't pinpoint the issue. Any help would be greatly appreciated!


Answer

Hey there! This is a super common gotcha with React Native's Fetch API on older Android versions—let's break down some fixes you can try right away:

1. Add a Network State Listener to Reset Requests

Android doesn't always notify React Native immediately when the network switches, which can leave the underlying HTTP client in a broken state. Use the @react-native-community/netinfo package to listen for network changes and reset your request logic:

First, install the package:

npm install @react-native-community/netinfo

Then add a listener in your app setup:

import NetInfo from '@react-native-community/netinfo';

// Add this in your root component or service initialization
NetInfo.addEventListener(state => {
  if (state.isConnected) {
    // When network reconnects, clear pending requests or retry failed ones
    console.log('Network reconnected—resetting request state');
    // You could also add logic here to retry the last failed fetch call
  }
});

2. Disable HTTP Keep-Alive (Quick Test)

Older Android versions struggle with persistent HTTP connections after network switches. Force a fresh connection for each request by adding a header:

const headers = {
  'Content-Type': body instanceof FormData ? 'multipart/form-data' : 'application/json',
  'Connection': 'close' // Add this line to disable keep-alive
};

This is a temporary fix but will help confirm if keep-alive is the culprit.

3. Check Network Security Config (If Using HTTP)

If your API uses HTTP (not HTTPS), Android 7+ blocks cleartext traffic by default. Switching networks might trigger this restriction. Create a res/xml/network_security_config.xml file:

<?xml version="1.0" encoding="utf-8"?>
<network-security-config>
    <base-config cleartextTrafficPermitted="true">
        <trust-anchors>
            <certificates src="system" />
        </trust-anchors>
    </base-config>
</network-security-config>

Then reference it in your AndroidManifest.xml:

<application
  ...
  android:networkSecurityConfig="@xml/network_security_config">

4. Try Axios Instead of Fetch

Many developers find Axios handles network switches more reliably than the native Fetch API. Here's how to refactor your request function:

Install Axios:

npm install axios

Updated request function:

import axios from 'axios';
import AsyncStorage from '@react-native-async-storage/async-storage';

export const request = async function request(path, body = null, method = 'GET') {
  try {
    const headers = {
      'Content-Type': body instanceof FormData ? 'multipart/form-data' : 'application/json',
    };
    const token = await AsyncStorage.getItem('authToken');
    if (token) {
      headers.Authorization = token;
    }

    const config = {
      method,
      url: Config.API_URL + path,
      headers,
      data: body,
    };

    const response = await axios(config);
    return response.data;
  } catch (e) {
    console.log('Error', path, e);
    return Promise.reject(e.response?.data?.error || e.message);
  }
};

5. Update Dependencies (Long-Term Fix)

Your Android SDK versions are quite outdated (compileSdk 25 is Android 7.1). React Native has fixed dozens of network-related bugs in newer versions—if possible, upgrade to a stable RN version (0.60+) and update your build tools to at least 28.0.3.

Start with fixes 1 and 2 since they're the fastest to test. Let me know if any of these work for you!

内容的提问来源于stack exchange,提问作者Mukund Kumar

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 09:22:06