JavaScriptのFetchとAPIの使い方!非同期通信でデータを取得

[PR]

プログラミング

非同期通信を使ったウェブアプリやフロントエンド開発において、Fetch APIは標準的な手段です。この記事では、JavaScriptでFetchを使うときの基本操作からPOSTリクエスト・ヘッダー設定・エラーハンドリング・キャンセル・セキュリティー・実践的な応用まで丁寧に解説します。最新情報を含めて、Fetch APIを初めて使う方からステップアップしたい方まで満足できる内容です。

JavaScript Fetch API 使い方の基本概要

Fetch APIとは何か、どういう場面で使うのか、XMLHttpRequestとの違いや利点を概説します。JavaScript Fetch API 使い方全体の土台を押さえることで、以降の具体的操作が理解しやすくなります。HTTPリクエストの種類やレスポンス形式、Promiseや非同期処理との関係など基本から丁寧に説明します。Fetchの基本構文、リクエストの送信、レスポンスの取得など、実際のコード例を交えてわかりやすくします。

Fetch APIとは何か

Fetch APIはブラウザや最近のJavaScript実行環境に標準で備わっている、HTTPリクエストを非同期で行うためのインターフェースです。Promiseベースで、コールバック地獄になりがちな旧来のXMLHttpRequestに比べ可読性が高く、モダンな機能との親和性があります。たとえばサービスワーカーやモジュール、ストリーミングレスポンスなどと組み合わせることが可能です。

XMLHttpRequestとの違い

主な違いとして、FetchではPromiseが使われるため`.then`や`await`で非同期処理が直感的になります。エラー処理もHTTPステータスで判断しないとならない点や、レスポンスボディがストリームとして扱われる点などが特徴です。また、XMLHttpRequestでは取得できなかった機能—モード設定やクレデンシャル(Cookie/認証ヘッダー等)の扱い、CORS制御など—がFetchになって簡単になっています。

Promiseとasync/awaitを使った基本構文

Fetchの基本構文は、URLだけを渡すシンプルな形から始まります。その後`.then(response => response.json())`のようにチェーンし、または`async function`内で`await fetch(…)`と書くことで読みやすくなります。エラーを投げるのであれば、`response.ok`をチェックしてthrowし、`catch`で包括的に処理するパターンが推奨されています。

GET・POSTリクエストの送信方法

Fetchを使ってデータを取得するGETと、データを送信するPOSTを行う手順を具体的に解説します。JSONデータ・フォームデータ・ファイル送信などさまざまな用途での使い方を扱います。ヘッダーの設定方法やボディの扱い、URLパラメータの構築など、実践的に即使えるコード例を交えます。読み手が実際にアプリを作る際の参考になります。

GETリクエストの基本

GETリクエストではURLのみを指定してFetchを呼び出します。必要であればクエリパラメータをURLに付けるか、URLSearchParamsなどを使って整理することができます。レスポンスは`.json()`, `.text()`, `.blob()`などのメソッドで読み取り、返ってきたヘッダーからContent-Typeやレスポンスステータスを確認することが重要です。

POSTやPUTなどの書き込みリクエスト

データをサーバーに送るには、`method`オプションを指定します。例えばJSONを送る場合は`headers: { ‘Content-Type’: ‘application/json’ }`を設定し、`body: JSON.stringify({…})`の形式で送信します。ファイルアップロードを行う場合にはFormDataを使ったり、headersのContent-Typeを自動処理に任せることもあります。

ヘッダー設定・ボディの形式の選び方

リクエストヘッダーはサーバーが期待するContent-Typeに合わせることが重要です。JSON以外にも`multipart/form-data`や`application/x-www-form-urlencoded`など使い分けが必要です。ボディの型には文字列・Blob・FormData・URLSearchParamsなどがあり、用途に応じて選ぶとレスポンスの予期せぬエラーを防げます。

レスポンスの処理とエラーハンドリング

Fetch APIを使う際、レスポンス取得後・非同期処理中に発生するエラーを適切に処理することが信頼性の高いアプリ開発に欠かせません。HTTPエラーコードの扱い方・JSONパース時のエラー・ネットワーク異常・タイムアウト・AbortControllerによるキャンセルなど、多様なパターンを網羅します。最新のベストプラクティスにもとづいたコード例で実装方法を紹介します。

