faro
Grafana Faro SDK for Flutter applications - Monitor your Flutter app with ease.
0.16.0
16K downloads/mo
#2397 most downloaded on pub.dev
grafana/faro-flutter-sdk
What this package is like to depend on
Last release 1 months ago
17 Jul 2026
Ships fairly regularly
a new release about every 4 weeks
Most releases are documented
notes for 19 of 22 stable releases
Nothing withdrawn
no release was ever pulled
1 years old
24 releases · first in 2025
14 releases in the last 12 months
see the full history below
Release timeline
24 releases · May 2025 to Jul 2026Releases
latest 24-
0.17.0-beta.217 Jul 2026 pre-releaseRelease notes
Open source →Faro Flutter SDK v0.17.0-beta.2
✨ Added
- Session rotation (#52): Sessions now rotate automatically after 15 minutes of inactivity or 4 hours of total lifetime. This change aligns with the Faro session definition and the collector's server-side validation. Upon rotation, a new session ID is generated, and a
session_extendevent is emitted (the initial session emitssession_start). The previous session ID is recorded in thepreviousSessionattribute to allow backends to link sessions. Note that automatic vitals (CPU, memory, etc.) count as activity only while the app is in the foreground. A foregrounded but idle app remains in one session, while a backgrounded app's vitals cannot keep its session alive. Sampling is not re-evaluated on rotation. See the Reference docs for full details.
🔧 Fixed
- Offline transport is now resilient to malformed cache data (#22). A corrupt cached entry (e.g., from a partial write or schema drift) is now skipped and purged instead of aborting the read and permanently blocking all remaining cached telemetry. Additionally, payloads with user-supplied log context or event attributes that cannot be JSON-encoded (such as a
DateTime, custom object, or non-finite double) are dropped with a type-only diagnostic rather than failing the cache write. - Offline transport connectivity probe reliability (#11): The DNS lookup used by
OfflineTransportto confirm internet access now has a 5-second timeout (previously it could hang indefinitely on some platforms, stalling online/offline decisions) and catches all probe errors instead of onlySocketException. Any probe failure is treated as offline: while offline, payloads are cached on disk and flushed once connectivity returns, whereas a send attempted while actually offline is dropped without retry. This means a false "offline" only costs disk usage, while a false "online" could risk permanent data loss. Overlapping probes from rapid connectivity changes are now ordered, ensuring that a stale probe result that completes after a newer probe cannot overwrite the newer online/offline state. The lookup function is also injectable for testing via the new requiredaddressLookupparameter and optionallookupTimeoutparameter onInternetConnectivityService.
See CHANGELOG.md for complete details.
Full Changelog: v0.17.0-beta.1...v0.17.0-beta.2
Release notes
Open source →Added
- Session rotation (#52): Sessions now rotate automatically after
15 minutes of inactivity or 4 hours of total lifetime (fixed to match
the Faro session definition and the collector's server-side
validation). On
rotation a new session id is generated, a
session_extendevent is emitted (the initial session emitssession_start), and the previous id is recorded in thepreviousSessionattribute so backends can link sessions. Automatic vitals (CPU, memory, etc.) count as activity only while the app is in the foreground: a foregrounded but idle app (e.g. a user reading a screen) stays in one session, while a backgrounded app's vitals cannot keep its session alive. Sampling is not re-evaluated on rotation. See the Reference docs for full details.
Fixed
- Offline transport is now resilient to malformed cache data
(#22).
A corrupt cached entry (e.g. from a partial write or schema drift) is
now skipped and purged instead of aborting the read and permanently
blocking all remaining cached telemetry. Additionally, payloads whose
user-supplied log context or event attributes cannot be JSON-encoded
(a
DateTime, custom object, or non-finite double) are dropped with a type-only diagnostic rather than failing the cache write. - Offline transport connectivity probe reliability
(#11): The DNS
lookup used by
OfflineTransportto confirm internet access now has a 5-second timeout (previously it could hang indefinitely on some platforms, stalling online/offline decisions) and catches all probe errors instead of onlySocketException. Any probe failure is still treated as offline: while offline, payloads are cached on disk and flushed once connectivity returns, whereas a send attempted while actually offline is dropped without retry — so a false "offline" only costs disk usage, while a false "online" would risk permanent data loss. Overlapping probes from rapid connectivity changes are now also ordered: a stale probe result that completes after a newer probe can no longer overwrite the newer online/offline state. The lookup function is also injectable for testing via the new requiredaddressLookupparameter and optionallookupTimeoutparameter onInternetConnectivityService.
- Session rotation (#52): Sessions now rotate automatically after 15 minutes of inactivity or 4 hours of total lifetime. This change aligns with the Faro session definition and the collector's server-side validation. Upon rotation, a new session ID is generated, and a
-
0.17.0-beta.101 Jul 2026 pre-releaseRelease notes
Open source →Faro Flutter SDK v0.17.0-beta.1
Changed
- Renamed the SDK-generated install identifier model and provider to
InstallationId/InstallationIdProvider. The persisteddevice_id
storage key and legacy flatsession.attributes['device_id']payload key are
unchanged for migration compatibility. - Swapped the underlying OpenTelemetry implementation from the Workiva
opentelemetryDart package todartastic_opentelemetryfor tracing.
(#242)
Deprecated
DeviceIdis deprecated; useInstallationIdinstead. The deprecated alias
is kept for backward compatibility.
Added
- Emit structured mobile metadata in Flutter SDK payloads:
meta.device,meta.os,meta.app.installationId, and
exception.fatal, while keeping legacy flat session attributes during
migration.
The duplicated flatdevice_*session attributes are kept for compatibility
and can be removed after collector and plugin query parity is confirmed.
Changed
- CI: Attest SLSA build provenance for the published pub.dev archive.
Inlined thedart-lang/setup-dartreusable publish workflow so we can
download the canonical archive pub.dev serves and attest those bytes via
actions/attest-build-provenance. Consumers can verify with
gh attestation verify <tarball> --repo grafana/faro-flutter-sdk.
Fixed
- Preserve stack trace lines that do not match the expected Dart VM format
instead of silently dropping the whole stack trace. Lines that cannot be
parsed into structured frames (e.g. sanitized, obfuscated, or free-form
lines) are now kept as raw text in the frame'sfunctionfield.
(#102) - iOS native crash reports no longer lose all stack frames: a broken
work-in-progress sanitization step inCrashReportingIntegration
unconditionally replaced non-empty stack traces with an empty array
before export. The dead sanitization has been removed so frames flow
through to the exported crash payload. Load/parse failures of pending
crash reports are now logged with a clearer message before the report
is purged. (#220)
See CHANGELOG.md for complete details.
Full Changelog: v0.16.0...v0.17.0-beta.1
Release notes
Open source →Changed
- Renamed the SDK-generated install identifier model and provider to
InstallationId/InstallationIdProvider. The persisteddevice_idstorage key and legacy flatsession.attributes['device_id']payload key are unchanged for migration compatibility. - Swapped the underlying OpenTelemetry implementation from the Workiva
opentelemetryDart package todartastic_opentelemetryfor tracing. (#242)
Deprecated
DeviceIdis deprecated; useInstallationIdinstead. The deprecated alias is kept for backward compatibility.
Added
- Emit structured mobile metadata in Flutter SDK payloads:
meta.device,meta.os,meta.app.installationId, andexception.fatal, while keeping legacy flat session attributes during migration. The duplicated flatdevice_*session attributes are kept for compatibility and can be removed after collector and plugin query parity is confirmed.
Changed
- CI: Attest SLSA build provenance for the published pub.dev archive.
Inlined the
dart-lang/setup-dartreusable publish workflow so we can download the canonical archive pub.dev serves and attest those bytes viaactions/attest-build-provenance. Consumers can verify withgh attestation verify <tarball> --repo grafana/faro-flutter-sdk.
Fixed
- Preserve stack trace lines that do not match the expected Dart VM format
instead of silently dropping the whole stack trace. Lines that cannot be
parsed into structured frames (e.g. sanitized, obfuscated, or free-form
lines) are now kept as raw text in the frame's
functionfield. (#102) - iOS native crash reports no longer lose all stack frames: a broken
work-in-progress sanitization step in
CrashReportingIntegrationunconditionally replaced non-empty stack traces with an empty array before export. The dead sanitization has been removed so frames flow through to the exported crash payload. Load/parse failures of pending crash reports are now logged with a clearer message before the report is purged. (#220)
- Renamed the SDK-generated install identifier model and provider to
-
0.16.011 May 2026Release notes
Open source →Faro Flutter SDK v0.16.0
✨ Added
-
Span exception handling control: Introduced
SpanExceptionOptionsfor managing how exceptions are recorded on spans. This can be configured globally throughFaroConfig.spanExceptionOptionsor on a per-span basis using theexceptionOptionsparameter ofstartSpan(). The new options include:ExceptionSanitizercallback for PII-safe error recording.- Boolean flags (
recordException,setStatusOnException) for selective control.
Per-span options are merged field-by-field with the global configuration, meaning omitted fields will inherit from the global settings. If the sanitizer callback throws an error, the span will be marked as failed with a generic status description to prevent PII leakage.
See CHANGELOG.md for complete details.
Full Changelog: v0.15.0...v0.16.0
Release notes
Open source →Added
- Span exception handling control: Added
SpanExceptionOptionsfor controlling how exceptions are recorded on spans. Configurable globally viaFaroConfig.spanExceptionOptionsor per-span via theexceptionOptionsparameter ofstartSpan(). IncludesExceptionSanitizercallback for PII-safe error recording and boolean flags (recordException,setStatusOnException) for selective control. Per-span options are merged field-by-field over the global config — omitted fields inherit from global configuration. If the sanitizer callback throws, the span is marked as failed with a generic status description to avoid leaking PII.
-
-
0.15.007 May 2026Release notes
Open source →Faro Flutter SDK v0.15.0
⚠️ Changed
- Breaking for consumers on Flutter < 3.29 / Dart < 3.7: Raised the declared Dart SDK lower bound to
>=3.7.0and Flutter lower bound to>=3.29.0to match the effectivedevice_info_plusdependency floor. - Widened
device_info_plusdependency to>=12.3.0 <14.0.0(adds v13.x support). - Widened
package_info_plusdependency to>=8.0.1 <11.0.0(adds v10.x support).
See CHANGELOG.md for complete details.
Full Changelog: v0.14.0...v0.15.0
Release notes
Open source →Changed
- Breaking for consumers on Flutter < 3.29 / Dart < 3.7: Raised the
declared Dart SDK lower bound to
>=3.7.0and Flutter lower bound to>=3.29.0to match the effectivedevice_info_plusdependency floor. - Widened
device_info_plusdependency to>=12.3.0 <14.0.0(adds v13.x support). - Widened
package_info_plusdependency to>=8.0.1 <11.0.0(adds v10.x support).
- Breaking for consumers on Flutter < 3.29 / Dart < 3.7: Raised the declared Dart SDK lower bound to
-
0.14.014 Apr 2026Release notes
Open source →Faro Flutter SDK v0.14.0
🔧 Fixed
- Fix OOM crash in
ANRTrackerwhen capturing stack traces on low-memory Android devices (#174).
⚠️ Changed
- SDK metadata improvements:
- Changed SDK name from
'faro-flutter-sdk'to'faro-mobile-flutter'to match naming convention discussed with Faro team. - Removed hardcoded version
'1.3.5'workaround and now sends actual SDK version inmeta.sdk.version. - Removed
integrationsfield from SDK metadata (following Faro Web SDK pattern). - Removed unused
Integrationmodel class and its export from models barrel file. - Backend endpoint service now properly handles Flutter SDK payloads with correct version checking.
- Enables better SDK version analytics and distribution tracking across different Faro implementations.
- Changed SDK name from
- Bump Android
compileSdkVersionfrom 35 to 36 (aligned with Flutter default since May 2025). - Reorganized iOS source files from
ios/Classes/toios/faro/Sources/faro/to support the SPM directory convention. - Bumped iOS deployment target from 11.0 to 13.0.
- Updated
faro.podspecmetadata (homepage, author, license type, summary/description). - Fixed pre-existing Swift compiler warnings in iOS native code.
✨ Added
- Swift Package Manager (SPM) support for the iOS plugin, enabling dependency resolution via SPM alongside existing CocoaPods support (#189, #35).
- Android native unit test infrastructure (JUnit) with CI and pre-release script integration.
See CHANGELOG.md for complete details.
Full Changelog: v0.13.0...v0.14.0
Release notes
Open source →Fixed
- Fix OOM crash in
ANRTrackerwhen capturing stack traces on low-memory Android devices (#174).
Changed
- SDK metadata improvements: Updated SDK identification to align with Faro Web SDK patterns and improve backend analytics
- Changed SDK name from
'faro-flutter-sdk'to'faro-mobile-flutter'to match naming convention discussed with Faro team - Removed hardcoded version
'1.3.5'workaround and now sends actual SDK version inmeta.sdk.version - Removed
integrationsfield from SDK metadata (following Faro Web SDK pattern - this field provided no actionable insights) - Removed unused
Integrationmodel class and its export from models barrel file - Backend endpoint service now properly handles Flutter SDK payloads with correct version checking
- Enables better SDK version analytics and distribution tracking across different Faro implementations
- Changed SDK name from
- Bump Android
compileSdkVersionfrom 35 to 36 (aligned with Flutter default since May 2025). - Reorganized iOS source files from
ios/Classes/toios/faro/Sources/faro/to support the SPM directory convention. - Bumped iOS deployment target from 11.0 to 13.0.
- Updated
faro.podspecmetadata (homepage, author, license type, summary/description). - Fixed pre-existing Swift compiler warnings in iOS native code.
Added
- Swift Package Manager (SPM) support for the iOS plugin, enabling dependency resolution via SPM alongside existing CocoaPods support (#189, #35).
- Android native unit test infrastructure (JUnit) with CI and pre-release script integration.
- Fix OOM crash in
-
0.13.009 Apr 2026Release notes
Open source →Faro Flutter SDK v0.13.0
✨ Added
-
FaroWebViewBridge— a public API for cross-boundary session and trace correlation between Flutter apps and web apps running in a WebView. It provides:instrumentedUrl()to decorate URLs withtraceparentandsession.parent_*query parameters.linkChildSession()to push asession.linkedevent correlating the web session.end()to close the WebView span.
-
Span.traceparentgetter — exposes the W3C Trace Contexttraceparentheader value (00-{traceId}-{spanId}-01) directly on theSpaninterface, removing the need to cast toInternalSpan.
⚠️ Changed
- Widened
connectivity_plusdependency to>=6.1.2 <8.0.0(adds v7.x support). - Widened
package_info_plusdependency to>=8.0.1 <10.0.0(adds v9.x support).
🔧 Fixed
Faro.init()now ignores repeated calls after the first successful initialization, preventing duplicate startup side effects such as extra transports, repeatedsession_startevents, and duplicate widget observers.- Asset loads and tracked HTTP requests now keep user actions pending until the underlying operation completes, avoiding prematurely ended or stalled actions when using long-running asset loads,
HttpClientRequest.done, orabort().
See CHANGELOG.md for complete details.
Full Changelog: v0.12.0...v0.13.0
Release notes
Open source →Added
-
FaroWebViewBridge— a public API for cross-boundary session and trace correlation between Flutter apps and web apps running in a WebView. ProvidesinstrumentedUrl()to decorate URLs withtraceparentandsession.parent_*query parameters,linkChildSession()to push asession.linkedevent correlating the web session, andend()to close the WebView span. -
Span.traceparentgetter — exposes the W3C Trace Contexttraceparentheader value (00-{traceId}-{spanId}-01) directly on theSpaninterface, removing the need to cast toInternalSpan.
Changed
- Widened
connectivity_plusdependency to>=6.1.2 <8.0.0(adds v7.x support). - Widened
package_info_plusdependency to>=8.0.1 <10.0.0(adds v9.x support).
Fixed
Faro.init()now ignores repeated calls after the first successful initialization, preventing duplicate startup side effects such as extra transports, repeatedsession_startevents, and duplicate widget observers.- Asset loads and tracked HTTP requests now keep user actions pending until
the underlying operation completes, avoiding prematurely ended or stalled
actions when using long-running asset loads,
HttpClientRequest.done, orabort().
-
-
0.12.005 Mar 2026Release notes
Open source →Faro Flutter SDK v0.12.0
⚠️ Deprecated
markEventStart()andmarkEventEnd()are now deprecated. UsestartSpan()for duration tracking. UsestartUserAction()when you need interaction-level correlation across logs, events, exceptions, and spans. UsestartSpanManual()for manual span lifecycle control.
✨ Added
- UI activity monitoring for user actions: The SDK now automatically monitors Flutter widget rebuilds to detect UI responses to user actions. This emits bounded activity signals that keep user actions alive while the UI is updating, similar to DOM mutation observation in the Web SDK. Disable via
enableUiActivityMonitoring: falseinFaroConfig. - Asset load lifecycle signals: Asset loads via
FaroAssetTrackingnow emit activity signals to keep user actions alive during resource loading. - Expanded asset tracking:
FaroAssetBundlenow also tracksloadBufferandloadStructuredBinaryDatain addition toloadandloadString.
⚠️ Changed
-
BREAKING:
FaroAssetTrackingreplacesFaroAssetBundlein public API:FaroAssetBundleis no longer exported frompackage:faro/faro.dart. UseFaroAssetTracking(child: ...)instead ofDefaultAssetBundle(bundle: FaroAssetBundle(), child: ...).Before After ```dart ```dart DefaultAssetBundle( FaroAssetTracking( bundle: FaroAssetBundle(), child: const FaroUserInteractionWidget(child: MyApp()), child: const FaroUserInteractionWidget(child: MyApp()), ) ) ``` ``` -
HTTP tracking no longer emits the legacy
http_requestcustom event fromHttpTrackingClient. -
HTTP request telemetry continues to be available through span-derived
faro.tracing.fetchevents and OTLP spans. -
Pending operation lifecycle signals are now span-driven via
UserActionConstants.pendingOperationKey:- HTTP spans set this marker automatically.
- Custom spans can opt in by setting this attribute to
true. - Marker-based pending operations use span ID as operation ID.
- The marker attribute is exported with the span/event attributes.
See CHANGELOG.md for complete details.
Full Changelog: v0.11.0...v0.12.0
Release notes
Open source →Deprecated
markEventStart()andmarkEventEnd()are now deprecated. UsestartSpan()for duration tracking. UsestartUserAction()when you need interaction-level correlation across logs, events, exceptions, and spans. UsestartSpanManual()for manual span lifecycle control.
Added
- UI activity monitoring for user actions: The SDK now automatically
monitors Flutter widget rebuilds to detect UI responses to user actions.
This emits bounded activity signals that keep user actions alive while the
UI is updating, similar to DOM mutation observation in the Web SDK.
Disable via
enableUiActivityMonitoring: falseinFaroConfig. - Asset load lifecycle signals: Asset loads via
FaroAssetTrackingnow emit activity signals to keep user actions alive during resource loading. - Expanded asset tracking:
FaroAssetBundlenow also tracksloadBufferandloadStructuredBinaryDatain addition toloadandloadString.
Changed
-
BREAKING:
FaroAssetTrackingreplacesFaroAssetBundlein public API:FaroAssetBundleis no longer exported frompackage:faro/faro.dart. UseFaroAssetTracking(child: ...)instead ofDefaultAssetBundle(bundle: FaroAssetBundle(), child: ...).// Before DefaultAssetBundle( bundle: FaroAssetBundle(), child: const FaroUserInteractionWidget(child: MyApp()), ) // After FaroAssetTracking( child: const FaroUserInteractionWidget(child: MyApp()), ) -
HTTP tracking no longer emits the legacy
http_requestcustom event fromHttpTrackingClient. -
HTTP request telemetry continues to be available through span-derived
faro.tracing.fetchevents and OTLP spans. -
Pending operation lifecycle signals are now span-driven via
UserActionConstants.pendingOperationKey:- HTTP spans set this marker automatically.
- Custom spans can opt in by setting this attribute to
true. - Marker-based pending operations use span ID as operation ID.
- The marker attribute is exported with the span/event attributes.
-
0.11.003 Mar 2026Release notes
Open source →Faro Flutter SDK v0.11.0
✨ Added
-
User Actions: Group related telemetry (logs, events, exceptions, traces) under a single action context to track end-to-end user interactions. (Resolves #131)
Faro().startUserAction('name')starts a new action that buffers and enriches telemetry with action context.Faro().getActiveUserAction()returns the currently active action handle.- Automatic lifecycle management with follow-up timeout (100ms) and halt timeout (10s).
- HTTP requests and navigation events automatically extend action lifetime via signal channels.
- Telemetry items captured during an action include
action.nameandaction.idfor correlation in Grafana. - Only one action can be active at a time; overlapping calls return
null. - Spans created during an action automatically receive
faro.action.user.nameandfaro.action.user.parentIdattributes viaFaroUserActionSpanProcessor.
-
HTTP Tracking Filter: New
HttpTrackingFilterfor controlling which URLs are instrumented.- Automatically excludes Faro collector URL from tracking.
- Supports
ignoreUrlspatterns fromFaroConfigto skip custom URL patterns.
-
New dependency: Added
dartypod(^0.2.0) for lightweight dependency injection.
⚠️ Changed
- Documentation consolidation: Replaced separate
Getting Started.md,Features.md, andConfigurations.mdwith a single comprehensiveReference.md.
See CHANGELOG.md for complete details.
Full Changelog: v0.10.0...v0.11.0
Release notes
Open source →Added
-
User Actions: Group related telemetry (logs, events, exceptions, traces) under a single action context to track end-to-end user interactions. (Resolves #131)
Faro().startUserAction('name')starts a new action that buffers and enriches telemetry with action contextFaro().getActiveUserAction()returns the currently active action handle- Automatic lifecycle management with follow-up timeout (100ms) and halt timeout (10s)
- HTTP requests and navigation events automatically extend action lifetime via signal channels
- Telemetry items captured during an action include
action.nameandaction.idfor correlation in Grafana - Only one action can be active at a time; overlapping calls return
null - Spans created during an action automatically receive
faro.action.user.nameandfaro.action.user.parentIdattributes viaFaroUserActionSpanProcessor
-
HTTP Tracking Filter: New
HttpTrackingFilterfor controlling which URLs are instrumented- Automatically excludes Faro collector URL from tracking
- Supports
ignoreUrlspatterns fromFaroConfigto skip custom URL patterns
-
New dependency: Added
dartypod(^0.2.0) for lightweight dependency injection
Changed
- Documentation consolidation: Replaced separate
Getting Started.md,Features.md, andConfigurations.mdwith a single comprehensiveReference.md
-
-
0.10.009 Feb 2026Release notes
Open source →Faro Flutter SDK v0.10.0
✨ Added
-
Session sampling support: New
samplingconfiguration option allows controlling what percentage of sessions send telemetry data. This enables cost management and traffic reduction for high-volume applications. (Resolves #89)- Use
SamplingRate(0.5)for fixed 50% sampling - Use
SamplingFunction((context) => ...)for dynamic sampling based on session context (user attributes, app environment, etc.) - If not provided, all sessions are sampled (100%)
- Sampling decision is made once per session at initialization and applies to all telemetry types (events, logs, exceptions, measurements, traces)
- Example:
sampling: SamplingFunction((context) => context.meta.user?.attributes?['role'] == 'beta' ? 1.0 : 0.1) - Aligns with Faro Web SDK sampling behavior
- Use
-
ContextScope for span context lifetime control: New
contextScopeparameter onstartSpan()controls how long a span remains active in zone context for auto-assignment.ContextScope.callback(default) deactivates the span when the callback completes, preventing timer/stream callbacks from inheriting it.ContextScope.zonekeeps the span active for the entire zone lifetime, useful when you want timer callbacks to be children of the parent span. (Resolves #105) -
Span.noParent sentinel: New
Span.noParentstatic constant allows explicitly starting a span with no parent, ignoring the active span in zone context. Useful for timer callbacks or event-driven scenarios where you want to start a fresh, independent trace. (Resolves #105)
🔧 Fixed
- SDK-internal span attributes now use typed values: HTTP span attributes (
http.status_code,http.request_size,http.response_size) are now sent as integers instead of strings, enabling proper numeric queries in Tempo (e.g.,status_code > 400). - Session attributes support typed values:
sessionAttributesconfig now acceptsMap<String, Object>allowing typed custom attributes. Thedevice_is_physicalattribute is now sent as a boolean instead of a string. (Resolves #133)
See CHANGELOG.md for complete details.
Full Changelog: v0.9.0...v0.10.0
Release notes
Open source →Added
-
Session sampling support: New
samplingconfiguration option allows controlling what percentage of sessions send telemetry data. This enables cost management and traffic reduction for high-volume applications. (Resolves #89)- Use
SamplingRate(0.5)for fixed 50% sampling - Use
SamplingFunction((context) => ...)for dynamic sampling based on session context (user attributes, app environment, etc.) - If not provided, all sessions are sampled (100%)
- Sampling decision is made once per session at initialization and applies to all telemetry types (events, logs, exceptions, measurements, traces)
- Example:
sampling: SamplingFunction((context) => context.meta.user?.attributes?['role'] == 'beta' ? 1.0 : 0.1) - Aligns with Faro Web SDK sampling behavior
- Use
-
ContextScope for span context lifetime control: New
contextScopeparameter onstartSpan()controls how long a span remains active in zone context for auto-assignment.ContextScope.callback(default) deactivates the span when the callback completes, preventing timer/stream callbacks from inheriting it.ContextScope.zonekeeps the span active for the entire zone lifetime, useful when you want timer callbacks to be children of the parent span. (Resolves #105) -
Span.noParent sentinel: New
Span.noParentstatic constant allows explicitly starting a span with no parent, ignoring the active span in zone context. Useful for timer callbacks or event-driven scenarios where you want to start a fresh, independent trace. (Resolves #105)
Fixed
- SDK-internal span attributes now use typed values: HTTP span attributes (
http.status_code,http.request_size,http.response_size) are now sent as integers instead of strings, enabling proper numeric queries in Tempo (e.g.,status_code > 400) - Session attributes support typed values:
sessionAttributesconfig now acceptsMap<String, Object>allowing typed custom attributes. Thedevice_is_physicalattribute is now sent as a boolean instead of a string. (Resolves #133)
-
-
0.9.028 Jan 2026Release notes
Open source →Faro Flutter SDK v0.9.0
🔧 What's Fixed
OTLP Trace Attributes Now Preserve Types
Span attributes and event attributes now correctly preserve their original types (int, double, bool, String) when sent via OTLP.
Before: All attribute values were converted to strings, making numeric querying impossible.
user.account_count: "42" ❌ String - can't query account_count > 10After: Attributes keep their native types, enabling proper queries and histogram bucketing in Grafana/Tempo.
user.account_count: 42 ✅ Integer - full numeric query supportAPI Changes (Backward Compatible)
Method Before After Span.setAttribute()Stringvalue onlyObjectvalue (String, int, double, bool)Span.setAttributes()Map<String, String>Map<String, Object>Span.addEvent()Map<String, String>attributesMap<String, Object>attributesNote: Existing code using string-only methods continues to work unchanged.
Resolves
- Issue #126: OTLP trace attributes forced to string type
See CHANGELOG.md for complete details.
Full Changelog: v0.8.0...v0.9.0
Release notes
Open source →Fixed
- OTLP trace attributes now preserve types: Span attributes and event attributes now correctly preserve their original types (int, double, bool, String) when sent via OTLP
- Previously, all attribute values were converted to strings, making numeric querying and bucketing difficult in Grafana/Tempo
- Now attributes like
user.account_count: 42are sent as integers, enabling queries likeaccount_count > 10and proper histogram bucketing - Updated
TraceAttributeValueto supportstringValue,intValue,doubleValue, andboolValuefields per OTLP specification - Updated
Span.setAttributes()andSpan.addEvent()to acceptMap<String, Object>for typed values - Updated
Span.setAttribute(String key, Object value)to accept any supported type (previously only String) - Backward compatible:
Span.setAttribute(String key, String value)still works for string-only use cases - Resolves issue #126: OTLP trace attributes forced to string type
-
0.8.013 Jan 2026Release notes
Open source →Added
-
User management with FaroUser model: New
FaroUserclass for comprehensive user identification- Replaces the legacy
Usermodel with a more feature-rich implementation - Supports
id,username,email, and customattributesfields - Custom attributes align with Faro Web SDK MetaUser for cross-platform consistency
- Includes
FaroUser.cleared()constructor to explicitly clear user data
- Replaces the legacy
-
User persistence: New
persistUseroption inFaroConfig(default:true)- Automatically saves user identity to device storage
- Restores user on subsequent app launches for consistent session tracking
- Early events like
appStartinclude user data when persistence is enabled - Fires
user_setevent on restore anduser_updatedevent on changes
-
Initial user configuration: New
initialUseroption inFaroConfig- Set a user immediately on SDK initialization
- Use
FaroUser.cleared()to explicitly clear any persisted user on start - Useful for apps that know the user at startup or need to force logout state
-
New setUser() API: Streamlined method for setting user identity
Faro().setUser(FaroUser(...))to set userFaro().setUser(FaroUser.cleared())to clear user- Returns
Future<void>for awaiting persistence completion
Changed
- Deprecated setUserMeta(): Use
setUser(FaroUser(...))instead- Legacy method still works but will be removed in a future version
- Migration: Replace
setUserMeta(userId: 'x', userName: 'y', userEmail: 'z')withsetUser(FaroUser(id: 'x', username: 'y', email: 'z')) - Breaking: Now requires SDK initialization (
init()orrunApp()) before calling. Previously,setUserMeta()could be called before initialization. Calls made before initialization will now be silently ignored.
-
-
0.7.002 Dec 2025Release notes
Open source →⚠️ Note: This release updates Android build requirements.
Due to the
device_info_plusv12 upgrade, your Android project now requires:- Android Gradle Plugin ≥8.7.0
- Gradle wrapper ≥8.10
- Kotlin ≥2.2.0
- Java 17
Added
- Human-readable device model name: Added new
deviceModelNamefield toDeviceInfoanddevice_model_namesession attribute- iOS: Returns marketing name (e.g., "iPhone 15 Pro") instead of internal identifier ("iPhone16,1")
- Android: Same as
deviceModel- Android does not provide a mapping from model codes to marketing names
Changed
- Upgraded
device_info_plusfrom v11.4.0 to v12.3.0- Enables access to new
modelNameproperty on iOS for human-readable device names - Includes latest device identifier mappings (iPhone 16/17 series, iPad Pro M5, etc.)
- Enables access to new
-
0.6.025 Nov 2025Release notes
Open source →Added
- control Flutter error reporting: new
enableFlutterErrorReportinginFaroConfigto control Flutter error reporting (default = true)
- control Flutter error reporting: new
-
0.5.031 Oct 2025Release notes
Open source →Added
- Custom session attributes: New optional
sessionAttributesparameter inFaroConfigfor adding custom labels to all telemetry- Allows setting custom key-value pairs that are included in all telemetry data (logs, events, exceptions, traces, measurements)
- Useful for access control labels, team/department segmentation, and environment-specific metadata
- Custom attributes are merged with default attributes (SDK version, device info, etc.)
- Default attributes take precedence if naming conflicts occur
- Equivalent to
sessionTracking.session.attributesin Faro Web SDK
- Custom session attributes: New optional
-
0.4.228 Aug 2025Release notes
Open source →Changed
- Removed intl dependency: Replaced custom date formatting with built-in
DateTime.toIso8601String()method- Removed
intlpackage dependency to reduce package footprint - Updated timestamp generation in Event, FaroLog, FaroException, and Measurement models
- Uses standard ISO 8601 format via Dart's native
DateTime.toIso8601String()method - Maintains compatibility while eliminating external dependency
- Removed
- Removed intl dependency: Replaced custom date formatting with built-in
-
0.4.116 Jul 2025Release notes
Open source →Fixed
-
SDK name consistency across telemetry types: Updated SDK identification to use consistent naming
- Changed hardcoded 'rum-flutter' SDK name to use
FaroConstants.sdkNamefor consistency with OpenTelemetry traces - Maintains backend-compatible version '1.3.5' for proper web SDK version validation
- Added actual Faro Flutter SDK version to session attributes as 'faro_sdk_version' for tracking real SDK version
- Changed hardcoded 'rum-flutter' SDK name to use
-
FaroZoneSpanManager span status preservation: Fixed issue where manually set span statuses were overridden by automatic status setting
- Added
statusHasBeenSetproperty toSpaninterface to track when status has been manually set - Updated
FaroZoneSpanManager.executeWithSpan()to respect manually set span statuses for both success and error cases - Prevents overriding of custom span statuses (e.g., business logic errors) when code executes without throwing exceptions
- Maintains existing behavior for spans that haven't had their status manually set
- Resolves issue #86: FaroZoneSpanManager overrides manually set span statuses on success
- Added
-
-
0.4.002 Jul 2025Release notes
Open source →Changed
- BREAKING: Package structure refactoring to follow Flutter plugin conventions: Reorganized the package to align with Flutter/Dart ecosystem standards and best practices
-
Breaking Change: Main entry point changed from
faro_sdk.darttofaro.dart- The package now follows the standard
lib/<package_name>.dartconvention - Removed
lib/faro_sdk.dartfile entirely lib/faro.dartis now the single main entry point with selective barrel exports
- The package now follows the standard
-
Migration: Update your imports to use the new main entry point
// Before import 'package:faro/faro_sdk.dart'; // After import 'package:faro/faro.dart'; -
Architecture Improvements:
- Moved core
Faroclass implementation fromlib/faro.darttolib/src/faro.dart lib/faro.dartnow serves as a clean barrel export file exposing only public APIs- All implementation details properly organized under
lib/src/directory - Clear separation between public API surface and private implementation
- Follows established Flutter ecosystem conventions used by popular packages like Provider, BLoC, and Dio
- Moved core
-
Benefits:
- Cleaner API boundaries: Clear distinction between public and private APIs
- Better maintainability: Implementation details can evolve without affecting public interface
- Consistent developer experience: Matches patterns developers expect from other Flutter packages
- Future-proof: Enables easier API evolution and versioning
- Community alignment: Follows official Flutter/Dart documentation recommendations
-
No functionality changes: All existing public APIs remain the same, only import paths have changed
-
Added
-
Type-Safe Log Level API: New
LogLevelenum for improved logging reliability and developer experience- Introduced
LogLevelenum with values:trace,debug,info,log,warn,error - Aligns with Grafana Faro Web SDK for cross-platform consistency
- Includes
fromString()method for backward compatibility, supporting both'warn'and'warning'variants
- Introduced
-
Enhanced Tracing and Span API: Major improvements to distributed tracing capabilities
- New
startSpan<T>()method for automatic span lifecycle management with callback-based execution - New
startSpanManual()method for manual span lifecycle management when precise control is needed - New
getActiveSpan()method to access the currently active span from anywhere in the execution context - Zone-based span context management ensures proper parent-child relationships across async boundaries
- Automatic session ID injection - all spans now include both
session_idandsession.idattributes - Improved error handling with automatic span status updates when exceptions occur
- Enhanced span status tracking with proper OpenTelemetry status code mapping
- Support for custom parent span specification to create explicit span hierarchies
- Comprehensive documentation with detailed examples for common tracing patterns
- New
-
Centralized Session Management: New
SessionIdProviderfor consistent session handling across the SDK- Dedicated session ID generation and management
- Better integration with tracing system for session context propagation
- Factory pattern for testable session management
-
SDK Constants Management: New centralized constants system
- Added
FaroConstantsclass for SDK version and name management - Better version tracking and consistency across the codebase
- Added
-
BREAKING: Synchronous API for telemetry methods: Refactored telemetry methods to remove unnecessary async patterns for improved performance and developer experience
-
Breaking Change: The following methods changed from
Future<void>?tovoid:pushEvent()- Send custom eventspushLog()- Send custom logspushError()- Send custom errorspushMeasurement()- Send custom measurementsmarkEventEnd()- Mark event completion
-
Migration: Remove
awaitkeywords from calls to these methods as they are now synchronous// Before await Faro().pushEvent('event_name'); await Faro().pushLog('message', level: LogLevel.info); // After Faro().pushEvent('event_name'); Faro().pushLog('message', level: LogLevel.info); -
Benefits:
- Improved performance by eliminating unnecessary async overhead
- Cleaner API that better reflects the synchronous nature of these operations
- Reduced complexity in application code
-
Internal Architecture: Introduced
BatchTransportFactorysingleton pattern for better dependency management and testing
-
-
BREAKING: pushLog API requires LogLevel enum: Enhanced logging API for better type safety and consistency
- Breaking Change:
pushLog()now requires aLogLevelparameter instead of optionalString? - Migration: Replace
level: "warn"withlevel: LogLevel.warnin your pushLog calls - Benefit: Eliminates typos in log levels and provides better IDE support
- Compatibility: Existing string-based log levels in internal code updated to use LogLevel enum
- Documentation: All examples and documentation updated to reflect the new API
- Breaking Change:
-
Tracing Architecture Refactoring: Complete redesign of the internal tracing system
- Replaced legacy
tracer.dartandtracer_provider.dartwith newFaroTracerimplementation - New
FaroZoneSpanManagerfor robust zone-based span context management - Improved
Spanclass with cleaner API and better OpenTelemetry integration - Enhanced span creation and management with proper resource attribution
- Better separation of concerns between tracing components
- Zone-based implementation ensures proper parent-child relationships across async boundaries
- Enhanced developer experience with multiple tracing approaches for different use cases
- Better integration between tracing and other SDK components
- Replaced legacy
-
Session Management: Extracted session logic from distributed components
- Removed deprecated
generate_session.dartutility - Centralized session management in dedicated provider
- Improved testability and maintainability of session-related functionality
- Removed deprecated
- BREAKING: Package structure refactoring to follow Flutter plugin conventions: Reorganized the package to align with Flutter/Dart ecosystem standards and best practices
-
0.3.710 Jun 2025Release notes
Open source →Added
- Enhanced HTTP tracing attributes: HTTP spans now include additional attributes for better observability
- Added
http.request_sizeattribute with request content length - Added
http.response_sizeattribute with response content length - Added
http.content_typeattribute with response content type - Provides more comprehensive HTTP request/response metadata for monitoring
- Added
- Session attributes in OpenTelemetry traces: Tracer resources now automatically include session attributes
- Session metadata is propagated to all OpenTelemetry spans
- Enables correlation of traces with user sessions and custom session data
- Supports dynamic session attribute values (strings, numbers, booleans, objects)
- Added comprehensive test coverage for
DartOtelTracerResourcesFactory
- Human-readable timestamps for Android crashes: Added readable timestamp formatting for crash reports
- Crash context now includes both original Unix epoch timestamp and human-readable ISO 8601 format
- Added
timestamp_readable_utcfield alongside existingtimestampfield - Timestamps converted to UTC ISO 8601 format (e.g., "2025-06-04T23:49:20.296Z")
- Includes new
TimestampExtensionutility for reusable timestamp conversion - Improves debugging experience with easily interpretable crash timestamps
- Resolves issue #53: Add human readable timestamp for Android crashes
- Trace event duration: Added duration information to trace events
- Events now include
duration_nsattribute with span duration in nanoseconds - Duration calculated as
endTime - startTimewhen both timestamps are valid - Improves observability by providing timing information for traced operations
- Resolves issue #23: Add duration to Faro events
- Events now include
Fixed
- Span event naming: Fixed incorrect event names for tracing spans
- HTTP spans now correctly use
faro.tracing.fetchevent name - Non-HTTP spans use
span.{name}format for better event categorization - Added logic to detect HTTP spans based on
http.schemeorhttp.methodattributes - Resolves issue #41: Incorrect span event names being sent to collector
- HTTP spans now correctly use
- Event data URL formatting: Fixed inconsistent formatting of event_data_url parameter
- Attribute values are now properly sanitized to remove surrounding quotes
- Ensures consistent formatting across all event attributes
- Resolves issue #25: Inconsistent event_data_url formatting
- Enhanced HTTP tracing attributes: HTTP spans now include additional attributes for better observability
-
0.3.605 Jun 2025Release notes
Open source →Added
- Data Collection Persistence: The
enableDataCollectionsetting now persists across app restarts- Automatically saves the data collection preference to device storage using SharedPreferences
- Defaults to enabled on first app launch
- Fire-and-forget persistence - no need to await setting changes
- Maintains full backward compatibility with existing API
- Resolves issue #62: "Persist faro.enableDataCollection"
- GitHub issue templates for bug reports and feature requests
- Pull request template for standardized contributions
- Code of Conduct (Contributor Covenant v1.4)
- Comprehensive Contributing Guidelines with setup instructions and development workflow
- Maintainers documentation listing current project maintainers
Changed
- Major documentation overhaul:
- Enhanced README with improved badges, clearer setup instructions, and better project description
- Completely rewritten Features documentation with detailed explanations and code examples
- Improved Getting Started guide with step-by-step setup for both Grafana Cloud and self-hosted options
- Updated example app to demonstrate latest SDK features and best practices
Improved
- Project governance and community guidelines establishment
- Developer experience with better onboarding documentation
- Code contribution workflow with standardized templates and processes
Fixed
- Critical NullPointerException in Android frame monitoring: Fixed crash when frame monitoring callbacks execute after Flutter engine detachment
- Added proper cleanup in
stopFrameMonitoring()to remove Choreographer callbacks - Added null checks in
handleFrameDrop(),handleSlowFrameDrop(), andhandleRefreshRate()methods - Added safety guards to prevent frame processing when monitoring is stopped
- Prevents crashes when app goes to background or during configuration changes
- Added proper cleanup in
- Data Collection Persistence: The
-
0.3.528 May 2025Release notes
Open source →Added
- Support for custom HTTP headers in
FaroConfigvia thecollectorHeadersfield- Allows users to specify headers that will be included in all requests to the collector endpoint
- Useful for deployments that require specific headers for routing or authentication
- Support for custom HTTP headers in
-
0.3.422 May 2025Release notes
Open source →Added
- Automated pub.dev deployment with GitHub Actions
- Pre-release validation tools
Changed
- Improved release workflow with safety checks
-
0.3.321 May 2025Nothing published for this version
-
0.3.212 May 2025Nothing published for this version
-
0.3.009 May 2025Nothing published for this version