A Crash Course in Debugging with about:net-internals #

This document is intended to help get people started debugging network errors with about:net-internals, with some commonly useful tips and tricks. This document is aimed more at how to get started using some of its features to investigate bug reports, rather than as a feature overview.

It would probably be useful to read life-of-a-url-request.md before this document.

What Data Net-Internals Contains #

about:net-internals provides a view of browser activity from net/'s perspective. For this reason, it lacks knowledge of tabs, navigation, frames, resource types, etc.

The top level network stack object is the URLRequestContext. The Events View has information for all Chrome URLRequestContexts that are hooked up to the single, global, ChromeNetLog object. This includes both incognito and non- incognito profiles, among other things. The Events view only shows events for the period that net-internals was open and running, and is incrementally updated as events occur. The code attempts to add a top level event for URLRequests that were active when the tab was opened, to help debug hung requests, but that's best-effort only, and only includes requests for the current profile and the system URLRequestContext.

The other views are all snapshots of the current state of the main URLRequestContext's components, and are updated on a 5 second timer. These will show objects that were created before about:net-internals was opened. Most debugging is done with the Events view (which will be all this document covers), but it's good to be aware of this distinction.

Events vs Sources #

The Event View shows events logged by the NetLog. The NetLog model is that long-lived network stack objects, called sources, emit events over their lifetime. Some events have a beginning and end point (during which other subevents may occur), and some only occur at a single point in time. Generally only one event can be occuring for a source at a time. If there can be multiple events doing completely independent thing, the code often uses new sources to represent the parallelism.

"Sources" correspond to certain net objects, however, multiple layers of net/ will often log to a single source. Here are the main source types and what they include (Excluding HTTP2 [SPDY]/QUIC):

When one source depends on another, the code generally logs an event with "source_dependency" value to both sources, which lets you jump between the two related events.

Debugging #

When you receive a report from the user, the first thing you'll generally want to do find the URLREQUEST[s] that are misbehaving. If the user gives an ERR* code or the exact URL of the resource that won't load, you can just search for it. If it's an upload, you can search for "post", or if it's a redirect issue, you can search for "redirect". However, you often won't have much information about the actual problem. There are two filters in net-internals that can help in a lot of cases:

For a list of other filter commands, you can mouse over the question mark on about:net-internals.

Once you locate the problematic request, the next is to figure out where the problem is - it's often one of the last events, though it could also be related to response or request headers. You can use "source_dependency" links to drill down into other related sources, or up from layers below URL_REQUEST.

You can use the name of an event to search for the code responsible for that event, and try to deduce what went wrong before/after a particular event. Note that the event names used in net-internals are not the entire string names, so you should not do an entire string match.

Some things to look for while debugging:

Miscellany #

These are just miscellaneous things you may notice when looking through the logs.