git-svn-id: https://svn.apache.org/repos/asf/ant/core/trunk@269247 13f79535-47bb-0310-9956-ffa450edef68master
@@ -1,8 +1,8 @@ | |||||
#!/bin/sh | #!/bin/sh | ||||
echo | echo | ||||
echo "Ant Build System" | |||||
echo "----------------" | |||||
echo "Myrmidon Build System" | |||||
echo "---------------------" | |||||
export MYRMIDON_HOME=tools | export MYRMIDON_HOME=tools | ||||
@@ -7,6 +7,7 @@ | |||||
*/ | */ | ||||
package org.apache.myrmidon.components.builder; | package org.apache.myrmidon.components.builder; | ||||
import java.net.URL; | |||||
import java.io.File; | import java.io.File; | ||||
import java.io.IOException; | import java.io.IOException; | ||||
import java.util.ArrayList; | import java.util.ArrayList; | ||||
@@ -61,8 +62,8 @@ public class DefaultProjectBuilder | |||||
private Project build( final File file, final HashMap projects ) | private Project build( final File file, final HashMap projects ) | ||||
throws Exception | throws Exception | ||||
{ | { | ||||
final String systemID = file.toURL().toString(); | |||||
final Project result = (Project)projects.get( systemID ); | |||||
final URL systemID = file.toURL(); | |||||
final Project result = (Project)projects.get( systemID.toString() ); | |||||
if( null != result ) | if( null != result ) | ||||
{ | { | ||||
return result; | return result; | ||||
@@ -73,9 +74,10 @@ public class DefaultProjectBuilder | |||||
process( systemID, handler ); | process( systemID, handler ); | ||||
final Configuration configuration = handler.getConfiguration(); | final Configuration configuration = handler.getConfiguration(); | ||||
final DefaultProject project = buildProject( file, configuration ); | final DefaultProject project = buildProject( file, configuration ); | ||||
projects.put( systemID, project ); | |||||
projects.put( systemID.toString(), project ); | |||||
//build using all top-level attributes | //build using all top-level attributes | ||||
buildTopLevelProject( project, configuration, projects ); | buildTopLevelProject( project, configuration, projects ); | ||||
@@ -83,7 +85,7 @@ public class DefaultProjectBuilder | |||||
return project; | return project; | ||||
} | } | ||||
protected void process( final String systemID, | |||||
protected void process( final URL systemID, | |||||
final SAXConfigurationHandler handler ) | final SAXConfigurationHandler handler ) | ||||
throws Exception | throws Exception | ||||
{ | { | ||||
@@ -96,19 +98,7 @@ public class DefaultProjectBuilder | |||||
parser.setContentHandler( handler ); | parser.setContentHandler( handler ); | ||||
parser.setErrorHandler( handler ); | parser.setErrorHandler( handler ); | ||||
parser.parse( systemID ); | |||||
/* | |||||
// Create a transform factory instance. | |||||
final TransformerFactory factory = TransformerFactory.newInstance(); | |||||
// Create a transformer for the stylesheet. | |||||
final Transformer transformer = factory.newTransformer( new StreamSource(xslID) ); | |||||
final Result result = new SAXResult( handler ); | |||||
// Transform the source XML to System.out. | |||||
transformer.transform( new StreamSource(sourceID), result ); | |||||
*/ | |||||
parser.parse( systemID.toString() ); | |||||
} | } | ||||
/** | /** | ||||
@@ -0,0 +1,59 @@ | |||||
/* | |||||
* 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.myrmidon.components.builder; | |||||
import java.util.ArrayList; | |||||
import org.xml.sax.Attributes; | |||||
import org.xml.sax.SAXException; | |||||
import org.xml.sax.helpers.DefaultHandler; | |||||
/** | |||||
* Handler that reacts to PIs before first element. | |||||
* Have to do it this way as there doesn't seem to be a *safe* way | |||||
* of redirecting content handlers at runtime while using transformers. | |||||
* | |||||
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a> | |||||
*/ | |||||
public class ReactorPIHandler | |||||
extends DefaultHandler | |||||
{ | |||||
private ArrayList m_targets = new ArrayList(); | |||||
private ArrayList m_data = new ArrayList(); | |||||
public int getPICount() | |||||
{ | |||||
return m_targets.size(); | |||||
} | |||||
public String getTarget( final int index ) | |||||
{ | |||||
return (String)m_targets.get( index ); | |||||
} | |||||
public String getData( final int index ) | |||||
{ | |||||
return (String)m_data.get( index ); | |||||
} | |||||
public void processingInstruction( final String target, final String data ) | |||||
throws SAXException | |||||
{ | |||||
m_targets.add( target ); | |||||
m_data.add( data ); | |||||
} | |||||
public void startElement( final String uri, | |||||
final String localName, | |||||
final String qName, | |||||
final Attributes atts ) | |||||
throws SAXException | |||||
{ | |||||
//Workaround to stop SAX pipeline | |||||
throw new StopParsingException(); | |||||
} | |||||
} |
@@ -0,0 +1,24 @@ | |||||
/* | |||||
* 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.myrmidon.components.builder; | |||||
import org.xml.sax.SAXException; | |||||
/** | |||||
* Dummy exception to stop parsing "safely". | |||||
* | |||||
* @author <a href="mailto:donaldp@apache.org">Peter Donald</a> | |||||
*/ | |||||
class StopParsingException | |||||
extends SAXException | |||||
{ | |||||
public StopParsingException() | |||||
{ | |||||
super( "" ); | |||||
} | |||||
} |
@@ -7,13 +7,25 @@ | |||||
*/ | */ | ||||
package org.apache.myrmidon.components.builder; | package org.apache.myrmidon.components.builder; | ||||
import javax.xml.transform.Transformer; | |||||
import java.net.URL; | |||||
import java.io.InputStream; | |||||
import java.util.Properties; | |||||
import javax.xml.parsers.SAXParser; | |||||
import javax.xml.parsers.SAXParserFactory; | |||||
import org.apache.avalon.framework.configuration.SAXConfigurationHandler; | |||||
import org.apache.avalon.framework.parameters.Parameterizable; | |||||
import org.apache.avalon.framework.parameters.Parameters; | |||||
import org.xml.sax.SAXException; | |||||
import org.xml.sax.XMLReader; | |||||
import javax.xml.transform.TransformerFactory; | import javax.xml.transform.TransformerFactory; | ||||
import javax.xml.transform.Transformer; | |||||
import javax.xml.transform.TransformerConfigurationException; | |||||
import javax.xml.transform.sax.SAXResult; | import javax.xml.transform.sax.SAXResult; | ||||
import javax.xml.transform.stream.StreamResult; | |||||
import javax.xml.transform.sax.SAXSource; | |||||
import javax.xml.transform.sax.SAXTransformerFactory; | |||||
import javax.xml.transform.sax.TransformerHandler; | |||||
import javax.xml.transform.stream.StreamSource; | import javax.xml.transform.stream.StreamSource; | ||||
import org.apache.avalon.framework.configuration.SAXConfigurationHandler; | |||||
import org.apache.avalon.excalibur.io.FileUtil; | |||||
import javax.xml.transform.stream.StreamResult; | |||||
/** | /** | ||||
* Default implementation to construct project from a build file. | * Default implementation to construct project from a build file. | ||||
@@ -22,24 +34,173 @@ import org.apache.avalon.excalibur.io.FileUtil; | |||||
*/ | */ | ||||
public class XSLProjectBuilder | public class XSLProjectBuilder | ||||
extends DefaultProjectBuilder | extends DefaultProjectBuilder | ||||
implements Parameterizable | |||||
{ | { | ||||
protected void process( final String sourceID, | |||||
private final static String PARAM_EXCEPTION = | |||||
"Malformed PI: expected <?xsl-param name=\"foo\" value=\"bar\"?>"; | |||||
private final static String PARAMS_EXCEPTION = | |||||
"Malformed PI: expected <?xsl-params location=\"myparams.properties\"?>"; | |||||
private final static String STYLE_EXCEPTION = | |||||
"Malformed PI: expected <?xsl-params href=\"mystylesheet.xsl\"?>"; | |||||
private Parameters m_parameters; | |||||
private URL m_systemID; | |||||
public void parameterize( final Parameters parameters ) | |||||
{ | |||||
m_parameters = parameters; | |||||
} | |||||
protected void process( final URL sourceID, | |||||
final SAXConfigurationHandler handler ) | final SAXConfigurationHandler handler ) | ||||
throws Exception | throws Exception | ||||
{ | { | ||||
final String xslSheet = FileUtil.removeExtension( sourceID ) + ".xsl"; | |||||
final SAXParserFactory saxParserFactory = SAXParserFactory.newInstance(); | |||||
final SAXParser saxParser = saxParserFactory.newSAXParser(); | |||||
final XMLReader reader = saxParser.getXMLReader(); | |||||
reader.setFeature( "http://xml.org/sax/features/validation", false ); | |||||
reader.setErrorHandler( handler ); | |||||
final ReactorPIHandler reactorHandler = new ReactorPIHandler(); | |||||
reader.setContentHandler( reactorHandler ); | |||||
try { reader.parse( sourceID.toString() ); } | |||||
catch( final StopParsingException spe ) | |||||
{ | |||||
//Ignore me | |||||
} | |||||
Transformer transformer = null; | |||||
final int size = reactorHandler.getPICount(); | |||||
for( int i = 0; i < size; i++ ) | |||||
{ | |||||
final String target = reactorHandler.getTarget( i ); | |||||
final String data = reactorHandler.getData( i ); | |||||
if( target.equals( "xsl-param" ) ) handleParameter( data ); | |||||
else if( target.equals( "xsl-params" ) ) handleParameters( data, sourceID ); | |||||
else if( target.equals( "xsl-stylesheet" ) ) | |||||
{ | |||||
if( null != transformer ) | |||||
{ | |||||
throw new SAXException( "Build file can not contain " + | |||||
"two xsl-stylesheet PIs" ); | |||||
} | |||||
final TransformerFactory factory = TransformerFactory.newInstance(); | |||||
final String stylesheet = getStylesheet( data, sourceID ); | |||||
transformer = factory.newTransformer( new StreamSource( stylesheet ) ); | |||||
} | |||||
} | |||||
if( null == transformer ) | |||||
{ | |||||
reader.setContentHandler( handler ); | |||||
reader.parse( sourceID.toString() ); | |||||
} | |||||
else | |||||
{ | |||||
final SAXResult result = new SAXResult( handler ); | |||||
transformer.transform( new StreamSource( sourceID.toString() ), result ); | |||||
} | |||||
} | |||||
private void handleParameter( final String data ) | |||||
throws SAXException | |||||
{ | |||||
int index = data.indexOf( '\"' ); | |||||
if( -1 == index ) | |||||
{ | |||||
throw new SAXException( PARAM_EXCEPTION ); | |||||
} | |||||
index = data.indexOf( '\"', index + 1 ); | |||||
if( -1 == index ) | |||||
{ | |||||
throw new SAXException( PARAM_EXCEPTION ); | |||||
} | |||||
// Create a transform factory instance. | |||||
final TransformerFactory factory = TransformerFactory.newInstance(); | |||||
//split between two "attributes" occurs on index | |||||
final String[] name = parseAttribute( data.substring( 0, index + 1 ) ); | |||||
final String[] value = parseAttribute( data.substring( index + 1 ).trim() ); | |||||
if( !name[ 0 ].equals( "name" ) || !value[ 0 ].equals( "value" ) ) | |||||
{ | |||||
throw new SAXException( PARAM_EXCEPTION ); | |||||
} | |||||
// Create a transformer for the stylesheet. | |||||
final Transformer transformer = factory.newTransformer( new StreamSource( xslSheet ) ); | |||||
m_parameters.setParameter( name[ 1 ], value[ 1 ] ); | |||||
} | |||||
final SAXResult result = new SAXResult( handler ); | |||||
private void handleParameters( final String data, final URL baseSource ) | |||||
throws SAXException | |||||
{ | |||||
final String[] params = parseAttribute( data ); | |||||
if( !params[ 0 ].equals( "location" ) ) | |||||
{ | |||||
throw new SAXException( PARAMS_EXCEPTION ); | |||||
} | |||||
try | |||||
{ | |||||
final Properties properties = new Properties(); | |||||
final URL url = new URL( baseSource, params[ 1 ] ); | |||||
final InputStream input = url.openStream(); | |||||
properties.load( input ); | |||||
final Parameters parameters = Parameters.fromProperties( properties ); | |||||
m_parameters.merge( parameters ); | |||||
} | |||||
catch( final Exception e ) | |||||
{ | |||||
throw new SAXException( "Error loading parameters: " + e ); | |||||
} | |||||
} | |||||
private String getStylesheet( final String data, final URL baseSource ) | |||||
throws SAXException | |||||
{ | |||||
final String[] stylesheet = parseAttribute( data ); | |||||
if( !stylesheet[ 0 ].equals( "href" ) ) | |||||
{ | |||||
throw new SAXException( STYLE_EXCEPTION ); | |||||
} | |||||
try { return new URL( baseSource, stylesheet[ 1 ] ).toString(); } | |||||
catch( final Exception e ) | |||||
{ | |||||
throw new SAXException( "Error locating stylesheet '" + stylesheet[ 1 ] + | |||||
"' due to " + e ); | |||||
} | |||||
} | |||||
private String[] parseAttribute( final String data ) | |||||
throws SAXException | |||||
{ | |||||
//name="value" | |||||
int index = data.indexOf( '=' ); | |||||
if( -1 == index ) | |||||
{ | |||||
throw new SAXException( "Expecting an attribute but received '" + | |||||
data + "'" ); | |||||
} | |||||
//Make a debug option for this | |||||
//transformer.transform( new StreamSource( sourceID ), new StreamResult( System.out ) ); | |||||
final int size = data.length(); | |||||
if( '\"' != data.charAt( index + 1 ) || | |||||
'\"' != data.charAt( size - 1 ) || | |||||
size - 1 == index ) | |||||
{ | |||||
throw new SAXException( "Expecting the value of attribute " + | |||||
data.substring( 0, index ) + | |||||
" to be enclosed in quotes" ); | |||||
} | |||||
final String[] result = new String[ 2 ]; | |||||
result[ 0 ] = data.substring( 0, index ); | |||||
result[ 1 ] = data.substring( index + 2, size - 1 ); | |||||
transformer.transform( new StreamSource( sourceID ), result ); | |||||
return result; | |||||
} | } | ||||
} | } |
@@ -76,6 +76,18 @@ public class Condition | |||||
return result; | return result; | ||||
} | } | ||||
public String toString() | |||||
{ | |||||
if( isIfCondition() ) | |||||
{ | |||||
return "if='" + getCondition() + "'"; | |||||
} | |||||
else | |||||
{ | |||||
return "unless='" + getCondition() + "'"; | |||||
} | |||||
} | |||||
} | } | ||||
@@ -80,7 +80,9 @@ public class Pattern | |||||
public String toString() | public String toString() | ||||
{ | { | ||||
return "Pattern['" + m_name + "'," + m_condition + "]" ; | |||||
String result = "Pattern['" + m_name + "',"; | |||||
if( null != m_condition ) result = result + m_condition; | |||||
return result + "]"; | |||||
} | } | ||||
/** | /** | ||||
@@ -54,6 +54,7 @@ Legal: | |||||
<target name="ant-call-test"> | <target name="ant-call-test"> | ||||
<!-- test elided until we decide scope and necessity of ant-call --> | <!-- test elided until we decide scope and necessity of ant-call --> | ||||
<echo message="AntCall test elided until we decide scope and necessity of ant-call"/> | |||||
<!-- | <!-- | ||||
<ant-call target="ant-call-test-target"> | <ant-call target="ant-call-test-target"> | ||||
<param name="blah" value="blah-value" /> | <param name="blah" value="blah-value" /> | ||||
@@ -0,0 +1,120 @@ | |||||
<?xml version="1.0"?> | |||||
<?xsl-param name="foo" value="bar"?> | |||||
<?xsl-stylesheet href="template-simple.xsl"?> | |||||
<!-- next is ignored --> | |||||
<?xsl-params-old location="foo.properties"?> | |||||
<!-- | |||||
============================================================================== | |||||
Sample build file | |||||
Authors: | |||||
Peter Donald <donaldp@apache.org> | |||||
Legal: | |||||
Copyright (c) 2000 The Apache Software Foundation. All Rights Reserved. | |||||
============================================================================== | |||||
--> | |||||
<project name="MySample" default="main" basedir="." | |||||
xmlns:ant="http://jakarta.apache.org/2001/Ant/ant" | |||||
xmlns:doc="http://jakarta.apache.org/2001/Ant/doc" | |||||
xmlns:blee="http://jakarta.apache.org/2001/Ant/blee" > | |||||
<?xsl-params ignored="true"?> | |||||
<projectref name="prim" location="primitive-tests.ant" /> | |||||
<import library="core.atl" /> | |||||
<property name="year" value="2000"/> | |||||
<target name="main" depends="typedef-test, converterdef-test, datatype-test, namespace-test, ant1-tasklib-test" /> | |||||
<target name="all" depends="property-test, typedef-test, converterdef-test, ant-call-test, datatype-test, namespace-test, ant1-tasklib-test, prim->main" /> | |||||
<!-- | |||||
<register-tasklib lib="../../dist/lib/core.atl" /> | |||||
--> | |||||
<target name="property-test"> | |||||
<property name="blah" value="fred" /> | |||||
<property name="${blah}" value="barney" /> | |||||
<echo message="Doing the funky Echo with ${blah} ${fred} Year=${year}!"/> | |||||
</target> | |||||
<target name="typedef-test"> | |||||
<typedef name="echo2" | |||||
type="task" | |||||
classname="org.apache.myrmidon.libs.core.Echo" | |||||
lib="../../dist/lib/core.atl" /> | |||||
<echo2 message="Luke to Echo base. Can you hear me?"/> | |||||
</target> | |||||
<target name="converterdef-test"> | |||||
<converterdef classname="org.apache.myrmidon.libs.core.StringToClassConverter" | |||||
source-type="java.lang.String" | |||||
destination-type="java.lang.Class" | |||||
lib="../../dist/lib/core.atl" /> | |||||
</target> | |||||
<target name="ant-call-test"> | |||||
<!-- test elided until we decide scope and necessity of ant-call --> | |||||
<echo message="AntCall test elided until we decide scope and necessity of ant-call"/> | |||||
<!-- | |||||
<ant-call target="ant-call-test-target"> | |||||
<param name="blah" value="blah-value" /> | |||||
</ant-call> | |||||
--> | |||||
</target> | |||||
<target name="ant-call-test-target"> | |||||
<echo message="This should fail ...."/> | |||||
<echo message="${blah}"/> | |||||
<echo message="Whoa - it no fail. You used ant-call to call me and set param blah!"/> | |||||
</target> | |||||
<target name="datatype-test"> | |||||
<property name="foo"> | |||||
<pattern name="*.java"/> | |||||
</property> | |||||
<pattern id="foo2" name="*.java" if="..." /> | |||||
<echo message="foo=${foo}" /> | |||||
<echo message="foo2=${foo2}" /> | |||||
</target> | |||||
<target name="namespace-test"> | |||||
<!-- ant and doc are built in namespaces --> | |||||
<echo ant:fail-on-error="true" message="Some random message"> | |||||
<doc:description> | |||||
Test case for aspects | |||||
</doc:description> | |||||
<ant:some-element some-attribute="blah"/> | |||||
</echo> | |||||
<!-- load facility for blee: namespace --> | |||||
<facility namespace="blee"> | |||||
<noop/> | |||||
</facility> | |||||
<echo blee:some-param="blah" message="Blee namespace test successful!"/> | |||||
</target> | |||||
<target name="ant1-tasklib-test"> | |||||
<ant1-tasklib prefix="a1-" lib="../../dist/lib/ant1-compat.jar"/> | |||||
<a1-echo message="Boo!" /> | |||||
<a1-mkdir dir="../../dist/test"/> | |||||
<a1-copy file="../../tools/lib/ant.jar" tofile="../../dist/test/ant1-compat.jar" /> | |||||
</target> | |||||
</project> |
@@ -1,9 +1,5 @@ | |||||
<ant-lib> | <ant-lib> | ||||
<types> | <types> | ||||
<task name="ant1-tasklib" classname="org.apache.myrmidon.libs.ant1.Ant1Tasklib" /> | <task name="ant1-tasklib" classname="org.apache.myrmidon.libs.ant1.Ant1Tasklib" /> | ||||
</types> | </types> | ||||
</ant-lib> | </ant-lib> |
@@ -1,3 +1,3 @@ | |||||
Manifest-Version: 1.0 | Manifest-Version: 1.0 | ||||
Main-Class: org.apache.myrmidon.frontends.CLIMain | Main-Class: org.apache.myrmidon.frontends.CLIMain | ||||
Created-By: Apache Ant Project | |||||
Created-By: Apache Ant Project |
@@ -1,14 +1,12 @@ | |||||
<ant-lib> | <ant-lib> | ||||
<types> | <types> | ||||
<!-- core tasks for operation --> | <!-- core tasks for operation --> | ||||
<task name="facility" classname="org.apache.myrmidon.libs.runtime.Facility" /> | <task name="facility" classname="org.apache.myrmidon.libs.runtime.Facility" /> | ||||
<task name="typedef" classname="org.apache.myrmidon.libs.runtime.TypeDef" /> | <task name="typedef" classname="org.apache.myrmidon.libs.runtime.TypeDef" /> | ||||
<task name="converterdef" classname="org.apache.myrmidon.libs.runtime.ConverterDef" /> | <task name="converterdef" classname="org.apache.myrmidon.libs.runtime.ConverterDef" /> | ||||
<task name="import" classname="org.apache.myrmidon.libs.runtime.Import" /> | <task name="import" classname="org.apache.myrmidon.libs.runtime.Import" /> | ||||
<task name="ant-call" classname="org.apache.myrmidon.libs.runtime.AntCall" /> | |||||
<!--<task name="ant-call" classname="org.apache.myrmidon.libs.runtime.AntCall" />--> | |||||
</types> | </types> | ||||
</ant-lib> | </ant-lib> |
@@ -1,13 +1,9 @@ | |||||
<ant-lib> | |||||
<ant-lib> | |||||
<types> | <types> | ||||
<!-- tasks to test operation of engine --> | <!-- tasks to test operation of engine --> | ||||
<task name="prim-test" classname="org.apache.myrmidon.libs.selftest.PrimitiveTypesTest" /> | <task name="prim-test" classname="org.apache.myrmidon.libs.selftest.PrimitiveTypesTest" /> | ||||
<task name="sub-elements-test" classname="org.apache.myrmidon.libs.selftest.SubElementTest" /> | <task name="sub-elements-test" classname="org.apache.myrmidon.libs.selftest.SubElementTest" /> | ||||
<task name="conf-test" classname="org.apache.myrmidon.libs.selftest.ConfigurationTest" /> | <task name="conf-test" classname="org.apache.myrmidon.libs.selftest.ConfigurationTest" /> | ||||
<task name="content-test" classname="org.apache.myrmidon.libs.selftest.ContentTest" /> | <task name="content-test" classname="org.apache.myrmidon.libs.selftest.ContentTest" /> | ||||
</types> | </types> | ||||
</ant-lib> | </ant-lib> |