yagisukeのWebなブログ

フロントエンドとサーバーサイドをさまようエンジニア

第2話: Fetch API の雑多なメモ 〜 REAL WORLD HTTP第7章より 〜

yagisuke.hatenadiary.com の第2話です。

Fetch API

Fetch APIXMLHttpRequestと同様の、サーバーアクセスを行う関数です。特徴としては、 デフォルトで厳格な設定がされており、必要に応じて明示的に解除するという設計となっていることです。

JavaScriptから用いられ以下の特徴を持ちます。 - XMLHttpRequestよりも、オリジンサーバー外へのアクセスなど、CORS(Cross-Origin Resource Sharing)の取り扱いが制御しやすい。 - JavaScriptのモダンな非同期処理の記述法であるPromiseに準拠している - キャッシュを制御できる - リダイレクトを制御できる - リファラーのポリシーを設定できる - Service Worker内から利用できる

注意 - IE対応してない。 http://caniuse.com/#search=fetch - Safariも対応していない? https://developer.mozilla.org/ja/docs/Web/API/Fetch_API

Fetch APIの基本

Fetch APIの使用例

fetch('news.json', { // 1
  method: 'GET', // 2
  mode: 'cors',
  credentials: 'include',
  cache: 'default',
  headers: {
    'Content-Type': 'application/json'
  }
}).then(response => { // 3
  return response.json()  // 4
}).then(json => {
  console.log(json)
})

基本要素は次の4つ

  1. XMLHttpRequestのようにオブジェクトを作成するのではなく、fetch()関数を呼び出す
  2. fetch()関数の第二引数はオプションのオブジェクト(省略可能)
  3. .then()関数に、サーバーレスポンスが帰ってきた後に呼び出されるコールバックを渡す(Promise)
  4. .then()に渡すコールバックがさらに時間がかかる処理を行い、それがPromiseを返すときは.then()を連結する

Fetch APIが対応するデータ

上記サンプルではjsonでした。以下のサンプルではstringで受け取ってます。
サンプル: https://codepen.io/osublake/pen/OMRdKq (string型でうけとってる)

メソッド 説明
arrayBuffer() ArrayBuffer 固定長のバイナリデータ。Typed Arrayを使って読み書き可能
blob() Blob ファイルコンテンツを表す MIMEタイプ + バイナリデータ。FileReaderを経由してArrayBufferに変換可能
formData() FormData HTMLフォームと互換の名前とあたいのペア
json() Object JSONを解釈してJavaScriptのオブジェクト、配列などで構成されるオブジェクト
text() string 文字列

Fetch APIで利用可能なメソッド

対応 メソッド一覧
CORS安全 GET, HEAD, POST
禁止メソッド CONNECT, TRACE, TRACK

参照: https://triple-underscore.github.io/Fetch-ja.html#methods

Fetch APIのCORSモード

Fetch APIではセキュリティ対策としてCORSをどのレベルまで許容するかを表明できます。 XMLHttpRequestの場合モードは変更できないようです。

設定値 Fetchデフォルト XHRデフォルト 説明
cors 別のオリジンサーバーへのアクセスを許容する
same-origin 別のオリジンサーバーへのアクセスをエラーにする
no-cors CORS接続は無視され空のレスポンスが返る

他にも、navigate、websocketがあります(HTML用の特別な値)。
参照: https://triple-underscore.github.io/Fetch-ja.html#concept-request-mode

Fetch APIのcredentials

クッキーの制限についてです。 XMLHttpRequestの場合、withCredentialプロパティにtrueを設定するとincludeできたのと同等に、 Fetch APIではcredentialsに設定します。

設定値 Fetchデフォルト XHRデフォルト 説明
omit クッキーを送信しない
same-origin 同一のオリジンの場合にのみクッキーを送信する
include クッキーを送信する

参照: https://triple-underscore.github.io/Fetch-ja.html#concept-request-credentials-mode

Fetch APIにしかできないこと

キャッシュの制御

キャッシュが細かく制御できることが特徴です。

設定値 デフォルト 説明
default 標準的なブラウザの動作
no-store キャッシュがないものとしてリクエストをする。結果もキャッシュしない
reload キャッシュがないものとしてリクエストをする。ETag等は送らない。キャッシュ可能であれば結果をキャッシュする
no-cache 期限内のキャッシュがあってもHTTPリクエストを送信する。ローカルのキャッシュのETag等も送り、サーバーが304を返したらキャッシュしたコンテンツを使う
force-cache 期限外のキャッシュでもあればそれを利用。なければHTTPリクエストする
only-if-cached 期限外のキャッシュでもあれば利用する。なければエラーにする

参照: https://triple-underscore.github.io/Fetch-ja.html#concept-request-cache-mode

リダイレクトの制御

設定値 デフォルト 説明
follow リダイレクトをたどる(最大20リダイレクト)
manual リダイレクトをたどらず、リダイレクトがあった旨をつたえる
error ネットワークエラーになる

注意 - Chrome47からはmanualになった模様。 https://developer.mozilla.org/ja/docs/Web/API/GlobalFetch/fetch - どうやらService Workersのみのお話しっぽい。

Service Worker対応

Fetch APIにできて、XMLHttpRequestにできないことは細々ありますが、 一番大きなものはService Workerへの対応です。 現在、Service Worker内から外部サービスへの接続にはFetch APIしかできないようになっています。

Service Workerに対応したWebサービスはオフライン動作が可能になったり、 通知を扱えるようになったりします。

引用元や参考情報