Asking users to clear cache in their browsers definitely is not something that you would like to do. How to make sure that browser's cache will not be a problem after deployment of the new application? It is unexpectedly easy with a proper Gulp plugin - cachebust.
Problem with cache after deployment
The problem can be observed with the following scenario:
- A user enters the website. The HTML page refers to scripts.js and styles.css so they are downloaded from the server along with the HTML page. The latter two files are cached by the user's browser.
- I make a change in the scripts.js and styles.css.
- I build a new deployment package with minified frontend.
- The package is deployed to the server.
- The use enters the website again. The HTML page still refers to scripts.js and styles.css but they changed. Unfortunately, the browser does not know that these two files are new until they are downloaded. There is a big chance that the browser will use the cached files instead of requesting new from the server.
The old version of the files are used and the user cannot take advantage of the new version.
Cachebust plugin
This issue can be easily solved by using cachebust Gulp plugin. I strongly recommend you to start with the code minification with Gulp article as the following instructions extend what I did there.
First, the plugin has to be added to the project.
D:\projects\sample\main-page>npm install --save-dev gulp-cache-bust
When the plugin exists in the project, I need a task in gulpfile.js.
gulp.task('cachebust', ['clean', 'htmlmin'], function () {
return gulp.src(webappDir + 'dist/*.html')
.pipe(cachebust({type: 'timestamp'}))
.pipe(gulp.dest(webappDir + 'dist'))
});
The cachebust task depends on two other: clean and htmlmin. Their definition is presented in the code minification with Gulp article. Of course, the task has to be added to the build task if you use the same configuration as I do.
What does the task? It simply modifies the HTML files in the dist directory. It modified link and script tags to add an HTTP variable based on a timestamp. For example this
<script src="scripts/scripts.js"></script>
is replaced with
<script src="scripts/scripts.js?t=1514663223906"></script>
Every time the cachebust task is executed, new t value is generated. When the browser sees that, it assumes scripts.js uses the t value so if the file is not cached with exactly the same t value, the browser requests the file from the server. It is exactly what I wanted to achieve.