HTTPステータスによる判定

Fetchは404や500などのHTTPステータスを返してもPromiseをrejectしません。したがって`response.ok`や`response.status`を使って明示的に判定し、ステータスが200~299以外の場合にはthrowしてcatchに流すパターンが基本です。このチェックを入れておかないと、エラーHTMLやテキストが無理にJSONとして処理されてしまい致命的なバグになることがあります。

JSONパース時の注意点

サーバーが返すレスポンスがJSONである期待される場合でも、Content-Typeが違ったり、中身が不正だったりすることがあります。`response.headers.get(‘Content-Type’)`で検査し、必要であればSyntaxErrorやTypeErrorのcatch処理を行うことが大切です。204 No Contentなど空のレスポンスにも注意が必要で、その場合はJSONパースをしない判断をすることが望ましいです。

ネットワークエラー・AbortController・タイムアウト

ネットワーク障害やCORS違反、ドメイン未解決などがあるとFetchはrejectします。またタイムアウトは標準では備わっていないので、AbortControllerを使って一定の時間内に完了しなければabortする実装が一般的です。これによりアクセス遅延時のユーザー体験を維持できます。

CORS・セキュリティ・同一オリジンの扱い方

Fetch APIを安全に使うためには、クロスオリジンの設定・クレデンシャルの扱い・HTTPヘッダーを理解しておくことが必要です。CORSポリシー、SameSite属性・Sec-Fetch系メタデータヘッダーなど、近年のセキュリティ仕様に対応することが推奨されます。これらは攻撃防止や個人情報の保護に直結する重要な要素です。

CORSモードとcredentialsオプション

リクエストを異なるオリジンに送る際、`mode`オプションでCORSやno-corsを設定できます。それとともに`credentials`(omit/same-origin/include)を指定しないとCookieや認証ヘッダーが送信されません。特にクロスオリジンで認証が必要なAPIを呼び出す場合は、サーバー側も適切なCORSヘッダーを返す必要があります。

Fetch metadataヘッダーの利用

セキュリティ向上のため、最近ではFetch metadataヘッダー(Sec-Fetch-Site や Sec-Fetch-Mode など)をサーバーが検査し、信頼できるリクエストかどうか判断する動きがあります。これによってCSRFやクロスサイトリークなどの攻撃を軽減することができます。サーバー側がこういったヘッダーを受け入れるかどうか設計段階で考えることが望ましいです。

Same-origin policyとドメインセキュリティ

同一オリジンポリシーはJavaScriptによるアクセス制限の基本です。スクリプトが読み込まれたオリジンと応答先が異なると、制約が生じます。例えばCookieの送信やレスポンスヘッダーの閲覧が制限されることがあります。安全にFetchを使うには、このポリシーとCORS設定を理解し、実装時に不正アクセスのリスクを抑える設計を行うべきです。

Fetch APIを使った高度な応用

基本を理解したら、次は実践的な応用です。複数リクエストの並列処理、ストリーミング読み込み、大きなファイルのダウンロード、キャッシュ制御などです。さらにラッパー関数を作って共通処理やリトライ処理をまとめたり、APIクライアントを設計する方法を取り上げます。最新のブラウザやJS環境で動作する実装例を紹介します。

複数のリクエストを並列で処理

複数のデータを同時に取得したい場面では、Promise.allを使います。例えばユーザー情報と投稿一覧を別APIから取得する場合、それぞれ個別にfetchし、両方のPromiseを同時に待つことで効率を高められます。ただし、一方が失敗したら全体がrejectするので、個別のエラーハンドリングを組み込むことが望ましいです。

大容量データのストリーミング処理

レスポンスボディが大きいデータ(画像・動画・大きなJSONなど)の場合、`.json()` や `.text()` のように一度で読み込むとメモリ消費が大きくなります。ReadableStream を使ってチャンク単位で読み込むことでメモリ使用を抑制しつつ処理が可能です。この手法はサービスワーカーやプログレッシブウェブアプリで特に有用です。

ラッパー関数と共通処理(retry/共通ヘッダーなど)

