Skip to main content
Session Replay lets you watch exactly what happened before an error occurred, helping you understand the user journey that led to the problem.

Overview

Proliferate’s session replay uses rrweb to record DOM snapshots and incremental changes. Unlike traditional screen recording, this approach:
  • Captures DOM state rather than pixels, allowing text selection and inspection
  • Uses minimal bandwidth by only recording changes, not full frames
  • Preserves privacy with built-in input masking

The Ring Buffer Architecture

Session replay uses a ring buffer that keeps only the most recent activity. This design has key advantages:
  1. Memory efficient: Old events are automatically discarded
  2. Bandwidth efficient: Replay is only sent when an error occurs
  3. Privacy-first: No continuous data transmission
┌────────────────────────────────────────────────────────────────────┐
│                        Ring Buffer (5 minutes)                      │
│                                                                      │
│  [Older events evicted] ◄── [Events] ──► [Newest events]           │
│                                                    ▲                 │
│                                                    │                 │
│                                              Error occurs            │
│                                              Buffer sent             │
└────────────────────────────────────────────────────────────────────┘

Buffer Limits

The replay buffer has three configurable limits:
LimitDefaultDescription
maxBufferMinutes5Maximum time span of recorded events
maxBufferEvents10,000Maximum number of events
maxBufferBytes5 MBMaximum buffer size in bytes
When any limit is reached, the oldest events are evicted to make room for new ones.

What Gets Recorded

DOM Snapshots

A full snapshot captures the entire DOM state at a point in time. This serves as the baseline for playback. Full snapshots are taken:
  • When recording starts
  • After long idle periods
  • When visibility changes (tab focus)

Incremental Changes

Between snapshots, incremental events record changes:
  • DOM mutations: Element additions, removals, text changes
  • Style changes: CSS property updates
  • Attribute changes: Class, id, data attributes

User Interactions

User activity is captured for accurate playback:
  • Mouse movements: Position updates for cursor rendering
  • Mouse clicks: Click events with target element
  • Scroll events: Scroll position changes
  • Input changes: Form field updates (masked by default)
  • Touch events: Mobile touch interactions

Session and Window IDs

Proliferate tracks sessions across page loads and tabs:
Session ID
string
  • Persisted in sessionStorage
  • Survives page reloads
  • Expires after 30 minutes of inactivity
  • Used to correlate all events in a user session
Window ID
string
  • Unique per browser tab
  • Allows multi-tab replay correlation
  • Generated fresh for each tab
// Access current IDs programmatically
const sessionId = Proliferate.getSessionId();
const windowId = Proliferate.getWindowId();

When Replay is Sent

Replay data is sent only when an error occurs—not continuously.
  1. Error is captured (captureException or automatic)
  2. SDK retrieves buffered replay events
  3. Replay is associated with the error’s event_id
  4. Data is sent to the backend
// This triggers replay to be sent along with the error
try {
  await riskyOperation();
} catch (error) {
  const eventId = Proliferate.captureException(error);
  // Replay for the last 5 minutes is sent with this error
}
If no error occurs, the replay buffer is simply discarded when the page closes.

Idle Detection

To save resources, recording pauses when the user is idle:
  1. Activity tracking: Mouse, keyboard, touch, scroll events reset the idle timer
  2. Idle timeout: After 5 minutes of inactivity, incremental recording pauses
  3. Full snapshots preserved: Even during idle, full snapshots are captured on visibility changes
  4. Resume on activity: Recording resumes immediately when user becomes active
// Configure idle timeout
Proliferate.init({
  replay: {
    idleTimeoutMs: 5 * 60 * 1000,  // 5 minutes (default)
  },
});

Mutation Throttling

To prevent performance issues from rapid DOM changes (e.g., animations, live data):
  1. Token bucket algorithm: Limits mutations per element
  2. Throttled elements tracked: When an element exceeds its mutation budget, further changes are dropped
  3. Periodic reset: Throttling state resets periodically and on full snapshots
// Configure mutation throttling
Proliferate.init({
  replay: {
    mutationThrottleBucketSize: 100,   // Max mutations per element
    mutationThrottleRefillRate: 10,     // Refill rate per second
  },
});

Playback in the Dashboard

When viewing an error with replay:
  • Timeline scrubbing: Navigate through the recording
  • Speed control: Play at 1x, 2x, or 4x speed
  • Event markers: See clicks, navigation, and console events on the timeline
  • Error highlight: Error occurrence is marked on the timeline
  • DOM inspection: Click elements to see their properties

Performance Considerations

Session replay is designed for minimal impact:
AspectImpact
Memory1-5 MB for buffer
CPU< 1% during active recording
Bundle size~50 KB (lazy loaded)
rrweb is dynamically imported, so it’s not included in your main bundle. Recording pauses when the tab is hidden or user is idle.