diff options
Diffstat (limited to 'framework/src/ant/apache-ant-1.9.6/manual/Types/custom-programming.html')
-rw-r--r-- | framework/src/ant/apache-ant-1.9.6/manual/Types/custom-programming.html | 415 |
1 files changed, 415 insertions, 0 deletions
diff --git a/framework/src/ant/apache-ant-1.9.6/manual/Types/custom-programming.html b/framework/src/ant/apache-ant-1.9.6/manual/Types/custom-programming.html new file mode 100644 index 00000000..96bade33 --- /dev/null +++ b/framework/src/ant/apache-ant-1.9.6/manual/Types/custom-programming.html @@ -0,0 +1,415 @@ +<!-- + 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. +--> +<html> + <head> + <meta http-equiv="Content-Language" content="en-us"></meta> +<link rel="stylesheet" type="text/css" href="../stylesheets/style.css"> +<title>Custom Components</title> + </head> + <body> + <h2>Custom Components</h2> + <h3>Overview</h3> + <p> + Custom components are conditions, selectors, filters and other + objects that are defined outside Apache Ant core. + </p> + <p> + In Ant 1.6 custom conditions, selectors and filters has + been overhauled. + </p> + <p> + It is now possible to define custom conditions, selectors and filters + that behave like Ant Core components. + This is achieved by allowing datatypes defined in build scripts + to be used as custom components if the class of the datatype + is compatible, or has been adapted by an adapter class. + </p> + <p> + The old methods of defining custom components are still supported. + </p> + <h3>Definition and use</h3> + <p> + A custom component is a normal Java class that implements a particular + interface or extends a particular class, or has been adapted to the + interface or class. + </p> + <p> + It is exactly like writing a + <a href="../develop.html#writingowntask">custom task</a>. + One defines attributes and nested elements by writing <i>setter</i> + methods and <i>add</i> methods. + </p> + <p> + After the class has been written, it is added to the ant system + by using <code><typedef></code>. + </p> + <h3><a name="customconditions">Custom Conditions</a></h3> + <p> + Custom conditions are datatypes that implement + <code>org.apache.tools.ant.taskdefs.condition.Condition</code>. + For example a custom condition that returns true if a + string is all upper case could be written as: + </p> + <blockquote> + <pre> +package com.mydomain; + +import org.apache.tools.ant.BuildException; +import org.apache.tools.ant.taskdefs.condition.Condition; + +public class AllUpperCaseCondition implements Condition { + private String value; + + // The setter for the "value" attribute + public void setValue(String value) { + this.value = value; + } + + // This method evaluates the condition + public boolean eval() { + if (value == null) { + throw new BuildException("value attribute is not set"); + } + return value.toUpperCase().equals(value); + } +} + </pre> + </blockquote> + + <p> + Adding the condition to the system is achieved as follows: + </p> + <blockquote> + <pre> +<typedef + name="alluppercase" + classname="com.mydomain.AllUpperCaseCondition" + classpath="${mydomain.classes}"/> + </pre> + </blockquote> + <p> + This condition can now be used wherever a Core Ant condition + is used. + </p> + <blockquote> + <pre> +<condition property="allupper"> + <alluppercase value="THIS IS ALL UPPER CASE"/> +</condition> + </pre> + </blockquote> + <h3><a name="customselectors">Custom Selectors</a></h3> + <p> + Custom selectors are datatypes that implement + <code>org.apache.tools.ant.types.selectors.FileSelector</code>. + </p> + <p>There is only one method required. + <code>public boolean isSelected(File basedir, String filename, + File file)</code>. + It returns true + or false depending on whether the given file should be + selected or not. + </p> + <p> + An example of a custom selection that selects filenames ending + in ".java" would be: + </p> + <blockquote> + <pre> +package com.mydomain; +import java.io.File; +import org.apache.tools.ant.types.selectors.FileSelector; +public class JavaSelector implements FileSelector { + public boolean isSelected(File b, String filename, File f) { + return filename.toLowerCase().endsWith(".java"); + } +} + </pre> + </blockquote> + <p> + Adding the selector to the system is achieved as follows: + </p> + <blockquote> + <pre> +<typedef + name="javaselector" + classname="com.mydomain.JavaSelector" + classpath="${mydomain.classes}"/> + </pre> + </blockquote> + <p> + This selector can now be used wherever a Core Ant selector + is used, for example: + </p> + <blockquote> + <pre> +<copy todir="to"> + <fileset dir="src"> + <javaselector/> + </fileset> +</copy> + </pre> + </blockquote> + + <p> + One may use + <code>org.apache.tools.ant.types.selectors.BaseSelector</code>, + a convenience class that provides reasonable default + behaviour. + It has some predefined behaviours you can take advantage + of. Any time you encounter a problem when setting attributes or + adding tags, you can call setError(String errmsg) and the class + will know that there is a problem. Then, at the top of your + <code>isSelected()</code> method call <code>validate()</code> and + a BuildException will be thrown with the contents of your error + message. The <code>validate()</code> method also gives you a + last chance to check your settings for consistency because it + calls <code>verifySettings()</code>. Override this method and + call <code>setError()</code> within it if you detect any + problems in how your selector is set up. + </p> + <p> + To write custom selector containers one should extend + <code>org.apache.tools.ant.types.selectors.BaseSelectorContainer</code>. + Implement the + <code>public boolean isSelected(File baseDir, String filename, File file)</code> + method to do the right thing. Chances are you'll want to iterate + over the selectors under you, so use + <code>selectorElements()</code> to get an iterator that will do + that. + </p> + <p> + For example to create a selector container that will select files + if a certain number of contained selectors select, one could write + a selector as follows: + </p> + <blockquote> + <pre> +public class MatchNumberSelectors extends BaseSelectorContainer { + private int number = -1; + public void setNumber(int number) { + this.number = number; + } + public void verifySettings() { + if (number < 0) { + throw new BuildException("Number attribute should be set"); + } + } + public boolean isSelected(File baseDir, String filename, File file) { + validate(); + int numberSelected = 0; + for (Enumeration e = selectorElements(); e.hasNextElement();) { + FileSelector s = (FileSelector) e.nextElement(); + if (s.isSelected(baseDir, filename, file)) { + numberSelected++; + } + } + return numberSelected == number; + } +} + </pre> + </blockquote> + <p> + To define and use this selector one could do: + </p> + <blockquote> + <pre> +<typedef name="numberselected" + classname="com.mydomain.MatchNumberSelectors"/> +... +<fileset dir="${src.path}"> + <numberselected number="2"> + <contains text="script" casesensitive="no"/> + <size value="4" units="Ki" when="more"/> + <javaselector/> + </numberselected> +</fileset> + </pre> + </blockquote> + <p> + <i>The custom selector</i> + </p> + <p> + The custom selector was the pre ant 1.6 way of defining custom selectors. + This method is still supported for backward compatibility. + </p> + <p>You can write your own selectors and use them within the selector + containers by specifying them within the <code><custom></code> tag.</p> + + <p>To create a new Custom Selector, you have to create a class that + implements + <code>org.apache.tools.ant.types.selectors.ExtendFileSelector</code>. + The easiest way to do that is through the convenience base class + <code>org.apache.tools.ant.types.selectors.BaseExtendSelector</code>, + which provides all of the methods for supporting + <code><param></code> tags. First, override the + <code>isSelected()</code> method, and optionally the + <code>verifySettings()</code> method. If your custom + selector requires parameters to be set, you can also override + the <code>setParameters()</code> method and interpret the + parameters that are passed in any way you like. Several of the + core selectors demonstrate how to do that because they can + also be used as custom selectors.</p> + + + <p>Once that is written, you include it in your build file by using + the <code><custom></code> tag. + </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">classname</td> + <td valign="top">The name of your class that implements + <code>org.apache.tools.ant.types.selectors.FileSelector</code>. + </td> + <td valign="top" align="center">Yes</td> + </tr> + <tr> + <td valign="top">classpath</td> + <td valign="top">The classpath to use in order to load the + custom selector class. If neither this classpath nor the + classpathref are specified, the class will be + loaded from the classpath that Ant uses. + </td> + <td valign="top" align="center">No</td> + </tr> + <tr> + <td valign="top">classpathref</td> + <td valign="top">A reference to a classpath previously + defined. If neither this reference nor the + classpath above are specified, the class will be + loaded from the classpath that Ant uses. + </td> + <td valign="top" align="center">No</td> + </tr> + </table> + + <p>Here is how you use <code><custom></code> to + use your class as a selector: + </p> + + <blockquote><pre> +<fileset dir="${mydir}" includes="**/*"> + <custom classname="com.mydomain.MySelector"> + <param name="myattribute" value="myvalue"/> + </custom> +</fileset> + </pre></blockquote> + + + <p>The core selectors that can also be used as custom selectors + are</p> + + <ul> + <li><a href="selectors.html#containsselect">Contains Selector</a> with + classname <code>org.apache.tools.ant.types.selectors.ContainsSelector</code> + </li> + <li><a href="selectors.html#dateselect">Date Selector</a> with + classname <code>org.apache.tools.ant.types.selectors.DateSelector</code> + </li> + <li><a href="selectors.html#depthselect">Depth Selector</a> with + classname <code>org.apache.tools.ant.types.selectors.DepthSelector</code> + </li> + <li><a href="selectors.html#filenameselect">Filename Selector</a> with + classname <code>org.apache.tools.ant.types.selectors.FilenameSelector</code> + </li> + <li><a href="selectors.html#sizeselect">Size Selector</a> with + classname <code>org.apache.tools.ant.types.selectors.SizeSelector</code> + </li> + </ul> + + <p>Here is the example from the Depth Selector section rewritten + to use the selector through <code><custom></code>.</p> + + <blockquote><pre> +<fileset dir="${doc.path}" includes="**/*"> + <custom classname="org.apache.tools.ant.types.selectors.DepthSelector"> + <param name="max" value="1"/> + </custom> +</fileset> + </pre></blockquote> + + <p>Selects all files in the base directory and one directory below + that.</p> + + <h3><a name="filterreaders">Custom Filter Readers</a></h3> + <p> + Custom filter readers selectors are datatypes that implement + <code>org.apache.tools.ant.types.filters.ChainableReader</code>. + </p> + <p>There is only one method required. + <code>Reader chain(Reader reader)</code>. + This returns a reader that filters input from the specified + reader. + </p> + <p> + For example a filterreader that removes every second character + could be: + </p> + <blockquote> + <pre> +public class RemoveOddCharacters implements ChainableReader { + public Reader chain(Reader reader) { + return new BaseFilterReader(reader) { + int count = 0; + public int read() throws IOException { + while (true) { + int c = in.read(); + if (c == -1) { + return c; + } + count++; + if ((count % 2) == 1) { + return c; + } + } + } + } + } +} + </pre> + </blockquote> + <p> + For line oriented filters it may be easier to extend + <code>ChainableFilterReader</code> an inner class of + <code>org.apache.tools.ant.filters.TokenFilter</code>. + </p> + <p> + For example a filter that appends the line number could be + </p> + <blockquote> + <pre> +public class AddLineNumber extends ChainableReaderFilter { + private void lineNumber = 0; + public String filter(String string) { + lineNumber++; + return "" + lineNumber + "\t" + string; + } +} + </pre> + </blockquote> + + + <hr></hr> + </body> +</html> + |