多くのAPI呼び出しで共通する処理(例:ヘッダー設定・認証トークンの付与・ステータスチェック・タイムアウト設定)の部分をラッパー関数にまとめるとコードの重複を減らせます。さらにリトライ処理(指数バックオフ)を導入することで、一時的なネットワーク障害にも耐える堅牢な仕様になります。ただしPOSTなど処理が冪等でないものは慎重に扱う必要があります。

ブラウザとサーバー環境での互換性と制限

Fetch APIはほぼすべての最新ブラウザでサポートされており、Node.jsの最近のバージョンでも標準化されています。ただし古いブラウザへの対応やポリフィルが必要な環境があります。また、fetchでのファイル扱いやメモリ制限、ストリーミングの挙動が環境によって異なるため、開発対象に応じたテストが重要です。

対応ブラウザとNode.jsでの動作

最新のブラウザ(主要ブラウザ各種)ではFetchが標準で利用でき、HTTP/2やTLS1.3といった最新の通信プロトコルとも組み合わされることが多くなっています。Node.jsのバージョン18以降ではFetchが標準搭載されており、その環境ではサーバーサイドでも同じAPIで通信処理ができるようになっています。

古いブラウザやポリフィルが必要なケース

Internet Explorer や古いバージョンのブラウザではFetchが未対応だったり部分対応だったりします。そのような場合はポリフィルを導入するか、XMLHttpRequestを利用した代替実装を準備する必要があります。特にモバイル端末でのサポート状況を事前に確認すべきです。

ファイルのアップロード/ダウンロード時の注意点

ファイルアップロードではFormDataやBlobを使い、ダウンロードではレスポンスをblobとして取得してURL.createObjectURLを利用するパターンがあります。ただしサーバーが Content-Disposition や Content-Type を正しく設定していないと想定外の形式で扱われたり、ファイルが破損したりする場合があります。

サンプルコード集とプロジェクトへの導入例

ここでは実際のコード例をいくつか提示し、Fetch API をプロジェクトに導入する方法を示します。小規模なユーティリティ関数からプロダクションレベルのAPIクライアントまで、どのように設計すればよいかを具体例で理解できます。またテスト・ロギング・モニタリングとの組み合わせ方にも触れます。

簡単なユーティリティ関数

例えば認証トークンを含める共通ヘッダーとステータスチェック・JSON変換を行うラッパー関数を作成すると、コードを再利用しやすくなります。以下のような構造を持つ関数が典型例です:リクエスト設定 → `fetch` 呼び出し → `response.ok` チェック → JSON取得またはエラー投げる → 必要であればタイムアウト/取消が可能。こうしたパターンがプロジェクト全体で統一されていると保守性が高まります。

プロジェクトへの組み込みと構造設計

API呼び出し部分をサービス層として分離し、UI層とは明確に責任を分ける設計が望ましいです。必要なHTTPヘッダーや認証方式は設定ファイルか環境変数で管理し、エラーハンドリングやタイムアウトのルールをドキュメント化してチームで共有します。またレスポンスの形式が変更されても影響が最小限になるよう型付けやバリデーションを導入することが有効です。

テスト・ロギング・モニタリングの活用

Fetchを使うコードはユニットテストや統合テストでHTTP応答モックを使って網羅的にチェックするべきです。また重大なエラーやタイムアウトはエラーログに残し、ユーザー体験を損なっていないかモニタリングします。これにより不具合発覚時の対応が迅速になります。

まとめ

JavaScript Fetch API は非同期通信を行うための強力でモダンな手段です。基本構文を押さえ、GET/POSTなどのリクエストやヘッダー・ボディの扱いを理解することから始め、HTTPステータスやJSONパースのエラーハンドリング、タイムアウト・キャンセルなどを取り入れて堅牢さを高めてください。

またセキュリティに関する仕様(CORS・credentials・Fetch metadata・同一オリジンポリシー)にも注意を払い、API呼び出し部分を汎用ラッパー関数にまとめることでコードの重複を減らせます。テストとモニタリングも忘れずに設定し、プロジェクト全体で一貫したFetch APIの使い方を共有すると良いでしょう。

関連記事

特集記事

コメント

この記事へのトラックバックはありません。

TOP
CLOSE