0

Is it possible (without an application layer cache of requests) to prevent sending an HTTP request for the same resource multiple times when it's cachable? And if yes, how?

E.g. instead of

at time 0: GET /data (request#1)
at time 1: GET /data (request#2)
at time 2: received response#1 for request#1 // headers indicate that the response can be cached
at time 3: received response#2 for request#2 // headers indicate that the response can be cached

 

at time 0: GET /data (request#1)
at time 1: GET /data (will wait for the response of request#1)
at time 2: received response#1 for request#1 // headers indicate that the response can be cached
at time 3: returns response#1 for request#2

This would require that its possible to indicate to the browser that the response will be cachable before the response headers are read. I am asking if there is such a mechanism. E.g. with a preceding OPTIONS or HEAD request of some kind.

Nick Russler
  • 4,608
  • 6
  • 51
  • 88
  • I think your saying "can you know a HTTP response is cachable before you send it", no. And also, why would you possibly want this? – Liam Sep 07 '20 at 14:39
  • I am asking, can I indicate to the browser that a response will be cachable. Or can I make a request to only get the browser to know that the response would be cachable. E.g. a HEAD request. – Nick Russler Sep 07 '20 at 14:41
  • Your initial response can set some [cache headers](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Cache-Control) to tell the browser that it should use this response not request a new one everytime – Liam Sep 07 '20 at 14:42
  • The HTTP HEAD method requests the headers that would be returned if the HEAD request's URL was instead requested with the HTTP GET method. [Source](https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods/HEAD) – Nick Russler Sep 07 '20 at 14:43
  • so yes then "The HTTP HEAD method requests the headers that would be returned if the HEAD request's URL was instead requested with the HTTP" the Cache control headers are in the head so they would be included. I'd guess browsers don't tend to do this as it's inefficient. It's more efficient to make one request than two. I've not head of that request so I'm guessing (being s I've been working with HTTP for 15 years) that it's rarely used – Liam Sep 07 '20 at 14:45
  • Being as it dates from HTTP 1.1 I'm guessing it was more of a thing when bandwidth (56k modem, etc.) was more of an issue. These days, HTTP requests are rarely large enough for this to be worthwhile – Liam Sep 07 '20 at 14:47
  • It was just meant as an example since its hard to ask for things you don't know. A HEAD request would not help at all of course, since it just omits the body in the response and still requires the costly operation to complete on the server. – Nick Russler Sep 07 '20 at 14:52
  • I still don't know what your actual question is? – Liam Sep 07 '20 at 14:54
  • Let us [continue this discussion in chat](https://chat.stackoverflow.com/rooms/221110/discussion-between-nick-russler-and-liam). – Nick Russler Sep 07 '20 at 14:55

2 Answers2

0

My questions is, if there is a mechanism to signal the browser that the response for URI will be cachable

Yes this is what the Cache-control headers do.

and any subsequent requests for that URI can return the response of any in-flight request....Ideally this would be part of the HTTP spec

No HTTP does not do this for you, you need to implement the caching yourself. This is what browsers do.

I did want to check if there is already something ready ouf-of-the-box

Javascript libraries don't typically honour caching, as a AJAX request is usually for data and any caching of data usually happens on the server. I don't know any library and of course asking for Js libraries is out of scope on SO.

Liam
  • 27,717
  • 28
  • 128
  • 190
  • When a http push of said resource was initiated but not yet finished at the time of a client side initiated GET, would it result in the push as well as the GET, or would the browser wait for the completion of the push? Another option but same question would be the use of preload tags. – Nick Russler Sep 08 '20 at 20:13
0

Depending on the browser the second request could be stalled and served if cachable, e.g. in Chromium for non range requests:

The cache implements a single writer - multiple reader lock so that only one network request for the same resource is in flight at any given time. https://www.chromium.org/developers/design-documents/network-stack/http-cache

Here an example where three concurrent requests result in only a single server call:

fetch('/data.json').then(async r => console.log(await r.json()));
fetch('/data.json').then(async r => console.log(await r.json()));;
setTimeout(() => fetch('/data.json').then(async r => console.log(await r.json())), 2000);

three calls

The subsequent request have 0B transferred and have the same random number, showing that only a single server call was made.

This behavior is not the same for e.g. Firefox: firefox does not avoid duplicate requests

An interesting question that comes to mind is what would happen when a request for a resource is made while a H2 push for that resource was initiated before but not yet finished.

For reproducing here the test code: https://gist.github.com/nickrussler/cd74ac1c07884938b205556030414d34

Nick Russler
  • 4,608
  • 6
  • 51
  • 88