Session Replay
Session Replay reconstructs a user’s session as a video: every page view, every DOM mutation, every click, every keystroke (with privacy controls). Use it for the “what did the user actually do?” debugging that no amount of metrics or logs can answer.
When to use replay
Section titled “When to use replay”- A user reports a bug you can’t reproduce.
- You’re investigating an error and want to see the exact path that triggered it.
- You’re studying a confusing UX flow and want to watch real users navigate it.
- A customer asks “why was I charged twice?” You can replay the actual checkout.
When NOT to use replay
Section titled “When NOT to use replay”- For aggregate analytics. That’s RUM’s measurement layer.
- As your only data source. Replay is heavy and only captured for filter-matched sessions. The other observability pillars are still your high-level monitoring.
How it works
Section titled “How it works”Replay is built on rrweb. The recorder:
- Snapshots the initial DOM.
- Records every mutation (additions, deletions, attribute changes).
- Records every input event (clicks, scrolls, typing).
- Records network requests (visually, so you see the loading state).
- Batches and ships these as segments to
https://replay.siteqwality.com.
Playback in the dashboard:
- Replays the initial DOM.
- Applies each mutation in real time.
- Renders mouse cursor, click highlights, typing.
- Lets you scrub the timeline, jump to errors, slow down.
Activation
Section titled “Activation”Replay is off by default. It activates only for sessions matching a session filter with capture_replay: true.
Once activated for a session, replay records from the activation moment onward, not from session start. So an errored session might have replay starting halfway through, when the error fired.
Privacy
Section titled “Privacy”Replay is a privacy-sensitive feature. Two SDK-level controls (set on the RUM application):
mask_inputs: replace input values with***in the recording. Critical for password fields, credit card forms.mask_text: replace user-visible text with***. Use when displaying customer names, financial figures, etc.
Both are stored per RUM application, and both are shown as toggles on the application’s privacy settings in the dashboard. Check them there before you rely on either. The toggles reflect what is actually stored for your application, which is the only thing that governs what gets recorded. Do not assume a default.
Per-element overrides:
<!-- Mask the text of this element and everything nested inside it --><div class="rr-mask">Sensitive content</div>
<!-- Record this element as an empty placeholder; its subtree is not recorded --><div class="rr-block">Don't record this at all</div>
<!-- Do not record input events fired on THIS element. Put it on the input itself --><input class="rr-ignore" />The rr-mask / rr-block / rr-ignore class names are rrweb’s own defaults. The SDK does not override them, which is why they work. They do not behave alike, and the differences matter more than the similarity:
| Class | What it covers | Cascades to descendants |
|---|---|---|
rr-mask | Text nodes only. Not input values, not attributes, not alt / title / placeholder. | Yes |
rr-block | The whole subtree. The element itself is still recorded, as an empty box of the right width and height. | Yes |
rr-ignore | Input events fired on the element carrying the class. | No |
rr-mask is the one to reach for when the concern is rendered text, and it is the only per-element control that cascades and masks rather than removes. If the concern is an input value, mask_inputs on the application is the control that covers it; rr-mask does not.
Pricing
Section titled “Pricing”Replay is paid. Sessions with replay are billed per recorded session and per stored MB. Set conservative session filters. Do not “replay everyone.”
Limits
Section titled “Limits”- Segment size: ~1MB per segment. Larger sessions are split into multiple segments.
- Retention: 30 days, fixed, on every plan. It is the same on the free tier and on every paid replay pack, and it is not configurable. Two independent mechanisms both enforce 30 days: a TTL on the
rum_replay_segmentsindex and a flat 30-day expiry rule on the S3 bucket holding the recordings. Buying a larger replay pack raises the number of sessions you can record, not how long they are kept. - Replay can be 10–100× the cost of plain RUM depending on session length and DOM complexity. Filter aggressively.