How to force nginx to reload client's browser for content change?

I have a very simple setup, but I am unable to achieve the end goal as of yet. I have an nginx installed on a VM that is serving a static html page. This html page contains the code for a video that I want to loop. I want to be able to replace the video file in the video directory and have nginx force the client's browser which is displaying the old video to reload and start playing the new file without restarting nginx or refreshing the browser manually. I should mention that the client browser is on a TV that displays the video and I do not want to manually refresh the browser on the TV and have this done automatically.

I have found few meta tags by searching around to have it work but it does not work for me. The page serves the old video and does not refresh after an hour (the value that I have specified in the meta tag).

<!DOCTYPE html>
<html>
<head>
<title>my video</title>
<meta http-equiv="Pragma" content="no-cache">
<meta http-equiv="Expires" content="-1">
<meta http-equiv="CACHE-CONTROL" content="NO-CACHE">
<meta http-equiv="refresh" content="3600">
<style>
    body {
        position: absolute;
            overflow: hidden;
            width: 100%;
            height: 100%;
    }

    #myvideo {
        width: 100%;
        height: 100%;
    }
</style>
</head>
<body>
    <!-- The video -->
    <video autoplay muted loop id="myvideo">
        <source src="videos/main.mp4" type="video/mp4">
    </video>
</body>
</html>

I upload a different video to video directory with the same name "main.mp4" and want the nginx to force the browser to reload and display the updated video.

1 answer

  • answered 2019-08-14 21:06 Danila Vershinin

    Few things to check/keep in mind:

    While <meta http-equiv="refresh" content="3600"> should work just fine, some (very rare ones) browsers may not support it. In that case, you might try adding Javascript-based solution, e.g.:

    <script>
    setTimeout(function() { window.location.reload(true); }, 60*60*1000);
    </script>
    

    The true will ensure that while reloading the page, the browser will skip its cache and load the page from the server.

    Since your page uses/links to the same video filename internally, you have to ensure that http://example.com/videos/main.mp4 does not have positive caching headers.

    You can use curl to check headers like so:

    curl -IL http://example.com/videos/main.mp4
    

    See what is the value for Cache-Control and Expires. You can have both, or either of those headers. For your case, they should dictate cacheability of less than one hour or none at all.

    In NGINX you can set this with:

    location = /videos/main.mp4 {
        expires -1;
    }
    

    Which basically tells it to send expiration in the past of 1 second behind the time when the video file was fetched (= no cache).