Bug 40678

Summary: [Patch] Allow macrodef to have arbitary xml elements
Product: Ant Reporter: Peter Reilly <peterreilly>
Component: CoreAssignee: Ant Notifications List <notifications>
Status: NEW ---    
Severity: enhancement Keywords: PatchAvailable
Priority: P2    
Version: unspecified   
Target Milestone: ---   
Hardware: All   
OS: All   
Attachments: patch containing differences and new files
new patch - separate task fragmentdef
New patch to enable any marcodef to be used.

Description Peter Reilly 2006-10-04 08:55:49 UTC
Currently <macrodef> only allows the creation of new tasks.
This makes it difficult to for example compose conditions
from other conditions - see 
http://marc.theaimsgroup.com/?t=115928538600003&r=1&w=2
for a dicussion.

This patch allows this.
Overview of changes:
<macrodef> to have a new element <fragment>, this can contain
arbitary xml and associate it with a name. The name *has* to
have a '-' in it (this means that the fragment will not be
confused with refection based elements).
If a fragment is used, macrodef will create a MacroFragmentTask
instead of a MacroInstance. This MacroFragmentTask extends MacroInstance
and implements MacroFragment.
MacroInstance has been modified a little so it can be extended.
UnknownElement has been modifed to check if child unknown elements
are MacroInstances and if so expand them by calling MacroFragment.getUnknowns()

Usage:
   <macrodef name="file-sets">
      <fragment>
        <fileset dir="build/a"/>
        <fileset dir="build/b"/>
      </fragment>
    </macrodef>

    <copy todir="build/c">
      <file-sets/>
    </copy>


and:
    <macrodef name="is-empty-file">
      <attribute name="file" />
      <fragment>
        <and>
          <available file="@{file}" type="file" />
          <length file="@{file}" length="0" />
        </and>
      </fragment>
    </macrodef>

    <condition property="build.is.empty">
      <is-empty-file file="build.xml"/>
    </condition>

    <echo>${build.is.empty}</echo>
    <touch file="empty.file"/>

    <condition property="empty.is.empty">
      <is-empty-file file="empty.file"/>
    </condition>

    <echo>${empty.is.empty}</echo>
Comment 1 Peter Reilly 2006-10-04 08:58:29 UTC
Created attachment 18962 [details]
patch containing differences and new files
Comment 2 Matt Benson 2006-10-05 07:09:13 UTC
1. It kicks ass that you were able to get something working here.
2. It's a little bit of a drawback that a fragment has to have a hyphen in the
name.  :(
Comment 3 Peter Reilly 2006-10-05 15:10:47 UTC
I think that the restiction can be removed.
the code can ask IH if the parent class has
explicit named elements, still we should
highlight that since the fragment can be used
nearly anywhere, one should be carefull with
the choice of name.

One issue outstanding is error reporting,
the location of the use of the fragment is
lost, this may not be an issue for some uses
(the task that has the fragment will be complaining)
but we need to experiment a little.
Comment 4 Peter Reilly 2007-09-04 04:36:01 UTC
Created attachment 20766 [details]
new patch - separate task fragmentdef

This is a new patch that adds a new task - fragmentdef.
It allows the definition of fairly arbitary element sequences
that can be placed in tasks or types. It does not have
the restriction of having a "-" in the name.
Usage:
<fragmentdef name="allfilesets">
  <sequential>
    <fileset dir="a" includes="*.jar"/>
    <fileset dir="b" includes="*.jar"/>
  </sequential>
</fragmentdef>

<javac ..>
   <classpath>
     <allfilesets/>
   </classpath>
</javac>

<jar jarfile="all.jar">
   <allfilesets/>
</jar>
Comment 5 Steve Loughran 2007-09-04 05:54:49 UTC
+1; much better re-use, but I'm not sure about the name. <datadef>? 
Comment 6 Peter Reilly 2007-09-04 06:09:29 UTC
names.....
Another alternative is to allow macrodef to be used like
this. I am a little worried about this (changing macrodef)
as it may effect current scripts, but it is something to
consider.

Comment 7 Peter Reilly 2007-09-17 04:04:35 UTC
Created attachment 20833 [details]
New patch to enable any marcodef to be used.

This patch allows macrodef to be used
to define any elements to be used.
for example:
<macrodefdef name="allfilesets">
  <sequential>
    <fileset dir="a" includes="*.jar"/>
    <fileset dir="b" includes="*.jar"/>
  </sequential>
</fragmentdef>

<javac ..>
   <classpath>
     <allfilesets/>
   </classpath>
</javac>

<jar jarfile="all.jar">
   <allfilesets/>
</jar>
Comment 8 Robert Krajewski 2012-05-18 16:52:46 UTC
What happened to this? fragmentdef or something similar would be really useful.
Comment 9 Stefan Bodewig 2014-01-06 20:11:58 UTC
Peter, this looks like something people have been asking for.  Do you recall why you didn't commit the final incarnation?
Comment 10 Peter Reilly 2014-01-06 22:00:54 UTC
No, I moved jobs and did not follow up.
I think that I used this in a number of test builds and got a little
confused with the embedding of elements in other tasks.
However it does seem to be a nice feature.

Peter