Gulp 定制专属提速“外挂”(下)

友情提示:推荐阅读时间10分钟 + 练习时间10分钟

上一期给大家分享了Gulp插件的安装与使用,只要掌握了Gulp插件安装的流程与配置,对于其他Gulp插件的使用基本上就没有太大的问题。毕竟Gulp的插件太丰富了,大家也没有太多的精力把所有的插件都去研究一遍。当一个网站进行改版升级的时候,会遇到静态资源版本更新的问题,那么对于前端开发工程师来说,该如何解决这个问题?所以今天要和大家一起探讨如何解决静态资源版本更新的问题和package.json的作用。

相关阅读:前端工程化 | 定制专属提速“外挂”(上)| 前端工程化 | 揭秘程序员的提速“外挂”

本文内容概要

  • Gulp解决静态资源版本更新的问题
  • package.json的作用
  • Gulp的小结

静态资源缓存更新的问题

为了让用户能够快速的访问网站,开发人员会对网站的静态资源做缓存处理,这样可以减少网站静态资源的加载。但是,又出现了一个新问题,当我们需要对网站做改版升级的时候,如何让缓存的静态资源失效。换句话说,只要把静态资源缓存下来,在缓存有效的时间内,用户访问网站时静态资源是从浏览器缓存里面加载而不是从服务器加载过来。如果想进一步了解“网站缓存”,可以发送关键字缓存到HTML5学堂公众号。如果网站的静态资源做了修改,如何保证用户访问的是最新的静态资源而不是缓存起来的静态资源?具体先来看看下面的几种解决方案。

为静态资源请求添加Query

这个理解起来比较简单,就是在静态资源请求后面添加参数,这个参数的值是时间戳和版本号的结合,当然也可以使用其它方式来计算该参数的值。

修改前

<!-- 代表结构 -->
<h2>梦幻雪冰</h2>


<!-- 代表静态资源 -->
<script type="text/javascript" src="index.js?v=201611131388" charset="utf-8"></script>
<script type="text/javascript" src="main.js?v=201611131388" charset="utf-8"></script>
<script type="text/javascript" src="list.js?v=201611131388" charset="utf-8"></script>

修改后

<!-- 代表结构 -->
<h2>HTML5学堂 - 码匠</h2>


<!-- 代表静态资源 -->
<script type="text/javascript" src="index.js?v=201611131389" charset="utf-8"></script>
<script type="text/javascript" src="main.js?v=201611131389" charset="utf-8"></script>
<script type="text/javascript" src="list.js?v=201611131389" charset="utf-8"></script>

这样看起来好像是可以解决掉静态资源缓存的问题,因为静态资源请求发生了变化。但是又出现了一个新问题,修改前后的静态资源文件名都是没有变化的,当开发人员把线下(本地)的文件覆盖掉线上(服务器)的文件,会出现一定的问题。因为在覆盖的过程中,静态资源和页面文件的部署有一定的时间间隔,对于一个大型网站来说即使时间间隔很小,都有可能出现新的用户访问。那在这个时间间隔内,用户访问网站会发生什么情况呢?

1、如果先覆盖index.html,后覆盖index.js,用户在这个时间间隔访问,会得到新的index.html引用旧的index.js的情况,从而出现错误的页面。

2、如果先覆盖index.js,后覆盖index.html,用户在这个时间间隔访问,会得到旧的index.html引用新的index.js的情况,从而也出现了错误的页面。

这也是一些互联网公司选择半夜这段时间等待访问低峰期再上线的原因之一。

基于文件内容的hash版本控制

对于静态资源缓存更新的问题,目前来说最优方案就是基于文件内容的hash版本控制了。

项目源代码

<!-- 代表结构 -->
<h2>梦幻雪冰</h2>


<!-- 代表静态资源 -->
<script type="text/javascript" src="index.js" charset="utf-8"></script>
<script type="text/javascript" src="main.js" charset="utf-8"></script>
<script type="text/javascript" src="list.js" charset="utf-8"></script>

