RORK LABEN
TOOLING — Rorkの開発者向けリポジトリが動き続けています。rork-xcodeが7月16日、rork-deviceが7月15日、rork-plistが7月13日に更新されましたOPUS46 — RorkでClaude Opus 4.6が稼働しています。Rork MaxはClaude Codeを土台にアプリを組み立てる設計ですSIM — ブラウザ上で動くクラウドのiOSシミュレータを備え、実機へのインストールは1クリック、App Storeへの提出は2クリックと案内されていますMAX — Rork MaxはReact Nativeではなく純粋なSwiftを出力します。iPhone・iPad・Apple Watch・Apple TV・Vision Pro、そしてiMessageまでが射程ですNATIVE — HealthKit、ARKitとLiDAR、NFC、Dynamic Island、Live Activities、Metalによる3D、Core MLのオンデバイス推論まで扱えますSEED — RorkはLeft Lane Capitalが主導する1,500万ドルのシードラウンドを実施し、Peak XVとa16z Speedrunが参加しましたTOOLING — Rorkの開発者向けリポジトリが動き続けています。rork-xcodeが7月16日、rork-deviceが7月15日、rork-plistが7月13日に更新されましたOPUS46 — RorkでClaude Opus 4.6が稼働しています。Rork MaxはClaude Codeを土台にアプリを組み立てる設計ですSIM — ブラウザ上で動くクラウドのiOSシミュレータを備え、実機へのインストールは1クリック、App Storeへの提出は2クリックと案内されていますMAX — Rork MaxはReact Nativeではなく純粋なSwiftを出力します。iPhone・iPad・Apple Watch・Apple TV・Vision Pro、そしてiMessageまでが射程ですNATIVE — HealthKit、ARKitとLiDAR、NFC、Dynamic Island、Live Activities、Metalによる3D、Core MLのオンデバイス推論まで扱えますSEED — RorkはLeft Lane Capitalが主導する1,500万ドルのシードラウンドを実施し、Peak XVとa16z Speedrunが参加しました
記事一覧/開発ツール
開発ツール/2026-04-30中級

Rork の『undefined is not an object』エラーを最短で特定する方法

Rorkで頻発する『undefined is not an object (evaluating ...)』エラーの読み解き方と、典型的な5つの原因をコード付きで解説します。Hermesのスタックが読みにくいときのデバッグ手順もまとめています。

Rork515Hermes6デバッグ22エラー対処3React Native209

Rork で生成されたコードを少し書き換えたら、いきなり赤い画面に「undefined is not an object (evaluating 'user.profile.name')」と表示された経験はありませんか。私も最初は「null チェックを足せば直るんでしょ」と高をくくっていたのですが、実際には参照しているプロパティそのものではなく、その上のオブジェクトが期待と違う形で返ってきている、というケースがほとんどでした。

このエラーは Hermes(Rork が標準で使う JavaScript エンジン)が「アクセスしようとした親が undefined だった」と教えてくれているメッセージです。原因は意外と少ないパターンに収束しますので、闇雲に ?. を足す前に、まず読み方とよくある落とし穴を押さえておくと、再発をぐっと減らせます。

まずエラーメッセージの『括弧の中』を必ず読む

このエラーで一番もったいないのが、undefined is not an object の文字だけ見て焦って手当てしてしまうことです。注目すべきはその後ろの (evaluating 'user.profile.name') の部分で、Hermes がどの式を評価したときに失敗したかをかなり正確に教えてくれます。

ERROR  undefined is not an object (evaluating 'user.profile.name')

この場合、問題は user.profile.name の評価ですが、Hermes の判定基準は「name を取り出そうとしたときに user.profile が undefined だった」です。つまり犯人は profile プロパティであって、user 自体や name ではない可能性が高い、ということになります。

デバッグの第一歩は『1つ手前で止めて中身を見る』こと

Rork で動かしているとスタックトレースが minify されたファイル名(例: index.bundle:135432)になりがちで、行番号からは原因が辿りにくいです。私は次のように一段ずつ console.log を仕込む方法を使っています。

