Loading
  • LIGHT

  • DARK

ROUTE

ルートゼロの
アクティビティ

async関数でthenが使えない?原因と対策を完全解説

6

【TypeError対策】async関数にthenが使えない?よくある落とし穴と解決法

`then is not a function` は、非同期処理の初学者が最もつまずくエラーの一つ。Promise や async/await の意味と役割から、型チェック・防止策までを図解&実例つきで解説!

async/await で「then is not a function」に遭遇した瞬間

非同期処理で .then() を使っていたら、ある日こういうエラーに出くわしたことはありませんか?

TypeError: resolveError(...).then is not a function

一見「Promise っぽい関数を呼び出したつもり」なのに、.then() が使えない…。このエラー、非同期処理の構造に潜む“思い込み”が原因です。

本記事では以下を順に解説し、理解 → 修正 → 再発防止の力をつけていきます。

  • Promise・async・await とは何か?(用語理解)
  • よくあるエラーのパターンと構造
  • 安全な使い方と Lint・型・テストによる防御策

Promise とは? — 非同期処理の「未来の結果」

Promise(プロミス)とは、JavaScript の非同期処理を扱うためのオブジェクトです。

簡単に言えば「これから完了する処理の結果を表す箱」のようなもの。

const promise = new Promise((resolve, reject) => {
  setTimeout(() => resolve('完了!'), 1000);
});
  • .then():成功時の処理
  • .catch():失敗時の処理
  • .finally():完了後に必ず実行
promise
  .then((result) => console.log(result)) // => "完了!"
  .catch((err) => console.error(err));

async/await とは?Promise をもっと読みやすくする仕組み

async とは?

async をつけた関数は、常に Promise を返す関数になります。

async function greet() {
  return 'Hello';
}
greet().then((msg) => console.log(msg)); // "Hello"

await とは?

await は、Promise が「完了するまで待ってから」次の処理を実行するための構文です。

async function run() {
  const msg = await greet();
  console.log(msg); // "Hello"
}

async/await の利点

  • .then().then() のネストを避けて、同期処理のようにスッキリ書ける
  • try/catch でエラー処理が明確になる
  • 非同期処理を分かりやすく構造化できる

ケース 1:async なし → Promise じゃない戻り値に.then()して TypeError

ダメなコード例

function fetchData() {
  return { data: 'hello' };
}
fetchData().then((res) => {
  console.log(res.data); // TypeError
});

修正例

async function fetchData() {
  return { data: 'hello' };
}
fetchData().then((res) => {
  console.log(res.data);
});
// await の場合
async function main() {
  const res = await fetchData();
  console.log(res.data);
}

デバッグ Tips

const result = fetchData();
if (typeof result.then === 'function') {
  result.then((res) => console.log(res));
} else {
  console.warn('Promiseじゃないので.then()不可');
}

ケース 2:await 忘れ → undefined.then()の落とし穴

ダメなコード例

async function getUser() {
  return { name: 'Alice' };
}
async function main() {
  const user = getUser(); // await 忘れ
  user.then((res) => {
    console.log(res.name);
  });
}

修正例

async function main() {
  const user = await getUser();
  console.log(user.name);
}

Lint での防止ルール

"rules": {
  "require-await": "error",
  "no-return-await": "error"
}

async/await と Promise の関係を図解で整理

[同期関数]         → 値(ただのオブジェクト)      → .then() ×
[async関数]        → Promise<値>                  → .then() 〇
[await付きasync]   → 値(Promiseの中身)          → .then() ×(不要)
  • async 関数は自動的に Promise<戻り値> を返す
  • .then() を使えるのは Promise に対してだけ
  • await を使うことで .then() を使わなくても中身が取り出せる

再発防止&設計ベストプラクティス

ESLint 設定例

"rules": {
  "no-misused-promises": "error",
  "consistent-return": "warn"
}

TypeScript の型チェック

async function getValue(): Promise<string> {
  return 'hello';
}
const value: string = await getValue();

Jest テスト例

test('Promise resolves correctly', async () => {
  const result = await getValue();
  expect(result).toBe('hello');
});

まとめ & 関連リンク

  • .then is not a function は「Promise を返していない」「await を忘れている」などが原因
  • async/await/Promise の意味と役割を知ることが根本対策
  • Lint・型チェック・テストで再発を未然に防ごう

【外部リンク】

MDN Web Docs: Promise

ESLint: require-await ルール

【内部リンク】

JavaScriptでよく発生するエラー「ReferenceError」「SyntaxError」などの原因と対策を具体例付きで解説

TypeError: Cannot read property ‘xxx’ of undefined の原因と対処法を徹底解説【初心者向け】

なぜ「undefined」が出る?原因と解決法10選|JavaScript のデバッグに効く実例集

非同期処理とは?JavaScriptとJavaの実例でわかる使い方・落とし穴・解決法

JavaScriptのAjax完全入門|fetchの使い方・CORSエラーの対処・非同期通信の基本を解説

RANKINGranking-icon

LATEST POSTS

もっとルートゼロを知りたいなら

DISCOVER MORE