发布的代码

<!-- 代表结构 -->
<h2>HTML5学堂 - 码匠</h2>


<!-- 代表静态资源 -->
<script type="text/javascript" src="index-46a6d95.js" charset="utf-8"></script>
<script type="text/javascript" src="main-367d728.js" charset="utf-8"></script>
<script type="text/javascript" src="list-e56e8e2.js" charset="utf-8"></script>

发布出来后JS被修改了文件名,产生了一个新文件,并不是覆盖已有的文件。其中“46a6d95”这串字符是根据js的文件内容进行hash计算出来的,只有文件内容发生变化了才会更改。由于这种不是采用同名文件覆盖,因此不存在上述说的那些问题。

因为它无法通过手工的形式来进行维护,所以需要借助工具来处理,在这边我们采用Gulp的插件来做处理。

使用Gulp对静态资源的处理

安装:gulp-asset-rev和gulp-rev插件

命令行:cnpm install gulp-asset-rev和cnpm install gulp-rev

提醒:gulp-asset-rev用于更改HTML文件引用静态资源的路径;gulp-rev用于修改静态资源的文件名。

在gulpfile.js中引入gulp-asset-rev和gulp-rev插件

  1. var assetRev = require('gulp-asset-rev');
  2. var rev = require('gulp-rev');

配置插件的功能

// 静态资源处理
gulp.task('revJS', function() {
    gulp.src('js/*.js') // 源文件下的所有js
    .pipe(rev()) // 修改静态资源的文件名
    .pipe(assetRev()) // 更改HTML文件引用静态资源的路径
    .pipe(gulp.dest('dist/js'));// 复制到目标文件路径
});


gulp.task('rev',['revJS'],function() {
    gulp.src("./**/*.html") // 源文件下的所有HTML
    .pipe(assetRev()) // 更改HTML文件引用静态资源的路径
    .pipe(gulp.dest('dist'));// 复制到目标文件路径
});

完整的配置代码

// 引入Gulp安装好的插件 require('模块名称')
var gulp = require('gulp');
var browserSync = require('browser-sync').create();
var reload = browserSync.reload;
var concat = require('gulp-concat');
var cleanCSS = require('gulp-clean-css');
var assetRev = require('gulp-asset-rev');
var rev = require('gulp-rev');


// 定义一个f5任务,名称自定义即可
// 浏览器自动刷新
gulp.task('f5', function(){
    browserSync.init({
        server:{
            baseDir:'./'
        }
    });


    gulp.watch(['./**/*.html']).on('change', reload);
});


// 文件合并
gulp.task('concatFile', function () {
    // 需要合并的文件
    gulp.src('css/*.css')
    //合并后的文件名
    .pipe(concat('common.css'))
    // 合并后的文件所在的文件夹
    .pipe(gulp.dest('dist/css'));
});


// CSS文件压缩
gulp.task('cssMin', function() {
    // 需要压缩的CSS文件
    gulp.src('css/*.css')
    // CSS文件压缩
    .pipe(cleanCSS())
    // 压缩后的C文件所在的文件夹
    .pipe(gulp.dest('dist/css'));
});


// 静态资源处理
gulp.task('revJS', function() {
    gulp.src('js/*.js') // 源文件下的所有js
    .pipe(rev()) // 修改静态资源的文件名
    .pipe(assetRev()) // 更改HTML文件引用静态资源的路径
    .pipe(gulp.dest('dist/js'));// 复制到目标文件路径
});


gulp.task('rev',['revJS'],function() {
    gulp.src("./**/*.html") // 源文件下的所有HTML
    .pipe(assetRev()) // 更改HTML文件引用静态资源的路径
    .pipe(gulp.dest('dist'));// 复制到目标文件路径
});

查看处理效果

package.json的作用

