Skip to content

[Session Replay / iOS] Blank screen after first navigation — recording works only on initial screen #1397

Description

@chung-clearstreet

Describe the issue

iOS Session Replay records the first screen correctly (sign-in), but every screen after the first navigation transition renders as a completely blank frame. Touches are still captured and appear in the replay, confirming the recording session is active, but no visual content is captured. The issue is iOS-only — Android records all screens correctly.

Screen.Recording.2026-09-05.at.12.17.29.AM.mov

Reproduction steps

// Initialize Datadog (called once at app startup)
await DdSdkReactNative.initialize(ddConfig);
await SessionReplay.enable({
  replaySampleRate: 100,
  textAndInputPrivacyLevel: TextAndInputPrivacyLevel.MASK_SENSITIVE_INPUTS,
  imagePrivacyLevel: ImagePrivacyLevel.MASK_NONE,
  touchPrivacyLevel: TouchPrivacyLevel.SHOW,
});

Steps:

  1. Launch app on iOS — the initial screen (sign-in) appears correctly in the replay.
  2. Navigate to any subsequent screen (e.g. sign-up / onboarding / authenticated home).
  3. In Datadog RUM → Session Replay, all screens after step 1 are blank. Tap gestures are visible, no visual content.

The app uses Expo Router (React Navigation under the hood, native stack on iOS). Navigation is from a sign-in screen to an (onboarding) or (authenticated) stack group.

SDK logs

No errors or warnings logged from the Datadog SDK during or after navigation. The bridge calls complete silently.

Device Information

  • iOS 17 / 18
  • Not reproducible on Android (all screens record correctly)

SDK version

SDK version: @datadog/mobile-react-native-session-replay: 3.7.0 / @datadog/mobile-react-native: 3.7.0

Integration Methods

NPM

React Native Version

No response

Package.json Contents

Package.json Contents:
{
"@datadog/mobile-react-native": "3.7.0",
"@datadog/mobile-react-native-session-replay": "3.7.0"
}

iOS Setup

require File.join(File.dirname(`node --print "require.resolve('expo/package.json')"`), "scripts/autolinking")
require File.join(File.dirname(`node --print "require.resolve('react-native/package.json')"`), "scripts/react_native_pods")

require 'json'
podfile_properties = JSON.parse(File.read(File.join(__dir__, 'Podfile.properties.json'))) rescue {}

def ccache_enabled?(podfile_properties)
  # Environment variable takes precedence
  return ENV['USE_CCACHE'] == '1' if ENV['USE_CCACHE']
  
  # Fall back to Podfile properties
  podfile_properties['apple.ccacheEnabled'] == 'true'
end

ENV['RCT_NEW_ARCH_ENABLED'] ||= '0' if podfile_properties['newArchEnabled'] == 'false'
ENV['EX_DEV_CLIENT_NETWORK_INSPECTOR'] ||= podfile_properties['EX_DEV_CLIENT_NETWORK_INSPECTOR']
ENV['RCT_USE_RN_DEP'] ||= '1' if podfile_properties['ios.buildReactNativeFromSource'] != 'true' && podfile_properties['newArchEnabled'] != 'false'
ENV['RCT_USE_PREBUILT_RNCORE'] ||= '1' if podfile_properties['ios.buildReactNativeFromSource'] != 'true' && podfile_properties['newArchEnabled'] != 'false'
platform :ios, podfile_properties['ios.deploymentTarget'] || '15.1'

prepare_react_native_project!

target 'ClearStreetDev' do
# @generated begin AppsFlyer Strict Mode - expo prebuild (DO NOT MODIFY) sync-b29372208dd0dbd1274e957795cd756926086c3a
$RNAppsFlyerStrictMode=false
# @generated end AppsFlyer Strict Mode
  use_expo_modules!
# @generated begin AppsFlyer Purchase Connector - expo prebuild (DO NOT MODIFY) sync-40d043aa4472dc51990344aee6329be6fe164eba
$AppsFlyerPurchaseConnector=false
# @generated end AppsFlyer Purchase Connector

  if ENV['EXPO_USE_COMMUNITY_AUTOLINKING'] == '1'
    config_command = ['node', '-e', "process.argv=['', '', 'config'];require('@react-native-community/cli').run()"];
  else
    config_command = [
      'npx',
      'expo-modules-autolinking',
      'react-native-config',
      '--json',
      '--platform',
      'ios'
    ]
  end

  config = use_native_modules!(config_command)

  use_frameworks! :linkage => podfile_properties['ios.useFrameworks'].to_sym if podfile_properties['ios.useFrameworks']
  use_frameworks! :linkage => ENV['USE_FRAMEWORKS'].to_sym if ENV['USE_FRAMEWORKS']

  use_react_native!(
    :path => config[:reactNativePath],
    :hermes_enabled => podfile_properties['expo.jsEngine'] == nil || podfile_properties['expo.jsEngine'] == 'hermes',
    # An absolute path to your application root.
    :app_path => "#{Pod::Config.instance.installation_root}/..",
    :privacy_file_aggregation_enabled => podfile_properties['apple.privacyManifestAggregationEnabled'] != 'false',
  )

  post_install do |installer|
    react_native_post_install(
      installer,
      config[:reactNativePath],
      :mac_catalyst_enabled => false,
      :ccache_enabled => ccache_enabled?(podfile_properties),
    )
  end
end

Android Setup

N/A — issue is iOS only.

Other relevant information

  • The app uses Expo Router with nested Stack navigators ((onboarding) and (authenticated) route groups).
  • Several onboarding screens render a WebView (react-native-webview) for identity verification and legal agreements.
  • The blank-screen behavior begins immediately on the first navigation away from the initial screen, before any WebView is encountered, so WebView interaction is not a prerequisite.
  • Re-calling SessionReplay.enable() with the same config after each route change (via Expo Router's usePathname) does not restore visual capture.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions