React
Learn how to set up and configure Sentry in your React application.
You need:
Select which Sentry features you'd like to configure to get the corresponding setup instructions below.
Run the command for your preferred package manager to add the Sentry SDK to your application:
npm install @sentry/react --save
The stack traces in your Sentry errors probably won't look like your actual code. To fix this, upload your source maps to Sentry. The easiest way to do this is by using the Sentry Wizard:
npx @sentry/wizard@latest -i sourcemaps
Add the following to your application's entry point (typically index.js
, main.js
, or App.js
) or to the file before you use any other Sentry method:
instrument.js
import * as Sentry from "@sentry/react";
Sentry.init({
dsn: "https://examplePublicKey@o0.ingest.sentry.io/0",
// Adds request headers and IP for users, for more info visit:
// https://docs.sentry.io/platforms/javascript/guides/react/configuration/options/#sendDefaultPii
sendDefaultPii: true,
integrations: [
// performance
Sentry.browserTracingIntegration(),
// performance
// session-replay
Sentry.replayIntegration(),
// session-replay
// user-feedback
Sentry.feedbackIntegration({
// Additional SDK configuration goes in here, for example:
colorScheme: "system",
}),
// user-feedback
// logs
Sentry.consoleLoggingIntegration({ levels: ["log", "warn", "error"] }),
// logs
],
// logs
// For help logging, see: https://docs.sentry.io/platforms/javascript/guides/react/logging/
enableLogs: true,
// logs
// performance
// Set sample rate for performance monitoring
// We recommend adjusting this value in production
tracesSampleRate: 1.0,
// performance
// session-replay
// For session replay
// See: https://docs.sentry.io/platforms/javascript/session-replay/
replaysSessionSampleRate: 0.1, // Sample 10% of sessions
replaysOnErrorSampleRate: 1.0, // Sample 100% of sessions with an error
// session-replay
// logs
// For help logging, see: https://docs.sentry.io/platforms/javascript/guides/react/logging/
extraErrorDataIntegration: false,
// logs
});
Import the instrument.js
file in your application's entry point before all other imports to initialize the SDK:
index.jsx
import "./instrument.js";
import { StrictMode } from "react";
import { createRoot } from "react-dom/client";
import App from "./App";
const container = document.getElementById("root");
const root = createRoot(container);
root.render(<App />);
To make sure Sentry captures all your app's errors, configure error handling based on your React version.
Starting with React 19, use the onCaughtError
and onUncaughtError
root options to capture React errors:
index.jsx
import "./instrument.js";
import * as Sentry from "@sentry/react";
import { createRoot } from "react-dom/client";
import App from "./App";
const container = document.getElementById("root");
const root = createRoot(container, {
// Callback for errors caught by React error boundaries
onCaughtError: Sentry.reactErrorHandler((error, errorInfo) => {
console.error("Caught error:", error, errorInfo.componentStack);
}),
// Callback for errors not caught by React error boundaries
onUncaughtError: Sentry.reactErrorHandler(),
});
root.render(<App />);
Use the Sentry Error Boundary to wrap your application:
index.jsx
import React from "react";
import * as Sentry from "@sentry/react";
<Sentry.ErrorBoundary fallback={<p>An error has occurred</p>} showDialog>
<App />
</Sentry.ErrorBoundary>;
Alternatively, if you're using a class component, you can wrap your application with Sentry.withErrorBoundary
. Find out more here.
Structured logging lets users send text-based log information from their applications to Sentry. Once in Sentry, these logs can be viewed alongside relevant errors, searched by text-string, or searched using their individual attributes.
Use Sentry's logger to capture structured logs with meaningful attributes that help you debug issues and understand user behavior.
import * as Sentry from "@sentry/react";
const { logger } = Sentry;
// Send structured logs with attributes
logger.info("User completed checkout", {
userId: 123,
orderId: "order_456",
amount: 99.99,
});
logger.error("Payment processing failed", {
errorCode: "CARD_DECLINED",
userId: 123,
attemptCount: 3,
});
// Using template literals for dynamic data
logger.warn(logger.fmt`Rate limit exceeded for user: ${userId}`);
Replays allow you to see video-like reproductions of user sessions.
By default, Session Replay masks sensitive data for privacy and to protect PII data. You can modify the replay configurations in your client-side Sentry initialization to show (unmask) specific content that's safe to display.
instrument.js
import * as Sentry from "@sentry/react";
Sentry.init({
dsn: "https://examplePublicKey@o0.ingest.sentry.io/0",
integrations: [
Sentry.replayIntegration({
// This will show the content of the div with the class "reveal-content" and the span with the data-safe-to-show attribute
unmask: [".reveal-content", "[data-safe-to-show]"],
// This will show all text content in replays. Use with caution.
maskAllText: false,
// This will show all media content in replays. Use with caution.
blockAllMedia: false,
}),
],
replaysSessionSampleRate: 0.1,
replaysOnErrorSampleRate: 1.0,
// ... your existing config
});
Tracing allows you to monitor interactions between multiple services or applications. Create custom spans to measure specific operations and add meaningful attributes. This helps you understand performance bottlenecks and debug issues with detailed context.
import * as Sentry from "@sentry/react";
// Create custom spans to measure specific operations
async function processUserData(userId) {
return await Sentry.startSpan(
{
name: "Process User Data",
op: "function",
attributes: {
userId: userId,
operation: "data_processing",
version: "2.1",
},
},
async () => {
// Your business logic here
const userData = await fetchUserData(userId);
// Nested span for specific operations
return await Sentry.startSpan(
{
name: "Transform Data",
op: "transform",
attributes: {
recordCount: userData.length,
transformType: "normalize",
},
},
() => {
return transformUserData(userData);
},
);
},
);
}
// Add attributes to existing spans
const span = Sentry.getActiveSpan();
if (span) {
span.setAttributes({
cacheHit: true,
region: "us-west-2",
performanceScore: 0.95,
});
}
You can prevent ad blockers from blocking Sentry events using tunneling. Use the tunnel
option to add an API endpoint in your application that forwards Sentry events to Sentry servers.
To enable tunneling, update Sentry.init
with the following option:
Sentry.init({
dsn: "https://examplePublicKey@o0.ingest.sentry.io/0",,
tunnel: "/tunnel",
});
This will send all events to the tunnel
endpoint. However, the events need to be parsed and redirected to Sentry, so you'll need to do additional configuration on the server. You can find a detailed explanation on how to do this on our Troubleshooting page.
Let's test your setup and confirm that Sentry is working correctly and sending data to your Sentry project.
Add the following test button to one of your pages, which will trigger an error that Sentry will capture when you click it:
<button
type="button"
onClick={() => {
throw new Error("Sentry Test Error");
}}
>
Break the world
</button>;
Open the page in a browser (for most React applications, this will be at localhost) and click the button to trigger a frontend error.
Important
Errors triggered from within your browser's developer tools (like the browser console) are sandboxed, so they will not trigger Sentry's error monitoring.
Now, head over to your project on Sentry.io to view the collected data (it takes a couple of moments for the data to appear).
At this point, you should have integrated Sentry into your React application and should already be sending error and performance data to your Sentry project.
Now's a good time to customize your setup and look into more advanced topics:
- Extend Sentry to your backend using one of our SDKs
- Continue to customize your configuration
- Learn more about the React Error Boundary
- Learn how to manually capture errors
- Avoid ad-blockers with tunneling
Our documentation is open source and available on GitHub. Your contributions are welcome, whether fixing a typo (drat!) or suggesting an update ("yeah, this would be better").