开发只是万里长征走完前半截,测试部署也是很重要的环节。
尤其是,前端面临着两个很大的问题:
- 前端代码是开放的,用户随时可以直接读代码
- 代码下载到用户电脑上运行,需要占用带宽
所以如果我们可以先压缩、混淆代码,再部署给用户使用,就可以大大改善这种情况。这个时候,ant是不二的选择(因为我只会ant……)。
关于Ant
基础
ant需要java环境,配好后就可以使用了。默认情况下,ant会读取同目录的build.xml作为编译脚本。
build.xml也遵守一般的XML规则,比如只能有一个根节点,可以使用<![CDATA[ …. ]]>来包裹文本数据等。具体的写法我就不多说了,随便去github上找个工程做参考,配合手册一看就明白。接下来说说我编译的思路。
合并JS库
项目中会用到大量外部库和框架,比如jQuery、jQueryUI、Mustache、Twitter Bootstrap、Backbone等。这些库一般都压缩过了,不需要再压缩;另外开源的库都有许可协议,理应保留。所以这部分文件简单压缩一下就可以了。这里有三点需要:
- 如果文件中包含中文,就必须指定编码,我喜欢UTF-8
- 如果文件末尾没有换行符,可能导致出错,所以需要设置fixlastline为true
- 如果不给定顺序,会按文件名合并,可能会出错,比如Backbone明显会比Underscore先合并进来,但前者却是依赖后者的,所以就得像我这样按顺序逐一排列
<target name="-concat.js.libs.files"> <mkdir dir="${dist}/js" /> <concat destfile="${dist}/js/libs.js" encoding="UTF-8" fixlastline="yes"> <filelist dir="js/libs/"> <file name="jquery-1.7.2.min.js" /> .... </filelist> </concat> </target>
复制HTML和其他素材
HTML包括index.html和一些模版,基本上压缩与否差别不大,所以直接复制就好;图片之类的东西都算素材,也不可能压缩,仍然直接复制。
<target name="-copy.html.files"> <copy file="index.html" todir="${dist}" /> <copy todir="${dist}/template/"> <fileset dir="template/" /> </copy> </target> <target name="-copy.image.files"> <copy todir="${dist}/img/"> <fileset dir="img/" /> </copy> </target>
编译CSS
现在直接写CSS都弱爆了,大家不是SCSS就是LESS,但是我们发给用户的肯定是最终输出的普通CSS,而且需要事先压缩。我特别喜欢Google,所以我(准备)用GCSS,于是需要用Closure Stylesheet编译CSS。
<target name="-compile.css.files"> <java jar="${build}/closure-stylesheets.jar" fork="true"> <arg line="--output-file ${dist}/css/admin.css" /> <arg line="css/admin.css" /> </java> </target>
编译项目JS
目前看来,我直接用Closure Compiler的Simple模式压缩代码是不够的,也没有跟我的代码结构结合起来,不过暂时可以用,等我有空去做自动解决依赖的功能再说吧。关于如何在ant中使用Closure Compiler,可以看这篇文章。不过里面说的不算太详细,比如我不想考虑IE兼容情况,就只能搜到命令行怎么做,最后还是看源码解决的——这就是开源的好处啊~~
<jscomp compilationLevel="simple" warning="default" debug="false" output="${dist}/js/apps.js" encoding="UTF-8"> <warning group="internetExplorerChecks" level="OFF" /> <warning group="globalThis" level="OFF" /> <sources dir="${temp}"> <file name="apps.js" /> </sources> </jscomp>
修改JS引用
最后,既然我把所有库编译成了libs.js,把所有项目JS编译成了apps.js,那么index.html里原有的引用就不行了,我需要把它们改成新的引用。利用Ant提供的replace语法可以实现这个功能。我在index.html里面用“<!– replace start –>”和“<!– replace over –>”作标记,中间是需要替换的。本想替掉全部js,后来发现比如Google Map就不能替换,所以改用这种方式。
<replaceregexp flags="gs" encoding="UTF-8"> <regexp pattern="\<!-- replace start --\>(.*?)\<!-- replace over --\>" /> <substitution expression="\<script src='js/libs.js'\>\</script\>\<script src='js/apps.js'\>\</script\>" /> <fileset dir="${dist}/" includes="index.html" /> </replaceregexp>
这里需要注意的是,ant不允许属性值里出现< / >这些符号,所以必须手工转码。我猜<! [CDATA[ …. ]] >也行,不过没试。
总结
我们写的代码是给人看的,所以要尽可能多用注释、多用模式、多换行、用最长的变量名。但最终用户并不关心这个,他们希望跑的越快越好;而个别别有用心的用户呢,我们也不希望他们轻易地读我们的代码。所以,利用Ant编译部署(目前这个版本的build.xml我还没放ftp部分的代码,不过后面会放的)就显得势在必行。
当然,这篇文章里的内容都比较浅显,比如没有增加分支开发的处理,css也只是简单压缩了一下,更没有ftp上传的东西,不过暂时够用了,进阶的内容以后再补充。
欢迎吐槽,共同进步