コース一覧
非同期JavaScript:API通信とモジュール
fetch でデータを取る

非同期JavaScript:API通信とモジュール

Promise と async/await、非同期エラー、HTTP/REST、fetch による GET、読み込み・成功・失敗の表示、モジュールの読み方を学ぶ全 19 レッスン(380 分)のコースです。最後は承認済みの読み取り専用 API から作品データを取得して表示します。POST はリクエストの組み立てまでで、外部サービスへの書き込みは行いません。

1
非同期処理
01. 同期と非同期15分
02. Promise をつくって返す20分
03. async と await20分
04. Promise.all で同時に待つ20分
05. 非同期のエラーを捕まえる20分
06. つくる 読み込み中の表示を出す30分
07. 第1章まとめクイズ10分
2
fetch で外のデータを使う
01. HTTP と REST の読みかた15分
02. fetch でデータを取る25分
03. 取ったデータを描画する25分
04. response.ok と失敗時の表示25分
05. POST のリクエストを組み立てる20分
06. つくる 作品データを API から読む30分
07. 第2章まとめクイズ10分
3
モジュールと総仕上げ
01. ファイルを分けるという考えかた15分
02. named export と default export15分
03. つくる ポートフォリオアプリを仕上げる40分
04. ここから先の学びかた15分
05. 第3章まとめクイズ10分

fetch でデータを取る

API リクエストの中身
解説

このレッスンで分かること

  • fetch で 1 往復を書くには await が 2 回要ります
  • 封筒にあたる response と、中身のデータは別物です

返事は届いているのに、中身が読めない

fetch はブラウザに用意されている関数で、指定した URL にリクエストを送り、返ってきたレスポンスを Promise で受け取ります。ところが、待って受け取ったはずのものから値を読もうとすると undefined が出ます。

JavaScript

async function peek() { const response = await fetch("https://yumesaku.tech/course-api/works/2.json"); console.log(response.status); // 200 console.log(response.title); // undefined } peek();

1 回目の await が終わった時点では、まだ中身は手元にありません。届いているのはステータスコードとヘッダー、つまり封筒の表書きだけです。中身を読むには、もう一度 await が要ります。

行待っているもの手に入るもの
await fetch(url)返事の先頭が届くまで封筒にあたる response
await response.json()本文を最後まで読み終わるまで配列やオブジェクト

JavaScript

const response = await fetch("https://yumesaku.tech/course-api/works/2.json"); const work = await response.json(); console.log(work.title); // 自己紹介カード

2 回目の await で、本文を最後まで読んで JSON として解釈します。ここで初めて、普通のオブジェクトとして触れるようになります。response.json() も Promise を返すので、await を付け忘れると変数に箱が入り、そこから読む値が全部 undefined になります。

形を確かめてから書く

取ってきたデータの形が分からないまま work.title と書いても、当たるかどうかは運です。書く前に一度 console.log で出してください。{ で始まっていればオブジェクト、[ で始まっていれば配列です。

JavaScript

// works/2.json が返すもの // { // "id": 2, // "title": "自己紹介カード", // "year": 2026, // "views": 48, // "tags": ["HTML", "CSS"] // }

配列になっている項目は、そのまま一覧にできます。入門で書いた描画のやりかたがそのまま使えます。

JavaScript

const list = document.querySelector("#tag-list"); work.tags.forEach(function (tag) { const item = document.createElement("li"); item.textContent = tag; list.append(item); });

URL は文字列なので、組み立てられる

fetch に渡すのはただの文字列です。途中に変数を混ぜて組み立てれば、1 件だけ取ってくる形になります。

JavaScript

// スラッシュが 1 本足りない。よくある壊れかた const url = "https://yumesaku.tech/course-api" + "works/" + id + ".json"; // テンプレートリテラルなら形が見たままになる const url = `https://yumesaku.tech/course-api/works/${id}.json`;

+ でつないでも構いませんが、URL は記号が多いので、${} で埋めるほうが / の付け忘れに気づきやすくなります。存在しない番号を渡すと 404 が返ります。まずは正しい番号で 1 件取れることを確かめてください。

解説

fetch は速いときで数十ミリ秒、遅いときは数秒かかります。そのあいだ画面には何もありません。fetch を呼んだ関数の下に書いた行は、通信が終わる前に走ります。取ってきたデータを使いたい処理は、必ず await の下に置いてください。

よくある間違い

  • fetch に await を付け忘れる — response に箱が入るので、次の行で response.json is not a function と出ます
  • いちばん外側で await を書く — await が使えるのは async を付けた関数の中だけです。処理を async function にまとめ、呼び出しだけを外に出してください
  • response をそのまま画面に出す — 封筒を貼り付けているので [object Response] と表示されます。中身を読んでから使います

課題

  1. async function loadProfile() の中で fetch と response.json() を await する
  2. #profile-name に name を、#profile-headline に headline を入れる
  3. #profile-months に months を含む文を入れる
  4. skills の各要素を li にして #skill-list に足す

ヒント

取ってきたデータの形が分からないうちは、console.log(profile) で 1 回出して確かめてください。name と headline と months と skills が入っています。

const response = await fetch(url) のあとに const profile = await response.json() と書きます。await は 2 回とも必要です。

skills は配列なので forEach で回せます。createElement("li") で作り、textContent を入れてから #skill-list に append してください。

index.html
script.js
プレビュー

できているか

  • 名前が見出しに入る
  • 肩書きが出る
  • 学習月数が出る
  • スキルが 3 件以上並ぶ
エディタを読み込んでいます