gulp自动化打包(上)
文章概述
本文分为上下两篇,上篇主要介绍一些常用的gulp插件(也是此次打包主要用的gulp插件),而下篇主要以一个demo项目为例,从本地checkout出合适的git版本,压缩、合并、到最后打成zip包,发送至指定目录,做一个全面的演示。
流程预览:
项目结构
首先,有一个类似于这样的项目结构
图中主要演示项目中大概会有的几种文件类型,fonts(ttf,svg),image(jpg,png),js,less(sass),实际项目会复杂得多,开始一个项目的时候,可以直接从git上拿一个angular-seed(webpack-seed)改。
开始使用gulp
下载gulp
开始玩gulp之前,要确定自己有nodejs的环境,没有的话,先去弄个nodejs,这个比较简单,直接在https://nodejs.org/en/,下载一个对应开发环境的nodejs,然后一路next,路径默认就好,window下自定义了路径后,就不是全局的了,需要自己再配环境变量,图省事的话,就一路next到finish。
ok,安装好nodejs之后,在项目的src目录下(与index.html的同级目录)建立一个package.json文件与gulpfile.js(这个名字要对,不然命令行识别不了,项目中有时建立两个gulp的js文件,如果两个都含有同一任务,不特殊说明的话,命令行只执行文件名为gulpfile.js的任务),在命令行输入npm install gulp --save-dev
(之前没有安装过gulp的话,执行npm install gulp -g --save-dev
)指令,
"--save-dev"表示在安装gulp之后,将安装的信息保存在package.json文件,以便之后利用package.json文件去install相关插件(多人开发尤其要注意保存安装信息),创建gulp成功后,目录结构变为
之后所有的gulp插件都以此方式安装,即npm install xx --save-dev
gulp插件详细介绍
按照实际的打包顺序, 我依次会介绍gulp-git、gulp-htmlmin、gulp-uglify、gulp-concat、gulp-ng-annotate
(如果不是angular框架不需要)、gulp-less、gulp-minify-css、minimist、del、gulp-zip、gulp-ftp、run-sequence
gulp-git
gulp-git主要的作用是通过gulp脚本,来执行一些git的操作,gulp-git插件基本上可以完成所有常用的git操作,比如add、commit、push等等,还可以查看git-log,十分方便,用法也非常简单,比如下面是一段获取git仓库中tag为v1.0.0的代码(也可以checkout分支名):
var git = require('gulp-git');
gulp.task('checkout', function () {
git.checkout('v1.0.0', function (err) {
if (err) throw err;
});
})
详细的gulp-git使用方法,请参照https://github.com/stevelacy/...。
gulp-htmlmin
就是一个压缩html的插件,没什么特别要讲的,这边也直接拿网上的一个常用配置来演示。
var htmlmin = require('gulp-htmlmin');
gulp.task('testHtmlmin', function () {
var options = {
removeComments: true,//清除HTML注释
collapseWhitespace: true,//压缩HTML
collapseBooleanAttributes: true,//省略布尔属性的值 <input checked="true"/> ==> <input />
removeEmptyAttributes: true,//删除所有空格作属性值 <input id="" /> ==> <input />
removeScriptTypeAttributes: true,//删除<script>的type="text/javascript"
removeStyleLinkTypeAttributes: true,//删除<style>和<link>的type="text/css"
minifyJS: true,//压缩页面JS
minifyCSS: true//压缩页面CSS
};
gulp.src('src/html/*.html')
.pipe(htmlmin(options))
.pipe(gulp.dest('dist/html'));
});
gulp-uglify
js压缩插件,有四个可选属性,分别为
mangle:是否混淆变量名,默认为true(混淆),全局变量不会被混淆,之前看到有的代码中的require被混淆掉了,导致代码错误,这个需要注意一下。
output:传递你一个对象去指定输出的选项,个人理解是定制化的去压缩,传递一个参数对象,否则执行默认的参数。(不确定)
compress:是否完全压缩,默认为true(全压);
preserveComments:是否保留备注,默认不保留;
本次压缩全部都采取默认参数:
gulp.task('compress', function (done) {
return gulp.src(config.input.javascript)
.pipe(ngAnnotate({single_quotes: true}))//等下介绍
.pipe(uglify())
.pipe(concat('index_components.min.js'))//等下介绍
.pipe(gulp.dest(config.dist.basePath))
});
参数具体参照:https://github.com/terinjokes...。
gulp-concat
合并代码,即将项目中各种JS合并成一个JS文件。一般与压缩连用,代码演示参考上方。
gulp-ng-annotate
如果不是angular框架,可以忽略。。。。
如果是的话,而且你的代码是这种写法:
angular.module('someApp')
.controller('someCtrl',function ($scope) {
})
即简写,玩angular的应该都懂,那么这个插件就比较重要了。
因为按照angular官方的说法,如果简写的话,压缩的时候,依赖注入很容易出问题,所以这个插件就是帮助我们解决简写压缩的问题。在打包JS的时候,往往压缩、合并是连着用的,即参考上方‘compress’的示例代码。
gulp-less
一个编译less文件的插件,在less编译中,可选择添加插件,如【autoprefix】,自动添加CSS前缀的插件,代码实现为:
var less=require('gulp-less');
gulp.task('less', function () {
gulp.src(config.input.less)
.pipe(less({
plugins: [autoprefix]
}))
.pipe(minifyCss())//等下介绍
.pipe(concat('index.min.css'))
.pipe(gulp.dest(config.dist.basePath));
});
less在开发中相对于直接使用css,效率可以提升不少,具体less使用,可参照<font color=#0099ff size=5 face="STCAIYUN">这篇文章</font>。
如果是sass开发,就下载gulp-sass的相关插件。
gulp-minify-css
一个压缩css的插件,与uglify类似,只不过一个压缩JS,一个压缩CSS。
可选参数为:
keepSpecialComments:是否保留特殊前缀。默认为“*”,保留全部,1为保留第一条,0位移除全部,为了避免浏览器不兼容样式,一般选默认。
keepBreaks:是否保留换行,默认false(不保留)。
removeEmpty:是否移除空元素,默认false(不移除)。
root、relativeTo:这两个属性都和@import相关,貌似是指出@import的路径(引用的less的路径),
比如:
指明lm-library的路径。
比较方便的做法就是直接把lm-library一起都算进压缩编译的路径当中,给import的less文件添加reference的属性,这样就不会对lm-library.less进行编译了,也不会影响正常的less。
具体属性参考:https://github.com/nfroidure/...。
minimist
这个插件,简单来说就是从命令行当中提取参数。
开发中经常会遇到的应用场景是提供不同的参数,即动态参数,对应到gulp中,如果我们需要在命令行中手动输入某个参数,此时就可以用minimist把他从命令行“提取”出来。
从minimist官方的文档来看,exp为这样:
$ node example/parse.js -a beep -b boop
{ _: [], a: 'beep', b: 'boop' }
文档解释也是一个‘-’为key,之后为value。但个人实际操作为两个‘-’为key。可能原因是,我下的插件不是看的文档的这个库,或者英文太差看错了。。。。。具体用的时候要自己注意了。
具体代码为:
var argv = require('minimist')(process.argv.slice(2));
gulp.task('checkout', function () {
var gitTag = argv.tag;
git.checkout(gitTag, function (err) {
if (err) throw err;
});
})
cmd中输入
gulp checkout --tag v1.0.0
此时,gitTag就会被赋值为v1.0.0。
参考文档为:https://github.com/substack/m...。
gulp-del
删除目标目录,目标文件,演示var del=require('gulp-del')
gulp.task('clean',function(){
return del(config.dist.basePath);
})易理解,就不详细介绍了。
gulp-zip
将src中的各种文件,打成一个zip包,演示代码:
var zip = require('gulp-zip');
gulp.task('zip', () {
gulp.src('src/*')
.pipe(zip('zipName.zip'))
.pipe(gulp.dest('dist'));
});
gulp-ftp
将目标文件,发送至FTP服务器,这边有5个参数是必填的,分别为:
host:服务器地址(必须)
port:服务器端口(必须)
user:ftp账户(必须) // 如果FTP没有访问限制,可以不填
pass:ftp账户密码(必须)// 如果FTP没有访问限制,可以不填
remote: 对应的服务器文件地址(必须)
logger:输出文件列表名称,默认在项目根目录生成文件(可选,默认:logger.txt)
froot: 提单文件前缀(可选,默认:/usr/local/imgcache/htdocs)
exp:体验环境地址(可选,默认null)
pro:正式环境地址(可选,默认null)
参考地址:https://github.com/sindresorh...。
演示代码:
gulp.task('ftp', function () {
return gulp.src("dist_zip/*")
.pipe(ftp({
host: 'testHost',
port: 21,
//user: 'anonymous',
//pass:null,
remotePath: "path/"
}));
});
run-sequence
一个串行方式跑gulp任务的插件,在实际场景中,不允许我们同时跑很多任务,因为任务之间往往是相互依赖的,此时run-sequence就是一个很好的选择,他可以让多个任务按照写入顺序执行,同时可以控制哪些任务并行跑,哪些按照顺序跑。
参考代码:
var runSequence = require('run-sequence');
gulp.task('publish', function (callback) {
runSequence('clean',['html', 'js','less', 'copy'],'zip_new',callback);
});
比如上述代码,执行顺序为1、'clean'。2、['html', 'js','less', 'copy']。3、'zip_new'。
当然也可以在gulp中使用依赖注入的方法。
比如:
gulp.task('two', ['one'], function() {
//任务two,会在任务one结束之后执行
});
但个人还是更喜欢,用run-sequence因为一旦依赖项变多之后,普通的注入,相互之间依赖过后,可读性就会变差,而sequence会让代码看起来更优雅,写起来也更简单。
上篇小结
本文上篇主要讲了gulp的安装,以及常用的插件的介绍,gulp插件超级多。。本文介绍的这些,主要是下篇实际用到的,下篇会使用上述介绍的所有插件,来进行一次较完整的打包,ok,上篇作为铺垫就到这里。
这里是下篇传送门。
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。