Debugging Tools
Every React Native app eventually breaks in a way that isn't obvious from just staring at the code.
The good news is React Native has a genuinely solid debugging toolkit — from the humble
console.log() all the way up to a full desktop inspector that shows you network
requests, component state, and stored data at a glance. This page walks through the tools you'll
reach for most often, roughly in the order you'd typically use them.
console.log(): The First Line of Defense
The humble console.log() works in React Native exactly like it does in any other
JavaScript environment, which makes it the fastest way to check a value without setting anything
up. Where the output shows up depends on how you're running the app: with a standard setup, logs
appear directly in the terminal window running the Metro bundler; if you've enabled remote
JS debugging (running your JS in a desktop browser tab instead of on-device), the same logs appear
in that browser's own developer console instead.
function handleSubmit(formValues) {
console.log('Submitting form with:', formValues);
// ... rest of the submit logic
}
It's quick, but it doesn't scale well — sprinkling dozens of console.log() calls
through a growing app gets noisy fast, which is where the tools below start to earn their keep.
The In-App Developer Menu
Every React Native app in development includes a built-in Developer Menu, briefly introduced back
in Your First App. Open it by shaking a physical device,
or with Cmd+D on an iOS simulator / Ctrl+M (or Cmd+M on Mac)
on an Android emulator. From there you get a handful of genuinely useful options:
| Option | What it does |
|---|---|
| Reload | Force-reloads the JS bundle from scratch, useful when Fast Refresh gets stuck |
| Debug Remote JS | Runs your app's JavaScript in a desktop browser instead of on-device, so you can use browser devtools/breakpoints |
| Toggle Inspector | Turns on the Element Inspector (covered below) for tapping any visible element |
React Native DevTools and Flipper
For anything beyond quick log statements, React Native DevTools (and its predecessor, Flipper) is a
standalone desktop application that connects to your running app and gives you a genuinely richer
debugging experience: a live component tree you can browse and click through, a network tab showing
every request your app makes (handy for debugging the fetch/Axios calls from
Networking: Fetch & Axios), and a way to
directly inspect what's currently stored in AsyncStorage — extremely useful when
tracking down why persisted data (see Local Storage:
AsyncStorage) isn't showing what you expect.
The Element Inspector: Debugging Layout Visually
Enabling the Element Inspector (from the Developer Menu) lets you tap directly on any element
rendered on screen and see exactly which component it is, along with its resolved style values —
the actual padding, margin, width, and flex properties currently being applied. This is by far the
fastest way to track down a spacing or alignment bug: rather than guessing which
flex/justifyContent/alignItems combination from
Flexbox Layout is misbehaving, you tap the
misbehaving element and read its computed layout directly.
A Common Real Bug: "Text strings must be rendered within a <Text> component"
This is one of the most common errors newcomers hit, and it comes directly from a rule covered in
Core Components: raw text can only ever appear
inside a <Text> component — never as a direct child of a <View>.
The mistake usually sneaks in through a conditional expression that accidentally evaluates to a
plain string or number sitting next to JSX.
// Throws: "Text strings must be rendered within a <Text> component"
function Greeting({ name }) {
return (
<View>
Hello, {name}! // this bare text is NOT inside <Text>
</View>
);
}
// Fixed: wrap the text in <Text>
function Greeting({ name }) {
return (
<View>
<Text>Hello, {name}!</Text>
</View>
);
}
The same trap shows up with a falsy value rendered directly inside a View — for
example {count && <Text>{count}</Text>} when count is
0 renders the literal number 0 as bare text next to the
<View>'s other children, triggering the same error. Whenever you see this
message, the fix is always the same: find the bare string/number sitting outside a
<Text> and wrap it.
React DevTools: Inspecting Component Tree, Props, and State
The React DevTools browser extension — the same one countless React web developers already have installed — also works with React Native. Once connected to your running app, it shows the live component tree, lets you click any component to see its current props and state, and lets you tweak those values on the fly to see how the UI reacts. If you're coming from web React, this is the fastest tool to feel productive with immediately, since the experience is nearly identical.