diff --git a/package-lock.json b/package-lock.json
index 303d2f4..95a9eb4 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -19,6 +19,7 @@
"@radix-ui/react-select": "^2.2.6",
"@radix-ui/react-separator": "^1.1.7",
"@radix-ui/react-slot": "^1.2.3",
+ "@sentry/react": "^10.33.0",
"@supabase/supabase-js": "^2.76.1",
"@tailwindcss/vite": "^4.1.14",
"@tanstack/react-query": "^5.90.9",
@@ -2375,6 +2376,97 @@
"win32"
]
},
+ "node_modules/@sentry-internal/browser-utils": {
+ "version": "10.33.0",
+ "resolved": "https://registry.npmjs.org/@sentry-internal/browser-utils/-/browser-utils-10.33.0.tgz",
+ "integrity": "sha512-nDJFHAfiFifBfJB0OF6DV6BIsIV5uah4lDsV4UBAgPBf+YAHclO10y1gi2U/JMh58c+s4lXi9p+PI1TFXZ0c6w==",
+ "license": "MIT",
+ "dependencies": {
+ "@sentry/core": "10.33.0"
+ },
+ "engines": {
+ "node": ">=18"
+ }
+ },
+ "node_modules/@sentry-internal/feedback": {
+ "version": "10.33.0",
+ "resolved": "https://registry.npmjs.org/@sentry-internal/feedback/-/feedback-10.33.0.tgz",
+ "integrity": "sha512-sN/VLWtEf0BeV6w6wldIpTxUQxNVc9o9tjLRQa8je1ZV2FCgXA124Iff/zsowsz82dLqtg7qp6GA5zYXVq+JMA==",
+ "license": "MIT",
+ "dependencies": {
+ "@sentry/core": "10.33.0"
+ },
+ "engines": {
+ "node": ">=18"
+ }
+ },
+ "node_modules/@sentry-internal/replay": {
+ "version": "10.33.0",
+ "resolved": "https://registry.npmjs.org/@sentry-internal/replay/-/replay-10.33.0.tgz",
+ "integrity": "sha512-UOU9PYxuXnPop3HoQ3l4Q7SZUXJC3Vmfm0Adgad8U03UcrThWIHYc5CxECSrVzfDFNOT7w9o7HQgRAgWxBPMXg==",
+ "license": "MIT",
+ "dependencies": {
+ "@sentry-internal/browser-utils": "10.33.0",
+ "@sentry/core": "10.33.0"
+ },
+ "engines": {
+ "node": ">=18"
+ }
+ },
+ "node_modules/@sentry-internal/replay-canvas": {
+ "version": "10.33.0",
+ "resolved": "https://registry.npmjs.org/@sentry-internal/replay-canvas/-/replay-canvas-10.33.0.tgz",
+ "integrity": "sha512-MTmP6uoAVzw4CCPeqCgCLsRSiOfGLxgyMFjGTCW3E7t62MJ9S0H5sLsQ34sHxXUa1gFU9UNAjEvRRpZ0JvWrPw==",
+ "license": "MIT",
+ "dependencies": {
+ "@sentry-internal/replay": "10.33.0",
+ "@sentry/core": "10.33.0"
+ },
+ "engines": {
+ "node": ">=18"
+ }
+ },
+ "node_modules/@sentry/browser": {
+ "version": "10.33.0",
+ "resolved": "https://registry.npmjs.org/@sentry/browser/-/browser-10.33.0.tgz",
+ "integrity": "sha512-iWiPjik9zetM84jKfk01UveW1J0+X7w8XmJ8+IrhTyNDBVUWCRJWD8FrksiN1dRSg5mFWgfMRzKMz27hAScRwg==",
+ "license": "MIT",
+ "dependencies": {
+ "@sentry-internal/browser-utils": "10.33.0",
+ "@sentry-internal/feedback": "10.33.0",
+ "@sentry-internal/replay": "10.33.0",
+ "@sentry-internal/replay-canvas": "10.33.0",
+ "@sentry/core": "10.33.0"
+ },
+ "engines": {
+ "node": ">=18"
+ }
+ },
+ "node_modules/@sentry/core": {
+ "version": "10.33.0",
+ "resolved": "https://registry.npmjs.org/@sentry/core/-/core-10.33.0.tgz",
+ "integrity": "sha512-ehH1VSUclIHZKEZVdv+klofsFIh8FFzqA6AAV23RtLepptzA8wqQzUGraEuSN25sYcNmYJ0jti5U0Ys+WZv5Dw==",
+ "license": "MIT",
+ "engines": {
+ "node": ">=18"
+ }
+ },
+ "node_modules/@sentry/react": {
+ "version": "10.33.0",
+ "resolved": "https://registry.npmjs.org/@sentry/react/-/react-10.33.0.tgz",
+ "integrity": "sha512-iMdC2Iw54ibAccatJ5TjoLlIy3VotFteied7JFvOudgj1/2eBBeWthRobZ5p6/nAOpj4p9vJk0DeLrc012sd2g==",
+ "license": "MIT",
+ "dependencies": {
+ "@sentry/browser": "10.33.0",
+ "@sentry/core": "10.33.0"
+ },
+ "engines": {
+ "node": ">=18"
+ },
+ "peerDependencies": {
+ "react": "^16.14.0 || 17.x || 18.x || 19.x"
+ }
+ },
"node_modules/@shikijs/types": {
"version": "3.13.0",
"resolved": "https://registry.npmjs.org/@shikijs/types/-/types-3.13.0.tgz",
diff --git a/package.json b/package.json
index 1f39e5b..8e34e01 100644
--- a/package.json
+++ b/package.json
@@ -22,6 +22,7 @@
"@radix-ui/react-select": "^2.2.6",
"@radix-ui/react-separator": "^1.1.7",
"@radix-ui/react-slot": "^1.2.3",
+ "@sentry/react": "^10.33.0",
"@supabase/supabase-js": "^2.76.1",
"@tailwindcss/vite": "^4.1.14",
"@tanstack/react-query": "^5.90.9",
diff --git a/src/lib/sentry.ts b/src/lib/sentry.ts
new file mode 100644
index 0000000..c606de6
--- /dev/null
+++ b/src/lib/sentry.ts
@@ -0,0 +1,27 @@
+import * as Sentry from "@sentry/react";
+
+export function initializeSentry() {
+ const SENTRY_DSN = import.meta.env.VITE_SENTRY_DSN;
+
+ if (SENTRY_DSN) {
+ Sentry.init({
+ dsn: SENTRY_DSN,
+ // Setting this option to true will send default PII data to Sentry.
+ // For example, automatic IP address collection on events
+ sendDefaultPii: true,
+ integrations: [
+ Sentry.browserTracingIntegration(),
+ Sentry.replayIntegration(),
+ ],
+ // Tracing
+ tracesSampleRate: 1.0, // Capture 100% of the transactions
+ // Set 'tracePropagationTargets' to control for which URLs distributed tracing should be enabled
+ tracePropagationTargets: ["localhost", /^https:\/\/yourserver\.io\/api/],
+ // Session Replay
+ replaysSessionSampleRate: 0.1, // This sets the sample rate at 10%. You may want to change it to 100% while in development and then sample at a lower rate in production.
+ replaysOnErrorSampleRate: 1.0, // If you're not already sampling the entire session, change the sample rate to 100% when sampling sessions where errors occur.,
+ // Enable logs to be sent to Sentry
+ enableLogs: true,
+ });
+ }
+}
diff --git a/src/main.tsx b/src/main.tsx
index 827b85e..b303245 100644
--- a/src/main.tsx
+++ b/src/main.tsx
@@ -16,29 +16,57 @@ import FindTeammates from "./pages/find-teammates/index.tsx";
import { QueryClientProvider } from "@tanstack/react-query";
import { queryClient } from "@/lib/queryClient";
import { ReactQueryDevtools } from "@tanstack/react-query-devtools";
+import { initializeSentry } from "@/lib/sentry";
+import * as Sentry from "@sentry/react";
import "./index.css";
-createRoot(document.getElementById("root")!).render(
-
잠시 후 다시 시도해주세요.
+ +