// app/screens/Profile.tsx
function ProfileScreen({ route }) {
  const userId = route.params?.userId;
 
  // ❌ いきなり最深部にアクセスしてエラー
  // return <Text>{user.profile.name}</Text>;
 
  // ✅ 段階的に中身を確認
  const { data: user } = useUser(userId);
  console.log('[Profile] user:', user);
  console.log('[Profile] user.profile:', user?.profile);
 
  if (!user?.profile) {
    return <Text>プロフィールを読み込み中...</Text>;
  }
 
  return <Text>{user.profile.name}</Text>;
}

期待出力は [Profile] user: { id: 1, name: '...' } のように出るはずなのに、実際には [Profile] user.profile: undefined と出る、というように犯人がはっきり見えます。?. を足すこと自体は対症療法ですので、まず「なぜ profile が来ていないのか」を必ず確認してから防御コードを書くようにしています。

典型的な原因 5 つと、それぞれの直し方

1. API レスポンスのキー名が想定と違う

これが一番多いパターンだと感じています。バックエンド側で profileuserProfile にリネームしたのに、フロント側だけが古い名前のまま、という事故です。

// ❌ レスポンス構造が変わったのに気付いていない
const { data } = await fetch('/api/me').then(r => r.json());
return data.profile.name;  // → undefined is not an object
 
// ✅ レスポンスを一度確認するクセをつける
const json = await fetch('/api/me').then(r => r.json());
console.log('me response:', json);
const profile = json.user?.profile ?? json.profile ?? null;
if (!profile) throw new Error('profile が API から返ってきませんでした');
return profile.name;

2. useState の初期値が undefined のまま render される

// ❌ 初期値なしの useState に、初回render で深いアクセスする
const [user, setUser] = useState();  // 初期値が undefined
useEffect(() => {
  fetchUser().then(setUser);
}, []);
return <Text>{user.email}</Text>;  // ← 初回 render で爆発
 
// ✅ 初期値を設定し、未ロード時の表示を分ける
const [user, setUser] = useState(null);
useEffect(() => { fetchUser().then(setUser); }, []);
if (!user) return <ActivityIndicator />;
return <Text>{user.email}</Text>;

3. ネストした props の destructuring 忘れ

ナビゲーション周りでよく踏みます。useRouteuseLocalSearchParams の戻り値はキーが存在しないと undefined を返します。

// ❌ params が空のときに userId を取り出そうとして爆発
const { params: { userId } } = useRoute();
 
// ✅ 一段ずつ optional chaining で受ける
const route = useRoute();
const userId = route.params?.userId;
if (!userId) {
  // 開発中は throw すると気付きやすい
  if (__DEV__) console.warn('userId がありません', route);
  return null;
}

4. ネイティブモジュールの import を忘れている

@react-native-async-storage/async-storage のように、Expo prebuild が必要なライブラリで起こりがちです。Rork のプレビュー上は動いていても、実機ビルドだとモジュールが解決されず undefined のまま import される、という現象です。

import AsyncStorage from '@react-native-async-storage/async-storage';
 
// 実機で undefined になっていないかを開発時に確認
if (__DEV__ && !AsyncStorage) {
  console.error('AsyncStorage が読み込めていません。expo prebuild を確認してください');
}

EAS Build のログに Could not find module の警告が出ていないかも合わせて確認すると、原因の切り分けが早くなります。

5. useEffect で setState する前に値を参照している

非同期で取得した値を、まだ存在しない段階で読みに行ってしまうケースです。

// ❌ items がまだ未定義の段階で .map にかかる
useEffect(() => {
  fetch('/api/items').then(r => r.json()).then(setItems);
}, []);
return items.map(i => <Item key={i.id} item={i} />);
 
// ✅ 配列なら空配列で初期化しておくのが安全
const [items, setItems] = useState([]);  // ← undefined ではなく []
return items.map(i => <Item key={i.id} item={i} />);

配列の場合は useState([])、オブジェクトの場合は useState(null) にして「未ロード」と「中身が空」を区別できる状態を作るのが、私の中での定石です。

それでも特定できないときの最終手段

