React Native fetch() Ошибка сетевого запроса - программирование
Подтвердить что ты не робот

React Native fetch() Ошибка сетевого запроса

Когда я создаю новый проект с использованием react-native init (версия RN 0.29.1) и помещаю выборку в методе рендеринга в общедоступный API-интерфейс демо-фильма facebook, он выдает Network Request Failed. Существует очень бесполезная трассировка стека, и я не могу отлаживать сетевые запросы в хром-консоли. Вот выбор, который я отправляю:

fetch('http://facebook.github.io/react-native/movies.json')
      .then((response) => response.json())
      .then((responseJson) => {
        return responseJson.movies;
      })
      .catch((error) => {
        console.error(error);
      });
4b9b3361

Ответ 1

Проблема здесь в том, что iOS не разрешает HTTP-запросы по умолчанию, только HTTPS. Если вы хотите включить HTTP-запросы, добавьте это в ваш info.plist:

<key>NSAppTransportSecurity</key>
<dict>
    <key>NSAllowsArbitraryLoads</key>
    <true/>
</dict>

Ответ 2

Не рекомендуется разрешать все домены для http. Сделайте исключение только для необходимых доменов.

Источник: Конфигурирование исключений безопасности приложений для транспорта в iOS 9 и OSX 10.11

Добавьте в файл info.plist вашего приложения следующее:

<key>NSAppTransportSecurity</key>
<dict>
  <key>NSExceptionDomains</key>
  <dict>
    <key>yourserver.com</key>
    <dict>
      <!--Include to allow subdomains-->
      <key>NSIncludesSubdomains</key>
      <true/>
      <!--Include to allow HTTP requests-->
      <key>NSTemporaryExceptionAllowsInsecureHTTPLoads</key>
      <true/>
      <!--Include to specify minimum TLS version-->
      <key>NSTemporaryExceptionMinimumTLSVersion</key>
      <string>TLSv1.1</string>
    </dict>
  </dict>
</dict>

Ответ 3

Я использовал localhost для адреса, что было явно неправильно. После замены на IP-адрес сервера (в сети, в которой находится эмулятор), все заработало отлично.

редактировать

В эмуляторе Android адрес машины для разработки - 10.0.2.2. Больше объяснений здесь

Для Genymotion, адрес 10.0.3.2. Больше информации здесь

Ответ 4

React Native Docs дает ответ на этот вопрос.

Apple заблокировала неявную загрузку HTTP-ресурсов открытым текстом. Поэтому нам нужно добавить следующий файл нашего проекта Info.plist (или эквивалентный).

<key>NSAppTransportSecurity</key>
<dict>
    <key>NSExceptionDomains</key>
    <dict>
        <key>localhost</key>
        <dict>
            <key>NSTemporaryExceptionAllowsInsecureHTTPLoads</key>
            <true/>
        </dict>
    </dict>
</dict>

React Native Docs → Интеграция с существующими приложениями → Проверка интеграции → Добавить исключение безопасности транспорта приложения

Ответ 5

Проблема может быть в конфигурации сервера.

Android 7.0 содержит описание здесь. Обходное решение, предложенное Вики Чиджвани:

Настройте сервер для использования эллиптической кривой prime256v1. Для Например, в Nginx 1.10 вы делаете это, установив ssl_ecdh_curve prime256v1;

Ответ 6

Для нас это было потому, что мы загружали файл, а RN filePicker не давал правильный тип пантомимы. Это просто дало нам "образ" как тип. Нам нужно было изменить его на "image/jpg", чтобы заставить работу работать.

form.append(uploadFileName, {
  uri : localImage.full,
  type: 'image/jpeg',
  name: uploadFileName
 })

Ответ 7

Я получил ту же проблему на Android, но мне удалось найти решение для нее. Android блокирует трафик открытым текстом (не https-запросы), начиная с уровня API 28 по умолчанию. Тем не менее, реагирующий-нативный добавляет конфигурацию безопасности сети к отладочной версии (android/app/src/debug/res/xml/react_native_config.xml), которая определяет некоторые домены (localhost и IP-адреса хоста для AVD/Genymotion), который можно использовать без SSL в режиме разработки. Вы можете добавить свой домен туда, чтобы разрешить http-запросы.

<?xml version="1.0" encoding="utf-8"?>
<network-security-config>
  <domain-config cleartextTrafficPermitted="true">
    <domain includeSubdomains="false">localhost</domain>
    <domain includeSubdomains="false">10.0.2.2</domain>
    <domain includeSubdomains="false">10.0.3.2</domain>
    <domain includeSubdomains="true">dev.local</domain>
  </domain-config>
</network-security-config>

Ответ 8

Для Android вы, возможно, пропустили, чтобы добавить разрешение в AndroidManifest.xml Необходимо добавить следующее разрешение.

<uses-permission android:name="android.permission.INTERNET" /> 

Ответ 9

У меня похожая проблема. В моем случае запросы к localhost работали и внезапно прекратились. Оказалось, что проблема была в том, что я отключил свой Wi-Fi на моем телефоне Android.

Ответ 10

У меня была эта проблема для Android-