安装插件的时候为何要将配置信息保存至package.json(package.json是nodejs项目配置文件)。

因为node插件包相对来说比较庞大,所以不加入版本管理,将配置信息写入package.json来进行版本管理,团队合作的时候方便成员下载所需要的包。(使用命令行:npm install,将会根据package.json下载所有需要的包)。另外,在其他项目也要使用Gulp的时候只要把gulpfile.js和package.json拷贝过去,再初始化Gulp就行了,而不用命令行来安装Gulp插件。

Gulp小结

到这边为止,对Gulp的分享算是告一段落了。合理的使用工具能够帮助我们提高开发效率,而不是把时间花在重复操作上面。最后,简单回顾Gulp的使用流程。

  1. ——>安装NodeJS
  2. ——>全局安装Gulp
  3. ——>项目安装Gulp
  4. ——>插件安装
  5. ——>配置gulpfile.js文件
  6. ——>运行Gulp任务

参考资料:

  • https://www.npmjs.com/package;
  • https://www.zhihu.com/question/28072766/answer/40642578

本文系HTML5学堂独家内容,转载请在文章开头显眼处注明作者和出处“HTML5学堂(http://www.h5course.com/)”

原文发布于微信公众号 - HTML5学堂(h5course-com)

原文发表时间:2016-11-14

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏L宝宝聊IT

ESXI网络及组件的基本概念

3064
来自专栏喵了个咪的博客空间

phalcon-进阶篇2(拦截器)

#phalcon-进阶篇2(拦截器)# ? 本教程基于phalcon2.0.9版本 ##前言## 先在这里感谢各位phalcon技术爱好者,我们提供这样一个优秀...

3187
来自专栏好好学java的技术栈

「文末赠书」http协议简介看这篇就够了

协议,网络协议的简称,网络协议是通信计算机双方必须共同遵从的一组约定。如怎么样建立连接、怎么样互相识别等。只有遵守这个约定,计算机之间才能相互通信交流。它的三要...

963
来自专栏散尽浮华

nginx应用总结(2)--突破高并发的性能优化

在日常的运维工作中,经常会用到nginx服务,也时常会碰到nginx因高并发导致的性能瓶颈问题。今天这里简单梳理下nginx性能优化的配置(仅仅依据本人的实战经...

3049
来自专栏小文网

查看QQ闪照的方法

来源http://www.xiaowennet.com/Study/date20180722-id101.html

4864
来自专栏好好学java的技术栈

http简介看这篇就够了

协议,网络协议的简称,网络协议是通信计算机双方必须共同遵从的一组约定。如怎么样建立连接、怎么样互相识别等。只有遵守这个约定,计算机之间才能相互通信交流。它的三要...

1132
来自专栏跟着阿笨一起玩NET

win7组件服务COM+应用程序编录错误解决办法

一般情况下,我们遇到过的COM+应用程序编录错误共有两个:(1)第一个是打开COM+应用程序时出现“编录错误,执行最后操作发生错误,错误代码8007042C-依...

2631
来自专栏零基础使用Django2.0.1打造在线教育网站

socket模拟发送http请求

嗨,小伙伴们,好久不见~~~,最近博主在研究socket编程,觉得socket真的好强大。之前一直我们都是在介绍爬虫的requests、urllib等库,我们知...

8222
来自专栏逸鹏说道

用户不在sudoers 文件中。此事将被报告

跨平台系列汇总:http://www.cnblogs.com/dunitian/p/4822808.html#linux 异常处理汇总-服 务 器 http:/...

3688
来自专栏PHP实战技术

一个查看框架源码,一个查找错误的小工具,你用了吗?

日常开发中还在一直var_dump?exit()?,是不是很不便捷,很不方便?今天小梦就给大家讲讲在PHP开发中(划重点:PHP开发,当然其他语言开发也是有类似...

1514

扫码关注云+社区

领取腾讯云代金券