给资源文件添加指纹(Gulp版)
至于为什么要费尽心思地给文件添加指纹,请参看前端静态资源缓存控制策略。这次要达到的小目标就是生成的资源文件能够被客户端缓存,而在文件内容变化后,能够请求到最新的文件。
需要用到的 gulp 插件是 gulp-rev2 ,看清楚了,不是 gulp-rev + gulp-rev-collector 的蹩脚组合,而是 gulp-rev2。
gulp-rev2 的设计思路:
根据文件的内容
file.contents生成文件指纹(hash值);根据前面生成的文件指纹集合成一张
(源文件,构建文件)映射对照表(并保存在清单文件 rev-manifest.json 中);根据前面生成的映射对照表级联更新存在引用的父文件;
下面以一个具体的栗子为例进行实践。
栗子的目录结构是这样的:

其中包含一个 css 样式源文件 .demo/demo.css,内容如下
a { background: url(../images/road.jpg); }
div { background: url(../images/a+b.jpg); }
接下来使用 gulp 进行构建,新建两个任务,一个构建 image,一个构建 css,
const gulp = require('gulp');
const rev2 = require('gulp-rev2');
gulp.task('build:image', ()=>{
return gulp.src('./demo/**/*.{png,jpg,gif,ico}')
.pipe(rev2()) // 生成文件指纹并修改文件名
.pipe(gulp.dest('dist')) // 输出到 dist 目录
.pipe(rev2.manifest()) // 生成映射对照表 rev-manifest.js
.pipe(gulp.dest('.')); // 输出到 gulpfile.js 同级目录
});
gulp.task('build:css', ['build:image'], ()=>{
return gulp.src('./demo/**/*.css')
.pipe(rev2.update()) // 根据映射对照表更新存在引用的父文件
.pipe(gulp.dest('dist'))
});
然后执行 gulp build:css,会发现根目录下生成了 dist 目录,并在里面存放了构建后的文件,

细心的同学可能已经发现在构建之后 ./demo/image/ 目录下的图片资源已经添加了文件指纹,

