Error Tracking: From a Vague Bug Report to a Stack Trace with Context

When an exception fires in production, the difference between a log file nobody reads and a tracked issue is context. What a good error-tracking setup captures, how to keep it out of the noise, and what that means for the error page your users see.

Error Tracking: From a Vague Bug Report to a Stack Trace with Context

Production errors surface in two ways. The good way: an exception fires, something captures it with enough context to diagnose it in minutes. The bad way: a user writes to support three days later with "it didn't work", and the trail is a log file with thousands of lines and no way to tell which one was theirs. Most projects sit closer to the bad way than their developers admit. Uptime checks and metrics, which we treat separately, tell you the app is alive. An error tracker tells you it is misbehaving, which is a quieter and more expensive problem.

What an error tracker buys you

A log file answers nothing on its own. The tracker layer does three jobs:

  • It captures the exception with context: the stack trace, the URL, the request method, the user ID, the tenant if the app is multi-tenant, and the release that was running.
  • It groups duplicates. The same null-pointer hit three thousand times in an hour is one issue, not three thousand log lines.
  • It notifies on what matters: a new exception in a money path, a sudden jump in an old one.

The tools here are commodity. Sentry is the default for Laravel and its official integration wires itself into the exception handler; self-hosted alternatives like GlitchTip speak the same protocol if data residency matters. The tool choice matters less than the setup discipline around it.

Context is the product

The stack trace tells you where. Context tells you for whom and since when. The fields that earn their place:

  • The release version or git SHA. "Checkout started throwing after yesterday's deploy" is an answer. "Checkout throws sometimes" is a shrug.
  • User and tenant identifiers, so you can reproduce with the same data. An ID, not a name; the tracker is a third party unless you self-host.
  • Breadcrumbs: the last handful of queries, jobs, and HTTP calls before the crash. In practice, the breadcrumb "queued a job 40 seconds before the exception" has settled more arguments than any dashboard.

What to keep out matters as much. Request bodies, headers, and local variables regularly contain passwords, tokens, and personal data, and an error tracker copies all of it to wherever it runs. Scrub sensitive fields in the SDK config and treat the tracker as part of your data inventory. An error tool that quietly stores PII is a GDPR problem you built yourself, and the stack trace doesn't need it to do its job.

Noise control decides whether it survives

Every tracker setup rots the same way: nobody triages, the issue list grows past a thousand items, and the notification emails get muted. Three habits prevent that:

  1. Resolve or ignore issues weekly. Ignoring scanner noise (bots hitting /wp-admin on a Laravel app) is legitimate, but it should be a decision, not an accident of neglect.
  2. Alert on new issues and on regressions, not on every event. A spike in an existing issue belongs to the same rules as your metrics alerting.
  3. Sample high-volume, low-value errors. A tracking endpoint throwing on malformed bot requests four thousand times a day doesn't need every occurrence stored.

The part users see

A custom error page turns a support ticket into a diagnosable one. Show a plain message and a short reference code, generate the same code into the report the tracker receives, and when a user pastes "error AB12CD" into a support form, the issue is one search away. In Laravel this is an exception renderer plus a correlation ID in the response, and the total cost is an afternoon.

What it doesn't replace

An error tracker is not monitoring, not logging, and not a test suite. It catches the exceptions your code throws; it says nothing about a job that silently produced wrong numbers, and it won't stop a regression from deploying. The layers stack: tests before merge, the tracker after release, metrics for trends. The ritual that makes it pay is small: open the tracker before the inbox each morning. Two minutes, and it's the difference between "users say the site is broken" and a fix with a linked issue by lunch.