Grunt针对静态文件的压缩,版本控制打包方案
在讲之前先谈谈大致步骤:安装nodejs -> 全局安装grunt -> 项目创建package.json --> 项目安装grunt以及grunt插件 -> 配置Gruntfile.js -> 运行任务
1.安装Node
我们开始之前需要安装Nodejs,如果没有安装的传送门
安装好了之后,查看是否安装成功,正常是这样的提示

这里建议npm换成淘宝的cnpm,速度杠杠的。
安装命令:
https://registry.npm.taobao.org 
2.安装全局Grunt
安装命令:
cnpm install grunt -g

3.项目创建package.json
在项目根目录下创建package.json文件,文件内容如下

4.项目安装grunt以及grunt插件
我们所需要的插件
| 插件名称 | 说明 | Github地址 |
| grunt-contrib-clean | 清空文件和文件夹 | https://github.com/gruntjs/grunt-contrib-clean |
| grunt-contrib-copy | 复制文件和文件夹 | https://github.com/gruntjs/grunt-contrib-copy |
| grunt-contrib-concat | 连接、合并文件(没用到) | https://github.com/gruntjs/grunt-contrib-concat |
| grunt-contrib-cssmin | (CSS文件)压缩 | https://github.com/gruntjs/grunt-contrib-cssmin |
| grunt-contrib-uglify | (JS文件)压缩 | https://github.com/gruntjs/grunt-contrib-uglify |
| grunt-filerev | 文件内容hash(MD5)(版本号控制) | https://github.com/yeoman/grunt-filerev |
| grunt-usemin | 文件进行引用修改 | https://github.com/yeoman/grunt-usemin |
| load-grunt-tasks | oad-grunt-tasks | https://github.com/sindresorhus/load-grunt-tasks |
我们打开我们的项目文件夹,在路径栏中输入cmd然后回车

回车后的界面

打开命令行窗口之后,我们输入安装命令:
cnpm install grunt grunt-contrib-clean grunt-contrib-copy grunt-contrib-concat grunt-contrib-cssmin grunt-contrib-uglify grunt-filerev grunt-usemin load-grunt-tasks --save-dev

5.配置Gruntfile.js (这是重点,重点,重点。重要的事情说三遍。)
先贴一下我的配置,后面慢慢说明
module.exports = function (grunt) {
require('load-grunt-tasks')(grunt);
var path = {
src : 'test',
dest : 'dist',
}
grunt.initConfig({
path : path,
clean : {//清空生产文件夹
beforebuild : {
files : [{
src : ['<%= path.dest %>/']
}
]
}
},
filerev : {//对css和js文件重命名
build : {
files : [{
src : ['<%= path.dest %>/**',
'!<%= path.dest %>/page/*.html',//html文件不加版本号
'!<%= path.dest %>/**/*.{png,jpg,jpeg}']//图片 不需要加版本号
}
]
}
},
useminPrepare : {//声明concat、cssmin、uglify
build : {
files : [{
src : '<%= path.src %>/page/*.html'
}
],
}
},
usemin : {//修改html中的css和js引用
html : {
files : [{
src : '<%= path.dest %>/page/*.html'
}
]
}
},
copy : {//复制文件
build : {
files : [{
expand : true,//为true启用cwd,src,dest选项
cwd : '<%= path.src %>/',//所有src指定的匹配都将相对于此处指定的路径(但不包括此路径)
src : ['**/*.*'],//相对于cwd路径的匹配模式。意思就是 src/**/*.*,匹配src下面所有文件
dest : '<%= path.dest %>/'//目标文件路径前缀。
}
]
}
},
cssmin :{
build : {
files : [{
expand : true,//为true启用cwd,src,dest选项
cwd : '<%= path.src %>/',//所有src指定的匹配都将相对于此处指定的路径(但不包括此路径)
src : ['css/*.css'],//相对于cwd路径的匹配模式。意思就是 src/**/*.css,匹配src下面所有css文件
dest : '<%= path.dest %>/'//目标文件路径前缀。
}
]
}
},
uglify :{
build : {
files : [{
expand : true,//为true启用cwd,src,dest选项
cwd : '<%= path.src %>/',//所有src指定的匹配都将相对于此处指定的路径(但不包括此路径)
src : ['js/*.js'],//相对于cwd路径的匹配模式。意思就是 src/**/*.js,匹配src下面所有js文件
dest : '<%= path.dest %>/'//目标文件路径前缀。
}
]
}
},
});
grunt.registerTask('default', ['clean:beforebuild', 'copy', 'cssmin', 'uglify','filerev', 'usemin']);
};
我们前面一直都在安装这个安装那个,但是安装的这些东西怎么用起来了?
首先我们通过学习 grunt入门 了解到插件如何使用,这是官网的例子。

