Distributed tracing links a request made by your Flutter application to the trace it produced on your backend. A slow screen in RUM then leads straight to the service that made it slow.
This page covers choosing which hosts are traced, which headers are sent, and how sampling works.
Before you start
You need two things:
- A network integration in place, so requests are reported as resources. See Flutter Network Tracking.
- Your backend services instrumented with Application Monitoring, so there is a trace to link to.
List your first party hosts
Tracing headers are only added to hosts you name. Set firstPartyHosts on your configuration:
final configuration = AtatusConfiguration(
licenseKey: '<LICENSE_KEY>',
env: '<ENV_NAME>',
appName: '<APP_NAME>',
firstPartyHosts: ['api.example.com', 'payments.example.com'],
)..enableHttpTracking();
A host matches itself and all of its subdomains, so api.example.com also matches beta.api.example.com. Wildcards, schemes, paths, and regular expressions are not supported. Use bare domain names.
Every host you list receives tracing headers on every request. Listing a third party domain sends your trace IDs to that third party, and can cause CORS preflight failures on services that do not expect the headers. List only hosts you control.
Requests to hosts that are not listed are still reported as RUM resources. They just do not carry tracing headers, so they cannot be joined to a backend trace.
Choose which headers are sent
By default, each host in firstPartyHosts receives two header formats: the Atatus headers and W3C trace context. That covers both an Atatus backend agent and any service that reads standard traceparent headers.
To control the formats per host, use firstPartyHostsWithTracingHeaders instead:
final configuration = AtatusConfiguration(
licenseKey: '<LICENSE_KEY>',
env: '<ENV_NAME>',
appName: '<APP_NAME>',
firstPartyHostsWithTracingHeaders: {
'api.example.com': {TracingHeaderType.atatus, TracingHeaderType.tracecontext},
'legacy.example.com': {TracingHeaderType.b3multi},
},
)..enableHttpTracking();
These are the four formats and the headers each one writes:
TracingHeaderType |
Headers sent |
|---|---|
atatus |
x-atatus-trace-id, x-atatus-parent-id, x-atatus-origin, x-atatus-sampling-priority, and baggage |
tracecontext |
traceparent, tracestate, and baggage |
b3 |
A single b3 header, formatted {traceId}-{spanId}-{sampled} |
b3multi |
X-B3-TraceId, X-B3-SpanId, X-B3-ParentSpanId, and X-B3-Sampled |
The baggage header carries the RUM session ID, and the user and account IDs when you have set them, so your backend can attribute a trace to the same person.
Setting firstPartyHosts replaces anything already in firstPartyHostsWithTracingHeaders. Use one or the other, not both.
Control how much is traced
Two options decide whether a request carries tracing headers:
| Option | Default | Purpose |
|---|---|---|
traceSampleRate |
100.0 |
Percentage of tracked resources that carry tracing headers, from 0.0 to 100.0 |
traceContextInjection |
TraceContextInjection.sampled |
Whether headers are written for unsampled requests as well as sampled ones |
Set them on your RUM configuration:
rumConfiguration: AtatusRumConfiguration(
traceSampleRate: 20.0,
traceContextInjection: TraceContextInjection.sampled,
),
Sampling is deterministic. The same trace produces the same decision every time, so a trace is never half recorded across services.
traceContextInjection decides what happens to the requests sampling dropped:
sampled, the default, writes no tracing headers on a dropped request.allstill writes the headers, with the sampling flag set to0. Your backend then sees the trace and can apply its own sampling decision.
Use all when your backend decides sampling. The frontend then reports every request to the backend without forcing its own decision on it, which keeps the two ends of a trace consistent.
Group requests into one trace
By default each request is its own trace. To tie several requests together as one operation, start a trace, make the requests, then stop it:
AtatusSdk.instance.rum?.startTrace();
await loadProfile();
await loadOrders();
await loadRecommendations();
AtatusSdk.instance.rum?.stopTrace();
Every request made while the trace is active joins it. The first request becomes the root, and each later request is attached as a child of the one before it, so the backend can show the whole sequence as one tree.
Always call stopTrace(). A trace left open keeps attaching later requests to it, including ones from a different screen.
Check whether a host is traced
Two helpers let you check the configuration at runtime, which is useful when debugging a request that is not joining its trace:
final uri = Uri.parse('https://api.example.com/orders');
// Is this host in firstPartyHosts?
final tracked = AtatusSdk.instance.isFirstPartyHost(uri);
// Which header formats will it receive?
final headerTypes = AtatusSdk.instance.headerTypesForHost(uri);
What lands on the resource
A traced resource carries these attributes, which are what the backend uses to join the two sides:
| Attribute | Description |
|---|---|
_atatus.trace_id |
The 128 bit trace ID shared with the backend trace |
_atatus.span_id |
The span ID for this request |
_atatus.parent_span_id |
The parent span, set when the request is part of a trace you started |
_atatus.rule_psr |
The trace sample rate that was applied |
_atatus.span.kind |
Set to client when the request has a parent span |
A request that sampling dropped keeps _atatus.rule_psr but carries no trace or span ID.
Troubleshooting
If a request is reported as a resource but never joins a backend trace, work through these in order:
- Confirm the host is listed in
firstPartyHosts, exactly, with no scheme or path. Check it withisFirstPartyHost. - Raise
traceSampleRateto100.0while testing, so sampling is not hiding the problem. - Confirm the backend service is instrumented and reads one of the header formats you send.
- Check that your own
HttpOverridesare installed before Atatus is initialized. See the warning in Flutter Network Tracking.
Next steps
- Add a network integration in Flutter Network Tracking.
- Configure the rest of the agent in Flutter Agent Configuration Options.
+1-415-800-4104