bodewig 01/12/10 02:10:35
Modified: . WHATSNEW
docs/manual/CoreTasks ant.html
src/etc/testcases/taskdefs ant.xml
src/main/org/apache/tools/ant/taskdefs Ant.java
CallTarget.java
src/testcases/org/apache/tools/ant/taskdefs AntTest.java
Added: src/etc/testcases/taskdefs/ant references.xml
Log:
Allow <ant> and <antcall> to pass references to the subbuilds.
Submitted by: Matthieu Bentot <[EMAIL PROTECTED]>
Revision Changes Path
1.188 +4 -0 jakarta-ant/WHATSNEW
Index: WHATSNEW
===================================================================
RCS file: /home/cvs/jakarta-ant/WHATSNEW,v
retrieving revision 1.187
retrieving revision 1.188
diff -u -r1.187 -r1.188
--- WHATSNEW 2001/12/07 07:16:56 1.187
+++ WHATSNEW 2001/12/10 10:10:35 1.188
@@ -117,6 +117,10 @@
* <apply> has a new attribute relative that allows users to pass the
filenames as relative instead of absolute paths on the command line.
+* References will now be copied into the child build by <ant> and
+ <antcall> unless a reference of the same name already exists in the
+ subbuild or inheritall has been set to false.
+
Changes from Ant 1.4 to Ant 1.4.1
===========================================
1.8 +94 -4 jakarta-ant/docs/manual/CoreTasks/ant.html
Index: ant.html
===================================================================
RCS file: /home/cvs/jakarta-ant/docs/manual/CoreTasks/ant.html,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -r1.7 -r1.8
--- ant.html 2001/10/30 10:05:34 1.7
+++ ant.html 2001/12/10 10:10:35 1.8
@@ -24,6 +24,16 @@
<p>You can also set properties in the new project from the old project by
using nested property tags. These properties are always passed regardless of
the
setting of <i>inheritAll</i>. This allows you to parameterize your
subprojects.</p>
+
+<p>References to data types will also be passed to the new project by
+default, but they will not override references defined in the new
+project. You can limit the references you want to copy by setting the
+<i>inheritall</i> attribute to <code>false</code> and using nested
+reference elements. The nested elements can also be used to copy
+references from the calling project to the new project under a
+different id. References taken from nested elements will override
+existing references in the new project.</p>
+
<h3>Parameters</h3>
<table border="1" cellpadding="2" cellspacing="0">
<tr>
@@ -60,16 +70,42 @@
<td align="center" valign="top">No</td>
</tr>
<tr>
- <td valign="top">inheritAll</td>
- <td valign="top">If <code>true</code>, pass all properties to the new Ant
- project. Defaults to <code>true</code>.
+ <td valign="top">inheritAll</td> <td valign="top">If
+ <code>true</code>, pass all properties and references to the new
+ Ant project. Defaults to <code>true</code>.
</td>
<td align="center" valign="top">No</td>
</tr>
</table>
-<h4>Basedir of the new project</h4>
+<h3>Parameters specified as nested elements</h3>
+<h4>property</h4>
+<p>See the description of the <a href="property.html">property task</a>.</p>
+
+<h4>reference</h4>
+<p>Used to chose references that shall be copied into the new project,
+optionally changing their id.</p>
+<table border="1" cellpadding="2" cellspacing="0">
+ <tr>
+ <td valign="top"><b>Attribute</b></td>
+ <td valign="top"><b>Description</b></td>
+ <td align="center" valign="top"><b>Required</b></td>
+ </tr>
+ <tr>
+ <td valign="top">refid</td>
+ <td valign="top">The id of the reference in the calling project.</td>
+ <td valign="top" align="center">Yes</td>
+ </tr>
+ <tr>
+ <td valign="top">toid</td>
+ <td valign="top">The id of the reference in the new project.</td>
+ <td valign="top" align="center">No, defaults to the value of refid.</td>
+ </tr>
+</table>
+
+<h3>Basedir of the new project</h3>
+
<p>The basedir value of the new project is affected by the two
attributes dir and inheritall, see the following table for
details:</p>
@@ -119,6 +155,60 @@
<property name="output.type" value="html"/>
</ant>
</pre>
+
+<p>The build file of the calling project defines some
+<code><path></code> elements like this:</p>
+
+<pre>
+ <path id="path1">
+ ...
+ </>
+ <path id="path2">
+ ...
+ </>
+</pre>
+
+<p>and the called build file (<code>subbuild.xml</code>) also defines
+a <code><path></code> with the id <code>path1</code>, but
+<code>path2</code> is not defined:</p>
+
+<pre>
+ <ant antfile="subbuild.xml" />
+</pre>
+
+<p>will not override <code>subbuild</code>'s definition of
+<code>path1</code>, but make the parent's definition of
+<code>path2</code> available in the subbuild. As does:</p>
+
+<pre>
+ <ant antfile="subbuild.xml" inheritall="true" />
+</pre>
+
+<pre>
+ <ant antfile="subbuild.xml" inheritall="false" />
+</pre>
+
+<p>will neither override <code>path1</code> nor copy
+<code>path2</code>.</p>
+
+<pre>
+ <ant antfile="subbuild.xml" inheritall="false" >
+ <reference refid="path1" />
+ </ant>
+</pre>
+
+<p>will override <code>subbuild</code>'s definition of
+<code>path1</code>.</p>
+
+<pre>
+ <ant antfile="subbuild.xml" inheritall="false" >
+ <reference refid="path1" torefid="path2" />
+ </ant>
+</pre>
+
+<p>will copy the parent's definition of <code>path1</code> into the
+new project using the id <code>path2</code>.</p>
+
<hr>
<p align="center">Copyright © 2000,2001 Apache Software Foundation. All
rights
Reserved.</p>
1.4 +14 -0 jakarta-ant/src/etc/testcases/taskdefs/ant.xml
Index: ant.xml
===================================================================
RCS file: /home/cvs/jakarta-ant/src/etc/testcases/taskdefs/ant.xml,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -r1.3 -r1.4
--- ant.xml 2001/10/30 08:42:13 1.3
+++ ant.xml 2001/12/10 10:10:35 1.4
@@ -53,4 +53,18 @@
<ant antfile="ant/ant.xml" target="callback" inheritAll="false" />
</target>
+ <target name="testInherit">
+ <ant antfile="ant/references.xml" inheritAll="true" target="dummy" />
+ </target>
+
+ <target name="testNoInherit">
+ <ant antfile="ant/references.xml" inheritAll="false" target="dummy" />
+ </target>
+
+ <target name="testRename">
+ <ant antfile="ant/references.xml" inheritAll="false" target="dummy">
+ <reference refid="path" torefid="newpath" />
+ </ant>
+ </target>
+
</project>
1.1 jakarta-ant/src/etc/testcases/taskdefs/ant/references.xml
Index: references.xml
===================================================================
<project name="test" default="def" basedir=".">
<path id="no-override" />
<target name="def">
<fail>This build file should only be run from within the testcase</fail>
</target>
<target name="dummy" />
</project>
1.35 +88 -8
jakarta-ant/src/main/org/apache/tools/ant/taskdefs/Ant.java
Index: Ant.java
===================================================================
RCS file:
/home/cvs/jakarta-ant/src/main/org/apache/tools/ant/taskdefs/Ant.java,v
retrieving revision 1.34
retrieving revision 1.35
diff -u -r1.34 -r1.35
--- Ant.java 2001/12/06 09:11:16 1.34
+++ Ant.java 2001/12/10 10:10:35 1.35
@@ -108,6 +108,9 @@
/** the properties to pass to the new project */
private Vector properties = new Vector();
+ /** the references to pass to the new project */
+ private Vector references = new Vector();
+
/** the temporary project created to run the build file */
private Project newProject;
@@ -256,14 +259,8 @@
dir = project.getBaseDir();
}
- // Override with local-defined properties
- Enumeration e = properties.elements();
- while (e.hasMoreElements()) {
- Property p=(Property) e.nextElement();
- p.setProject(newProject);
- p.execute();
- }
-
+ overrideProperties();
+
if (antFile == null) {
antFile = "build.xml";
}
@@ -278,6 +275,8 @@
target = newProject.getDefaultTarget();
}
+ addReferences();
+
// Are we trying to call the target in which we are defined?
if (newProject.getBaseDir().equals(project.getBaseDir()) &&
newProject.getProperty("ant.file").equals(project.getProperty("ant.file")) &&
@@ -295,6 +294,65 @@
}
/**
+ * Override the properties in the new project with the one
+ * explicitly defined as nested elements here.
+ */
+ private void overrideProperties() throws BuildException {
+ Enumeration e = properties.elements();
+ while (e.hasMoreElements()) {
+ Property p = (Property) e.nextElement();
+ p.setProject(newProject);
+ p.execute();
+ }
+ }
+
+ /**
+ * Add the references explicitly defined as nested elements to the
+ * new project. Also copy over all references that don't override
+ * existing references in the new project if inheritall has been
+ * requested.
+ */
+ private void addReferences() throws BuildException {
+ Hashtable thisReferences = (Hashtable)
project.getReferences().clone();
+ Hashtable newReferences = newProject.getReferences();
+ Enumeration e;
+ if (references.size() > 0) {
+ for(e = references.elements(); e.hasMoreElements();) {
+ Reference ref = (Reference)e.nextElement();
+ String refid = ref.getRefId();
+ if (refid == null) {
+ throw new BuildException("the refid attribute is
required for reference elements");
+ }
+ if (!thisReferences.containsKey(refid)) {
+ log("Parent project doesn't contain any reference '"
+ + refid + "'",
+ Project.MSG_WARN);
+ continue;
+ }
+
+ Object o = thisReferences.remove(refid);
+ String toRefid = ref.getToRefid();
+ if (toRefid == null) {
+ toRefid = refid;
+ }
+ newProject.addReference(toRefid, o);
+ }
+ }
+
+ // Now add all references that are not defined in the
+ // subproject, if inheritAll is true
+ if (inheritAll) {
+ for(e = thisReferences.keys(); e.hasMoreElements();) {
+ String key = (String)e.nextElement();
+ if (newReferences.containsKey(key)) {
+ continue;
+ }
+ newProject.addReference(key, thisReferences.get(key));
+ }
+ }
+ }
+
+ /**
* ...
*/
public void setDir(File d) {
@@ -335,5 +393,27 @@
p.setTaskName("property");
properties.addElement( p );
return p;
+ }
+
+ /**
+ * create a reference element that identifies a data type that
+ * should be carried over to the new project.
+ */
+ public void addReference(Reference r) {
+ references.addElement(r);
+ }
+
+ /**
+ * Helper class that implements the nested <reference>
+ * element of <ant> and <antcall>.
+ */
+ public static class Reference
+ extends org.apache.tools.ant.types.Reference {
+
+ public Reference() {super();}
+
+ private String targetid=null;
+ public void setToRefid(String targetid) { this.targetid=targetid; }
+ public String getToRefid() { return targetid; }
}
}
1.12 +8 -0
jakarta-ant/src/main/org/apache/tools/ant/taskdefs/CallTarget.java
Index: CallTarget.java
===================================================================
RCS file:
/home/cvs/jakarta-ant/src/main/org/apache/tools/ant/taskdefs/CallTarget.java,v
retrieving revision 1.11
retrieving revision 1.12
diff -u -r1.11 -r1.12
--- CallTarget.java 2001/11/22 08:40:21 1.11
+++ CallTarget.java 2001/12/10 10:10:35 1.12
@@ -125,6 +125,14 @@
return callee.createProperty();
}
+ /**
+ * create a reference element that identifies a data type that
+ * should be carried over to the new project.
+ */
+ public void addReference(Ant.Reference r) {
+ callee.addReference(r);
+ }
+
public void setTarget(String target) {
subTarget = target;
}
1.6 +94 -2
jakarta-ant/src/testcases/org/apache/tools/ant/taskdefs/AntTest.java
Index: AntTest.java
===================================================================
RCS file:
/home/cvs/jakarta-ant/src/testcases/org/apache/tools/ant/taskdefs/AntTest.java,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- AntTest.java 2001/11/14 12:25:30 1.5
+++ AntTest.java 2001/12/10 10:10:35 1.6
@@ -59,13 +59,14 @@
import junit.framework.AssertionFailedError;
import org.apache.tools.ant.BuildEvent;
+import org.apache.tools.ant.BuildFileTest;
import org.apache.tools.ant.BuildListener;
+import org.apache.tools.ant.types.Path;
-import org.apache.tools.ant.BuildFileTest;
/**
* @author Nico Seessle <[EMAIL PROTECTED]>
* @author <a href="mailto:[EMAIL PROTECTED]">Stefan Bodewig</a>
- * @version $Revision: 1.5 $
+ * @version $Revision: 1.6 $
*/
public class AntTest extends BuildFileTest {
@@ -156,6 +157,59 @@
}
}
+ public void testReferenceInheritance() {
+ Path p = new Path(project);
+ project.addReference("path", p);
+ project.addReference("no-override", p);
+ testReference("testInherit", new String[] {"path", "path"},
+ new boolean[] {true, true}, p);
+ testReference("testInherit",
+ new String[] {"no-override", "no-override"},
+ new boolean[] {true, false}, p);
+ testReference("testInherit",
+ new String[] {"no-override", "no-override"},
+ new boolean[] {false, false}, null);
+ }
+
+ public void testReferenceNoInheritance() {
+ Path p = new Path(project);
+ project.addReference("path", p);
+ project.addReference("no-override", p);
+ testReference("testNoInherit", new String[] {"path", "path"},
+ new boolean[] {true, false}, p);
+ testReference("testNoInherit", new String[] {"path", "path"},
+ new boolean[] {false, true}, null);
+ testReference("testInherit",
+ new String[] {"no-override", "no-override"},
+ new boolean[] {true, false}, p);
+ testReference("testInherit",
+ new String[] {"no-override", "no-override"},
+ new boolean[] {false, false}, null);
+ }
+
+ public void testReferenceRename() {
+ Path p = new Path(project);
+ project.addReference("path", p);
+ testReference("testRename", new String[] {"path", "path"},
+ new boolean[] {true, false}, p);
+ testReference("testRename", new String[] {"path", "path"},
+ new boolean[] {false, true}, null);
+ testReference("testRename", new String[] {"newpath", "newpath"},
+ new boolean[] {false, true}, p);
+ }
+
+ protected void testReference(String target, String[] keys,
+ boolean[] expect, Object value) {
+ ReferenceChecker rc = new ReferenceChecker(keys, expect, value);
+ project.addBuildListener(rc);
+ executeTarget(target);
+ AssertionFailedError ae = rc.getError();
+ if (ae != null) {
+ throw ae;
+ }
+ project.removeBuildListener(rc);
+ }
+
private class BasedirChecker implements BuildListener {
private String[] expectedBasedirs;
private int calls = 0;
@@ -177,6 +231,44 @@
try {
assertEquals(expectedBasedirs[calls++],
event.getProject().getBaseDir().getAbsolutePath());
+ } catch (AssertionFailedError e) {
+ error = e;
+ }
+ }
+ }
+
+ AssertionFailedError getError() {
+ return error;
+ }
+
+ }
+
+ private class ReferenceChecker implements BuildListener {
+ private String[] keys;
+ private boolean[] expectSame;
+ private Object value;
+ private int calls = 0;
+ private AssertionFailedError error;
+
+ ReferenceChecker(String[] keys, boolean[] expectSame, Object value) {
+ this.keys = keys;
+ this.expectSame = expectSame;
+ this.value = value;
+ }
+
+ public void buildStarted(BuildEvent event) {}
+ public void buildFinished(BuildEvent event) {}
+ public void targetFinished(BuildEvent event){}
+ public void taskStarted(BuildEvent event) {}
+ public void taskFinished(BuildEvent event) {}
+ public void messageLogged(BuildEvent event) {}
+
+ public void targetStarted(BuildEvent event) {
+ if (error == null) {
+ try {
+ assertEquals("Call "+calls+" refid=\'"+keys[calls]+"\'",
+ expectSame[calls],
+
event.getProject().getReferences().get(keys[calls++]) == value);
} catch (AssertionFailedError e) {
error = e;
}
--
To unsubscribe, e-mail: <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>