Skip to main content
This page describes the advanced configuration options of the Flutter SDK. All configuration is passed through DatadogConfiguration and DatadogRumConfiguration.

Sampling rate

Remote configuration

Starting with flashcat_flutter_plugin 0.2.0, the session sample rate can be adjusted online from the console under Application Management → Remote Configuration, with no code change or new release. The feature is off by default and has to be enabled at initialization:
Once enabled, the configuration is fetched by the native Android / iOS SDK underneath the plugin, and behaves exactly as it does there:
  • A rate published in the console applies to the next new session; a session already under way is not affected.
  • The delivered values are persisted locally, so the first session after a cold start is already drawn under the last delivered rate.
  • A failed, timed-out or unreadable response leaves the values in force untouched; they are never cleared. When remote configuration is disabled in the console, the SDK falls back to the sessionSamplingRate passed at initialization.
  • The Flutter SDK reads only the session sample rate and custom configuration keys; the other settings have no effect. Read the custom keys with getRemoteConfig(), which returns null when remote configuration is off or no configuration has arrived yet:
To decide sampling by your own business rules, use the beforeSampling callback. Before each new session is sampled, the callback receives the rate that would apply (sessionSampleRate) and the console’s custom keys (custom). Return a rate to override it, or null to keep it. It runs synchronously, so keep it fast; returning a value outside 0–100, throwing, or timing out all keep the native SDK’s decision. The callback also runs when remote configuration is off — sessionSampleRate is then the local value and custom is null.
To collect the current user regardless of the sample rate (for example while investigating one user’s issue), call DatadogSdk.instance.rum?.setForcedSession(). If the current session was sampled out it ends immediately and a collected one starts; every session afterwards is collected for the lifetime of the process. The setting cannot be reverted until the app restarts.
When Flutter attaches to an already initialized native SDK (add-to-app), the native side must set remoteConfigurationEnabled and beforeSampling when it initializes RUM. See iOS SDK Advanced Configuration and Android SDK Advanced Configuration. getRemoteConfig() and setForcedSession() still work from Dart.
Custom configuration keys are delivered to clients and readable by anyone who holds the Client Token. Never put secrets, access tokens, or personally sensitive information in them.
For the console side (settings, publishing and when a version takes effect), see Application Management · Remote Configuration. TrackingConsent controls whether data is collected and reported, to meet compliance requirements such as GDPR:

Event filtering and masking

Event mappers run before events are reported; return null to drop the event, or return it after modification. You can use them to mask sensitive fields, remove noise, or rename views.

Distributed tracing

For hosts that match firstPartyHosts, the SDK injects the W3C traceparent to correlate frontend RUM with backend APM. Tracing requires network collection (enableHttpTracking()).

Custom reporting endpoint

For on-premises deployments, override the default reporting endpoint through customEndpoint:
customEndpoint is the final RUM intake URL, not a base origin. It must include /api/v2/rum. If the deployment uses a path prefix, preserve it as well, for example https://example.com/flashduty/api/v2/rum.

WebView tracking

When a Flutter screen embeds a WebView, use flashcat_webview_tracking to correlate Browser RUM events from the WebView with the current native RUM session.
pubspec.yaml
Pass the allowed hostnames to trackDatadogEvents. A hostname matches its subdomains, but wildcards are not supported. The page loaded in the WebView must already use the Flashduty Browser SDK. On Android, you must also enable JavaScriptMode.unrestricted, or correlation will not work.

Symbol file upload

To resolve crash and error stacks back to source locations, you need to upload symbol files. A Flutter application may contain both Dart and native frames:
Dart stacks cannot be symbolicated on iOS yet. Flutter produces Mach-O symbol files for Apple targets, but the platform currently parses only the ELF format used on Android. An iOS .symbols upload is therefore rejected. iOS native crashes are unaffected — upload dSYMs to symbolicate them.If you ship both iOS and Android, you can still enable --obfuscate: Android Dart stacks resolve normally while iOS Dart stacks stay obfuscated. If readable iOS stacks matter more, leave --obfuscate off for that platform’s build.
Use the FlashCat CLI to upload symbol files:
Symbol files are matched to crash events by the build’s build ID; service and release-version take no part in the lookup. Symbolication therefore still works when they differ from the SDK initialization values — the difference only affects how the file is grouped and filtered in the console’s Source code mapping list. Keeping them aligned is still recommended, and Flutter’s build-number suffix (for example 1.2.3+45) is an easy way for them to drift apart.The build ID must match in three places: the app.<platform>-<arch>.symbols file from --split-debug-info, the libapp.so inside the APK, and the Build ID column under Source code mapping → Flutter in the console. Every change to your Dart code produces a new build ID, so symbol upload has to be part of every release build — otherwise that version’s stacks silently degrade to unresolved.

Other configuration