Writing

Software, technology, sysadmin war stories, and more. Feed
Tuesday, November 12, 2019

Just how fast is too fast when it comes to web requests?

There's meta, and then there's meta about meta.

An anonymous reader wrote in with some feedback about a broken post (since fixed, thanks!) ... and then immediately wrote in with something else that's so amusing I figured it needed to be shared:

Your "Feedback saved. Thanks!" message popped up so quickly that I doubt a network request was sent. I have enabled monitoring now I'm submitting this test message.

Upon showing this to a friend, he suggested I make it say how long it took to be a bit more convincing, and that's when I realized I had no idea how long it took to run. So, I did just that a few minutes ago, and here it is:

Feedback saved in 274ms

Now I know: it's about 220-275 milliseconds for me.

What figures into that?

First, I'm on my laptop with a wireless link in a relatively congested area. It's also a link back to a commodity Internet connection that's shared with streaming HD video (re-watching Eureka episodes, naturally).

It's a link in the SF Bay Area, and the server is in Texas, so it has to get out there and back. That's at least 50 milliseconds right there when measured by a boring old ping, and it varies quite a bit.

Then there's the matter of bringing up the TCP connection which has a three-way handshake, and then TLS has to come up over that since I'm doing this over https. Apache has to read it, figure out where to send it, and kick off the CGI handler, which is just a tiny C++ binary.

That handler parses through the environment to make sure it's a POST request, then grovels around in stdin to figure out what the POST body looks like, and assuming everything looks okay, it opens a connection to the (local) database over a Unix domain socket. A single INSERT drops the comment into a table, and once that comes back, it sends just enough stuff to stdout to make Apache throw back a 200.

Back in the browser, it gets kicked into the success handler for the AJAX call, where it does the math and prints the result.

Of course, my initial implementation was using a naive "x = new Date" approach, which uses wall time, so any shenanigans on the part of the system clock could have screwed it up. It turns out that there's something called window.performance.now() which seems decently supported, and provides something approaching monotonic time. So, now it's on that instead.

So, here's a free tip: if you are measuring durations with wall times, stop now. Find a way to use a monotonic clock, instead. Otherwise, you will have problems the next time something messes with your wall time, like a NTP step, someone running ntpdate, or a non-smeared leap second.

Back to the problem at hand though, apparently 250 ms was too fast to be seen as having done something? Are people really that used to web stuff being that slow and laggy? That's terrible.

Late amendment: I decided to try it over http.. and got 130 msec. Clearly, all of those round trips for TLS add up.