壹 ❀ 引
fis3是百度推出的一款前端工程构建工具,类似的还有webpack,gulp等工具;无论大家有没有使用过,从事前端行业应该都略知一二了,所以对于此类工具用干嘛的我这里就不做重复了。
其实对于这类构建工具,大部分人是不感兴趣,或者说有些畏惧的,配置多贼麻烦,无法像js一样调试很恐怖,给人感觉很难;特别是fis3这种相对比较冷门的构建工具,出现问题百度一圈相关答案真的很少...
我也曾抱怨公司为啥不用webpack,但我毕竟不是抉择者,已经决定了使用这个还不如沉下心去学习了解;本文会抽出我觉得常用的,好用的配置,并通过我的理解来加以描述,一定能看得懂,我也会在文章结尾贴上我的项目配置,希望看完基本教程你能看懂,那么本文开始。
贰 ❀ 简单配置入门(不难,耐心点看)
fis3编译流程都是通过配置完成的,我们的配置等于告诉fis3工具应该按怎样的规则编译我们的项目,这里说下必用的配置API:
1.fis.set(key,value)
此方法提供了多种key字段,不同的key作用不同,这里只说下key为'project.files'的作用,它能帮我们过滤文件夹。
一个项目文件夹那么多,肯定有一些文件我们并不希望fis3帮我们编译,比如三方库node_modules这样,举个例子:
fis.set('project.files', ['commonLess/**', 'components/**', 'modules/**', 'pages/**']);
这段代码的意思是,我希望fis3后续配置只对commonLess,components等文件夹下的所有文件起作用,没添加的文件夹都被过滤掉了,所以这个方法请写在配置的第一行,你可以点击这里查看完整的key说明。
2.fis.hook()
此方法能启用模块化开发,为js文件提供模块化开发的支持;我们可以下载fis3提供的插件并利用hook方法启用模块化,fis3提供了三种模块插件。
我司选择了commonjs规范,这个需要配合mod.js一起使用,先下载fis3提供的fis3-hook-commonjs插件(mod.js这里就不说怎么用了)
npm install fis3-hook-commonjs
在fis3配置表中添加如下配置就启用了commonjs规范:
fis.hook('commonjs');
当然单hook还不够,我们还没指定哪些文件使用此规范,这个需要下面的match方法指定;这行代码也请加在fis3配置文件头部位置,先启用模块化,后面再指定哪些文件使用模块化。
2.fis.match(selector, props)
selector:表示匹配路径,你希望哪个路径下的文件被编译处理,就将此路径写在这里,这是fis3提供的匹配语法:
*
匹配0或多个除了/
以外的字符?
匹配单个除了/
以外的字符**
匹配多个字符包括/
{}
可以让多个规则用,
逗号分隔,起到或者
的作用!
出现在规则的开头,表示取反。即匹配不命中后面规则的文件
props:编译规则,你希望前面你选择的路径下的文件被怎么编译,这个规则就写在这里。
fis3大部分配置都是通过match方法实现的,这段请耐心点看:
fis3建议路径都是以/开头,/代表根目录,举个例子:
fis.match('a.js', {});
这段代码表示匹配整个项目中的所有a.js文件,包括/a.js /a/a.js /a/b/a.js
但如果我们加了斜线,意义就不同了:
fis.match('/a.js', {});
此时表示,只匹配根目录下的a.js,并不会匹配所有路径下的a.js。
除此之外,/a/*.js表示只匹配/a目录下所有的js文件,不包含/a目录下子目录中的js,不过我们可以通过这种写法/a/**.js达到此目的。
说完match匹配路径的规则,简单说下match的props属性,注意,所有的属性都包裹在一个{}中,这里就主要说下常用的几个:
release:设置文件的产出路径
我们按路径匹配了一些文件,经过某些编译之后输出到哪里,这个产出就是由release决定的,例如:
fis.match('*.{png,js,css}', {
release: '/static/$0'
});
这段代码的意思是,匹配整个项目中所有的png,js,css类型的文件,并输出到根目录下的static文件中;
$0表示match方法的整个selector字段,就像一个变量,匹配到什么,$0就代表什么,那么在这里的意思就是按照文件原名输出到static目录下。
顺带一体,除了$0还有一个$1也很常用,举个例子:
fis.match('/pages/**/(*.html)', {
release: '/$1'
});
这段代码的意思是,将pages目录下所有html文件按文件原名输出到根目录下,前面说了/代表根目录。此时$1代表(*.html)这一段匹配的所有字段,也就是文件名了。如果是$0就代表/pages/**/(*.html) 这一段,应该不难理解。
isMod:是否启用模块化
前面我们通过fis.hook()方法调用了模块化插件,现在就可以利用isMod属性指定哪些文件模块化,比如:
fis.match('*.js', {
isMod: true,
release: '/static/$0'
});
这段代码的意思是,匹配所有的js文件,模块化,并且输出到根目录下static文件中,并按原名显示。
useHash:文件是否添加md5戳
这个做http缓存会用,给文件添加md5戳便于客户端主动感知文件变化,如果对于http缓存感兴趣,可以阅读博客这边文章---http缓存详解,http缓存推荐方案
fis.match('*.css', {
useHash: true
});
这段代码的意思是,匹配所有的css文件,在编译时全部添加md5戳。
rExt:设置文件编译后的产出后缀
说直白点,改变文件发布后的文件后缀,比如less,sass文件转义后我们希望是css格式,那么就可以这样:
fis.match('*.{less,sass}', {
rExt: '.css'
});
packTo:设置文件合并后的输出路径与文件
这个属性是合并文件用的,比如我一个页面用了三个js文件,我想合并成一个js文件,就可以利用这个属性,举个例子:
fis.match('/index/**.js', {
packTo: '/static/pkg_index.js'
});
这段配置的意思是,找到根目录下index文件下所有js文件,合并发布到根目录下static文件下的pkg_index.js文件中。
id:指定文件的资源id
这么解释可能看不懂,直接上个例子:
fis.match('/static/jquery.js', {
id: 'jquery',
isMod: true
});
// 引用文件时
var $ = require('jquery');
我们将根目录下的static文件夹中的jquery.js文件的id设置成了jquery字段,在引用时直接require id设置的字段就可以了,如果不设置,我们require就是这样:
var $ = require('/static/jquery.js');
所以id的作用就像指定了一个字段作为key去保存一段复杂的路径,这样做的好处是在require时能更加简单。
其它match属性暂时没用到,点击这里可以查看完整的match属性
叁 ❀ 关于发布命令
知道了基本的配置,就要通过发布指令,将我们的项目按照配置发布出去,这里简单说下发布指令,很简单:
fis3 release -d <path>
<path>代表任意发布路径
fis3 release -d ./output
发布到当前项目目录的outout目录下
fis3 release -d ../dist
发布到项目父级目录的dist目录下
fis3 release -d D:\output
发布到D盘下的output目录下
除此之外,我们还能在发布指令目录后添加属性,比如:
fis3 release -d D:\output -w
-w启用文件监听功能,发布后此命令不会退出,而是一直显示。
fis3 release -d D:\output -wL
-L一般与w一起使用,监听文件变化,只要修改任何东西,都会自动刷新页面
fis3 release -d D:\output -wLc
-c表示每次发布清除编译缓存
关于发布指令path与match属性release的区别
不知道大家会不会把match release属性指定输出路径和发布指令中指定输出路径弄混;实际开发中,发布指令的path决定的是大格局,整个项目要发布到哪,而match release的路径往往是基于项目路径后决定个别文件发布到哪,这是有区别的。
肆 ❀ 常用插件与配置
前面聊的入门的配置规则与发布命令其实只是为了让你看懂下面这些配置,拷贝到配置中进行发布,如果提示缺少插件,请对应下载对应插件即可:
1.转义所有less文件,并为css3属性添加浏览器兼容前缀,如果有sass做法也一样,请下载对应插件:
fis.match('*.less', {
rExt: '.css',
parser: fis.plugin('less-2.x', { })
}).match('*.{css,less,scss}', {
preprocessor: fis.plugin('autoprefixer', {
"browsers": ["Android >= 2.1", "iOS >= 4", "ie >= 8", "firefox >= 15"],
"cascade": true
})
});
2.压缩js与css文件,需要下载对应插件
fis.media('prod').match("**.js", {
//压缩js
optimizer: fis.plugin('uglify-js')
});
fis.match('**.{css,less}', {
//压缩css
optimizer: fis.plugin('clean-css')
});
3.单页面零散资源合并,这个在生产环境需要使用
比如将index页面的所有js合并成一个js,所有css文件合并成一个css,也需要下载插件
fis.match('::package', {
postpackager: fis.plugin('loader', {
//单页面合并零散资源
allInOne: true
})
});
4.为css,js添加md5戳,http缓存必备
fis.match('*.{js,css}', {
//为js,css类型文件添加md5戳
useHash: true
})
5.为所有图片添加md5戳
fis.match('::image', {
//为所有的图片类型添加md5戳
useHash: true
});
伍 ❀ 我的前端项目完整配置
// 过滤文件,只有数组中的目录才会被fis3编译
fis.set('project.files', ['bootstrap/**', 'commonLess/**', 'components/**', 'modules/**', 'pages/**', 'partials/**']); //启用relative插件,所有文件使用相对路径
fis.hook('relative')
.match('**', {
relative: true
}); // commonJS规范
fis.hook('commonjs'); //将pages下所有html按原文件名发布至根目录
fis.match('/pages/**/(*.html)', {
release: '/$1',
isMod: true,
}); //为js文件启用模块化
fis.match('{modules,pages,partials,components}/(**.js)', {
isMod: true
}); //less转义css,并添加浏览器前缀
fis.match('**/*.less', {
rExt: '.css',
parser: fis.plugin('less-2.x', { })
}).match('*.{css,less,scss}', {
preprocessor: fis.plugin('autoprefixer', {
"browsers": ["Android >= 2.1", "iOS >= 4", "ie >= 8", "firefox >= 15"],
"cascade": true
})
}); //使用postcss,并使用pxtoviewport插件
var pxtoviewport = require('postcss-px-to-viewport');
fis.match('*.{css,less,scss}', {
postprocessor: fis.plugin('postcss', {
processConfig: {},
plugins: [pxtoviewport],
sourceMap: true,
sourceMapRelative: false
})
}); fis.match('::packager', {
postpackager: fis.plugin('loader', {
resourceType: 'mod',
useInlineMap: true // 资源映射表内嵌
})
}); //生产环境配置,相比测试环境,多了代码合并压缩,添加时间戳等操作。
fis.media('prod').match("**.js", {
//压缩js
optimizer: fis.plugin('uglify-js')
}).match('**.{css,less}', {
//压缩css
optimizer: fis.plugin('clean-css')
}).match('::package', {
postpackager: fis.plugin('loader', {
//单页面合并零散资源
allInOne: true
})
}).match('*.{js,css}', {
//为js,css类型文件添加md5戳
useHash: true
})
.match('::image', {
//为所有的图片类型添加md5戳
useHash: true
});
所以配置上半部分都属于测试环境发布配置,只处理less转义,js模块化,文件资源定位输出等基本操作。
在代码最下方有一段属于生产环境的配置,只有在生产环境下我们才需要代码合并,压缩,添加md5戳,不然合并压缩了我们也不好调试功能。
这两段配置是可以通过发布指令区分发布的,比如我在测试环境发布,指令应该是这样:
fis3 release -d D:\output
如果你要在生产环境发布,请在release后添加meaid中的字段prod(这个字段是随便写的),比如:
fis3 release prod -d D:\output
说直白点,我们前面的配置都是fis.match(),后面有一段配置是fis.media('随便取名').match()这样写的。
在发布时,如果你在发布指令release后加了media自定义的字段,整个配置都会执行,但如果你不加media字段,那么就只执行fis.match()相关配置,这样我们就能在不同环境区分发布了。
那么针对于fis3就聊这么多了,琢磨着用这玩意的人真不多,估计也没多少人愿意看,那么本文结束。