Free lesson · Frontend System Design
Your frontend runs where you can't see it
Here is the uncomfortable fact that makes observability essential for frontend specifically: your frontend code runs on your users' devices, in their browsers, on their networks - not on infrastructure you control and can inspect. A backend engineer can SSH into a server, read its logs, and watch it run. You cannot reach into a user's phone in another country on a flaky connection running a browser version you've never tested. Your production frontend is, by default, a black box: you have no idea what's actually happening to it in the real world unless the app itself tells you - unless it emits data about its own behavior. Observability is the discipline of making the app emit that data and using it to understand what's happening in production from the outside. Without it, you are flying blind: errors users hit but never report, performance that's terrible for some segment, features breaking only on specific device/browser combinations - all invisible.
This is the opening lesson of the Observability cluster, and it establishes what observability is, why frontend needs it acutely, and the vocabulary (logging, monitoring, the three pillars) the rest of the cluster builds on. The defining frontend challenge throughout: you operate in an environment of enormous, uncontrollable variability - countless device, browser, OS, network, and locale combinations - where bugs occur that you cannot reproduce locally because you can't even see the conditions that triggered them. Observability is how you turn that black box into something you can understand, by instrumenting the app to report on itself and then watching, analyzing, and acting on what it reports.
Why frontend observability is acutely necessary
Several factors make production frontend especially opaque without observability:
- It runs on devices you don't control. Unlike a server, you can't inspect the runtime - your only window is the telemetry the app sends back. The frontend is fundamentally remote and inaccessible.
- Staggering environment variability. Your users span thousands of device models, browser versions, OS versions, screen sizes, network conditions, locales, and extensions. A bug might occur only on a specific old browser, or only under a slow network, or only with a particular extension installed - conditions you'll never hit on your dev machine. You can't reproduce what you can't see.
- Silent failures. Most users who hit an error don't report it - they just leave, frustrated. The performance that's fine for you might be miserable for a user on a slow device in the field. Without data, these failures are invisible - you'd never know a checkout button throws an error on a certain browser unless the app told you.
- The gap between "works on my machine" and reality. Everything passes locally and in staging, yet real users on real conditions hit problems. Observability is what closes the gap between your controlled testing and the uncontrolled real world.
The bottom line: for frontend, production is a black box, and observability is the only way to see inside it. Naming this - that the frontend runs on users' uncontrollable devices and you only know what's happening through emitted data - is the framing that makes everything in this cluster matter.
graph LR
App[Your app running on<br/>a user's device - a black box] -->|emits data| Inst[Instrumentation<br/>captures errors, metrics, events]
Inst -->|sends telemetry| Collect[Collection / backend<br/>Sentry, RUM, analytics]
Collect --> Monitor[Monitoring<br/>dashboards, health over time]
Monitor --> Alert[Alerting<br/>notify when something's wrong]
Alert --> Fix[Triage + fix]
Fix -->|improves the app| App
This diagram shows the observability loop. Your app runs on a user's device, which is a black box you can't directly inspect. The app emits data through instrumentation, which captures errors, metrics, and events. That telemetry is sent to a collection backend such as Sentry, a RUM tool, or analytics. Monitoring then watches the collected data through dashboards and tracks health over time. Alerting notifies you when something is wrong. You then triage and fix the issue, which improves the app - closing the loop. Each stage of this cluster maps to one part of this loop: instrumentation, collection, monitoring, alerting, and triage-and-fix.
The three pillars: logs, metrics, traces
The classic framework for observability data is the three pillars, and knowing them organizes everything:
- Logs - discrete records of events that happened ("user clicked checkout," "API call failed with 500," "error thrown in component X"). Logs are the detailed, granular trail - what happened, when, with what context. On the frontend, this includes error logs and custom event logs (and "breadcrumbs," the trail of events leading up to an error).
- Metrics - aggregated numerical measurements over time (error rate, p75 LCP, requests per minute, conversion rate). Metrics are quantitative and trended - they tell you how much and how it's changing, ideal for dashboards and thresholds. Frontend metrics include the Core Web Vitals from real users (RUM, connecting to the Performance cluster), error rates, and business metrics.
- Traces - the path of a single operation across the system - for frontend, following a user action through the frontend and into the backend request(s) it triggers, seeing where time went and where it failed. Distributed tracing connects the frontend and backend views of the same operation.
These three give complementary views: metrics tell you something is wrong (error rate spiked), logs tell you what specifically happened (this error, with this context), and traces tell you where in the flow it happened. Together they let you both detect problems (metrics, alerting) and diagnose them (logs, traces) - which maps exactly onto this cluster's later lessons. Knowing the three pillars is the baseline vocabulary of observability.
Logging versus monitoring versus observability
Three related terms are worth distinguishing precisely, since they're often conflated:
- Logging is recording events and data - producing the raw material (the logs). It's the capture step.
- Monitoring is watching the collected data - dashboards, tracking health and key metrics over time, and detecting when something looks wrong. It's the observation step, typically of known metrics you decided to track in advance.
- Observability is the broader capability of being able to understand your system's behavior - including answering new questions you didn't anticipate - built on rich instrumentation, collection, and analysis. The classic distinction: monitoring tells you whether the things you predicted to watch are okay; observability lets you ask why when something unexpected happens, exploring the data to understand novel problems.
For practical purposes, the pipeline is: instrument the app to emit telemetry → collect it → monitor/analyze it (dashboards, exploration) → alert on problems → act. Logging and monitoring are stages within the larger observability capability. The distinction that matters for an interview: monitoring watches the known; observability enables understanding the unknown - and good frontend observability provides both.
What frontend observability actually captures
Concretely, a frontend observability setup captures several data types, each with characteristic tooling:
- Errors and exceptions - JavaScript errors, unhandled promise rejections, errors caught by React error boundaries. Error monitoring (e.g., Sentry) captures these with rich context - the headline frontend observability use, since errors are the most direct signal that something's broken.
- Performance (RUM) - real-user Core Web Vitals and custom timings from actual sessions, connecting directly to the Performance cluster's field-monitoring half.
- User behavior / product analytics - what users do, funnels, feature usage (the product-facing side of telemetry).
- Session replay - tools (LogRocket, FullStory) that reconstruct what the user actually saw and did leading to a problem, an extraordinarily powerful diagnosis aid (covered more in triage).
The frontend observability stack, then, centers on error monitoring (Sentry), RUM (web-vitals + a RUM platform), session replay, and analytics - together turning the black box into something you can see into.
Important: Frontend runs on users' uncontrollable devices, making production a black box you can only understand through the data the app emits - that's why observability is acutely necessary for frontend, given staggering device/browser/network variability and silent failures users never report. The three pillars: logs (discrete events - what happened), metrics (aggregated numbers over time - how much/trend), traces (one operation across frontend→backend - where it failed); metrics detect, logs/traces diagnose. Distinguish logging (recording), monitoring (watching known metrics), and observability (the broader capability to understand even unexpected problems). The pipeline: instrument → collect → monitor → alert → act. Frontend captures errors (Sentry), performance/RUM (Web Vitals from real users), user behavior, and session replay.
Interview: Lead with the black-box framing: "The frontend runs on users' devices I can't inspect, across thousands of device, browser, and network combinations, so production is a black box - I only know what's happening through the data the app emits. That's why observability matters: errors users hit but never report, performance that's bad for some segment, bugs that only occur on specific configs - all invisible without it. I think in the three pillars: metrics like error rate and real-user Web Vitals to detect problems, logs and breadcrumbs to know what happened, and traces to follow an operation from the frontend into the backend to see where it failed. Concretely I'd set up error monitoring like Sentry, RUM for real-user performance, and session replay for diagnosis. Monitoring watches the known; observability lets me ask why when something unexpected breaks." The black-box framing plus the three pillars is the senior answer.
Monitoring the known versus exploring the unknown
The distinction between monitoring and full observability deserves a closer look, because it captures why observability is more than dashboards. Monitoring is built around known questions: you decide in advance which metrics matter (error rate, LCP, conversion), build dashboards for them, and watch. It answers "are the things I expected to watch okay?" - and it's essential, but it has a blind spot: it only shows you problems you anticipated. Observability aims higher - it's the ability to answer new, unanticipated questions about your system by exploring the rich data it emits, without shipping new code to investigate. When something breaks in a way you never predicted (a specific interaction on a specific browser produces a subtle failure), monitoring's pre-built dashboards won't have a chart for it - but observable systems, with rich, high-cardinality telemetry (errors tagged with many dimensions, traces, detailed context), let you slice and explore to understand the novel problem.
This is the "unknown unknowns" idea: monitoring handles known unknowns (problems you knew to watch for), while observability handles unknown unknowns (problems you couldn't have anticipated). For frontend, where the environment variability is so vast that you genuinely cannot predict every failure mode, the ability to explore - to ask "show me errors for this browser version in this release on this flow" after the fact - is what lets you diagnose the weird, config-specific bugs that dominate real-world frontend issues. Good frontend observability provides both: dashboards and alerts for the known metrics, and rich, explorable data for the unknown problems. Articulating that monitoring watches the known while observability explores the unknown - and why frontend's variability makes the explorable kind essential - is the nuanced framing that goes beyond "set up some dashboards."
Observability is built incrementally
A practical, reassuring point: you don't build full observability overnight, and you shouldn't try to. Observability is built incrementally, in rough priority order of value:
- Start with error monitoring. Wiring up Sentry-style error capture is the highest-value first step - it immediately turns invisible production errors into visible, actionable reports, often surfacing problems you didn't know existed. This alone is transformative.
- Add real-user performance (RUM). Capturing field Web Vitals gives you the real-world performance truth the Performance cluster emphasized.
- Add session replay for the diagnosis power it brings to tricky bugs.
- Add tracing and richer telemetry as the system and team mature, for end-to-end and exploratory visibility.
The point is that some observability is dramatically better than none, and the first increment (error monitoring) delivers most of the initial value for modest effort. A team that has only error monitoring is already far ahead of a team flying blind. This incremental framing matters because "observability" can sound like a heavy, all-or-nothing platform investment, when in practice the pragmatic path is to start with error monitoring, get immediate value, and layer on more as needs grow. Knowing the sensible order to build observability - errors first, then performance, then replay and tracing - is practical, senior guidance.
What you should carry out of this lesson
The frontend runs on users' uncontrollable devices, so production is a black box you can only understand through the data the app emits - which makes observability acutely necessary given enormous device/browser/network variability and silent failures users never report. The three pillars organize observability data: logs (discrete events - what happened), metrics (aggregated numbers over time - how much and how it's trending), and traces (one operation across frontend and backend - where it failed), with metrics detecting problems and logs and traces diagnosing them. Distinguish logging (recording the data), monitoring (watching known metrics for known problems), and observability (the broader capability to understand even unanticipated problems), all stages of the pipeline: instrument → collect → monitor → alert → act. A frontend observability setup centers on error monitoring (Sentry), real-user performance (RUM/Web Vitals), user behavior, and session replay - turning the black box into something you can see inside.
Observability begins with the app emitting data - but that data doesn't appear by magic. The next lesson covers how you make the app report on itself: telemetry and instrumentation - capturing errors with rich context, performance from real users, and key events, while controlling volume, protecting privacy, and keeping the instrumentation itself lightweight. Telemetry and instrumentation is next.