Sentryを導入したら、本番エラーに『気づけない問題』が解消した話

本番環境のエラーをユーザー報告で初めて知る状態が続いていたので、Sentryを導入したところ、エラーの検知から原因特定までのスピードがかなり変わりました。

🙌 結論から

個人開発のサービスで、本番のエラーをユーザーからの問い合わせで初めて知るという状態がしばらく続いていました。

これはさすがにまずいと思い、エラートラッキングサービスの Sentry を導入したところ、エラーの発生から気づくまでのスピードが別次元になりました

フロントエンドとバックエンドの両方にSDKを仕込むだけで、例外が起きた瞬間にスタックトレースとユーザーの操作履歴まで自動で送られてくるようになります。

無料枠でもエラー件数がそこそこ扱えるので、個人開発や小規模プロジェクトから始めやすいのも助かるポイントでした(・∀・)

今回は、実際に導入してから気づいた良い点とハマった点を整理してみます。

👀 Sentry とは何か

Sentryは、アプリケーションのエラー監視・パフォーマンス監視を行うプラットフォームです。

JavaScript・Node.js・Python・Rubyなど主要な言語・フレームワーク向けにSDKが用意されていて、数行の初期化コードを書くだけで例外を自動的に収集してくれます。

似たようなエラーは自動でグルーピングされ、「この不具合は何件・何人のユーザーに影響しているか」がダッシュボードで一目でわかります。

さらにリリースごとに発生件数を比較できるので、「このデプロイでエラーが増えた」という変化にもすぐ気づけます。

パフォーマンス監視や画面操作を録画するセッションリプレイの機能もありますが、まずはエラートラッキングだけでも十分に価値がありました。

💡 導入してみた

対象はExpress製のAPIサーバーと、React製のフロントエンドです。

npm install @sentry/node @sentry/react

サーバー側の初期化はこんな感じです。

import * as Sentry from '@sentry/node';

Sentry.init({
  dsn: process.env.SENTRY_DSN,
  environment: process.env.NODE_ENV,
  tracesSampleRate: 0.1,
});

app.use(Sentry.expressErrorHandler());

フロントエンド側も同様に Sentry.init() を呼び出し、エラーバウンダリと組み合わせて使います。

ソースマップをアップロードしておかないとスタックトレースがミニファイ後のコードのまま表示されるので、CIのビルド時に sentry-cli でアップロードするステップも追加しました。

sentry-cli releases files "$RELEASE" upload-sourcemaps ./dist

ここまで設定すれば、あとは例外が起きた瞬間にSentryのダッシュボードとSlackに通知が飛んでくる状態になります。

✨ 使ってみた感想

導入してすぐ、Safariの一部バージョンだけで発生していたnull参照のバグを検知できました。

これは発生率が低く、以前ならユーザーからの報告がない限りまず気づけなかったタイプの不具合だと思います(^o^)/

特にありがたいのが、エラー直前の**ユーザー操作の履歴(breadcrumbs)**が一緒に残ることです。

「どのボタンを押した後に落ちたか」がログとして残るので、再現条件を推測する時間がかなり短縮されました。

夜に子どもを寝かしつけたあと、スマホの通知でエラーに気づいて、翌朝の作業開始と同時に原因箇所へ直行できたこともあります。

「気づくまでのタイムラグ」が縮まっただけで、心理的な余裕もだいぶ変わった気がします。

パパ系Webエンジニア〜愛用ガジェット一覧 🛍️

この記事を書いている作業環境のガジェットを楽天ROOMにまとめています ✨ 在宅エンジニアのデスク作りの参考にどうぞ 🙌

👍 ハマったポイントと対処

最初にハマったのが、ソースマップのアップロードタイミングです。

デプロイより先にソースマップをアップロードしてしまい、リリースの紐付けがずれてスタックトレースが読めない状態になりました(・_・;)

これはCIのステップを「ビルド→ソースマップアップロード→デプロイ」の順に整理し直して解決しました。

もう一つは tracesSampleRate を最初 1.0 にしていたせいで、無料枠のクォータをあっという間に使い切ってしまったことです。

パフォーマンス監視まではまだ必要なかったので、ここは 0.1 程度まで下げて運用しています。

あとは beforeSend フックを使って、エラーに紛れ込みやすいメールアドレスなどの個人情報を送信前にマスキングする設定も忘れずに入れておきました。

Sentry.init({
  beforeSend(event) {
    if (event.user?.email) {
      delete event.user.email;
    }
    return event;
  },
});

🤖 Seerでもう一歩踏み込んでみた

導入してしばらく経ってから気づいたのが、SentryにSeerというAIデバッグ機能が搭載されていたことです。

エラーのIssue画面から「Root Cause Analysis」を実行すると、スタックトレースとコードベース(GitHub連携)を突き合わせて、原因の推測から修正案のコード生成までをSeerが一気にやってくれます。

最初は「どうせ的外れな提案だろう」と半信半疑で試したんですが、Nullチェック漏れのような単純な不具合では、修正のPRドラフトまでほぼそのまま使える精度でした(・∀・)

もちろん、業務ロジックが絡む複雑な不具合まではさすがに任せられないので、「まず当たりをつける一次調査」として使うくらいの距離感がちょうどいいと感じています。

自分のチームだったら、と考えると、深夜アラートが飛んできたときの一次対応にSeerを挟むのが向いていそうです。

人間が起きて確認する前にSeerが原因候補と再現条件をまとめてくれていれば、朝一の対応スピードはもう一段階変わるはずです。

無料枠でSeerがどこまで使えるかはプランによって変わってくるので、導入する際は現在の料金ページで対象プランを確認しておくのがおすすめです。

🙌 まとめ

Sentryを導入したことで、本番エラーに気づくまでの時間が体感でかなり短くなりました🙌

ユーザー報告に頼っていた頃と比べると、心理的な安心感の差が大きいです。

ソースマップの取り扱いとサンプリングレートの調整さえ押さえておけば、個人開発でも無理なく運用できると思います。

エラー監視をまだ入れていない方は、まず一番よく使うエンドポイントだけでも試してみる価値があると思います!

※ SDKの詳細な設定や対応フレームワークは Sentry公式ドキュメント をご確認ください👀