Safari does not always send If-None-Match for a Get on Page Load

889 Views Asked by At

I have a mock project where I am testing Etag and If-None-Match behavior on different browsers. A Get request is sent on page load and I will always respond with 200 and assign a new Etag value.

window.addEventListener('load', () => getEtag(false));

function getEtag() {
    var xhr = new XMLHttpRequest();
    xhr.onreadystatechange = function () {
        if (xhr.readyState === 4 && xhr.status === 200) {
            console.log("Success");
        }
    };

    xhr.onerror = function () {
        console.log("Failure");
    };

    xhr.open("Get", "http://localhost:8080/etag", true);
    xhr.send();
}

Java server side:

   @GetMapping("/etag")
    public String getEtag(HttpServletRequest request, HttpServletResponse response) {
        response.setHeader("ETag", UUID.randomUUID());
        return "";
    }

I understand that this not the intended use for Etags but bear with me. On Chrome and Firefox this works as expected. On every page load the request includes the If-None-Match header. However on Safari the header is included only in every other request. I know there are several questions pertaining to Etags and If-None-Match and Safari but they are all about its complete absence. In my case the first request does not contain the If-None-Match (as expected), the second request will but then the third request will not. It then oscillates between sending the header and not. I modified my code to return 304 if the If-None-Match header was present which prompted Safari to send the header with every request but it would not update the Etag value with the new one assigned. I understand that that is expected behavior, but is there a way to make Safari behave like chrome and Firefox when I return 200 and a new Etag?

1

There are 1 best solutions below

0
On BEST ANSWER

Short Asnwer

Unfortunately, ETags (Entity Tags) were not officially supported by Safari until the release of the early version of 17.2 on December 11, 2023. This means that before this date, Safari browsers did not recognize or understand ETags, which are a type of HTTP header that can be used to improve caching performance by allowing servers to quickly determine whether a client already has a cached copy of a resource. As a result, websites that relied on ETags for caching would not work as expected in Safari browsers prior to 17.2.

More explanation for other visitors:

ETags are a mechanism used by web servers and browsers to improve the performance of web pages by reducing the need to download the same resource from the server multiple times. When a browser requests a resource, the server can include an ETag in its response. The browser can then store this ETag along with the cached copy of the resource. If the browser subsequently requests the same resource, it can send the ETag back to the server. If the ETag matches the server's current representation of the resource, the server can send back a 304 Not Modified response, indicating that the cached copy is still valid. This can save time and bandwidth by avoiding the need to download the entire resource again.

However, Safari did not natively support ETags until the release of the early version of 17.2 in December 2023. This meant that websites that relied on ETags for caching would not work as expected in Safari browsers prior to 17.2. Developers had to resort to workarounds, such as using the Last-Modified header or JavaScript to manually compare the cached copy of the resource to the server's current representation.

Reference