これらをチェックしても直らない場合、Hermes のスタックトレースの読み方を一段深めるのが有効です。Rork から Companion アプリに繋ぐと開発ビルドで sourcemap が有効になり、minify 前のファイル名と行番号が出るようになります。さらに、エラーが画面のどこで起きているかを切り分けるために、コンポーネントツリーを ErrorBoundary で部分的に囲み、原因の枝を機械的に絞り込む方法もあります。

function SafeBox({ name, children }) {
  return (
    <ErrorBoundary fallback={<Text>{name} で失敗しました</Text>}>
      {children}
    </ErrorBoundary>
  );
}
 
// ✅ 怪しい枝を1つずつ ErrorBoundary で包んで切り分ける
<SafeBox name="ProfileHeader">
  <ProfileHeader user={user} />
</SafeBox>
<SafeBox name="PostsList">
  <PostsList userId={user?.id} />
</SafeBox>

「画面全体が落ちる」を「特定のセクションだけが落ちる」に変えると、後の console.log もピンポイントで仕掛けられるようになります。

再発を減らすための日々の習慣

このエラーを根本的に減らすには、TypeScript で API レスポンスの型を厳密に書き、undefined の可能性を型レベルで強制するのが一番効きます。zod などのバリデーションを通せば、レスポンス形が変わったときにフロントの型と実体がずれることを防げます。型まわりのつまずきは TypeScript の型エラーが消えないときの直し方 にもまとめていますので、合わせて読んでみてください。React Native ランタイムで起きる他のエラーパターンも整理した React Native / Expo のランタイムエラー修正ガイド も参考になるはずです。

全体を振り返って

このエラーに出会ったら、まず (evaluating '...') の式をそのまま読み、一段手前のオブジェクトの実体を console.log で確認する、というクセを付けてみてください。?. を足して赤画面が消えても、データの形がそもそも想定と違っていれば、別の場所で必ず再発します。今日の自分のコードに useState() で初期値を省略している箇所がないかだけでも、ぜひ一度 grep してみると、思わぬ地雷が見つかるかもしれません。

シェア

お読みいただきありがとうございます

Rork Lab は広告なしで運営しており、サーバー費用などの運営コストはメンバーシップのご支援で賄っています。実装コード・ベンチマーク・本番設計パターンなど、実務でお役立ていただける記事を毎日更新しています。もし読んでよかったと感じていただけましたら、ぜひご覧ください。

  • コピー&ペーストで使える実装コード付き
  • 毎日新しい上級ガイドを追加
  • ¥580/月 または ¥1,480 の永久アクセス
メンバーシップを見る →

もしこの記事がお役に立ちましたら、チップ(¥150)で応援いただけると大変励みになります。広告なしでの運営を続けるため、皆さまのご支援が大きな力になっています。

関連記事

開発ツール2026-06-20
Rork が直せるバグと自分で直すバグを見分ける — エクスポートコードのトリアージ手順
Rork が自力で直すバグと、エクスポートしたReact Native/Expoコードを自分で手当てすべきバグを切り分けるトリアージ手順を、動くコードとともに整理しました。
開発ツール2026-06-17
Rork が自分で直せない3割を見極める — エクスポート前提の手直しワークフロー
Rork は遭遇したバグのおよそ7割を自力で直しますが、残り3割は手作業が必要です。再プロンプトで粘るべきか、エクスポートして自分で直すべきかを切り分ける判断基準と、動くコードでの手直し例をまとめました。
開発ツール2026-05-27
Rork × Hermes を本番で2ヶ月運用した所感 — 初回起動とメモリの実測値
Rork で生成したアプリで Hermes を有効にしたまま2ヶ月運用してきた中で、初回起動・メモリ・クラッシュの実測値がどう変化したかを記録します。個人開発の運用感覚から見た所感です。
📚RECOMMENDED BOOKS
大規模言語モデル入門
山田育矢
LLM開発
生成AIプロンプトエンジニアリング入門
我妻幸長
プロンプト
Claude CodeによるAI駆動開発入門
平川知秀
AI駆動開発
※ アフィリエイトリンクを含みます
もっと見る →