Connect API failures to what users see

Investigate failed requests and unexpected responses alongside screenshots, logs, and app events across every Ansight SDK.

When a screen shows an error or unexpected data, request and response evidence helps you inspect the network activity behind it. Ansight keeps sanitized HTTP details alongside the rest of the session so you can compare what the API returned with what the user saw.

Ansight records completed HTTP requests as ansight.network-request.v1 evidence alongside screenshots, logs, and application events. Capture is available across every SDK, but interception and opt-in behavior vary by platform.

For OS connection state, Wi-Fi/cellular changes, and supported link-quality estimates, enable Connectivity Capture separately. Review both streams at the same time to investigate request failures.

SDKAutomatic integrationManual recording
.NET / MAUIProcess-wide HttpClient diagnostics; Apple targets also use the native URL Loading System interceptorRuntime.RecordNetworkRequest(...) or AnsightHttpMessageHandler
AndroidIntegrate with the app’s HTTP clientAnsightRuntime.recordNetworkRequest(...)
iOS / SwiftURL Loading System interceptorAnsightRuntime.shared.recordNetworkRequest(...)
React NativeOpt-in fetch and XMLHttpRequest instrumentationrecordNetworkRequest(...)
FlutterAnsightHttpClient wrapperAnsight.instance.recordNetworkRequest(...)
Cordova / CapacitorOpt-in fetch and XMLHttpRequest instrumentationrecordNetworkRequest(...)

Passive performance measurements

Captures can include an optional performance object with time to first byte, DNS, connection, TLS, upload/download durations, transferred body byte counts, and connection reuse. Apple native capture obtains these from the final URLSessionTaskTransactionMetrics transaction. This requires a rebuilt SDK/native bridge and a new capture; older recordings and other collectors may omit these fields.

Missing phases remain unknown, including DNS or TLS on reused connections. Cache/local fetches do not emit network performance. includeBodySizes also controls the transferred byte counts. Timing collection does not enable body capture or send additional requests.

The player’s Connectivity tab summarizes measured requests completed in the last 60 seconds at the playhead, grouped by server. Latency percentiles use the available time-to-first-byte samples; transfer rates use actual body bytes and measured transfer durations. These describe observed transfers, not connection capacity. The HTTP request’s Timing view shows its individual measurements.

Defaults and Privacy

Network evidence can contain URLs, headers, error messages, and request or response bodies. Treat it as sensitive.

  • Simulator and emulator native capture defaults may enable the platform integration; use the explicit enable/disable API when policy must be fixed.
  • Text bodies are bounded to 64 KiB per body by default in body-aware capture integrations. Request and response bodies can be disabled independently.
  • Binary bodies require an explicit opt-in and are represented as Base64.
  • Standard credential headers, cookies, URL user information, cloud signed-URL fields, and sensitive text assignments are redacted before transport.
  • Apps can add sensitive header and query-parameter names, rewrite URLs or records, or suppress a record entirely.
  • The host applies its own sanitization before persisting network/requests/.

Disabling redaction is suitable only for a deliberately isolated local test with non-sensitive data. Do not capture production credentials or personal data.

.NET / MAUI

Enable process-wide capture through the normal options builder:

using Ansight;

var options = Options.CreateBuilder()
    .WithNetworkCapture(network =>
    {
        network.WithMaximumBodyBytes(64 * 1024);
        network.WithRequestBodies();
        network.WithResponseBodies();
    })
    .Build();

WithoutNetworkCapture() disables process-wide automatic capture. Explicit AnsightHttpMessageHandler instances remain active. Automatic HttpClient diagnostics are metadata-only because observers do not consume application bodies; use the explicit handler when bounded body capture is required.

An explicit handler can also apply app-specific sensitive names and a final record filter:

var handler = new AnsightHttpMessageHandler(
    new NetworkRequestSanitizationOptions
    {
        AdditionalSensitiveHeaderNames = ["x-tenant-secret"],
        AdditionalSensitiveQueryParameterNames = ["session"],
        RequestSanitizer = request =>
            request.Url.Contains("/health", StringComparison.Ordinal)
                ? null
                : request,
    });
var client = new HttpClient(handler);

Android

Android core accepts sanitized typed records from the app’s existing OkHttp, Retrofit, or other client integration:

AnsightRuntime.recordNetworkRequest(
    AnsightNetworkRequest(
        id = requestId,
        source = "okhttp",
        startedAtUtc = startedAt,
        completedAtUtc = completedAt,
        durationMilliseconds = durationMs,
        method = request.method,
        url = request.url.toString(),
        statusCode = response.code,
    )
)

AnsightNetworkRequestSanitizer is always applied inside the native runtime, including records received from framework bridges.

iOS / Swift

Enable or disable native URL Loading System interception in the options builder:

let options = try AnsightOptions.createBuilder()
    .withNetworkCapture(AnsightNetworkCaptureOptions(
        enabled: true,
        maximumBodyBytes: 64 * 1_024,
        captureBinaryBodies: false
    ))
    .build()

Use .withoutNetworkCapture() to disable the interceptor. Custom clients can submit an AnsightNetworkRequest directly with AnsightRuntime.shared.recordNetworkRequest(...).

React Native

await Ansight.initializeAndActivate(
  Ansight.createOptionsBuilder()
    .withAnsightDefaults()
    .withNetworkCapture({
      maximumBodyBytes: 64 * 1024,
      additionalSensitiveHeaderNames: ["x-tenant-secret"],
      additionalSensitiveQueryParameterNames: ["session"],
      requestSanitizer: request =>
        request.url.includes("/health") ? null : request,
    })
    .build(),
);

Use installNetworkCapture(...) and uninstallNetworkCapture() when the hooks need an independent lifecycle. sanitizeNetworkRequest(...) exposes the same app-side policy for tests and custom integrations.

Flutter

Wrap the package:http client used by the app:

final client = AnsightHttpClient(
  inner: http.Client(),
  sanitizationOptions: AnsightNetworkSanitizationOptions(
    maximumBodyBytes: 64 * 1024,
    additionalSensitiveHeaderNames: <String>['x-tenant-secret'],
    additionalSensitiveQueryParameterNames: <String>['session'],
    requestSanitizer: (request) =>
        request.url.contains('/health') ? null : request,
  ),
);

Use Ansight.instance.recordNetworkRequest(...) for a different HTTP stack.

Cordova / Capacitor

The Capacitor builder uses the same opt-in fetch and XMLHttpRequest capture model as React Native:

await Ansight.initializeAndActivate(
  Ansight.createOptionsBuilder()
    .withAnsightDefaults()
    .withNetworkCapture({ maximumBodyBytes: 64 * 1024 })
    .withoutNetworkResponseBodies() // optional
    .build(),
);

Use installNetworkCapture(...), uninstallNetworkCapture(), and recordNetworkRequest(...) for explicit lifecycle and custom-client control.