ant-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Dominique Devienne <DDevie...@lgc.com>
Subject RE: having datatypes load classes
Date Wed, 09 Apr 2003 14:22:46 GMT
Two comments:

1) DynamicTag is fully Ant 1.5.x compatible. No need for 1.6. Just use it
along side your own classes, and you're good to go.

2) DynamicTag *relies* on <taskdef> or <typedef> (you can declare your
custom extension either way), which takes care of all the classloading,
already has all the special stuff like loaderref. Any enhancement to these
tasks automatically benefit DynamicTag.

With your use case, imagine you have a JAR of all your filters, with a
properties file within it called filters.properties like so:

xincludefilter = org.outerj.xml.XIncludeFilter
filter1 = org.outerj.xml.SomeFilter

You could do:

<typedef resource="org/outerj/xml/filters.properties"
         classpath="org_outerj_xml.jar" />

<target name="test" depends="-init" >
   <xmlchain toDir="./build/chain" extension=".xxx">
     <fileset refid="workOnStuf" />
     <customfilters>
	 <filter1 attr1="v1" attr2="v2">
	   <mysubelement .../>
	 </filter1>
       <xincludefilter .../>
     <customfilters>
     <xmlfilter refid="other-filter"/>
   </xmlchain>
</target>

And in your code, all you have to do is:

public Object createCustomFilters() {
  // dynatag must contain at least 1 element, no upper limit
  DynamicTag dynatag = new DynamicTag(org.outerj.xml.XmlFilter.class,
                                      1, Integet.MAX_INT);
  _filterVector.addElement(dynatag);
  return dynatag;
}

Then at execute time, convert the DynamicTags added to the vector to real
filters (pseudo-code):

Vector filters = new Vector();
foreach o in _filterVector {
  if (o instanceof DynamicTag) {
    filters.addAll(((DynamicTag)o).getTags());
  }
}

DynamicTag guarantees you all elements within it are of the required type,
the fictitious XmlFilter interface here. The really nice part is that you
code XIncludeFilter and SomeFilter like a regular bean, and Ant
automatically configures it using its normal rules (calls setters methods,
or add/create methods, with all the magic type conversion it does to go from
String to int, File (resolved to basedir), etc...). Your current filters
might not have much in term of configuration now, but DynamicTag allows a
very rich configuration of any extension point.

I personally think it's pretty elegant, and doesn't require mucking at all
with class loading issues.

But again, my perspective is biased, since I authored DynamicTag. --DD

-----Original Message-----
From: Marc Portier [mailto:mpo@outerthought.org] 
Sent: Wednesday, April 09, 2003 1:32 AM
To: Ant Developers List
Subject: Re: having datatypes load classes

Stefan Bodewig wrote:
> On Tue, 08 Apr 2003, Marc Portier <mpo@outerthought.org> wrote:
> 
> 
>>but since that pattern is to be seen more around ant iteself, I was
>>hoping for some reuse here....
> 
> 
> One would think so, but the truth is that you'll find copy-paste reuse
> in this area instead of delegation or something.
> 
> Patches for a nice little utility class are welcome 8-)
> 

Stefan,

thx for the invitation, if others want to be on the party: please 
join.

Have to think about this some more,
and have to read the replies from Dominique first (which at first 
sight seem to go somewhat over the 'nice little' attributes that 
I was seeking as well)

woke up with something along the lines of a
ClassLoaderFactory (name should be tuned down a bit, too much 
expectations here, inspiration welcome, PathUtil?)
  - public ClassLoader getClassLoaderForPath(Path);

having the responsibility to check off against the project map of 
references (as does the Definer)

possibly having a variant
  - public ClassLoader getUniqueClassLoaderForPath(Path)

while the first would follow the documented rules of the 
ant.reuse.loader property, the latter would always make a new 
one, and never store that in the references map.

in fact if ant.reuse.loader == false the behaviour of both 
methods would be equal.

combination of both offers the flexibility to cover all the use 
cases I see

I'm guessing this approach would offer the least pressure on 
having to rethink more interfaces/existing stuff. (compared to 
e.g. introduction of the ClassLoader datatype that was suggested 
in the thread I mentioned)
Another advantage I see is that it's orthogonal to existing 
stuff, so people could just use it without neading to switch to 
cvs head or something (me included :-))
The real effort would be in refactoring and testing the existing 
implementations to use this utility then (but that's somewhat 
future music)

(also thinking about singleton vs statics for the beast)

not overseeing _all_ use cases, and some general greenhorn 
feeling around the complete internals of ant makes me hesitate 
and think some more first though.

but again, all of this might be in the answers from Dominique 
already.

regards,
-marc=

Mime
View raw message