in our project we use Ant to distribute files. There is hierarchy of files, and they overwrite files from previous level. Like this: default - level1 - level2. Currently it is made the way:
<copy todir="...">
<fileset dir="${root}/default" includes="**/*" excludes="file1" />
<fileset dir="${root}/level1" includes="**/*" />
<fileset dir="${root}/level2" includes="**/*" excludes="file2"/>
</copy>
So we expected that all the folders contain file with the same name, it will be taken from level2 directory.
Not long ago we moved to a new build box with another version of Java and we discovered that the order of filesets is broken.
Is there a way to fix this issue without modifying ant config files? We have a big number of it. If there is no way, how can I got it off cheap? Thank you.
I don't know if the order of filesets is quaranteed, but the order of copy tasks is.
So, following the suggestion of this answer, it might be a good idea to write several copy tasks with overwrite="true":
<copy todir="...">
<fileset dir="${root}/default" includes="**/*" excludes="file1" />
</copy>
<copy todir="...">
<fileset dir="${root}/level1" includes="**/*" overwrite="true" />
</copy>
<copy todir="...">
<fileset dir="${root}/level2" includes="**/*" excludes="file2" overwrite="true" />
</copy>
You can wrap a sort resource collection around your filesets and ensure the order used by copy this way. Sort itself only likes a single resource collection as child element, so you need to wrap the fileset inside a union or resources container.
See http://ant.apache.org/manual/Types/resources.html#sort
Something like
<sort>
<resources>
<fileset dir="${root}/default" includes="**/*" excludes="file1" />
<fileset dir="${root}/level1" includes="**/*" />
<fileset dir="${root}/level2" includes="**/*" excludes="file2"/>
</resources>
<name/>
</sort>
to sort the files by name.
Related
I have an ANT target that unzips every jar with a "for" task, but I want to exclude a specific jar called Neo.jar. This is what I have so far, but it is unzipping every single jar that is available to it.
<target name="unzipjars">
<for param="jar">
<sequential>
<unzip dest="${expanded.dirs}" src="#{jar}">
<exclude name="Neo.jar/**"/>
</unzip>
</sequential>
</for>
</target>
I was looking at trying to exclude something from "for param="jar"" but I don't think anything like that exists. The "exclude name" for Neo.jar doesn't seem to work because I believe it doesn't think it is a directory because it is a jar
As you can see here, it's quietly easy.
All you need is to add the tag patternset to your configuration (and you don't need to iterate by the way...). Like this:
<target name="unzipjars">
<unzip dest="${expanded.dirs}">
<patternset>
<exclude name="**/Neo.jar"/>
</patternset>
<fileset dir="${jar}">
<include name="**/*.*"/>
</fileset>
</unzip>
</target>
You can use the if task (http://ant-contrib.sourceforge.net/tasks/tasks/if.html) to filter out the Neo.jar file. For example
<for param="jar">
<sequential>
<if>
<not><equals arg1="#{jar}" arg2="Neo.jar" /></not>
<then><!-- unzip the jar --></then>
</if>
</sequential>
</for>
I've looked through ant tasks like copy, but can't really seem to find a way. With this kind of file structure:
/Resources/Docs/SpecificDoc/ScalaDocs
I want to rename "ScalaDocs" to "TargetDocs", having an end structure like so:
/Resources/Docs/TargetDocs
Try this.
<copy todir="/Resources/Docs/TargetDocs">
<fileset dir="/Resources/Docs/SpecificDoc/ScalaDocs">
<include name="*" />
</fileset>
</copy>
Let's say I have a directory structure like this:
animals/dog/details
animals/cat/details
animals/frog/details
animals/horse/details
Using ant, I would like to rename all sub-directories under animals called details to now be named new. So the result would be this:
animals/dog/new
animals/cat/new
animals/frog/new
animals/horse/new
I've tried something like this:
<move tofile="new">
<path id="directories.to.rename">
<dirset dir="animals">
<include name="**/details"/>
</dirset>
</path>
</move>
But get this error:
Cannot concatenate multiple files into a single file.
You can carry out the rename you describe by means of a mapper. For example:
<move todir="animals">
<dirset dir="animals" includes="**/details" />
<globmapper from="*/details" to="*/new"/>
</move>
(There's a similar example at the end of the move task docs.)
The error you saw arose because you've mixed the single-file mode of the move task (tofile) with multiple-file mode.
There's no need to nest the dirset in a path as the move task accepts any file-based resource collection, including dirset.
Use Ant-Contrib's for task and propertyregex task.
<target name="test">
<for param="detailsDir">
<dirset dir="animals">
<include name="**/details"/>
</dirset>
<sequential>
<propertyregex property="output.dir" input="#{detailsDir}" regexp="(.*)/details" replace="\1" />
<move file="#{detailsDir}" toFile="${output.dir}/new" />
</sequential>
</for>
</target>
I'm sure this has either been asked before or is pretty straightforward. But for whatever reason, I cannot seem to make it work. I want to use ant to copy the ${build.classpath} (which contains a colon separated list of jars) to the ${output.dir}/myapp/WEB-INF/lib.
I have this right now and it doesn't seem to work:
<copy toDir="${output.dir}/myapp/WEB-INF/lib">
<fileset file="${build.classpath}" />
</copy>
It treats the whole classpath as one file. How do I get this to work?
The Ant Manual on the copy task contains the answer for your problem. One of the example snippets it provides:
Collect all items from the current CLASSPATH setting into a destination directory, flattening the directory structure.
<copy todir="dest" flatten="true">
<path>
<pathelement path="${java.class.path}"/>
</path>
</copy>
I think somethink like this should work:
<copy todir="${output.dir}/myapp/WEB-INF/lib" verbose="yes" flatten="yes" failonerror="no">
<fileset dir="${build.classpath}">
<include name="*.jar" />
</fileset>
</copy>
or with wildcard in include: <include name="**/*.jar" />
I think you should put all your colon separated jar files to one root folder. If it is not possible then create a separate task that put those jar files into one folder(may be temporary). And assign ${build.classpath} to that folder. Use <fileset dir="${build.classpath}"/> in your copy clause.
I hope, it should help.
In my build.xml, below works fine :-
<path id="build.classpath">
<fileset dir="lib [myUtils]" includes="*.jar" />
</path>
if lib [myUtils] is of folder type, but don't works, if it's of Linked Folder type.
Also, I found this when googled :-
https://bugs.eclipse.org/bugs/show_bug.cgi?id=265960
https://bugs.eclipse.org/bugs/show_bug.cgi?id=43081
https://bugs.eclipse.org/bugs/show_bug.cgi?id=265960
Is there any trick to achieve this, without copying the dependencies in work folder??
Note that ant should work outside of eclipse as well. So you can't reply in IDE abstractions. You can use symbolic links (if your OS supports them).
If not, you can use the FileSync plugin to synchronize eclipse project folders with external folders. Or you can simply use the <copy> ant task.
I resolved this using copy task:
<copy todir="target/web/linked1">
<fileset dir="../linkdProject/source1" />
</copy>
<copy todir="target/web/linked2">
<fileset dir="../linkedProject/source2" />
</copy>
....
<war destfile="target/webApp.war">
<fileset dir="WebContent" />
<fileset dir="target/web" /> <!-- copy linked resources -->
...
</war>
<delete dir="target"/>