URL- localhost/authToken.json - не работает :(

URL- 10.106.105.103/authToken.json - не работает :(

URL- http://10.106.105.103/authToken.json - сработало :): D

Note- Используйте ifconfig в Linux или ipconfig в Windows, чтобы найти IpAddress компьютера

Ответ 11

Для пользователя Android:

  1. Замените localhost на IP-адреса Lan, потому что при запуске проекта на устройстве Android localhost указывает на устройство Android, а не на ваш компьютер, например: измените http://localost на http://192.168.1.123

  2. Если URL-адрес вашего запроса - HTTPS, а ваше Android-устройство использует прокси-сервер, предположим, что на вашем Android-устройстве установлен добавленный CA user- (например, CA Burp Suite или Charles CA), убедитесь, что ваша версия Android ниже Nougat (7.0), потому что: Изменения в доверенных центрах сертификации в Android Nougat

    user- добавлены CA
    Защита всех данных приложения является ключевой целью песочницы приложения Android. Android Nougat изменяет взаимодействие приложений с user- и центрами сертификации, предоставляемыми администратором. По умолчанию приложения, ориентированные на уровень API 24, по своей природе не будут учитывать такие ЦС, если приложение явно не выберет этот параметр. Этот безопасный по умолчанию параметр уменьшает поверхность атаки приложений и обеспечивает согласованную обработку сетевых и файловых данных приложений.

Ответ 12

Я столкнулся с той же проблемой в эмуляторе Android, где пытался получить доступ к внешнему URL-адресу HTTPS с действующим сертификатом. Но получить этот URL-адрес в реакции-родной не удалось

'fetch error:', { [TypeError: Network request failed]
sourceURL: 'http://10.0.2.2:8081/index.delta?platform=android&dev=true&minify=false' }

1) Чтобы узнать точную ошибку в журналах, я сначала включил "Отладку JS Remote" с помощью Cmd + M в приложении

2) Сообщение об ошибке было

java.security.cert.CertPathValidatorException: Trust anchor for certification path not found.

3) Я добавил действительный сертификат URL, используя этот метод → ШАГ 2

http://lpains.net/articles/2018/install-root-ca-in-android/

Этот сертификат добавляется на вкладку Пользователь.

4) Добавьте атрибут android:networkSecurityConfig в AndroidManifest.xml

Добавьте файл конфигурации сетевой безопасности res/xml/network_security_config.xml:

<network-security-config>
    <base-config>
        <trust-anchors>
            <certificates src="user"/>
            <certificates src="system"/>
        </trust-anchors>
    </base-config>
</network-security-config>

Это должно сработать и дать вам ожидаемый ответ.

Ответ 13

Это сработало для меня, Android использует специальный тип IP-адреса 10.0.2.2, а затем номер порта

import { Platform } from 'react-native';

export const baseUrl = Platform.OS === 'android' ?
    'http://10.0.2.2:3000/'
: 
'http://localhost:3000/';

Ответ 14

если вы используете docker для API REST, для меня было бы http://demo.test/api заменить имя хоста: http://demo.test/api на ip-адрес компьютера: http://xxxx/api. Вы можете получить IP-адрес, проверив, какой ipv4 используется в вашей беспроводной сети. Вы должны иметь также Wi-Fi с телефона.

Ответ 15

Вы должны обработать ошибку в .then для получения API.

Например:

fetch(authURl,{ method: 'GET'})
.then((response) => {      
  const statusCode = response.status;
  console.warn('status Code',statusCode);
  if(statusCode==200){
    //success code
  }else{
    //handle other error code
  }      
},(err) => {
  console.warn('error',err)
})
.catch((error) => {
  console.error(error);
  return error;
});

Ответ 16

Просто у вас есть изменения в Fetch....

fetch('http://facebook.github.io/react-native/movies.json')
    .then((response) => response.json())
    .then((responseJson) => {
        /*return responseJson.movies; */
        alert("result:"+JSON.stringify(responseJson))
        this.setState({
            dataSource:this.state.dataSource.cloneWithRows(responseJson)
        })
     }).catch((error) => {
         console.error(error);
     });

Ответ 17

причина, по которой реагирует собственная ошибка запроса сети; Устройство должно быть подключено к Wi-Fi и должно быть на сервере API.

* API для сервера ** * Открыть устройство Wi-Fi ***

Ответ 18

Для Android добавьте android: networkSecurityConfig = "@xml/network_security_config" в теге

network_security_config.xml

<?xml version='1.0' encoding='utf-8'?>
<network-security-config>
<debug-overrides>
    <trust-anchors>
        <!-- Trust user added CAs while debuggable only -->
        <certificates src="user" />
    </trust-anchors>
</debug-overrides>

<base-config cleartextTrafficPermitted="true" />
</network-security-config>

Ответ 19

Для устройств Android перейдите в корневую папку вашего проекта и выполните команду:

adb reverse tcp:[your_own_server_port] tcp:[your_own_server_port]

напр., adb reverse tcp:8088 tcp:8088

Это заставит ваше физическое устройство (например, телефон Android) прослушивать сервер localhost, работающий на вашем компьютере разработчика (то есть на вашем компьютере) по адресу http://localhost: [your_own_server_port].

После этого вы можете напрямую использовать http:localhost:[your_port]/your_api в вашем http:localhost:[your_port]/your_api fetch().

Ответ 20

Пример:

return fetch('http://<your ip>')
  .then((response) => response.json())
  .then((responseJson) => {
    console.log(responseJson)
  })
  .catch((error) => {
    console.error(error);
  });