ant-user mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "Shackelford, John-Mason" <john-mason.shackelf...@pearson.com>
Subject evolving techniques for large projects
Date Mon, 02 Jun 2003 16:11:22 GMT
I am about to refactor our project's build files and wanted to check in to
see if the state-of-the-art for handling large projects has changed any in
the last year. 


PROBLEM:

We have a large application made up of 25 components each of which has its
own build file and use a master build file to kick the whole thing off. Our
major complaint with the current build system is that it performs poorly.
Since we are reliant on the <ant> task to call down into each build file we
do not benefit from the dependency tree ant normally builds and so many
targets are run and rerun. We to be able to build each component
independently, so each component build file calls the build files of
components on which it is dependent. Even though each component has
up-to-date checking the over head of each component calling its dependencies
is rather significant.

POSSIBLE SOLUTIONS:

1. master build file has proxy targets

Hatcher & Loughran recommend against having components call their
dependencies given the performance impact and the danger of coupling
projects too tightly (214) though they acknowledge that this may be an
inevitable in a growing project with many interdependent components even
given a clean dependency graph (219).

Hatcher & Loughran suggest using proxy targets in the master build file so
that we gain the benefit of ant's own dependency computation (219-220).
While this does allow us to avoid the expense of duplicate <ant> calls from
the master build file, it requires us to either to (a) move all knowledge
regarding the component decencies from the component build files themselves
such that a component can not be built independent of the master build file
or (b) add targets to all components which by-pass component dependency
checking & building for use by the master build file.

Losing the ability to build components without the master build file (or
some manual intervention) may  be insignificant if components are never used
alone since another project using the shared components will likely have its
own master build file and dependency resolution.


2. single logical build file and broken into physical files via XML entities

While this allows ant to use it's native dependency tree to avoid running
targets multiple times, and partitions the project into smaller physical
files, component build files will lack <project> tags and will cease to
function independent of the master build file. 


3. single build file

While this jeopardizes the independence of components (as does option 2) and
forces the maintainer to deal with a very large file, it does allow us to
leverage ant's own dependency graph while avoiding the confusion the XML
entities introduce.


4. ant 1.6's  <import>

Other than allowing the master file to conditionally include targets from
other build files, and its simplicity, I do not have a clear understanding
as to how this will contribute anything beyond an XML entity based solution.
I could use some education here.


5. Gump, Maven, etc.

Other build tools seem to have developed specifically for builds with many
interdependent components; however, adding entirely new tools to the mix
increases the effort required of developers in environments where the build
system is distributed and used widely by developers with varying levels of
configuration management expertise & interest.


IMHO, THE BEST OF ALL POSSIBLE WORLDS

While the following solution may pose insurmountable (or perhaps very
awkward) development requirement challenges, from a usability perspective it
seems to me that the best solution would be if ant's native dependency
resolution mechanism would allow users to include targets from other
functioning build files. (Perhaps this is what Ant 1.6's <import> would
do--I am unclear about it.) For example one could specify:

<project name "master-build-file">
   <buildfile name="componentA" location="../A/build.xml"/>
   <buildfile name="componentB" location="../B/build.xml"/>
   <target name="build-everything" 
           depends="init,componentA:build,componentB:build">
....

Thus one could indicate to ant that targets should be drawn from several
build files, and could build a dependency graph across files. The
<buildfile> directive would tell ant to import targets from the a particular
build file and append the prefix (indicated in the name parameter) to the
import targets so as to prevent naming collisions. Ant would then build it
dependency graph and begin executing the default target, or target specified
on the command line, etc.


REQUEST FOR FEEDBACK

I would be interested to know (a) if I have missed any solutions for large
project configuration, or misrepresented the strengths & weaknesses of the
solutions presented (b) if the <import> task offers a better solution than I
have understood, (c) if there is any merit to my final suggestion.


John-Mason Shackelford

Software Developer
Pearson Educational Measurement - eMeasurement Group

2510 North Dodge St.
Iowa City, IA 52245
ph. 319-354-9200x6214
john-mason.shackelford@pearson.com
http://etest.ncspearson.com

**************************************************************************** 
This email may contain confidential material. 
If you were not an intended recipient, 
Please notify the sender and delete all copies. 
We may monitor email to and from our network. 
****************************************************************************

Mime
View raw message