分享
 
 
 

Ant使得JavaJARs打包变得简单和可靠

王朝java/jsp·作者佚名  2008-05-19
窄屏简体版  字體: |||超大  

对于开发人员,除了不兼容性经常发生之外,Ant版本1.2遵循版本1.1的所有规则,而版本2.0能够完全与版本1.2匹配。由于开发版本的不断改变而导致的项目进度混乱,系统bug蚕生,以及源码知识库破坏,开发队伍很长一段时间以来都争议着版本号与内部识别系统的关系,比如发布、修正、转折点、建立号。这些只限于办公室的讨论很少见于数据表格,网站,以及CDs中。然而,相比于办公室的版本号,他们的争议往往显得更加有用,尤其是当回答一个新的bug出现时提出的“这在这一版本号中有什么区别?”的问题的时候。

不同版本系统的存在是因为其能够指定Build工具中的发布标示。有些制作商对开发代码做出严格的保密,开发人员必须记住每一种版本改变所需要更改的信息。其他工程依赖于一些由许多源码管理系统支持的符号替换系统。另外,很多其他工程仍然需要手工地建立存档文件内部的一些小的文本文件。

然而,每一个版本都有自己的问题。开发人员通常会忘记增加Build数目──尤其是对“quick, little fixes”的分类,这样会很有可能导致出现bug。源码管理系统是基于文件,而且反映的只是简单文件的版本信息。当JARs打包,优化,融合的时候可以去掉文本文件。

使用发布标识符来打包的更好方法是依赖于使用Ant build系统提供的符号过滤器。当从一个地方复制文件到另一个地方时,Ant复制任务可以使用任意字符串替代形成@TEXT@的符号。使用这一特性和一些其他Ant build文件技巧,我们可以确保所有的JARs能够具有一个发布号而获得打包,从而可以避免开发过程中的很多麻烦。

源文件

现在让我们看一看我们范例程序的源文件,即MyApp.java ( Listing A)。

Listing A

public class MyApp {

public static final String RELEASE = "@RELEASE@";

public static final String APP_NAME = "MyApp";

public static final String VERSION =

"1.0";

public static String getVersionString() {

return APP_NAME + " " + VERSION + " ("

+ System.getProperty("os.arch")+"; "+System.getProperty("os.name")

+ ((("@REL" + "EASE@").equals(RELEASE))?"":("; " + RELEASE))

+ ")";

}

public static void main(String[] args) {

System.out.println(getVersionString());

}

}

在这一类文件中,你可以看到一个静态域和方法。第一个静态域名为RELEASE,其具有一个“@RELEASE@”的值。这也就是我们等下使用Ant复制过滤器取代的符号。然而现在,我们只需要将其置为“@RELEASE@”。

两个静态方法中的第一个为getVersionString(),只是简单地连接了一些其他静态域的值,然后有选择性地添加RELEASE值,除非其值为字符串@RELEASE@。这种情况不需要添加RELEASE值,因为它包含很多无用的build识别信息。如果RELEASE在源文件编译之前已经被更改,这一值就会被添加到返回的版本字符中。

请注意到,我们所使用与RELEASE值相比较的常量字符被分成两个字符串,这两个字符串在编译时被连接,这就防止Ant符号替代过滤器替代@RELEASE@常量。

Build文件

现在,我们将注意力转移到Build.xml文件(Listing B)。

表B

<project name="myapp" default="jar"

<!-- where the project source code is found --

<property name="sources" value="src"/

<!-- where compiled class files should be left --

<property name="classes" value="classes"/

<target name="jar" depends="pre-jar,classes"

description="build release jar"

<jar destfile="jar/${ant.project.name}.jar"

<fileset dir="classes"

<include name="**/*.class"/

</fileset

</jar

</target

<target name="pre-jar" depends="ensure-release"

<property name="srcdir" value="jar/src"/

<mkdir dir="${srcdir}"/

<copy todir="${srcdir}"

<fileset dir="${sources}"

<include name="**/*.java"/

</fileset

<filterset

<filter token="RELEASE" value="${release}"/

</filterset

</copy

</target

<target name="ensure-release" unless="release"

<fail message="You must define -Drelease=<name>"/

</target

<target name="classes" description="compile classes"

<property name="srcdir" value="${sources}"/

<mkdir dir="${classes}"/

<echo message="srcdir=${srcdir}"/

<javacdestdir="${classes}" srcdir="${srcdir}"

</javac

</target

<target name="clean" depends="tidy" description="delete all generated files"

<delete dir="jar" quiet="true"/

</target

<target name="tidy" description="delete all intermediary files"

<delete dir="jar/src" quiet="true"/

<delete dir="classes" quiet="true"/

</target

</project

Build.xml文件采用了非普通的技巧,其中的一个目标是防止开发人员对每一次的编译指定发布信息。绝大部分的编译并非都需要发布,为了给每一测试编译提供一个发布名称,开发人员将通过使用一个固定的Build标识符的值来对他们的Builds过程进行脚本化。

为了达到这一目的,我们将对象分离以建立类和任何的JARs。名为classes的类首先将其srcdir属性设置为前一个定义好的sources属性值,然后,当classes对象直接运行,使用编辑的Java sources文件将可以在scr目录中查找到。开发人员编写的源代码在被编译之前,允许使用IDE和其他程序,这就能够从编译错误信息中提取文件名然后可以在编辑程序中得以纠正。

然而,当sources文件被编译为包含在一个JAR的类时,我们不会将这些类编译在scr目录中。相反,我们必须复制这些文件,然后执行符号替代。源代码目录的建立和声明都在pre-jar目标中执行。

然后,pre-jar目标从scr目录中复制源代码层次到jar目录之下。在复制过程中,一个过滤器通过release属性的值取代字符@RELEASE@的所有具体值。在pre-jar对象中设置过滤源目录之后,classes对象将设置srcdir的值。幸运的是,Ant的不允许属性重新定义的规则防止了设置的值不会被覆盖。

pre-jar目标处理过滤过程,但它无法保证用于@RELEASE@替代符号的release属性一定具有一个赋予值。这一过程可以通过ensure-release目标来检查,如果没有赋予值,就会跳出一个失败信息以说明如何指定一个发布标识符。

集中

pre-jar和ensure-release目标能够自动地被相关jar目标处理。尤其是jar目标确保它的任务被处理之前,pre-jar和classes被运行。首先pre-jar调用ensure-release目标以校验是否已经对发布标识符已经设置。结果是形成一个Build系统,这一系统能够使用classes目标(开发人员每一天编译和测试)运行。

使用打包或非打包形式,缺省的Build标识符等,这些轮换构建方法都成为可能。现实中的Build过程通常会比较复杂,但是,只要能够避免javac任务的复本出现,绝大部分的构建都会变得直接明了。

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有