pkg是通过读取package.json生成的json对象。
uglify是 grunt-contrib-uglify 指定的任务名,每个插件都有对应的任务名,可以在对应的github里面查看
grunt.loadNpmTasks('grunt-contrib-uglify'); 从字面上就可以看出来/,加载能够提供"uglify"任务的插件。
grunt.registerTask('default', ['uglify']); 注册别名任务,这个别名任务对应的是一个任务列表
当通过 grunt 别名时,实际是执行列表里的任务,并按顺序执行
这些基本的信息都可以通过官网查看。
我们来说说我们需求,我们需要对静态文件打包压缩,并且需要对静态文件加入版本号而且所有引用静态文件的html或css都得修改文件名,我们的需求明确后来来看看我们怎么做。
第一步:我们需要重新打包,那就需要复制文件,所以我们需要grunt-contrib-copy插件。
在copy之前我们先要确定源文件和目标文件,我这里源文件都放在test文件夹中,目标文件都放在dist文件夹中

我们创建文件路径
var path = {
src : 'test',
dest : 'dist',
}
文件路径创建好了,我们来看copy
copy : {//复制文件
build : {
files : [{
expand : true,//为true启用cwd,src,dest选项
cwd : '<%= path.src %>/',//所有src指定的匹配都将相对于此处指定的路径(但不包括此路径)
src : ['**/*.*'],//相对于cwd路径的匹配模式。意思就是 src/**/*.*,匹配src下面所有文件
dest : '<%= path.dest %>/'//目标文件路径前缀。
}
]
}
},
从代码的注释就可以看出一二了。这里说下cwd,src,dest 。
其实这里的源路径是 cwd + src。这才是真正的源路径。dest是目标路径前缀。
我这里的意思是src下面所有的文件,意思就是把 src文件夹 里面的文件复制到 dest文件夹 里。这里可以指定需要复制的具体文件夹或者文件类型
第二步:进行文件压缩,我这里只是针对js和css压缩,对img的压缩可以查看对应的插件,思路都一样。
css压缩需要用到 grunt-contrib-cssmin 插件,该插件对应的任务名为 cssmin
cssmin :{
build : {
files : [{
expand : true,//为true启用cwd,src,dest选项
cwd : '<%= path.src %>/',//所有src指定的匹配都将相对于此处指定的路径(但不包括此路径)
src : ['css/*.css'],//相对于cwd路径的匹配模式。意思就是 src/**/*.css,匹配src下面所有文件
dest : '<%= path.dest %>/'//目标文件路径前缀。
}
]
}
},
js 压缩需要用到 grunt-contrib-uglify 插件,该插件对应的任务名为 uglify
uglify :{
build : {
files : [{
expand : true,//为true启用cwd,src,dest选项
cwd : '<%= path.src %>/',//所有src指定的匹配都将相对于此处指定的路径(但不包括此路径)
src : ['js/*.js'],//相对于cwd路径的匹配模式。意思就是 src/**/*.js,匹配src下面所有文件
dest : '<%= path.dest %>/'//目标文件路径前缀。
}
]
}
},
第三步:静态文件重命名,我们这里的版本控制是通过对静态文件重命名来现实的。
重命名需要用到 grunt-filerev 插件,该插件对应的任务名为 filerev
filerev : {//对css和js文件重命名
build : {
files : [{
src : ['<%= path.dest %>/**',
'!<%= path.dest %>/page/*.html',//html文件不加版本号
'!<%= path.dest %>/**/*.{png,jpg,jpeg}']//图片 不需要加版本号
}
]
}
},
这里只有一个src参数,传的是个数组,我们这里是只想给css和js重命名,其他文件不需要。所以数组第一个参数 src/** 匹配src文件夹中所有文件,后面两个 ! xx,是排除的意思,
第四步:修改html中css和js的引用
修改文件引用需要用到 grunt-usemin 插件,该插件对应的任务名为 usemin
usemin : {//修改html中的css和js引用
html : {
files : [{
src : '<%= path.dest %>/page/*.html'
}
]
}
},
这里也只有一个src参数,给出的是html的地址,如果你还有css 可以这样写
usemin : {//修改html中的css和js引用
html : {
files : [{
src : '<%= path.dest %>/page/*.html'
}
]
},
css :{
files : [{
src : '<%= path.dest %>/css/*.css'
}
]
}
},
这里需要注意 :usemin 除了需要在 Gruntfile.js中配置外,还需要在需要修改引用的文件中加入指令。 <!-- build:type path --> 具体可以在github查看,上面有地址。
(但是在idea中我没加也可以,不知道是什么原因。)
<!DOCTYPE html>
<html lang="en">
<head>
<title>Grunt</title>
<!-- build:js ../../css/common/common.css -->
<link href="../../css/common/common.css" type="text/css" rel="stylesheet">
<!-- endbuild -->
</head>
<body>
<div class="wrap">
</div>
<!-- build:js ../js/constants.js-->
<script src="../../js/tools/constants.js"></script>
<!-- endbuild -->
</body>
</html>
第五步:我们从 复制,压缩,重命名,修改引用都说了一遍,这里还少一个东西,就是我们每次复制之前需要把目标文件夹里面的文件删除掉。
修改文件引用需要用到 grunt-contrib-clean 插件,该插件对应的任务名为 clean
clean : {//清空生产文件夹
beforebuild : {
files : [{
src : ['<%= path.dest %>/']
}
]
}
},
这里也只有一个src参数,给出目标文件夹的地址。
所有任务到这里就结算了。
我们注册任务别
grunt.registerTask('default', ['clean:beforebuild', 'copy', 'cssmin', 'uglify','filerev', 'usemin']);
可以看到,我们这里只是注册了任务,并没有应用插件。我们添加插件是听过 load-grunt-tasks 插件完成的
require('load-grunt-tasks')(grunt);
这里指令相当于我们一个个写
grunt.loadNpmTasks('xxx');
Gruntfile.js 配置完了之后我们执行grunt命令就可以在目标文件夹中得到我们所需要的文件
这里补充说明几点:
这种写法是动态构建文件对象 传送门

这种写法是文件数组格式 传送门

Grunt针对静态文件的压缩,版本控制打包方案的更多相关文章
- Linux下文件的压缩与打包
一.Linux下常见的文件压缩命令: 在Linux的环境中,压缩文件的扩展名大多是:『*.tar, *.tar.gz, *.tgz, *.gz, *.Z, *.bz2』,为什么会有这样的扩展名呢? 这 ...
- linux(3)磁盘与文件系统管理/查看硬盘、内存空间/文件系统的操作/ 文件的压缩和打包
一.磁盘与文件系统管理 1.分区与文件系统分区:记录每一个分区的开始柱面和结束柱面主引导区(master boot recorder):记录分区的数据,记录硬盘里所有的分区信息分区划分好后,要将分区格 ...
- ASP.NET Core应用针对静态文件请求的处理[5]: DefaultFilesMiddleware中间件如何显示默认页面
DefaultFilesMiddleware中间件的目的在于将目标目录下的默认文件作为响应内容.我们知道,如果直接请求的就是这个默认文件,那么前面介绍的StaticFileMiddleware中间件会 ...
- ASP.NET Core应用针对静态文件请求的处理[4]: DirectoryBrowserMiddleware中间件如何呈现目录结构
和StaticFileMiddleware中间件一样,DirectoryBrowserMiddleware中间本质上还是定义了一个请求地址与某个物理目录之间的映射关系,而目标目录体现为一个FilePr ...
- ASP.NET Core应用针对静态文件请求的处理[3]: StaticFileMiddleware中间件如何处理针对文件请求
我们通过<以Web的形式发布静态文件>和<条件请求与区间请求>中的实例演示,以及上面针对条件请求和区间请求的介绍,从提供的功能和特性的角度对这个名为StaticFileMidd ...
- ASP.NET Core应用针对静态文件请求的处理[2]: 条件请求与区间请求
通过调用ApplicationBuilder的扩展方法UseStaticFiles注册的StaticFileMiddleware中间件帮助我们处理针对文件的请求.对于StaticFileMiddlew ...
- ASP.NET Core应用针对静态文件请求的处理[1]: 以Web的形式发布静态文件
虽然ASP.NET Core是一款"动态"的Web服务端框架,但是在很多情况下都需要处理针对静态文件的请求,最为常见的就是这对JavaScript脚本文件.CSS样式文件和图片文件 ...
- linux文件压缩与文件夹压缩(打包)
目录 一:linux文件压缩 1.linux常见的压缩包有哪些? 2.bzip压缩(文件) 二:打包(文件夹压缩) 1.打包命令 2.参数 3.参数解析(实战) 4.注意事项 简介: win中的压缩包 ...
- 3.Linux 文件的压缩与打包
1.常用压缩打包命令 常用的压缩打包扩展名为如下: *.Z compress 程序压缩的文件,非常老旧了,不再细说 *.gz gzip 程序压缩的文件: *.bz2 bzip2 程序压缩的文件: *. ...
随机推荐
- 关闭Excel提示文件格式和扩展名不匹配的警告框
打开某些excel表时,Excel会提示: "a.xls"的文件格式和扩展名不匹配.文件可能已损坏或不安全.除非您信任其来源,否则请勿打开.是否仍要打开它? 在编辑大量的xls ...
- 题目1522:包含min函数的栈
#include <iostream> #include <cstdio> #include <stack> using namespace std; int ma ...
- Html5笔记之第五天
Html5增强的文件上传域 <!DOCTYPE html> <html> <head> <title>Html5增强的文件上传域</title&g ...
- tomcat设置文件编码
tomcat修改bin文件夹下面的catalina.bat文件可以解决乱码在文件中加上JAVA_OPTS="-server -Xms128M -Xmx4096M -XX:PermSize=5 ...
- 马士兵讲jsp项目--BBS项目分析笔记
1 导言 作为一个新手JAVA程序员,我相信很多人和我一样急切的想要寻找项目来做,这里我把马士兵老师讲的JAVA WEB的第一个小项目拿过来给大家分享一下. 首先,对一个项目而言我们先要认识清楚我们要 ...
- Java中常见数据结构Set之HashSet
今天来说说Java集合中的Set系列之HashSet. Set我们众所周知的就是虑重功能, 我们平时在项目开发中也常用到这个特性的.那么Set为何能够虑重呢? 接下来我们就看下源码吧. Set ...
- mysql 用多次查询代替一次复杂join查询的优点分析
详见:http://blog.yemou.net/article/query/info/tytfjhfascvhzxcyt344 多高性能的应用都会对关联查询进行分解.简单地,可以对每一个表进行一次单 ...
- 基于C语言的UTF-8中英文替换密码设计
简要说明 本设计为湖南大学密码学的一次课程作业设计.非作业目的可随意引用. 由于本人初次接触密码学,本设计可能存在问题以及漏洞.若发现望指出. GitHub : https://github.com/ ...
- 转:js闭包
一切都是对象 "一切都是对象"这句话的重点在于如何去理解"对象"这个概念. --当然,也不是所有的都是对象,值类型就不是对象. 首先咱们还是先看看javascr ...
- 201521123083 《Java程序设计》第7周学习总结
1. 本周学习总结 以你喜欢的方式(思维导图或其他)归纳总结集合相关内容. 参考资料: 2. 书面作业 1. ArrayList代码分析 1.1 解释ArrayList的contains public ...