这时候打开生成的 ./dist/demo.css,内容如下
a { background: url(../images/road-f7ee61d96b.jpg); }
div { background: url(../images/a+b-d41d8cd98f.jpg); }
可以看到引用了图片资源的 css 文件内容也得到了相应更新。只要图片资源发生更新(文件指纹就会发生变化),引用者(css文件)也应该级联更新。这两个应该是始终同步的,否则就会出现驴唇不对马嘴引用错乱。
文件指纹总算加上了,但是这种修改文件名的方式并不总是所希望的。有时我们可能需要更简单传统的方式,也就是通过url参数(query string)的形式进行关联。也就是我们期望的 css 可能是这样的:
a { background: url(../images/road.jpg?_v_=f7ee61d96b); }
div { background: url(../images/a+b.jpg?_v_=d41d8cd98f); }
gulp-rev2 已经提供了这个选项,可以说是服务非常周到。只需要在原来的 gulp 代码上简单加一行配置项:
. . .
.pipe(rev2({ // 生成文件指纹并修改文件名
query: true, // 以query string的方式进行指纹关联
}))
. . .
重新执行 gulp build:css,打开 ./dist/demo.css,会发现样式表已经变成了我们预期的样子:
a { background: url(../images/road.jpg?_v_=f7ee61d96b); }
div { background: url(../images/a+b.jpg?_v_=d41d8cd98f); }
你可以尝试对单个图片资源进行更新(比如 override 操作),gulp-rev2 只会更新发生变动的资源的指纹,这也是所期望的。
注意点
...
.pipe(rev2.manifest()) // 生成映射对照表 rev-manifest.js
.pipe(gulp.dest('.')); // 输出到 gulpfile.js 同级目录
请确保 gulp-rev2 生成的清单文件 rev-manifest.js 输出在 gulpfile.js 同级目录下。这是因为 gulp-rev2 会在这个目录进行读取,否则将会导致错误。建议你在 .gitignore 文件中忽略掉该文件,因为它是构建生成的,没有任何加入版本控制的需要。
给资源文件添加指纹(Gulp版)的更多相关文章
- ASP.NET MVC 扩展HtmlHelper类为 js ,css 资源文件添加版本号
写在前面 在项目部署当中会需要更新 css 文件或 js 等资源文件,为了避免由于浏览器缓存的原因无法加载新的 css 或 js ,一般的做法是在资源文件的后面加上一个版本号来解决,这样浏览器就会去服 ...
- Qt之生成Window资源文件(.rc 文件)
简述 qmake 可以随意地自动生成一个适当填充的 Windows 资源文件.本节主要讲解如何用 qmake 处理一个 Windows 资源文件,并将其链接到一个可执行应用程序(EXE)或动态链接库( ...
- 控件注册 - 利用资源文件将dll、ocx打包进exe文件(C#版)
原文:控件注册 - 利用资源文件将dll.ocx打包进exe文件(C#版) 很多时候自定义或者引用控件都需要注册才能使用,但是如何使要注册的dll或ocx打包到exe中,使用户下载以后看到的只是一个e ...
- VS工程添加资源文件
1. 添加资源文件: 2. 资源文件内写相应代码: <ResourceDictionary xmlns="http://schemas.microsoft.com/winfx/2006 ...
- Qt 添加资源文件
*本人乃小白,博文主要用于个人记录,不保证内容准确无误* 我们编写的gui可能需要一些额外的资源(比如贴图用的图片),可用资源文件统一管理.以下以图片为例. 用qt creator 打开工程,为工程新 ...
- Qt之添加Windows资源文件(.rc文件)
简述 在Windows下使用Qt时,通常会用到Windows的资源文件 - 为exe设置信息,其中包括:文件说明.产品名称.产品版本.版权等信息... 由于是Windows平台相关的东西,Qt助手中对 ...
- WPF中动态添加xaml资源文件
一.新建一个资源文件,然后设置其Build Actoin(生成操作)为Resource(资源): 二.在App.xaml.cs的StartUp事件或者是你需要的时机代码段写上如下代码: Resourc ...
- SpringMVC+FreeMarker实现静态资源文件自动添加版本号(md5)
近日切换java开发,开始学习springframework.在实现静态资源文件自动计算版本号的实例时,因为不熟悉框架,走了不少弯路,好在最终解决了问题.这里写篇文章记录一下实现,也希望对大家有些用处 ...
- 添加ASP.NET网站资源文件夹
ASP.NET应用程序包含7个默认文件夹,分别为Bin.APP_Code.App_GlobalResources.App_LocalResources.App_WebReferences.App_Br ...
随机推荐
- Activiti-02-activiti api
流程引擎API和服务 通过ProcessEngine你可以获取各种服务,它和所有的服务对象都是线程安全的,因此整个整个应用中可以只有一份. ProcessEngine processEngine =P ...
- 排查Linux机器是否已经被入侵
随着开源产品的越来越盛行,作为一个Linux运维工程师,能够清晰地鉴别异常机器是否已经被入侵了显得至关重要,个人结合自己的工作经历,整理了几种常见的机器被黑情况供参考 背景信息:以下情况是在CentO ...
- 【Spring】Spring的bean装配
前言 bean是Spring最基础最核心的部分,Spring简化代码主要是依赖于bean,下面学习Spring中如何装配bean. 装配bean Spring在装配bean时非常灵活,其提供了三种方式 ...
- 【Conclusion】MySQL使用
MySQL使用 因为数据库实验用到了MySQL,这里对现在已经涉及到的MySQL部分操作做一个简单的小结. 1.安装MySQL 上MySQL的官网下载对应自己OS平台的MySQL安装文件,有在线安装和 ...
- python和C语言混编的几种方式
Python这些年风头一直很盛,占据了很多领域的位置,Web.大数据.人工智能.运维均有它的身影,甚至图形界面做的也很顺,乃至full-stack这个词语刚出来的时候,似乎就是为了描述它. Pytho ...
- [js高手之路] html5 canvas系列教程 - 图片操作(drawImage,clip,createPattern)
接着上文[js高手之路] html5 canvas系列教程 - 文本样式(strokeText,fillText,measureText,textAlign,textBaseline)继续,本文介绍的 ...
- Python协程爬取妹子图(内有福利,你懂得~)
项目说明: 1.项目介绍 本项目使用Python提供的协程+scrapy中的选择器的使用(相当好用)实现爬取妹子图的(福利图)图片,这个学会了,某榴什么的.pow(2, 10)是吧! 2.用到的知 ...
- mvc的filter
如果想要记录ajax的请求和输出信息.内部发生异常记录日志.需要登录认证.需要权限判断:那mvc的各种filter可以帮助你实现你想要的.Mvc框架支持5种不同类型的过滤器:我会按照执行顺序进行简单的 ...
- C#中System.DateTime.Now.ToString()用法
//Asp.net中的日期处理函数 //2008年4月24日 System.DateTime.Now.ToString("D"); //2008-4-24 ...
- ZOJ2067 经典 DP
题目:一个由'.'和'#'组成矩形,统计里面'.'组成的矩形的个数.点击打开链接 自己写挂了,懒得搞了 #include <stdio.h> #include <string.h&g ...