User passes a list of files in an XML file, below will be the sample:
<property-bundle name = "abc">
<action>clean</action>
<target-location>/vst/property/pog/</target-location>
<file-name>test1.props</file-name>
<file-name>test2.props</file-name>
<file-name>test3.props</file-name>
</property-bundle>
Now based on that action remove, I have to incorporate logic in build.xml to delete the files in the directory , but for that I want to perform a validation only if the file exists then remove or else throw the build failure error. I was able to read the values from the user input XML and takes those files into a file list property
<property name="file.list" value="test1.props,test2.props,test3.props"/>
<target name = "clean">
<delete>
<fileset dir="${target.location}" includes = "${file.list}"/>
</delete>
</target>
but with the clean target it only validates if the directory exists since it is fileset but does not do the validation if file exists , I read that filelist does validation for file exists but filelist can work with delete.
Since we are using Ant 1.6.5 in our environment I can not use antcontrib , It takes whole lot of process and approvals to upgrade Ant now , Can you please guide me on how it can be achieved with the pure Ant.
You should be able to just use delete
's @failonerror
attribute which throws an error if the file cannot be deleted.
<target name = "clean">
<delete failonerror="true">
<fileset dir="${target.location}" includes="${file.list}"/>
</delete>
</target>
The above will delete files and then error when it doesn't find a file, leaving you in a partially deleted state. If you want to avoid partial deletions, you can run another task to check first
<target name="failIfMissing">
<copy failonerror="true" todir="${temp.directory}">
<fileset dir="${target.location}" includes="${file.list}"/>
</copy>
</target>
by attempting to copy to a temporary directory, failing if some of the target files did not exist.
It is possible to loop over files with Ant-Contrib Tasks and then it will look something like this:
<target name="clean">
<foreach target="delete.if.exists" param="fileName">
<fileset dir="${target.location}" includes="${file.list}"/>
</foreach>
</target>
<target name="delete.if.exists">
<delete failonerror="true" file="$fileName"/>
</target>
Folks,
Thank you all for your outstanding help & contributions , I have finally achieved this with below
<target name="validate.file" depends="defineAntContribTasks,validate.dir">
<echo message=" The value of the filelist is ::::::::::::: ${file.list} :::::::::::::::::: "/>
<for param="file" list="${file.list}">
<sequential>
<if>
<available file="${target.location}/@{file}"/>
<then>
<echo message = "File::: @{file} ::::is valid , Found in :::${target.location}::: "/>
</then>
<else>
<fail message=" File::: @{file} ::::is not valid ,it is not found in :::${target.location}::: ,plesae recheck and submit again"/>
</else>
</if>
</sequential>
</for>
</target>
Thanks again for all of your valuable time and guidance.
<target name="removeUnwantedFiles" description="delete the build destination tree to ensure that it will contain ONLY what is explicitly needed for a build and ONLY what is intended to be release.">
<delete>
<fileset dir="${project-home}">
<includesfile name="${scripts}/excludeJavaFilesForV1.txt"/>
</fileset>
</delete>
</target>
This works for me.. hope this helps..
Ant is not a programming language and therefore has no native looping mechanism. In the absence of external plugins a trick that can used is an XSL transformation. Process the input XML file into a Ant script which implements the desired operation on each file.
Example
├── build.xml
├── files-process.xsl
├── files.xml <-- Input listed above
├── test1.props
├── test2.props
└── test3.props
Run the build and the files listed in "files.xml" are deleted:
build:
[delete] Deleting: /home/mark/tmp/test1.props
[delete] Deleting: /home/mark/tmp/test2.props
[delete] Deleting: /home/mark/tmp/test3.props
Run the build a second time and an error is generated:
BUILD FAILED
/home/mark/tmp/build.xml:6: The following error occurred while executing this line:
/home/mark/tmp/build-tmp.xml:4: file not found: test1.props
build.xml
Use the xslt task to generate a temporary Ant script containing the desired file deletion logic:
<project name="demo" default="process-files">
<target name="process-files">
<xslt style="files-process.xsl" in="files.xml" out="build-tmp.xml"/>
<ant antfile="build-tmp.xml"/>
</target>
<target name="clean">
<delete file="build-tmp.xml"/>
</target>
</project>
files-process.xsl
The following stylesheet generates an Ant script:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes"/>
<xsl:template match="/">
<project name="genbuild" default="build">
<target name="build">
<xsl:apply-templates select="property-bundle/file-name"/>
</target>
</project>
</xsl:template>
<xsl:template match="file-name">
<available file="{.}" property="{generate-id()}.exists"/>
<fail message="file not found: {.}" unless="{generate-id()}.exists"/>
<delete file="{.}" verbose="true"/>
</xsl:template>
</xsl:stylesheet>
build-tmp.xml
To aid readability I have formatted the generated Ant script:
<project name="genbuild" default="build">
<target name="build">
<available file="test1.props" property="N65547.exists"/>
<fail message="file not found: test1.props" unless="N65547.exists"/>
<delete file="test1.props" verbose="true"/>
<available file="test2.props" property="N65550.exists"/>
<fail message="file not found: test2.props" unless="N65550.exists"/>
<delete file="test2.props" verbose="true"/>
<available file="test3.props" property="N65553.exists"/>
<fail message="file not found: test3.props" unless="N65553.exists"/>
<delete file="test3.props" verbose="true"/>
</target>
</project>
Note:
- Properties in Ant are immutable, so I used the XSL generate-id() function to create a unique property name.
Software used
This example was tested with the following software versions:
$ ant -version
Apache Ant version 1.6.5 compiled on June 2 2005
$ java -version
java version "1.7.0_25"
Java(TM) SE Runtime Environment (build 1.7.0_25-b15)
Java HotSpot(TM) 64-Bit Server VM (build 23.25-b01, mixed mode)