diff --git a/CONTRIBUTORS b/CONTRIBUTORS index e8cf42774..49cf4f0dd 100644 --- a/CONTRIBUTORS +++ b/CONTRIBUTORS @@ -38,6 +38,7 @@ Brant Langer Gurganus Brian Curnow Brian Deitte Brian Felder +Brian Repko Bruce Atherton Cedomir Igaly Charles Hudak diff --git a/contributors.xml b/contributors.xml index f16c3fdba..3ac7e9fd6 100644 --- a/contributors.xml +++ b/contributors.xml @@ -177,6 +177,10 @@ Brian Felder + + Brian + Repko + Bruce Atherton diff --git a/docs/faq.html b/docs/faq.html index 4e18fcd65..b242ff29c 100644 --- a/docs/faq.html +++ b/docs/faq.html @@ -431,6 +431,11 @@ Ant runs into an infinite loop/throws an OutOfMemoryError when I compile my project under Mac OS X. + +
  • + extension-point doesn't work + with import like the documentation + states.
  • @@ -2184,6 +2189,49 @@ mv /tmp/foo $ANT_HOME/bin/antRun there is another symlink bundle that points to the Home directory and will cause infite recursions as well.

    +

    + + extension-point doesn't work + with import like the documentation + states. +

    +

    Yes, there is + a bug + in Ant 1.8.0.

    +

    When using two build files like

    +
    +importing.xml:
    +<project>
    +   ...
    +   <import file="imported.xml"/>
    +   <target name="bar" extensionOf="foo"/>
    +</project>
    +imported.xml:
    +<project>
    +   <extension-point name="foo"/>
    +</project>
    +
    +

    Ant 1.8.0 will fail, claiming there was no extension point + named "foo".

    +

    This bug has been fixed for Ant 1.8.1. For Ant 1.8.0 there + is + a work-around: + add an additional layer of importing like in

    +
    +importing.xml:
    +<project>
    +   <target name="bar" extensionOf="foo"/>
    +</project>
    +imported.xml:
    +<project>
    +   <extension-point name="foo"/>
    +</project>
    +build.xml:
    +<project>
    +   <import file="imported.xml"/>
    +   <import file="importing.xml"/>
    +</project>
    +
    diff --git a/src/main/org/apache/tools/ant/ProjectHelper.java b/src/main/org/apache/tools/ant/ProjectHelper.java index 93294a141..70aa56238 100644 --- a/src/main/org/apache/tools/ant/ProjectHelper.java +++ b/src/main/org/apache/tools/ant/ProjectHelper.java @@ -19,6 +19,8 @@ package org.apache.tools.ant; import java.io.File; import java.util.Hashtable; +import java.util.LinkedList; +import java.util.List; import java.util.Locale; import java.util.Vector; @@ -89,6 +91,7 @@ public class ProjectHelper { // that read build files using ProjectHelper ). private Vector importStack = new Vector(); + private List extensionStack = new LinkedList(); /** * Import stack. @@ -101,6 +104,18 @@ public class ProjectHelper { return importStack; } + /** + * Extension stack. + * Used to keep track of targets that extend extension points. + * + * @return a list of two element string arrays where the first + * element is the name of the extensionpoint and the second the + * name of the target + */ + public List getExtensionStack() { + return extensionStack; + } + private final static ThreadLocal targetPrefix = new ThreadLocal() { protected Object initialValue() { return (String) null; diff --git a/src/main/org/apache/tools/ant/helper/ProjectHelper2.java b/src/main/org/apache/tools/ant/helper/ProjectHelper2.java index 1fa4a36bd..5f29e6aee 100644 --- a/src/main/org/apache/tools/ant/helper/ProjectHelper2.java +++ b/src/main/org/apache/tools/ant/helper/ProjectHelper2.java @@ -177,6 +177,28 @@ public class ProjectHelper2 extends ProjectHelper { parse(project, source, new RootHandler(context, mainHandler)); // Execute the top-level target context.getImplicitTarget().execute(); + + // resolve extensionOf attributes + for (Iterator i = getExtensionStack().iterator(); i.hasNext(); ) { + String[] extensionInfo = (String[]) i.next(); + String tgName = extensionInfo[0]; + String name = extensionInfo[1]; + Hashtable projectTargets = project.getTargets(); + if (!projectTargets.containsKey(tgName)) { + throw new BuildException("can't add target " + + name + " to extension-point " + + tgName + + " because the extension-point" + + " is unknown."); + } + Target t = (Target) projectTargets.get(tgName); + if (!(t instanceof ExtensionPoint)) { + throw new BuildException("referenced target " + + tgName + + " is not an extension-point"); + } + t.addDependency(name); + } } } @@ -987,6 +1009,9 @@ public class ProjectHelper2 extends ProjectHelper { project.addOrReplaceTarget(newName, newTarget); } if (extensionPoint != null) { + ProjectHelper helper = + (ProjectHelper) context.getProject(). + getReference(ProjectHelper.PROJECTHELPER_REFERENCE); for (Iterator iter = Target.parseDepends(extensionPoint, name, "extensionOf") .iterator(); @@ -995,20 +1020,12 @@ public class ProjectHelper2 extends ProjectHelper { if (isInIncludeMode()) { tgName = prefix + sep + tgName; } - if (!projectTargets.containsKey(tgName)) { - throw new BuildException("can't add target " - + name + " to extension-point " - + tgName - + " because the extension-point" - + " is unknown."); - } - Target t = (Target) projectTargets.get(tgName); - if (!(t instanceof ExtensionPoint)) { - throw new BuildException("referenced target " - + tgName - + " is not an extension-point"); - } - t.addDependency(name); + + // defer extensionpoint resolution until the full + // import stack has been processed + helper.getExtensionStack().add(new String[] { + tgName, name + }); } } } diff --git a/src/tests/antunit/core/extension-point-test.xml b/src/tests/antunit/core/extension-point-test.xml index 012375c09..810ad33aa 100644 --- a/src/tests/antunit/core/extension-point-test.xml +++ b/src/tests/antunit/core/extension-point-test.xml @@ -57,30 +57,35 @@ - + - - + + ]]> + expectedMessage="referenced target foo is not an extension-point"> - + + + + +]]> - - + + + + in target prepare + ]]> - - - + + diff --git a/xdocs/faq.xml b/xdocs/faq.xml index 090ab8f41..7a598cf7b 100644 --- a/xdocs/faq.xml +++ b/xdocs/faq.xml @@ -1912,6 +1912,54 @@ mv /tmp/foo $ANT_HOME/bin/antRun recursions as well.

    + + + extension-point doesn't work + with import like the documentation + states. + + +

    Yes, there is + a bug + in Ant 1.8.0.

    + +

    When using two build files like

    + + ... + + + +imported.xml: + + + +]]> +

    Ant 1.8.0 will fail, claiming there was no extension point + named "foo".

    + +

    This bug has been fixed for Ant 1.8.1. For Ant 1.8.0 there + is + a work-around: + add an additional layer of importing like in

    + + + +imported.xml: + + + +build.xml: + + + + +]]> +
    +