Made conditions (if/unless interpreted in a context) git-svn-id: https://svn.apache.org/repos/asf/ant/core/trunk@268342 13f79535-47bb-0310-9956-ffa450edef68master
@@ -27,7 +27,7 @@ import org.apache.ant.project.Project; | |||
import org.apache.ant.project.ProjectBuilder; | |||
import org.apache.ant.project.ProjectEngine; | |||
import org.apache.ant.project.ProjectListener; | |||
import org.apache.ant.project.ProjectToListenerAdapter; | |||
import org.apache.ant.project.LogTargetToListenerAdapter; | |||
import org.apache.ant.tasklet.JavaVersion; | |||
import org.apache.ant.tasklet.TaskletContext; | |||
import org.apache.ant.tasklet.engine.TaskletEngine; | |||
@@ -232,7 +232,8 @@ public class Main | |||
new CLOptionDescriptor( "define", | |||
CLOptionDescriptor.ARGUMENTS_REQUIRED_2, | |||
DEFINE_OPT, | |||
"Define a variable (ie -Dfoo=var)" ); | |||
"Define a variable (ie -Dfoo=var)", | |||
new int[ 0 ] ); | |||
return options; | |||
} | |||
@@ -481,7 +482,7 @@ public class Main | |||
protected void setupListener( final String listenerName ) | |||
{ | |||
m_listener = createListener( listenerName ); | |||
m_logger.addLogTarget( new ProjectToListenerAdapter( m_listener ) ); | |||
m_logger.addLogTarget( new LogTargetToListenerAdapter( m_listener ) ); | |||
} | |||
/** | |||
@@ -566,7 +567,6 @@ public class Main | |||
defines.put( AntContextResources.LIB_DIR, m_libDir ); | |||
defines.put( AntContextResources.TASKLIB_DIR, m_taskLibDir ); | |||
//defines.put( AntContextResources.USER_DIR, m_userDir ); | |||
defines.put( TaskletContext.LOGGER, m_logger ); | |||
defines.put( TaskletContext.JAVA_VERSION, getJavaVersion() ); | |||
final TaskletContext context = project.getContext(); | |||
@@ -19,8 +19,10 @@ import org.apache.avalon.ComponentNotFoundException; | |||
import org.apache.avalon.Composer; | |||
import org.apache.avalon.ConfigurationException; | |||
import org.apache.avalon.Context; | |||
import org.apache.avalon.Loggable; | |||
import org.apache.avalon.util.PropertyException; | |||
import org.apache.avalon.util.PropertyUtil; | |||
import org.apache.log.Logger; | |||
/** | |||
* Class used to configure tasks. | |||
@@ -28,7 +30,7 @@ import org.apache.avalon.util.PropertyUtil; | |||
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a> | |||
*/ | |||
public class DefaultConfigurer | |||
implements Configurer, Composer | |||
implements Configurer, Composer, Loggable | |||
{ | |||
protected final static String RESERVED_ATTRIBUTES[] = | |||
{ | |||
@@ -40,7 +42,14 @@ public class DefaultConfigurer | |||
"content" | |||
}; | |||
protected final static boolean DEBUG = false; | |||
protected Converter m_converter; | |||
protected Logger m_logger; | |||
public void setLogger( final Logger logger ) | |||
{ | |||
m_logger = logger; | |||
} | |||
public void compose( final ComponentManager componentManager ) | |||
throws ComponentNotFoundException, ComponentNotAccessibleException | |||
@@ -66,18 +75,39 @@ public class DefaultConfigurer | |||
final Context context ) | |||
throws ConfigurationException | |||
{ | |||
if( DEBUG ) | |||
{ | |||
m_logger.debug( "Configuring " + object ); | |||
} | |||
if( object instanceof Configurable ) | |||
{ | |||
if( DEBUG ) | |||
{ | |||
m_logger.debug( "Configuring object via Configurable interface" ); | |||
} | |||
((Configurable)object).configure( configuration ); | |||
} | |||
else | |||
{ | |||
final Iterator attributes = configuration.getAttributeNames(); | |||
if( DEBUG ) | |||
{ | |||
m_logger.debug( "Configuring object via Configurable reflection" ); | |||
} | |||
final Iterator attributes = configuration.getAttributeNames(); | |||
while( attributes.hasNext() ) | |||
{ | |||
final String name = (String)attributes.next(); | |||
final String value = configuration.getAttribute( name ); | |||
if( DEBUG ) | |||
{ | |||
m_logger.debug( "Configuring attribute name=" + name + | |||
" value=" + value ); | |||
} | |||
configureAttribute( object, name, value, context ); | |||
} | |||
@@ -86,6 +116,12 @@ public class DefaultConfigurer | |||
while( elements.hasNext() ) | |||
{ | |||
final Configuration element = (Configuration)elements.next(); | |||
if( DEBUG ) | |||
{ | |||
m_logger.debug( "Configuring subelement name=" + element.getName() ); | |||
} | |||
configureElement( object, element, context ); | |||
} | |||
@@ -95,6 +131,11 @@ public class DefaultConfigurer | |||
{ | |||
if( !content.trim().equals( "" ) ) | |||
{ | |||
if( DEBUG ) | |||
{ | |||
m_logger.debug( "Configuring content " + content ); | |||
} | |||
configureContent( object, content, context ); | |||
} | |||
} | |||
@@ -206,22 +247,24 @@ public class DefaultConfigurer | |||
parameterType = getComplexTypeFor( parameterType ); | |||
} | |||
if( !parameterType.isAssignableFrom( sourceClass ) ) | |||
try | |||
{ | |||
try | |||
{ | |||
value = m_converter.convert( parameterType, object ); | |||
} | |||
catch( final ConverterException ce ) | |||
{ | |||
return false; | |||
} | |||
catch( final Exception e ) | |||
value = m_converter.convert( parameterType, value ); | |||
} | |||
catch( final ConverterException ce ) | |||
{ | |||
if( DEBUG ) | |||
{ | |||
throw new ConfigurationException( "Error converting attribute for " + | |||
method.getName(), | |||
e ); | |||
m_logger.debug( "Failed to find converter ", ce ); | |||
} | |||
return false; | |||
} | |||
catch( final Exception e ) | |||
{ | |||
throw new ConfigurationException( "Error converting attribute for " + | |||
method.getName(), | |||
e ); | |||
} | |||
try | |||
@@ -15,6 +15,6 @@ import org.apache.log.Logger; | |||
public interface ConverterEngine | |||
extends Component, Converter, Loggable | |||
{ | |||
LocatorRegistry getLocatorRegistry(); | |||
ConverterRegistry getConverterRegistry(); | |||
LocatorRegistry getRegistry(); | |||
ConverterRegistry getInfoRegistry(); | |||
} |
@@ -19,9 +19,10 @@ import org.apache.log.Logger; | |||
public class DefaultConverterEngine | |||
implements ConverterEngine, Initializable | |||
{ | |||
protected final static boolean DEBUG = false; | |||
protected DefaultFactory m_factory; | |||
protected LocatorRegistry m_locatorRegistry; | |||
protected ConverterRegistry m_converterRegistry; | |||
protected LocatorRegistry m_registry; | |||
protected ConverterRegistry m_infoRegistry; | |||
protected Logger m_logger; | |||
public void setLogger( final Logger logger ) | |||
@@ -29,30 +30,30 @@ public class DefaultConverterEngine | |||
m_logger = logger; | |||
} | |||
public LocatorRegistry getLocatorRegistry() | |||
public LocatorRegistry getRegistry() | |||
{ | |||
return m_locatorRegistry; | |||
return m_registry; | |||
} | |||
public ConverterRegistry getConverterRegistry() | |||
public ConverterRegistry getInfoRegistry() | |||
{ | |||
return m_converterRegistry; | |||
return m_infoRegistry; | |||
} | |||
public void init() | |||
throws Exception | |||
{ | |||
m_converterRegistry = createConverterRegistry(); | |||
m_locatorRegistry = createLocatorRegistry(); | |||
m_infoRegistry = createInfoRegistry(); | |||
m_registry = createRegistry(); | |||
m_factory = createFactory(); | |||
} | |||
protected ConverterRegistry createConverterRegistry() | |||
protected ConverterRegistry createInfoRegistry() | |||
{ | |||
return new DefaultConverterRegistry(); | |||
} | |||
protected LocatorRegistry createLocatorRegistry() | |||
protected LocatorRegistry createRegistry() | |||
{ | |||
return new DefaultLocatorRegistry(); | |||
} | |||
@@ -65,18 +66,31 @@ public class DefaultConverterEngine | |||
public Object convert( Class destination, final Object original ) | |||
throws Exception | |||
{ | |||
final Class originalClass = original.getClass(); | |||
if( destination.isAssignableFrom( originalClass ) ) | |||
{ | |||
return original; | |||
} | |||
if( DEBUG ) | |||
{ | |||
m_logger.debug( "Looking for converter from " + originalClass.getName() + | |||
" to " + destination.getName() ); | |||
} | |||
final String name = | |||
m_converterRegistry.getConverterInfoName( original.getClass().getName(), | |||
destination.getName() ); | |||
m_infoRegistry.getConverterInfoName( originalClass.getName(), | |||
destination.getName() ); | |||
if( null == name ) | |||
{ | |||
throw new ConverterException( "Unable to find converter for " + | |||
original.getClass() + " to " + destination + | |||
" conversion" ); | |||
originalClass.getName() + " to " + | |||
destination.getName() + " conversion" ); | |||
} | |||
final Locator locator = m_locatorRegistry.getLocator( name ); | |||
final Locator locator = m_registry.getLocator( name ); | |||
final Converter converter = (Converter)m_factory.create( locator, Converter.class ); | |||
return converter.convert( destination, original ); | |||
} | |||
@@ -0,0 +1,71 @@ | |||
/* | |||
* Copyright (C) The Apache Software Foundation. All rights reserved. | |||
* | |||
* This software is published under the terms of the Apache Software License | |||
* version 1.1, a copy of which has been included with this distribution in | |||
* the LICENSE file. | |||
*/ | |||
package org.apache.ant.datatypes; | |||
import org.apache.ant.AntException; | |||
import org.apache.avalon.Component; | |||
import org.apache.avalon.Context; | |||
import org.apache.avalon.util.PropertyException; | |||
import org.apache.avalon.util.PropertyUtil; | |||
/** | |||
* Class representing a condition. | |||
* | |||
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a> | |||
*/ | |||
public class Condition | |||
implements Component | |||
{ | |||
protected String m_condition; | |||
protected boolean m_isIfCondition; | |||
public Condition( final boolean isIfCondition, final String condition ) | |||
{ | |||
m_isIfCondition = isIfCondition; | |||
m_condition = condition; | |||
} | |||
public String getCondition() | |||
{ | |||
return m_condition; | |||
} | |||
public boolean isIfCondition() | |||
{ | |||
return m_isIfCondition; | |||
} | |||
public boolean evaluate( final Context context ) | |||
{ | |||
try | |||
{ | |||
final Object resolved = | |||
PropertyUtil.resolveProperty( m_condition, context, false ); | |||
boolean result = false; | |||
if( null != resolved ) | |||
{ | |||
result = ( null != context.get( resolved ) ); | |||
} | |||
if( !m_isIfCondition ) | |||
{ | |||
result = !result; | |||
} | |||
return result; | |||
} | |||
catch( final PropertyException pe ) | |||
{ | |||
throw new AntException( "Error resolving " + m_condition, pe ); | |||
} | |||
} | |||
} | |||
@@ -0,0 +1,22 @@ | |||
/* | |||
* Copyright (C) The Apache Software Foundation. All rights reserved. | |||
* | |||
* This software is published under the terms of the Apache Software License | |||
* version 1.1, a copy of which has been included with this distribution in | |||
* the LICENSE file. | |||
*/ | |||
package org.apache.ant.datatypes; | |||
import org.apache.avalon.Component; | |||
/** | |||
* Base class for those classes that can appear inside the build file | |||
* as stand alone data types. | |||
* | |||
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a> | |||
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a> | |||
*/ | |||
public interface DataType | |||
extends Component | |||
{ | |||
} |
@@ -0,0 +1,23 @@ | |||
/* | |||
* Copyright (C) The Apache Software Foundation. All rights reserved. | |||
* | |||
* This software is published under the terms of the Apache Software License | |||
* version 1.1, a copy of which has been included with this distribution in | |||
* the LICENSE file. | |||
*/ | |||
package org.apache.ant.datatypes; | |||
import org.apache.avalon.Component; | |||
import org.apache.avalon.Loggable; | |||
import org.apache.avalon.camelot.FactoryException; | |||
import org.apache.avalon.camelot.LocatorRegistry; | |||
import org.apache.avalon.camelot.RegistryException; | |||
public interface DataTypeEngine | |||
extends Component, Loggable | |||
{ | |||
LocatorRegistry getRegistry(); | |||
DataType createDataType( String name ) | |||
throws RegistryException, FactoryException; | |||
} |
@@ -0,0 +1,73 @@ | |||
/* | |||
* Copyright (C) The Apache Software Foundation. All rights reserved. | |||
* | |||
* This software is published under the terms of the Apache Software License | |||
* version 1.1, a copy of which has been included with this distribution in | |||
* the LICENSE file. | |||
*/ | |||
package org.apache.ant.datatypes; | |||
import org.apache.ant.AntException; | |||
import org.apache.avalon.Initializable; | |||
import org.apache.avalon.Loggable; | |||
import org.apache.avalon.camelot.DefaultFactory; | |||
import org.apache.avalon.camelot.DefaultLocatorRegistry; | |||
import org.apache.avalon.camelot.Locator; | |||
import org.apache.avalon.camelot.LocatorRegistry; | |||
import org.apache.avalon.camelot.RegistryException; | |||
import org.apache.avalon.camelot.FactoryException; | |||
import org.apache.log.Logger; | |||
public class DefaultDataTypeEngine | |||
implements DataTypeEngine, Initializable | |||
{ | |||
protected DefaultFactory m_factory; | |||
protected LocatorRegistry m_registry; | |||
protected Logger m_logger; | |||
public void setLogger( final Logger logger ) | |||
{ | |||
m_logger = logger; | |||
} | |||
public LocatorRegistry getRegistry() | |||
{ | |||
return m_registry; | |||
} | |||
public void init() | |||
throws Exception | |||
{ | |||
m_registry = createRegistry(); | |||
setupComponent( m_registry ); | |||
m_factory = createFactory(); | |||
setupComponent( m_factory ); | |||
} | |||
protected void setupComponent( final Object object ) | |||
throws Exception | |||
{ | |||
if( object instanceof Loggable ) | |||
{ | |||
((Loggable)object).setLogger( m_logger ); | |||
} | |||
} | |||
protected LocatorRegistry createRegistry() | |||
{ | |||
return new DefaultLocatorRegistry(); | |||
} | |||
protected DefaultFactory createFactory() | |||
{ | |||
return new DefaultFactory(); | |||
} | |||
public DataType createDataType( final String name ) | |||
throws RegistryException, FactoryException | |||
{ | |||
final Locator locator = m_registry.getLocator( name ); | |||
return (DataType)m_factory.create( locator, DataType.class ); | |||
} | |||
} |
@@ -0,0 +1,60 @@ | |||
/* | |||
* Copyright (C) The Apache Software Foundation. All rights reserved. | |||
* | |||
* This software is published under the terms of the Apache Software License | |||
* version 1.1, a copy of which has been included with this distribution in | |||
* the LICENSE file. | |||
*/ | |||
package org.apache.ant.datatypes; | |||
import org.apache.ant.AntException; | |||
/** | |||
* Basic data type for holding patterns. | |||
* | |||
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a> | |||
*/ | |||
public class Pattern | |||
implements DataType | |||
{ | |||
protected String m_name; | |||
protected Condition m_condition; | |||
public String getName() | |||
{ | |||
return m_name; | |||
} | |||
public Condition getCondition() | |||
{ | |||
return m_condition; | |||
} | |||
public void setName( final String name ) | |||
{ | |||
m_name = name; | |||
} | |||
public void setIf( final String condition ) | |||
throws AntException | |||
{ | |||
verifyConditionNull(); | |||
m_condition = new Condition( true, condition ); | |||
} | |||
public void setUnless( final String condition ) | |||
throws AntException | |||
{ | |||
verifyConditionNull(); | |||
m_condition = new Condition( false, condition ); | |||
} | |||
protected void verifyConditionNull() | |||
throws AntException | |||
{ | |||
if( null != m_condition ) | |||
{ | |||
throw new AntException( "Can only set one of if/else for pattern data type" ); | |||
} | |||
} | |||
} |
@@ -13,6 +13,7 @@ import java.util.Iterator; | |||
import org.apache.ant.AntException; | |||
import org.apache.ant.configuration.Configuration; | |||
import org.apache.ant.configuration.ConfigurationBuilder; | |||
import org.apache.ant.datatypes.Condition; | |||
import org.apache.ant.tasklet.TaskletContext; | |||
import org.apache.avalon.ConfigurationException; | |||
import org.apache.log.Logger; | |||
@@ -133,21 +134,21 @@ public class DefaultProjectBuilder | |||
"unless condition at " + configuration.getLocation() ); | |||
} | |||
final DefaultTarget target = new DefaultTarget(); | |||
Condition condition = null; | |||
if( null != ifCondition ) | |||
{ | |||
m_logger.debug( "Target if condition: " + ifCondition ); | |||
target.setIfCondition( true ); | |||
target.setCondition( ifCondition ); | |||
condition = new Condition( true, ifCondition ); | |||
} | |||
else if( null != unlessCondition ) | |||
{ | |||
m_logger.debug( "Target unless condition: " + unlessCondition ); | |||
target.setIfCondition( false ); | |||
target.setCondition( unlessCondition ); | |||
condition = new Condition( false, unlessCondition ); | |||
} | |||
final DefaultTarget target = new DefaultTarget( condition ); | |||
if( null != depends ) | |||
{ | |||
int start = 0; | |||
@@ -11,6 +11,7 @@ import java.util.ArrayList; | |||
import java.util.Iterator; | |||
import org.apache.ant.AntException; | |||
import org.apache.ant.configuration.Configuration; | |||
import org.apache.ant.datatypes.Condition; | |||
import org.apache.ant.tasklet.DefaultTaskletContext; | |||
import org.apache.ant.tasklet.TaskletContext; | |||
import org.apache.ant.tasklet.engine.DefaultTaskletEngine; | |||
@@ -100,13 +101,9 @@ public class DefaultProjectEngine | |||
m_listenerSupport.projectStarted( projectName ); | |||
executeTargetWork( "<init>", project.getImplicitTarget(), context ); | |||
//context = new DefaultTaskletContext( context ); | |||
//placing logger lower (at targetlevel or at task level) | |||
//is possible if you want more fine grained control | |||
context.setProperty( TaskletContext.LOGGER, m_logger ); | |||
executeTargetWork( "<init>", project.getImplicitTarget(), context ); | |||
execute( project, target, context ); | |||
@@ -168,6 +165,18 @@ public class DefaultProjectEngine | |||
final Target target, | |||
final TaskletContext context ) | |||
{ | |||
final Condition condition = target.getCondition(); | |||
if( null != condition ) | |||
{ | |||
if( false == condition.evaluate( context ) ) | |||
{ | |||
m_logger.debug( "Skipping target " + name + | |||
" as it does not satisfy condition" ); | |||
return; | |||
} | |||
} | |||
m_logger.debug( "Executing target " + name ); | |||
final Iterator tasks = target.getTasks(); | |||
@@ -10,43 +10,38 @@ package org.apache.ant.project; | |||
import java.util.ArrayList; | |||
import java.util.Iterator; | |||
import org.apache.ant.configuration.Configuration; | |||
import org.apache.ant.datatypes.Condition; | |||
public class DefaultTarget | |||
implements Target | |||
{ | |||
protected ArrayList m_dependencies = new ArrayList(); | |||
protected ArrayList m_tasks = new ArrayList(); | |||
protected String m_condition; | |||
protected boolean m_isIfCondition; | |||
protected final ArrayList m_dependencies = new ArrayList(); | |||
protected final ArrayList m_tasks = new ArrayList(); | |||
protected final Condition m_condition; | |||
public Iterator getDependencies() | |||
public DefaultTarget( final Condition condition ) | |||
{ | |||
return m_dependencies.iterator(); | |||
m_condition = condition; | |||
} | |||
public Iterator getTasks() | |||
public DefaultTarget() | |||
{ | |||
return m_tasks.iterator(); | |||
this( null ); | |||
} | |||
public String getCondition() | |||
public Condition getCondition() | |||
{ | |||
return m_condition; | |||
} | |||
public void setCondition( final String condition ) | |||
{ | |||
m_condition = condition; | |||
} | |||
public boolean isIfCondition() | |||
public Iterator getDependencies() | |||
{ | |||
return m_isIfCondition; | |||
return m_dependencies.iterator(); | |||
} | |||
public void setIfCondition( final boolean isIfCondition ) | |||
public Iterator getTasks() | |||
{ | |||
m_isIfCondition = isIfCondition; | |||
return m_tasks.iterator(); | |||
} | |||
public void addDependency( final String dependency ) | |||
@@ -10,13 +10,13 @@ package org.apache.ant.project; | |||
import org.apache.log.LogEntry; | |||
import org.apache.log.LogTarget; | |||
public class ProjectToListenerAdapter | |||
public class LogTargetToListenerAdapter | |||
implements LogTarget | |||
{ | |||
protected final ProjectListener m_listener; | |||
public ProjectToListenerAdapter( final ProjectListener listener ) | |||
public LogTargetToListenerAdapter( final ProjectListener listener ) | |||
{ | |||
m_listener = listener; | |||
} |
@@ -9,14 +9,14 @@ package org.apache.ant.project; | |||
import java.util.Iterator; | |||
import org.apache.avalon.Component; | |||
import org.apache.ant.datatypes.Condition; | |||
public interface Target | |||
extends Component | |||
{ | |||
Iterator getDependencies(); | |||
Iterator getTasks(); | |||
String getCondition(); | |||
boolean isIfCondition(); | |||
Condition getCondition(); | |||
} | |||
@@ -26,6 +26,16 @@ public abstract class AbstractTasklet | |||
private TaskletContext m_context; | |||
private Logger m_logger; | |||
/** | |||
* Receive logger from container. | |||
* | |||
* @param logger the logger | |||
*/ | |||
public void setLogger( final Logger logger ) | |||
{ | |||
m_logger = logger; | |||
} | |||
/** | |||
* Retrieve context from container. | |||
* | |||
@@ -34,7 +44,6 @@ public abstract class AbstractTasklet | |||
public void contextualize( final Context context ) | |||
{ | |||
m_context = (TaskletContext)context; | |||
m_logger = (Logger)m_context.getLogger(); | |||
} | |||
/** | |||
@@ -13,7 +13,6 @@ import org.apache.avalon.DefaultContext; | |||
import org.apache.avalon.util.PropertyException; | |||
import org.apache.avalon.util.PropertyUtil; | |||
import org.apache.avalon.util.io.FileUtil; | |||
import org.apache.log.Logger; | |||
/** | |||
* Default implementation of TaskletContext. | |||
@@ -68,16 +67,6 @@ public class DefaultTaskletContext | |||
return (String)get( NAME ); | |||
} | |||
/** | |||
* Retrieve Logger associated with task. | |||
* | |||
* @return the logger | |||
*/ | |||
public Logger getLogger() | |||
{ | |||
return (Logger)get( LOGGER ); | |||
} | |||
/** | |||
* Retrieve base directory. | |||
* | |||
@@ -209,13 +198,7 @@ public class DefaultTaskletContext | |||
protected void checkPropertyValid( final String name, final Object value ) | |||
throws AntException | |||
{ | |||
if( LOGGER.equals( name ) && !( value instanceof Logger ) ) | |||
{ | |||
throw new AntException( "property " + LOGGER + | |||
" must have a value of type " + | |||
Logger.class.getName() ); | |||
} | |||
else if( BASE_DIRECTORY.equals( name ) && !( value instanceof File ) ) | |||
if( BASE_DIRECTORY.equals( name ) && !( value instanceof File ) ) | |||
{ | |||
throw new AntException( "Property " + BASE_DIRECTORY + | |||
" must have a value of type " + | |||
@@ -9,6 +9,7 @@ package org.apache.ant.tasklet; | |||
import org.apache.avalon.Component; | |||
import org.apache.avalon.Contextualizable; | |||
import org.apache.avalon.Loggable; | |||
/** | |||
* This represents the individual tasks. | |||
@@ -23,6 +24,6 @@ import org.apache.avalon.Contextualizable; | |||
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a> | |||
*/ | |||
public interface Tasklet | |||
extends Component, Contextualizable, Runnable | |||
extends Component, Contextualizable, Runnable, Loggable | |||
{ | |||
} |
@@ -11,7 +11,6 @@ import java.io.File; | |||
import org.apache.avalon.Context; | |||
import org.apache.avalon.util.Enum; | |||
import org.apache.avalon.util.ValuedEnum; | |||
import org.apache.log.Logger; | |||
/** | |||
* This represents the *Context* in which a task can be executed. | |||
@@ -30,7 +29,6 @@ public interface TaskletContext | |||
//these are the names of properties that every TaskContext must contain | |||
String JAVA_VERSION = "ant.java.version"; | |||
String BASE_DIRECTORY = "ant.base.directory"; | |||
String LOGGER = "ant.logger"; | |||
String NAME = "ant.task.name"; | |||
/** | |||
@@ -46,13 +44,6 @@ public interface TaskletContext | |||
* @return the name | |||
*/ | |||
String getName(); | |||
/** | |||
* Retrieve Logger associated with task. | |||
* | |||
* @return the logger | |||
*/ | |||
Logger getLogger(); | |||
/** | |||
* Retrieve base directory. | |||
@@ -14,6 +14,7 @@ import org.apache.ant.configuration.Configuration; | |||
import org.apache.ant.configuration.Configurer; | |||
import org.apache.ant.configuration.DefaultConfigurer; | |||
import org.apache.ant.convert.ConverterEngine; | |||
import org.apache.ant.datatypes.DataTypeEngine; | |||
import org.apache.ant.tasklet.Tasklet; | |||
import org.apache.ant.tasklet.TaskletContext; | |||
import org.apache.avalon.Component; | |||
@@ -23,13 +24,13 @@ import org.apache.avalon.Context; | |||
import org.apache.avalon.Contextualizable; | |||
import org.apache.avalon.DefaultComponentManager; | |||
import org.apache.avalon.Disposable; | |||
import org.apache.avalon.Loggable; | |||
import org.apache.avalon.Initializable; | |||
import org.apache.avalon.Loggable; | |||
import org.apache.avalon.camelot.DefaultFactory; | |||
import org.apache.avalon.camelot.DefaultLocatorRegistry; | |||
import org.apache.avalon.camelot.FactoryException; | |||
import org.apache.avalon.camelot.LocatorRegistry; | |||
import org.apache.avalon.camelot.Locator; | |||
import org.apache.avalon.camelot.DefaultLocatorRegistry; | |||
import org.apache.avalon.camelot.LocatorRegistry; | |||
import org.apache.avalon.camelot.RegistryException; | |||
import org.apache.log.Logger; | |||
@@ -41,6 +42,7 @@ public class DefaultTaskletEngine | |||
protected LocatorRegistry m_locatorRegistry; | |||
protected Configurer m_configurer; | |||
protected Logger m_logger; | |||
protected DataTypeEngine m_dataTypeEngine; | |||
protected ConverterEngine m_converterEngine; | |||
public void setLogger( final Logger logger ) | |||
@@ -58,27 +60,41 @@ public class DefaultTaskletEngine | |||
return m_converterEngine; | |||
} | |||
public LocatorRegistry getLocatorRegistry() | |||
public LocatorRegistry getRegistry() | |||
{ | |||
return m_locatorRegistry; | |||
} | |||
/** | |||
* Retrieve datatype engine. | |||
* | |||
* @return the DataTypeEngine | |||
*/ | |||
public DataTypeEngine getDataTypeEngine() | |||
{ | |||
return m_dataTypeEngine; | |||
} | |||
public void init() | |||
throws Exception | |||
{ | |||
m_locatorRegistry = createLocatorRegistry(); | |||
m_factory = createFactory(); | |||
setupSubComponent( m_factory ); | |||
//converter must be created before configurerer | |||
//so that it gets placed in configurers componentManager | |||
m_converterEngine = createConverterEngine(); | |||
m_converterEngine.setLogger( m_logger ); | |||
setupSubComponent( m_converterEngine ); | |||
m_configurer = createConfigurer(); | |||
setupSubComponent( m_configurer ); | |||
m_locatorRegistry = createLocatorRegistry(); | |||
m_factory = createFactory(); | |||
setupSubComponent( m_factory ); | |||
m_dataTypeEngine = createDataTypeEngine(); | |||
setupSubComponent( m_dataTypeEngine ); | |||
m_tskDeployer = createTskDeployer(); | |||
m_tskDeployer.setLogger( m_logger ); | |||
setupSubComponent( m_tskDeployer ); | |||
} | |||
@@ -93,10 +109,10 @@ public class DefaultTaskletEngine | |||
if( component instanceof Composer ) | |||
{ | |||
final DefaultComponentManager componentManager = new DefaultComponentManager(); | |||
componentManager.put( "org.apache.ant.convert.Converter", | |||
getConverterEngine() ); | |||
componentManager.put( "org.apache.ant.convert.ConverterEngine", | |||
componentManager.put( "org.apache.ant.convert.Converter", | |||
getConverterEngine() ); | |||
componentManager.put( "org.apache.ant.configuration.Configurer", | |||
m_configurer ); | |||
componentManager.put( "org.apache.ant.tasklet.engine.TaskletEngine", | |||
this ); | |||
@@ -108,6 +124,13 @@ public class DefaultTaskletEngine | |||
((Initializable)component).init(); | |||
} | |||
} | |||
protected DataTypeEngine createDataTypeEngine() | |||
{ | |||
final TaskletDataTypeEngine engine = new TaskletDataTypeEngine(); | |||
engine.setFactory( m_factory ); | |||
return engine; | |||
} | |||
protected TskDeployer createTskDeployer() | |||
{ | |||
@@ -143,9 +166,9 @@ public class DefaultTaskletEngine | |||
final ComponentManager componentManager ) | |||
throws AntException | |||
{ | |||
m_logger.debug( "Creating" ); | |||
final Tasklet tasklet = createTasklet( task ); | |||
final Tasklet tasklet = createTasklet( task.getName() ); | |||
tasklet.setLogger( m_logger ); | |||
m_logger.debug( "Contextualizing" ); | |||
doContextualize( tasklet, task, context ); | |||
@@ -185,9 +208,15 @@ public class DefaultTaskletEngine | |||
final ComponentManager componentManager ) | |||
throws AntException | |||
{ | |||
final DefaultComponentManager subComponentManager = | |||
new DefaultComponentManager( componentManager ); | |||
subComponentManager.put( "org.apache.ant.configuration.Configurer", m_configurer ); | |||
if( tasklet instanceof Composer ) | |||
{ | |||
try { ((Composer)tasklet).compose( componentManager ); } | |||
try { ((Composer)tasklet).compose( subComponentManager ); } | |||
catch( final Throwable throwable ) | |||
{ | |||
throw new AntException( "Error composing task " + task.getName() + " at " + | |||
@@ -244,10 +273,9 @@ public class DefaultTaskletEngine | |||
} | |||
} | |||
protected Tasklet createTasklet( final Configuration configuration ) | |||
protected Tasklet createTasklet( final String name ) | |||
throws AntException | |||
{ | |||
final String name = configuration.getName(); | |||
try | |||
{ | |||
final Locator locator = m_locatorRegistry.getLocator( name ); | |||
@@ -45,6 +45,7 @@ public class DefaultTskDeployer | |||
{ | |||
protected final static String TSKDEF_FILE = "TASK-LIB/taskdefs.xml"; | |||
protected LocatorRegistry m_dataTypeRegistry; | |||
protected LocatorRegistry m_taskletRegistry; | |||
protected LocatorRegistry m_converterRegistry; | |||
protected ConverterRegistry m_converterInfoRegistry; | |||
@@ -69,16 +70,17 @@ public class DefaultTskDeployer | |||
public void compose( final ComponentManager componentManager ) | |||
throws ComponentNotFoundException, ComponentNotAccessibleException | |||
{ | |||
final ConverterEngine converterEngine = (ConverterEngine)componentManager. | |||
lookup( "org.apache.ant.convert.ConverterEngine" ); | |||
m_converterInfoRegistry = converterEngine.getConverterRegistry(); | |||
m_converterRegistry = converterEngine.getLocatorRegistry(); | |||
final TaskletEngine taskletEngine = (TaskletEngine)componentManager. | |||
lookup( "org.apache.ant.tasklet.engine.TaskletEngine" ); | |||
m_taskletRegistry = taskletEngine.getLocatorRegistry(); | |||
final ConverterEngine converterEngine = taskletEngine.getConverterEngine(); | |||
m_converterInfoRegistry = converterEngine.getInfoRegistry(); | |||
m_converterRegistry = converterEngine.getRegistry(); | |||
m_taskletRegistry = taskletEngine.getRegistry(); | |||
m_dataTypeRegistry = taskletEngine.getDataTypeEngine().getRegistry(); | |||
} | |||
public void setLogger( final Logger logger ) | |||
@@ -106,6 +108,13 @@ public class DefaultTskDeployer | |||
final Configuration converter = (Configuration)converters.next(); | |||
handleConverter( converter, url ); | |||
} | |||
final Iterator datatypes = taskdefs.getChildren( "datatype" ); | |||
while( datatypes.hasNext() ) | |||
{ | |||
final Configuration datatype = (Configuration)datatypes.next(); | |||
handleDataType( datatype, url ); | |||
} | |||
} | |||
catch( final ConfigurationException ce ) | |||
{ | |||
@@ -138,6 +147,11 @@ public class DefaultTskDeployer | |||
throw new DeploymentException( "Malformed taskdefs.xml", ce ); | |||
} | |||
} | |||
public void deployDataType( final String name, final String location, final URL url ) | |||
throws DeploymentException | |||
{ | |||
} | |||
public void deployTasklet( final String name, final String location, final URL url ) | |||
throws DeploymentException | |||
@@ -213,4 +227,22 @@ public class DefaultTskDeployer | |||
m_logger.debug( "Registered tasklet " + name + " as " + classname ); | |||
} | |||
protected void handleDataType( final Configuration datatype, final URL url ) | |||
throws DeploymentException, ConfigurationException | |||
{ | |||
final String name = datatype.getAttribute( "name" ); | |||
final String classname = datatype.getAttribute( "classname" ); | |||
final DefaultLocator info = new DefaultLocator( classname, url ); | |||
try { m_dataTypeRegistry.register( name, info ); } | |||
catch( final RegistryException re ) | |||
{ | |||
throw new DeploymentException( "Error registering " + name + " due to " + re, | |||
re ); | |||
} | |||
m_logger.debug( "Registered datatype " + name + " as " + classname ); | |||
} | |||
} |
@@ -0,0 +1,29 @@ | |||
/* | |||
* Copyright (C) The Apache Software Foundation. All rights reserved. | |||
* | |||
* This software is published under the terms of the Apache Software License | |||
* version 1.1, a copy of which has been included with this distribution in | |||
* the LICENSE file. | |||
*/ | |||
package org.apache.ant.tasklet.engine; | |||
import org.apache.ant.datatypes.DefaultDataTypeEngine; | |||
import org.apache.avalon.camelot.DefaultFactory; | |||
public class TaskletDataTypeEngine | |||
extends DefaultDataTypeEngine | |||
{ | |||
/** | |||
* Set the DataTypeFactory. | |||
* Package access intended. | |||
*/ | |||
void setFactory( final DefaultFactory factory ) | |||
{ | |||
m_factory = factory; | |||
} | |||
protected DefaultFactory createFactory() | |||
{ | |||
return m_factory; | |||
} | |||
} |
@@ -10,10 +10,11 @@ package org.apache.ant.tasklet.engine; | |||
import org.apache.ant.AntException; | |||
import org.apache.ant.configuration.Configuration; | |||
import org.apache.ant.convert.ConverterEngine; | |||
import org.apache.ant.datatypes.DataTypeEngine; | |||
import org.apache.ant.tasklet.TaskletContext; | |||
import org.apache.avalon.Component; | |||
import org.apache.avalon.Loggable; | |||
import org.apache.avalon.ComponentManager; | |||
import org.apache.avalon.Loggable; | |||
import org.apache.avalon.camelot.LocatorRegistry; | |||
import org.apache.log.Logger; | |||
@@ -37,7 +38,7 @@ public interface TaskletEngine | |||
* | |||
* @return the LocatorRegistry | |||
*/ | |||
LocatorRegistry getLocatorRegistry(); | |||
LocatorRegistry getRegistry(); | |||
/** | |||
* Retrieve converter engine. | |||
@@ -46,6 +47,13 @@ public interface TaskletEngine | |||
*/ | |||
ConverterEngine getConverterEngine(); | |||
/** | |||
* Retrieve datatype engine. | |||
* | |||
* @return the DataTypeEngine | |||
*/ | |||
DataTypeEngine getDataTypeEngine(); | |||
/** | |||
* execute a task. | |||
* | |||
@@ -23,7 +23,10 @@ public interface TskDeployer | |||
{ | |||
void deployConverter( String name, String location, URL url ) | |||
throws DeploymentException; | |||
void deployDataType( String name, String location, URL url ) | |||
throws DeploymentException; | |||
void deployTasklet( String name, String location, URL url ) | |||
throws DeploymentException; | |||
} | |||
@@ -15,6 +15,7 @@ import org.apache.ant.tasklet.AbstractTasklet; | |||
import org.apache.ant.tasklet.DefaultTaskletContext; | |||
import org.apache.ant.tasklet.TaskletContext; | |||
import org.apache.avalon.ComponentManager; | |||
import org.apache.avalon.Context; | |||
import org.apache.avalon.ComponentNotAccessibleException; | |||
import org.apache.avalon.ComponentNotFoundException; | |||
import org.apache.avalon.Composer; | |||
@@ -32,10 +33,19 @@ public class AntCall | |||
protected Project m_project; | |||
protected String m_target; | |||
protected ArrayList m_properties = new ArrayList(); | |||
protected TaskletContext m_childContext; | |||
protected ComponentManager m_componentManager; | |||
public void contextualize( final Context context ) | |||
{ | |||
super.contextualize( context ); | |||
m_childContext = new DefaultTaskletContext( getContext() ); | |||
} | |||
public void compose( final ComponentManager componentManager ) | |||
throws ComponentNotFoundException, ComponentNotAccessibleException | |||
{ | |||
m_componentManager = componentManager; | |||
m_projectEngine = (ProjectEngine)componentManager. | |||
lookup( "org.apache.ant.project.ProjectEngine" ); | |||
m_project = (Project)componentManager.lookup( "org.apache.ant.project.Project" ); | |||
@@ -47,8 +57,12 @@ public class AntCall | |||
} | |||
public Property createParam() | |||
throws Exception | |||
{ | |||
final Property property = new Property(); | |||
property.setLogger( getLogger() ); | |||
property.contextualize( m_childContext ); | |||
property.compose( m_componentManager ); | |||
m_properties.add( property ); | |||
return property; | |||
} | |||
@@ -61,17 +75,14 @@ public class AntCall | |||
throw new AntException( "Target attribute must be specified" ); | |||
} | |||
final TaskletContext context = new DefaultTaskletContext( getContext() ); | |||
final int size = m_properties.size(); | |||
for( int i = 0; i < size; i++ ) | |||
{ | |||
final Property property = (Property)m_properties.get( i ); | |||
property.contextualize( context ); | |||
property.run(); | |||
} | |||
getLogger().info( "Calling target " + m_target ); | |||
m_projectEngine.execute( m_project, m_target, context ); | |||
m_projectEngine.execute( m_project, m_target, m_childContext ); | |||
} | |||
} |
@@ -7,27 +7,130 @@ | |||
*/ | |||
package org.apache.ant.tasks.core; | |||
import java.util.Iterator; | |||
import org.apache.ant.AntException; | |||
import org.apache.ant.configuration.Configurable; | |||
import org.apache.ant.configuration.Configuration; | |||
import org.apache.ant.configuration.Configurer; | |||
import org.apache.ant.convert.Converter; | |||
import org.apache.ant.datatypes.DataType; | |||
import org.apache.ant.datatypes.DataTypeEngine; | |||
import org.apache.ant.tasklet.AbstractTasklet; | |||
import org.apache.ant.tasklet.TaskletContext; | |||
import org.apache.ant.tasklet.engine.TaskletEngine; | |||
import org.apache.avalon.ComponentManager; | |||
import org.apache.avalon.ComponentNotAccessibleException; | |||
import org.apache.avalon.ComponentNotFoundException; | |||
import org.apache.avalon.Composer; | |||
import org.apache.avalon.ConfigurationException; | |||
import org.apache.avalon.Resolvable; | |||
/** | |||
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a> | |||
*/ | |||
public class Property | |||
extends AbstractTasklet | |||
implements Configurable, Composer | |||
{ | |||
protected String m_name; | |||
protected String m_value; | |||
protected Object m_value; | |||
protected boolean m_localScope = true; | |||
protected DataTypeEngine m_engine; | |||
protected Converter m_converter; | |||
protected Configurer m_configurer; | |||
public void compose( final ComponentManager componentManager ) | |||
throws ComponentNotFoundException, ComponentNotAccessibleException | |||
{ | |||
m_configurer = (Configurer)componentManager. | |||
lookup( "org.apache.ant.configuration.Configurer" ); | |||
final TaskletEngine taskletEngine = (TaskletEngine)componentManager. | |||
lookup( "org.apache.ant.tasklet.engine.TaskletEngine" ); | |||
m_engine = taskletEngine.getDataTypeEngine(); | |||
m_converter = taskletEngine.getConverterEngine(); | |||
} | |||
public void configure( final Configuration configuration ) | |||
throws ConfigurationException | |||
{ | |||
final Iterator attributes = configuration.getAttributeNames(); | |||
while( attributes.hasNext() ) | |||
{ | |||
final String name = (String)attributes.next(); | |||
final String value = configuration.getAttribute( name ); | |||
final Object object = getContext().resolveValue( value ); | |||
if( null == object ) | |||
{ | |||
throw new AntException( "Value for attribute " + name + "resolved to null" ); | |||
} | |||
if( name.equals( "name" ) ) | |||
{ | |||
try { setName( (String)m_converter.convert( String.class, object ) ); } | |||
catch( final Exception e ) | |||
{ | |||
throw new ConfigurationException( "Error converting value", e ); | |||
} | |||
} | |||
else if( name.equals( "value" ) ) | |||
{ | |||
setValue( object ); | |||
} | |||
else if( name.equals( "local-scope" ) ) | |||
{ | |||
try | |||
{ | |||
final Boolean localScope = | |||
(Boolean)m_converter.convert( Boolean.class, object ); | |||
setLocalScope( Boolean.TRUE == localScope ); | |||
} | |||
catch( final Exception e ) | |||
{ | |||
throw new ConfigurationException( "Error converting value", e ); | |||
} | |||
} | |||
else | |||
{ | |||
throw new ConfigurationException( "Unknown attribute " + name ); | |||
} | |||
} | |||
final Iterator children = configuration.getChildren(); | |||
while( children.hasNext() ) | |||
{ | |||
final Configuration child = (Configuration)children.next(); | |||
try | |||
{ | |||
final DataType value = m_engine.createDataType( child.getName() ); | |||
setValue( value ); | |||
m_configurer.configure( value, child, getContext() ); | |||
} | |||
catch( final Exception e ) | |||
{ | |||
throw new ConfigurationException( "Unable to set datatype", e ); | |||
} | |||
} | |||
} | |||
public void setName( final String name ) | |||
{ | |||
m_name = name; | |||
} | |||
public void setValue( final String value ) | |||
public void setValue( final Object value ) | |||
throws AntException | |||
{ | |||
if( null != m_value ) | |||
{ | |||
throw new AntException( "Value can not be set multiple times" ); | |||
} | |||
m_value = value; | |||
} | |||
@@ -50,7 +153,18 @@ public class Property | |||
} | |||
final TaskletContext context = getContext(); | |||
final Object value = context.resolveValue( m_value ); | |||
Object value = m_value; | |||
if( value instanceof String ) | |||
{ | |||
value = context.resolveValue( (String)value ); | |||
} | |||
while( null != value && value instanceof Resolvable ) | |||
{ | |||
value = ((Resolvable)value).resolve( context ); | |||
} | |||
if( m_localScope ) | |||
{ | |||
@@ -112,10 +112,8 @@ public class RegisterConverter | |||
try | |||
{ | |||
m_engine.getConverterEngine(). | |||
getConverterRegistry().register( m_classname, info ); | |||
m_engine.getConverterEngine(). | |||
getLocatorRegistry().register( m_classname, locator ); | |||
m_engine.getConverterEngine().getInfoRegistry().register( m_classname, info ); | |||
m_engine.getConverterEngine().getRegistry().register( m_classname, locator ); | |||
} | |||
catch( final RegistryException re ) | |||
{ | |||
@@ -37,7 +37,7 @@ public class RegisterTasklet | |||
else | |||
{ | |||
final DefaultLocator locator = new DefaultLocator( classname, url ); | |||
m_engine.getLocatorRegistry().register( name, locator ); | |||
m_engine.getRegistry().register( name, locator ); | |||
} | |||
} | |||
} |
@@ -20,12 +20,13 @@ Legal: | |||
<target name="main" depends="property-test" /> | |||
<!-- | |||
=================================================================== | |||
Help on usage | |||
=================================================================== | |||
--> | |||
<target name="option-test"> | |||
<target name="no-test-target" unless="do-tests"> | |||
<echo message="No tests done here"/> | |||
</target> | |||
<target name="test-target" depends="no-test-target" if="do-tests"> | |||
<echo message="Tests away"/> | |||
<prim-test | |||
integer="1" | |||
@@ -54,7 +55,7 @@ Legal: | |||
</target> | |||
<target name="property-test"> | |||
<target name="property-test" depends="test-target"> | |||
<property name="blah" value="fred" /> | |||
<property name="${blah}" value="barney" /> | |||
@@ -77,6 +78,12 @@ Legal: | |||
<param name="blah" value="blah-value" /> | |||
</ant-call> | |||
<property name="foo"> | |||
<pattern name="*.java"/> | |||
</property> | |||
<echo message="foo=${foo}" /> | |||
</target> | |||
<target name="property-test2"> | |||
@@ -9,6 +9,8 @@ | |||
<task name="register-converter" classname="org.apache.ant.tasks.core.RegisterConverter" /> | |||
<task name="ant-call" classname="org.apache.ant.tasks.core.AntCall" /> | |||
<datatype name="pattern" classname="org.apache.ant.datatypes.Pattern" /> | |||
<converter classname="org.apache.ant.convert.core.StringToLongConverter" | |||
source="java.lang.String" | |||
destination="java.lang.Long" /> | |||