# Fetch

[RN官方](https://facebook.github.io/react-native/docs/network.html)   [RN中文網](http://reactnative.cn/docs/0.49/network.html#content)

React Native可以使用多種方式來進行網路請求（fetch、XMLHttpRequest等等） fetch API是基於 Promise 設計的，因此了解Promise也是有必要的，推薦閱讀 [MDN Promise](https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Promise) fetch返回的是Promise對象

### &#x20;請求的對象中包含以下屬性 （上面三個為常用參數）

* method: 網路請求的方式（GET, POST等）。fetch默認的method為GET。
* headers: 網路請求的header，裡面包含（Accept, Content-Type, token等）
* body: POST請求的body。要送去server的資料
* mode: 跨域設置（cors, no-cors, same-origin）
* cache: 緩存選項（default, no-store, reload, no-cache, force-cache, only-if-cached）

### &#x20;response對象有提供了些方法

* clone(): 複製一份response
* error(): 返回一個與網路相關的錯誤
* redirect(): 返回一個可以重定向到某URL的response
* response對象的解析方式

  * json(): 返回（return）一個Json對象（格式）的Promise
  * text(): 返回一個文字的Promise
  * formData(): 返回一個FormData的Promise
  * arrayBuffer(): 返回一個arrayBuffer的Promise
  * blob(): 返回一個blob的Promise

### **GET請求**

```
fetch(url, { 
        method: 'GET’, 
        headers: { 
            'Accept': 'application/json’, 
            'Content-Type': 'application/json', }
     }) 
    .then((response) => response.json()) // json方式解析，如果是text就是response.text()                         
    .then((responseData) => { // 處理獲取到的資料 }) 
    .catch((error) => { // 錯誤處理 })
    .done()

作者：光强_上海
链接：https://www.jianshu.com/p/df4f13ba486b
來源：简书
著作权归作者所有。商业转载请联系作者获得授权，非商业转载请注明出处
```

fetch方法會返回一個Promise對象，這個對象內包含了response，也就是第一個 then內的response\
第一個then收到response後，透過 .json() 將response轉換成json對象的Promise並返回，也就是第二個 then 內的responseData 用 .catch 捕捉網路請求的錯誤情況

除了上面的寫法，還可以使用Request\
先創建Request對象並設置後交給fetch處理，如下

```
let request = new Request(url, {
                    method: 'GET',
                    headers: ({
                        'Content-Type': 'application/json'
                     })
                });
fetch(request).then((response) => {
        console.log(response);
    }).catch((err) => {
        console.error(err);
    });
```

ps. get url 可用 <https://facebook.github.io/react-native/movies.json> 來測試

### **POST請求**

```
fetch(url, { 
        method: "POST”, 
        headers: { 
            'Accept': 'application/json’, 
            'Content-Type': 'application/json’}, 
        body: JSON.stringify({key1: value1, key2: value2}) }) 
    .then((response) => { // 資料的解析方式 }) 
    .then((responseData) => { // 處理獲取到的資料 }) 
    .catch((error) => { // 處理錯誤 }) 
    .done()


作者：光强_上海
链接：https://www.jianshu.com/p/df4f13ba486b
來源：简书
著作权归作者所有。商业转载请联系作者获得授权，非商业转载请注明出处。
```

\
在解析response時，也可以使用ES2017的 **async/await**

```
async function getMoviesFromApi() {
  try {
    let response = await fetch(
      'https://facebook.github.io/react-native/movies.json'
    );
    let responseJson = await response.json();
    return responseJson.movies;
  } catch (error) {
    console.error(error);
  }
}
```

ps.此例為RN官網內的例子，並且可以到官網去實際執行看看

### **maybe you want to know**

1.網路方面（圖片路徑為網址、連線等）   for ios http問題。 由於apple應用安全的管控，但下面的方法會將apple提供的安全保障關閉     用Xcode 打開/ios/ProjectName.xocdeproj     後點選 Info.plist 內的App Transport Security Settings(Key) =>     Exception Domains 案＋ =>     選擇Allow Arbitrary Loads 並且改為 Yes(Value) 2.Android App連線至某些網站或打某些api(url)，會收不到response或是空白，請參考 [Missing intermediate certificate authority](https://developer.android.com/training/articles/security-ssl.html#MissingCa)，確認下server端

### &#x20;參考

* 刘望舒的博客 - [React Native探索（五）使用fetch进行网络请求](http://liuwangshu.cn/rn/primer/5-fetch.html)
* 光強 簡書 - [React Native封裝fetch網路請求組件](https://www.jianshu.com/p/df4f13ba486b)
