Ant 编译项目
现在我们已经学习了 Ant 的数据类型,是时候在实际过程中运用所学知识了。在这一章节中,我们将会构建一个项目。这一章节的目的是创建一个 Ant build 文件,该文件能够编译 Java 源文件和将这些类文件存储在 WEB-INF\classes 文件夹下。
考虑接下来构建项目的结构:
- 数据脚本存储在 db 文件夹中。
- java 源文件存储在 src 文件夹中。
- images (图像),js (JavaScript 脚本),style (css 层叠样式表)存储在 war 文件夹中。
- JSPs 文件存储在 jsp 文件夹中。
- 第三方的 jar 文件存储在 lib 文件夹中。
- java 类文件存储在 WEB-INF\classes 文件夹中。
学习完本教程的剩余部分后,就能知道这个项目是一个 Hello World 传真应用。
C:\work\FaxWebApplication>tree
Folder PATH listing
Volume serial number is 00740061 EC1C:ADB1
C:.
+---db
+---src
. +---faxapp
. +---dao
. +---entity
. +---util
. +---web
+---war
+---images
+---js
+---META-INF
+---styles
+---WEB-INF
+---classes
+---jsp
+---lib
下面给出上述项目的 build.xml 文件的内容。让我们来一条语句接一条语句地来分析它。
<?xml version="1.0"?>
<project name="fax" basedir="." default="build">
<property name="src.dir" value="src"/>
<property name="web.dir" value="war"/>
<property name="build.dir" value="${web.dir}/WEB-INF/classes"/>
<property name="name" value="fax"/>
<path id="master-classpath">
<fileset dir="${web.dir}/WEB-INF/lib">
<include name="*.jar"/>
</fileset>
<pathelement path="${build.dir}"/>
</path>
<target name="build" description="Compile source tree java files">
<mkdir dir="${build.dir}"/>
<javac destdir="${build.dir}" source="1.5" target="1.5">
<src path="${src.dir}"/>
<classpath refid="master-classpath"/>
</javac>
</target>
<target name="clean" description="Clean output directories">
<delete>
<fileset dir="${build.dir}">
<include name="**/*.class"/>
</fileset>
</delete>
</target>
</project>
首先,让我们来声明一些源文件,web 文件和构建文件的一些属性信息。
<property name="src.dir" value="src"/>
<property name="web.dir" value="war"/>
<property name="build.dir" value="${web.dir}/WEB-INF/classes"/>
在上面的例子中:
- src.dir 表示这个项目的源文件目录,也就是存储 java 文件的地方。
- web.dir 表示这个项目的 web 文件目录,也就是存储 JSPs 文件,web.xml,css,javascript 以及其它与 web 相关的文件的地方。
- build.dir 表示该项目的输出文件。
属性也可以引用其它属性。在上面的例子中,build.dir 属性引用了 web.dir 属性。
在上面的例子中,src.dir 就是项目源文件存放的地方。
我们项目的默认目标是编译目标。但是首先让我们来看一下 clean 目标。
clean 目标,就像它的名字所表明的意思一样,删除构建文件夹中的所有文件。
<target name="clean" description="Clean output directories">
<delete>
<fileset dir="${build.dir}">
<include name="**/*.class"/>
</fileset>
</delete>
</target>
控制类路径 (master-classpath) 保存类路径的相关信息。在这种情况下,它包含了构建文件夹和 jar 文件夹中的所有的类文件。
<path id="master-classpath">
<fileset dir="${web.dir}/WEB-INF/lib">
<include name="*.jar"/>
</fileset>
<pathelement path="${build.dir}"/>
</path>
最后,构建目标构建这些文件。首先,我们创建一个构建目录,如果该目录不存在,我们就执行 javac 命令(具体以 jdk 1.5 作为我们目标的编译环境)。 我们对 javac 任务提供源文件夹和类路径,并且通过执行 javac 任务将类文件存放在构建文件夹中。
<target name="build" description="Compile main source tree java files">
<mkdir dir="${build.dir}"/>
<javac destdir="${build.dir}" source="1.5" target="1.5" debug="true"
deprecation="false" optimize="false" failonerror="true">
<src path="${src.dir}"/>
<classpath refid="master-classpath"/>
</javac>
</target>
在这个文件上执行 Ant,编译 java 源文件,并将编译后的类文件存放在构建文件夹的地方。
运行 Ant 文件后,能看到以下输出:
C:\>ant
Buildfile: C:\build.xml
BUILD SUCCESSFUL
Total time: 6.3 seconds
文件被编译后,将存储在 build.dir 文件夹中。
我的Demo
builde.xml:
<?xml version="1.0" encoding="UTF-8"?>
<project name="demo" default="build">
<property file="build.properties"/>
<target name="build" description="编译demo项目">
<mkdir dir="${build.dir}"/>
<!--
srcdir:java源文件的文件夹
source:指定用哪个版本的编译器对java源码进行编译
target:指定生成的class文件将保证和哪个版本的虚拟机进行兼容
deprecation:是否给出不建议使用的API,默认值false
optimize:指出是否应该用优化方式编译源代码,默认为 off
failonerror:Ant 任务在出现编译错误的情况下是否继续执行,默认值为 True
-->
<javac destdir="${build.dir}" source="1.5" target="1.5" deprecation="true" optimize="false" failonerror="true" encoding="utf-8">
<src path="${src.dir}"/>
<classpath refid="master-classpath"/>
</javac>
</target>
<path id="master-classpath">
<fileset dir="lib">
<include name="*.jar"/>
</fileset>
<pathelement path="${build.dir}"/>
</path>
<target name="clean" description="清除编译生成的所有class文件">
<!-- 删除指定目录下的所有文件和目录,不包括指定目录-->
<delete includeEmptyDirs="true">
<fileset dir="${build.dir}" includes="**/*"/>
</delete>
</target>
</project>
<!--
<javac>标签属性的设置:
(1). srcdir:java源文件的文件夹,也可以在内部嵌套<src>标签
(2). destdir:用于存放编译后class文件的文件夹,默认是当前文件夹。
(3). includes:必须包括的文件模式的列表,以逗号或空格分隔。如果忽略,将包括所有文件。
(4). includesfile:指定一个包含很多include的文件,同样可以用通配符来指定。
(5). excludes:必须排除的文件模式的列表,以逗号或空格分隔。如果忽略,将不排除任何文件。
(6). excludesfile:指定一个包含很多exclude的文件,同样可以用通配符来指定。
(7). classpath: 编译所使用的classpath
(8). sourcepath: 指定源资源文件夹。默认指向srcdir
(9). bootclasspath: 启动时设置classpath
(10). classpathref: 引用其他classpath
(11). sourcepathref:引用其他源文件目录
(12). bootclasspathref: 启动时引用其他classpath设置
(13). extdirs:扩展文件的路径。
(14). encoding:编码格式
(15). nowarn:忽略警告信息
(16). debug: 是否产生调试信息,默认off。
(17). debuglevel:debug级别
(18). optimize: 指出是否应该用优化方式编译源代码,默认为 off。
(19). deprecation:是否给出不建议使用的API,默认值false。
(20). target: 根据特定的vm版本生成class文件
(21). verbose:要求编译器输出详细信息,默认no。
(22). depend: 当运行这个任务时,首先按照顺序依次执行完依赖的任务,如果出错将停止执行。
(23. includeAntRuntime:指出是否应在类路径中包括 Ant 运行时程序库,默认为 yes。
(24). includeJavaRuntime: 指出是否应在类路径中包括来自执行 VM 的默认运行时程序库,默认为 no。
(25). fork:是否执行外部的javac,默认no。
(26). executable:当fork="yes"时,所执行的javac的完整路径。默认的是当前跑ant的java版本,fork="no"就忽略
(27). memoryInitialSize:当是外部javac的时候,获得基本vm的初始内存大小。否则忽略。
(28). memoryMaximumSize: 同上只不过是获得最大的内存大小。
(29). failonerror: Ant 任务在出现编译错误的情况下是否继续执行,默认值为 True。
(30). errorProperty:当编译失败的时候要设置的属性。
(31). source:命令行-source的开关。 假如设置为1.4,将激活断言。默认是1.3。默认不使用-source。
(32). compiler:设置用来选择编译器,如果不设置,将使用默认的编译器。
(33). listfiles:是否显示被编译文件列表,默认是no。
(34). tempdir:指定存放临时文件的地方,这个只在设置了fork和命令行超过参数长度超过4k的时候使用,默认为java.io.tmpdir
(35). updatedProperty:更新property属性
(36). includeDestClasses:是否包含目标class文件夹包含到classpath。默认是true。意思是之前生成的class文件自动加到classpath。
-->
build.properties:
src.dir=src
web.dir=demo
# properties文件也可以引用web.dir属性
build.dir=${web.dir}/WEB-INF/classes
Ant 生成文档
文档在任何项目中都是必须的。文档对一个项目的维护起了至关重要的作用。 通过使用内置的 Javadoc 工具,使用 Java 生成文档变得更加容易。Ant 通过按需生成文档使得这个步骤甚至变得更简单。
如你所知,javadoc 工具具有高度的灵活性,而且其还允许进行一些配置。Ant 通过使用 javadoc 任务的方式来公开这些配置选项。如果你对 javadoc 不熟悉的话,我们建议你先看一下 Java 文档教程。
下述的章节列出了在 Ant 中最常使用的 javadoc 的选项。
属性
源包括源路径,源路径引用或者源文件三个属性。
- 源路径 (sourcepath) 指向源文件所在的文件夹,例如: src 文件夹。
- 源路径引用 (sourcepathref) 指向由该路径属性引用的路径,例如:delegates.src.dir 。
- 源文件 (sourcefiles) 在你想指定单独的文件时使用,比如指定一个逗号分隔列表。
目标路径是通过使用 destdir 文件夹来指定的,例如 build.dir 。
你能够通过指定应被包括的包的名字来过滤 javadoc 任务。这可以通过使用 packagenames 属性实现,即一个以逗号分隔的包文件列表。
你可以过滤 javadoc 过程以只显示公有的,私有的,包或者被保护的类和成员。这些可以通过使用 private,public,package 和 protected 属性实现。
你也可以通过使用相应的属性来告诉 javadoc 任务去包含作者和版本信息。
你也可以使用 group 属性将所有的包组织在一起,以使得他们更易被操作。
将上述内容集中到一起
让我们继续我们的主题,Hello world 传真应用程序。让我们给我们的传真应用项目添加一个文档目标。
下面给出的例子是我们在项目中使用的 javadoc 任务。在这个例子中,我们指定 javadoc 去使用 src.dir 作为源目录,doc 作为目标。
我们还定制窗口标题,标题,以及显示在 java 文档页上的页脚信息。
此外,我们还创建了三个组:
- 为源文件夹中的实用工具类创建了一个组。
- 为用户接口的类创建了一个组。
- 为数据库相关的类创建了一个组。
您可能会注意到,数据包组含有两个包 -- faxapp.entity 和 faxapp.dao 。
<target name = "generate-javadoc">
<javadoc packagenames="faxapp.*" sourcepath="${src.dir}"
destdir = "doc" version = "true" windowtitle = "Fax Application">
<doctitle><![CDATA[= Fax Application =]]></doctitle>
<bottom>
<![CDATA[Copyright © 2011. All Rights Reserved.]]>
</bottom>
<group title = "util packages" packages = "faxapp.util.*"/>
<group title = "web packages" packages = "faxapp.web.*"/>
<group title = "data packages" packages = "faxapp.entity.*:faxapp.dao.*"/>
</javadoc>
<echo message = "java doc has been generated!" />
</target>
让我们运行 javadoc Ant 任务。它将生成 java 文档文件,并将这些文件放置于 doc 文件夹中。
当执行 javadoc 目标时,其产生以下的输出:
>C:\>ant generate-javadoc
>Buildfile: C:\build.xml
>java doc has been generated!
>BUILD SUCCESSFUL
>Total time: 10.63 second
java 文档文件现在出现在 doc 文件夹中。
通常情况下,javadoc 文件作为发行版或者包目标的一部分。