Improve the resolution of the extension point to bind to: - first try the extension point which might be in the same file - then try the one in the root file Still some work to do: there might be intermediate file in the import stack which we would to resolve the name against, but the ProjectHelper doesn't hold the prefix stacking. git-svn-id: https://svn.apache.org/repos/asf/ant/core/trunk@1373326 13f79535-47bb-0310-9956-ffa450edef68master
@@ -88,6 +88,9 @@ Other changes: | |||
and extension points. | |||
Bugzilla Report 53549. | |||
* Make extension point bindable to imported prefixed targets | |||
Bugzilla Report 53550. | |||
Changes from Ant 1.8.3 TO Ant 1.8.4 | |||
=================================== | |||
@@ -629,27 +629,52 @@ public class ProjectHelper { | |||
public void resolveExtensionOfAttributes(Project project) | |||
throws BuildException { | |||
for (String[] extensionInfo : getExtensionStack()) { | |||
String tgName = extensionInfo[0]; | |||
String name = extensionInfo[1]; | |||
String extPointName = extensionInfo[0]; | |||
String targetName = extensionInfo[1]; | |||
OnMissingExtensionPoint missingBehaviour = OnMissingExtensionPoint.valueOf(extensionInfo[2]); | |||
// if the file has been included or imported, it may have a prefix | |||
// we should consider when trying to resolve the target it is | |||
// extending | |||
String prefixAndSep = extensionInfo.length > 3 ? extensionInfo[3] : null; | |||
// find the target we're extending | |||
Hashtable projectTargets = project.getTargets(); | |||
if (!projectTargets.containsKey(tgName)) { | |||
String message = "can't add target " + name | |||
+ " to extension-point " + tgName | |||
Target extPoint = null; | |||
if (prefixAndSep == null) { | |||
// no prefix - not from an imported/included build file | |||
extPoint = (Target) projectTargets.get(extPointName); | |||
} else { | |||
// we have a prefix, which means we came from an include/import | |||
// FIXME: here we handle no particular level of include. We try | |||
// the fully prefixed name, and then the non-prefixed name. But | |||
// there might be intermediate project in the import stack, | |||
// which prefix should be tested before testing the non-prefix | |||
// root name. | |||
extPoint = (Target) projectTargets.get(prefixAndSep + extPointName); | |||
if (extPoint == null) { | |||
extPoint = (Target) projectTargets.get(extPointName); | |||
} | |||
} | |||
// make sure we found a point to extend on | |||
if (extPoint == null) { | |||
String message = "can't add target " + targetName | |||
+ " to extension-point " + extPointName | |||
+ " because the extension-point is unknown."; | |||
if (missingBehaviour == OnMissingExtensionPoint.FAIL) { | |||
throw new BuildException(message); | |||
} else if (missingBehaviour == OnMissingExtensionPoint.WARN) { | |||
Target target = (Target) projectTargets.get(name); | |||
project.log(target, "Warning: " + message, Project.MSG_WARN); | |||
Target t = (Target) projectTargets.get(targetName); | |||
project.log(t, "Warning: " + message, Project.MSG_WARN); | |||
} | |||
} else { | |||
Target t = (Target) projectTargets.get(tgName); | |||
if (!(t instanceof ExtensionPoint)) { | |||
throw new BuildException("referenced target " + tgName | |||
if (!(extPoint instanceof ExtensionPoint)) { | |||
throw new BuildException("referenced target " + extPointName | |||
+ " is not an extension-point"); | |||
} | |||
t.addDependency(name); | |||
extPoint.addDependency(targetName); | |||
} | |||
} | |||
} | |||
@@ -1011,17 +1011,24 @@ public class ProjectHelper2 extends ProjectHelper { | |||
ProjectHelper helper = | |||
(ProjectHelper) context.getProject(). | |||
getReference(ProjectHelper.PROJECTHELPER_REFERENCE); | |||
for (String tgName : Target.parseDepends(extensionPoint, name, "extensionOf")) { | |||
if (isInIncludeMode()) { | |||
tgName = prefix + sep + tgName; | |||
} | |||
for (String extPointName : Target.parseDepends(extensionPoint, name, "extensionOf")) { | |||
if (extensionPointMissing == null) { | |||
extensionPointMissing = OnMissingExtensionPoint.FAIL; | |||
} | |||
// defer extensionpoint resolution until the full | |||
// import stack has been processed | |||
helper.getExtensionStack().add(new String[] { | |||
tgName, name, extensionPointMissing.name() }); | |||
if (isInIncludeMode()) { | |||
// if in include mode, provide prefix we're including by | |||
// so that we can try and resolve extension point from | |||
// the local file first | |||
helper.getExtensionStack().add( | |||
new String[] {extPointName, target.getName(), | |||
extensionPointMissing.name(), prefix + sep}); | |||
} else { | |||
helper.getExtensionStack().add( | |||
new String[] {extPointName, target.getName(), | |||
extensionPointMissing.name()}); | |||
} | |||
} | |||
} | |||
} | |||
@@ -0,0 +1,34 @@ | |||
<?xml version="1.0"?> | |||
<!-- | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
--> | |||
<project xmlns:au="antlib:org.apache.ant.antunit" default="antunit"> | |||
<import file="../../antunit-base.xml" /> | |||
<!-- declare a target that depends on the extension point --> | |||
<target name="compile" depends="all.compile" /> | |||
<!-- declare our extension point --> | |||
<extension-point name="all.compile" /> | |||
<!-- import all our modules --> | |||
<import file="module1.xml" as="module1" /> | |||
<target name="testImport" depends="compile"> | |||
<au:assertLogContains text="In module1 compile. Yay!" /> | |||
</target> | |||
</project> |
@@ -0,0 +1,25 @@ | |||
<?xml version="1.0"?> | |||
<!-- | |||
Licensed to the Apache Software Foundation (ASF) under one or more | |||
contributor license agreements. See the NOTICE file distributed with | |||
this work for additional information regarding copyright ownership. | |||
The ASF licenses this file to You under the Apache License, Version 2.0 | |||
(the "License"); you may not use this file except in compliance with | |||
the License. You may obtain a copy of the License at | |||
http://www.apache.org/licenses/LICENSE-2.0 | |||
Unless required by applicable law or agreed to in writing, software | |||
distributed under the License is distributed on an "AS IS" BASIS, | |||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | |||
See the License for the specific language governing permissions and | |||
limitations under the License. | |||
--> | |||
<project name="module1"> | |||
<!-- declare a target with the same name as one in the master --> | |||
<target name="compile" extensionOf="all.compile"> | |||
<echo message="In module1 compile. Yay!"/> | |||
</target> | |||
</project> |