How Chromium Batches and Sends Network Error Logs

This article provides a quick overview of how the Chromium web browser utilizes the Reporting API to collect, batch, and transmit Network Error Logging (NEL) data out-of-band. It covers the initial configuration via HTTP headers, the internal queuing mechanism that aggregates multiple error reports, the timing and grouping logic governing batch creation, and the final background delivery and retry processes used to send JSON payloads to specified collector endpoints.

Configuration and Initialization

Chromium relies on two HTTP response headers from a server to initialize error logging: Reporting-Endpoints (or the legacy Report-To header) and NEL. When a user successfully connects to a site, these headers instruct the browser to cache a reporting policy inside its network stack. This policy defines the collector endpoint URLs, the lifespan of the configuration, and the sampling rates for both successful and failed network requests.

Capturing and Queuing Logs

Once a policy is active, Chromium monitors all network requests made to that origin. If a network error occurs—such as a DNS resolution failure, TCP connection timeout, TLS handshake error, or HTTP 500-level response—Chromium's network stack generates a structured NEL report.

Instead of transmitting this report immediately, the network stack passes the data to Chromium's internal ReportingService. The service places the report into an in-memory queue. This step decouples error generation from report transmission, ensuring the browser does not immediately attempt to send network requests over a connection that just proved to be unstable or offline.

The Batching Mechanism

To minimize bandwidth consumption and wake-ups on mobile devices, Chromium batches queued reports before attempting to send them. The ReportingService uses an internal timer to periodically sweep the report queue.

When the delivery timer fires, Chromium executes the following batching process:

  1. Selection: It pulls pending reports from the queue, respecting limits on the maximum number of reports and total payload size.
  2. Grouping: It groups the selected reports by their origin and their designated collector endpoint URL.
  3. Serialization: For each group, Chromium combines the individual reports into a single JSON array.
  4. Age Calculation: Just before serialization, the browser calculates how long each report sat in the queue and populates the age property (in milliseconds) for every individual report object in the batch.

Because of this batching mechanism, if a single webpage fails to load twenty different image assets due to a sudden connection drop, the collector endpoint will eventually receive one HTTP request containing an array of twenty error objects, rather than twenty separate requests.

Out-of-Band Transmission

Transmission occurs "out-of-band," meaning it operates entirely in the background within Chromium's network service, independent of the lifecycle of the web page that generated the errors. Even if the user navigates away from the page or closes the tab, the queued reports remain in the browser's memory awaiting the next delivery cycle.

Chromium transmits the batched payload by dispatching an asynchronous HTTP POST request to the configured collector endpoint. This request is sent with the Content-Type header set to application/reports+json. For security and privacy reasons, these requests are uncredentialed, meaning they are stripped of cookies and client certificates to prevent cross-site tracking via error logs.

Failure Handling and Retries

Because NEL deals specifically with network failures, the transmission of the error report itself will frequently fail if the user's internet connection is completely down.

If the POST request to the collector endpoint fails, Chromium does not discard the batch. Instead, it follows a strict retry and eviction protocol:

  • Exponential Backoff: The browser marks the specific collector endpoint as failing and applies an exponential backoff timer to delay future delivery attempts to that URL.
  • Re-queuing: The failed reports are returned to the in-memory queue, and an internal attempts counter is incremented for each report in the failed batch.
  • Eviction: If a report fails to send after reaching the maximum number of allowed delivery attempts, or if the in-memory queue reaches its maximum storage capacity, Chromium evicts the oldest and most-attempted reports to free up memory for new logs.

Because the entire queuing and batching system lives strictly in volatile memory for privacy and performance reasons, any batched or queued reports that have not been successfully transmitted are permanently deleted if the user completely quits the Chromium browser process.