await の戻り値を一言でいうと
await の「戻り値」は、
「Promise が resolve(成功)したときに渡される“中身の値”」 です。
const result = await somePromise; と書いたとき、result には Promise そのものではなく、その Promise が解決したときの値 が入ります。
ここが重要です。await が返してくるのは Promise ではありません。
「Promise の箱のフタを開けて、中から取り出した中身」 です。
この感覚をしっかり持っておくと、非同期処理のコードがかなりスッキリ理解できるようになります。
基本:resolve の値がそのまま await の戻り値になる
シンプルな Promise と await の対応
まず、小さな Promise を自分で作ってみます。
function getNumber() {
return new Promise(resolve => {
resolve(42);
});
}
JavaScriptこの getNumber() は「いつか 42 を渡してくれる Promise」を返します。
これを await してみましょう。
async function run() {
const value = await getNumber();
console.log(value); // 42
}
JavaScriptここでの流れはこうです。
getNumber()はPromiseを返すawait getNumber()は、その Promise の完了(resolve)を待つ- resolve されたときの値
42が、awaitの戻り値になる - その値が
valueに代入される
つまり、
「Promise.resolve(42)」
↓
「await」
↓
「42 が手元に来る」
というイメージです。
実際に console.log してみると違いが分かる
違いを並べて見てみます。
async function run() {
const promise = getNumber(); // Promise
const value = await getNumber(); // 42
console.log("promise:", promise);
console.log("value:", value);
}
JavaScriptpromise は Promise のオブジェクト(箱)。value は中身の 42 です。
ここが重要です。await の戻り値は「Promise の中身」。
「箱そのもの」が欲しいなら await しない、「中身」が欲しいなら await する。
“箱か中身か” を常に意識すると、await の使い方で迷いにくくなります。
実用例:API のレスポンスと await の戻り値
fetch の例で確認してみる
fetch は「レスポンスオブジェクトを resolve する Promise」を返します。
async function fetchJson(url) {
const response = await fetch(url); // await の戻り値は Response オブジェクト
const data = await response.json(); // await の戻り値は パース済みの JSON データ
return data;
}
JavaScriptここでは、
await fetch(url) の戻り値 → Responseawait response.json() の戻り値 → 解析済みの JS オブジェクト(あるいは配列など)
という風に、「Promise の中身」がそのまま受け取れています。
もし await を付けなかったらどうなるか。
async function fetchJson(url) {
const responsePromise = fetch(url);
console.log(responsePromise); // Promise オブジェクト
// const response = await responsePromise; // ← ここで初めて中身を取り出せる
}
JavaScriptここが重要です。
「Promise を返す関数」を呼び出した時点では「箱」しか手に入りません。await を使うことで、「箱が完了したタイミングで中身をちょうどいい形で受け取る」ことができる。await の戻り値は、まさにその“ちょうどいい中身”です。
エラー(reject)のとき、await の戻り値はどうなるか
reject されたときは「戻り値」ではなく「例外」が飛ぶ
await が「戻り値」を返すのは、Promise が「resolve(成功)」したときだけです。
Promise が reject された場合、await は値を返してくれません。
代わりに、その場でエラー(例外)が投げられます。
function failAfter1sec() {
return new Promise((_, reject) => {
setTimeout(() => {
reject(new Error("失敗しました"));
}, 1000);
});
}
async function run() {
try {
const value = await failAfter1sec(); // ここで throw される
console.log("これは実行されない:", value);
} catch (err) {
console.log("エラーをキャッチ:", err.message); // "失敗しました"
}
}
JavaScriptこの場合、
await failAfter1sec()の「戻り値」は存在しません- 代わりに、
throw new Error("失敗しました")と同じ扱いになります
つまり、await の戻り値は
「成功(resolve)のときだけ手に入る」
「失敗(reject)のときは例外になって飛ぶ」
という二段構えです。
ここが重要です。
await を使うと、「成功時の値」は戻り値としてその場で受け取れ、
「失敗時の値」は try / catch で扱うエラーになる。
Promise の resolve / reject を、同期コードの return / throw に対応させてくれるのが await の役割です。
await と「値の型」の関係
await する前と後で「型」がどう変わるか
例えば、こんな関数があったとします。
function getUser() {
return new Promise(resolve => {
resolve({ name: "Taro", age: 20 });
});
}
JavaScriptこのとき:
getUser() の戻り値の型 → Promise<{ name: string; age: number }>await getUser() の戻り値の型 → { name: string; age: number }
実際のコードにすると:
async function run() {
const userPromise = getUser(); // Promise<ユーザー>
const user = await getUser(); // ユーザーオブジェクトそのもの
console.log(userPromise); // Promise
console.log(user.name); // "Taro"
}
JavaScript「await は Promise を“はがす”」というイメージ
型の目線で見ると、await は
Promise<T> → T に変換してくれる演算子
です。
Promise<number> を await すると numberPromise<string> を await すると stringPromise<User> を await すると User
というふうに、
Promise に包まれていたものを一枚はがして“中身の型”にしてくれる と考えてください。
ここが重要です。
await の戻り値を考えるときは、「この Promise は最終的に何を返す Promise なのか?」を意識すること。
その “最終的な中身” がそのまま await の戻り値になる、という対応関係を頭に固定しておくと、型やデータ構造で迷いにくくなります。
特殊なケース:await の引数が「Promise じゃない」とき
非 Promise 値を await した場合
実は、await の後ろが Promise でなくても、文法上は通ります。
async function run() {
const value1 = await 42;
const value2 = await "hello";
console.log(value1, value2); // 42 "hello"
}
JavaScriptこれは内部的に
await Promise.resolve(42)await Promise.resolve("hello")
のように扱われます。
実務でこう書く場面はほぼありませんが、
「await は Promise っぽく扱えるものなら何でも受け取る」とだけ知っておけば十分です。
実用的な意味はあまりないが、頭の片隅に置いておく
あくまで理解用の知識として:
await value; は
「value が Promise ならそれを待ち、中身を返す」
「Promise でなければ、そのまま value を返す」
という挙動を取ります。
ここが重要です。
「await の戻り値」は、基本的に「Promise の中身」。
ただし Promise じゃないものを渡した場合は、「その値自身」が戻り値になる。
実務ではほぼ“Promise の中身を取り出すもの”と考えて問題ありません。
await の戻り値を意識した設計のコツ
「この async 関数は、何を返す関数なのか?」を先に決める
例えば、ユーザー情報を取ってくる async 関数を作るなら、
async function fetchUser() {
// ...
return userObject; // await fetchUser() の戻り値になる
}
JavaScriptと書いたとき、
「await fetchUser() の戻り値は userObject だ」と自分に宣言しているのと同じです。
このとき、関数の役割を
「Promise を返すこと」ではなく
「`await されたときに、どんな形の値を返すか」
として設計すると、コードの見通しがかなり良くなります。
途中の await を“つなげる”感覚
async function getUserName() {
const user = await fetchUser(); // user を取り出す
return user.name; // await getUserName() の戻り値は name
}
JavaScriptこうしておけば、
const name = await getUserName();
JavaScriptで、最終的に欲しい name だけを
スッと取り出せます。
ここが重要です。
async 関数や await の設計は、「呼び出し側から見てどんな値が欲しいか」から逆算する。
途中の await たちは、その最終的な戻り値にたどり着くために「Promise を一枚ずつはがしていく」ステップだと捉えると、流れがとてもスムーズに考えられます。
初心者として await の戻り値で本当に押さえてほしいこと
await promise の戻り値は、「その promise が resolve したときの値」。
Promise そのものではなく、「中身」が返ってくる。
Promise の型が Promise<T> なら、await の戻り値は T になる。
「箱(Promise)から中身(値)を取り出す」のが await の役割。
Promise が reject されたとき、await は値を返さず、その場で例外(throw)が発生する。
try / catch で受け止めることで、エラーも同期コードのように扱える。
Promise でない値を await した場合、その値自身が戻り値になる(内部的に Promise.resolve されるイメージ)。
ただし実務では「Promise の中身を取り出すもの」と考えておけば十分。
ここが重要です。
await の戻り値を考えるときは、
“この Promise は最終的に何を返すのか?”
“自分はその中身をどの変数で受け取りたいのか?”
を意識してください。
「箱か中身か」を見失わなくなった瞬間、async / await のコードは一気に読みやすく・書きやすくなります。
もし練習したくなったら、次のようなコードを自分で書いてみてください。
// 1. 数字を受け取って、その2倍を resolve する Promise 関数 doubleAsync(n) を作る。
// 2. それを await して結果を受け取り、さらにその2倍を計算して返す async 関数 quadrupleAsync(n) を作る。
// 3. await quadrupleAsync(5) の戻り値が何になるか、実際に console.log して確かめてみる。
JavaScript「どの時点で Promise を扱っていて、どの時点で“ただの数値”を扱っているか」を意識しながら書くと、
await の「戻り値」のイメージがかなりクリアに定着していきます。
