Browse Source

Rewritten part of the regexp stuff, adding substitution and options.

New optional replaceregexp tasks that takes advantage of it.

Submitted by:	Matthew Inger <matti@sedonacorp.com>

This doesn't really work (but doesn't break anything either), but I
wanted to get the stuff committed now, I will put work into it
tomorrow.  See mail to the list for details.


git-svn-id: https://svn.apache.org/repos/asf/ant/core/trunk@269820 13f79535-47bb-0310-9956-ffa450edef68
master
Stefan Bodewig 23 years ago
parent
commit
ffea0a9f74
19 changed files with 1596 additions and 59 deletions
  1. +2
    -0
      WHATSNEW
  2. +17
    -9
      build.xml
  3. +2
    -0
      src/etc/testcases/taskdefs/optional/replaceregexp.properties
  4. +19
    -0
      src/etc/testcases/taskdefs/optional/replaceregexp.xml
  5. +1
    -0
      src/main/org/apache/tools/ant/taskdefs/defaults.properties
  6. +423
    -0
      src/main/org/apache/tools/ant/taskdefs/optional/ReplaceRegExp.java
  7. +161
    -0
      src/main/org/apache/tools/ant/types/RegularExpression.java
  8. +129
    -0
      src/main/org/apache/tools/ant/types/Substitution.java
  9. +80
    -18
      src/main/org/apache/tools/ant/util/regexp/JakartaOroMatcher.java
  10. +99
    -0
      src/main/org/apache/tools/ant/util/regexp/JakartaOroRegexp.java
  11. +59
    -13
      src/main/org/apache/tools/ant/util/regexp/JakartaRegexpMatcher.java
  12. +88
    -0
      src/main/org/apache/tools/ant/util/regexp/JakartaRegexpRegexp.java
  13. +73
    -14
      src/main/org/apache/tools/ant/util/regexp/Jdk14RegexpMatcher.java
  14. +106
    -0
      src/main/org/apache/tools/ant/util/regexp/Jdk14RegexpRegexp.java
  15. +75
    -0
      src/main/org/apache/tools/ant/util/regexp/Regexp.java
  16. +113
    -0
      src/main/org/apache/tools/ant/util/regexp/RegexpFactory.java
  17. +55
    -3
      src/main/org/apache/tools/ant/util/regexp/RegexpMatcher.java
  18. +22
    -2
      src/main/org/apache/tools/ant/util/regexp/RegexpMatcherFactory.java
  19. +72
    -0
      src/main/org/apache/tools/ant/util/regexp/RegexpUtil.java

+ 2
- 0
WHATSNEW View File

@@ -17,6 +17,8 @@ Fixed bugs:
Other changes:
--------------

* New task replaceregexp

* The attributes zipfile, jarfile, warfile and earfile (from the Zip,
Jar, War and Ear tasks) have been deprecated and superseded by a
new attribute "file".


+ 17
- 9
build.xml View File

@@ -174,6 +174,14 @@
classpathref="classpath"/>
</and>
</condition>

<condition property="some.regexp.support">
<or>
<isset property="jdk1.4+" />
<isset property="jakarta.regexp.present" />
<isset property="jakarta.oro.present" />
</or>
</condition>
</target>

<!--
@@ -210,11 +218,11 @@
deprecation="${deprecation}"
optimize="${optimize}" >
<classpath refid="classpath" />
<exclude name="${ant.package}/util/regexp/JakartaRegexpMatcher.java"
<exclude name="${ant.package}/util/regexp/JakartaRegexp*.java"
unless="jakarta.regexp.present" />
<exclude name="${ant.package}/util/regexp/JakartaOroMatcher.java"
<exclude name="${ant.package}/util/regexp/JakartaOro*.java"
unless="jakarta.oro.present" />
<exclude name="${ant.package}/util/regexp/Jdk14RegexpMatcher.java"
<exclude name="${ant.package}/util/regexp/Jdk14Regexp*.java"
unless="jdk1.4+" />
<exclude name="${ant.package}/AntSecurityManager.java"
unless="jdk1.2+" />
@@ -642,11 +650,11 @@

<exclude name="org/apache/tools/ant/taskdefs/optional/ANTLRTest.java"
unless="antlr.present" />
<exclude name="org/apache/tools/ant/util/regexp/JakartaRegexpMatcherTest.java"
<exclude name="org/apache/tools/ant/util/regexp/JakartaRegexp*Test.java"
unless="jakarta.regexp.present" />
<exclude name="org/apache/tools/ant/util/regexp/JakartaOroMatcherTest.java"
<exclude name="org/apache/tools/ant/util/regexp/JakartaOro*Test.java"
unless="jakarta.oro.present" />
<exclude name="org/apache/tools/ant/util/regexp/Jdk14RegexpMatcherTest.java"
<exclude name="org/apache/tools/ant/util/regexp/Jdk14Regexp*Test.java"
unless="jdk1.4+" />
<exclude name="org/apache/tools/ant/taskdefs/optional/sitraka/*.java"
unless="jakarta.oro.present" />
@@ -712,11 +720,11 @@
<!-- only run these tests if their required libraries are installed -->
<exclude name="org/apache/tools/ant/taskdefs/optional/ANTLRTest.java"
unless="antlr.present" />
<exclude name="org/apache/tools/ant/util/regexp/JakartaRegexpMatcherTest.java"
<exclude name="org/apache/tools/ant/util/regexp/JakartaRegexp*Test.java"
unless="jakarta.regexp.present" />
<exclude name="org/apache/tools/ant/util/regexp/JakartaOroMatcherTest.java"
<exclude name="org/apache/tools/ant/util/regexp/JakartaOro*Test.java"
unless="jakarta.oro.present" />
<exclude name="org/apache/tools/ant/util/regexp/Jdk14RegexpMatcherTest.java"
<exclude name="org/apache/tools/ant/util/regexp/Jdk14Regexp*Test.java"
unless="jdk1.4+" />
<exclude name="${optional.package}/ide/VAJExportTest.java" unless="vaj.present" />
<exclude name="${optional.package}/sitraka/*.java" unless="jakarta.oro.present" />


+ 2
- 0
src/etc/testcases/taskdefs/optional/replaceregexp.properties View File

@@ -0,0 +1,2 @@
OldAbc=Def


+ 19
- 0
src/etc/testcases/taskdefs/optional/replaceregexp.xml View File

@@ -0,0 +1,19 @@
<project name="test" default="def" basedir=".">

<target name="setup">
<copy file="replaceregexp.properties" tofile="test.properties" />
</target>

<target name="def" depends="setup">
<replaceregexp file="test.properties" byline="true">
<regularexpression pattern="Old(.*)=(.*)" />
<substitution expression="NewProp=\1\2" />
</replaceregexp>
</target>

<target name="cleanup">
<delete file="test.properties" />
</target>

</project>


+ 1
- 0
src/main/org/apache/tools/ant/taskdefs/defaults.properties View File

@@ -123,6 +123,7 @@ jpcovmerge=org.apache.tools.ant.taskdefs.optional.sitraka.CovMerge
jpcovreport=org.apache.tools.ant.taskdefs.optional.sitraka.CovReport
p4add=org.apache.tools.ant.taskdefs.optional.perforce.P4Add
jspc=org.apache.tools.ant.taskdefs.optional.jsp.JspC
replaceregexp=org.apache.tools.ant.taskdefs.optional.ReplaceRegExp

# deprecated ant tasks (kept for back compatibility)
javadoc2=org.apache.tools.ant.taskdefs.Javadoc


+ 423
- 0
src/main/org/apache/tools/ant/taskdefs/optional/ReplaceRegExp.java View File

@@ -0,0 +1,423 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.taskdefs.optional;

import org.apache.tools.ant.BuildException;
import org.apache.tools.ant.DirectoryScanner;
import org.apache.tools.ant.Project;
import org.apache.tools.ant.Task;
import org.apache.tools.ant.util.regexp.Regexp;
import org.apache.tools.ant.types.RegularExpression;
import org.apache.tools.ant.types.Substitution;
import org.apache.tools.ant.types.FileSet;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.io.LineNumberReader;
import java.io.PrintWriter;
import java.util.Vector;

/***
* <pre>
* Task to do regular expression string replacements in a text
* file. The input file(s) must be able to be properly processed by
* a Reader instance. That is, they must be text only, no binary.
*
* The syntax of the regular expression depends on the implemtation that
* you choose to use. The system property <code>ant.regexp.regexpimpl</code>
* will be the classname of the implementation that will be used (the default
* is <code>org.apache.tools.ant.util.regexp.JakartaOroRegexp</code> and
* requires the Jakarta Oro Package).
*
* <pre>
* For jdk <= 1.3, there are two available implementations:
* org.apache.tools.ant.util.regexp.JakartaOroRegexp (the default)
* Requires the jakarta-oro package
*
* org.apache.tools.ant.util.regexp.JakartaRegexpRegexp
* Requires the jakarta-regexp package
*
* For jdk <= 1.4, and additional implementation is available:
* org.apache.tools.ant.util.regexp.Jdk14RegexpRegexp
* Requires the jdk 1.4 built in regular expression package.
* </pre>
*
* Usage:
*
* Task declaration in the project:
*
* &lt;taskdef name="replaceregexp" class="com.sedona.ant.taskdef.ReplaceRegExp" /&gt;
*
* Call Syntax:
*
* &lt;replaceregexp file="file"
* match="pattern"
* replace="pattern"
* flags="options"?
* byline="true|false"? &gt;
* regularexpression?
* substitution?
* fileset*
* &lt;/replaceregexp&gt;
*
* NOTE: You must have either the file attribute specified, or at least one fileset subelement
* to operation on. You may not have the file attribute specified if you nest fileset elements
* inside this task. Also, you cannot specify both match and a regular expression subelement at
* the same time, nor can you specify the replace attribute and the substitution subelement at
* the same time.
*
* Attributes:
*
* file --> A single file to operation on (mutually exclusive with the fileset subelements)
* match --> The Perl5 Regular expression to match (see perl5 documentation)
* replace --> The Perl5 Expression replacement string (see perl5 documentation)
* flags --> The Perl5 options to give to the replacement (see perl5 documentation for full list)
* g = Substitute all occurrences. default is to replace only the first one
* i = Case insensitive match
*
* byline --> Should this file be processed a single line at a time (default is false)
* "true" indicates to perform replacement on a line by line basis
* "false" indicates to perform replacement on the whole file at once.
*
* Example:
*
* The following call could be used to replace an old property name in a ".properties"
* file with a new name. In the replace attribute, you can refer to any part of the
* match expression in parenthesis using the syntax appropriate for the specified
* implementation ('$$1' for org.apache.tools.ant.util.regexp.JakartaOroRegexp).
*
* &lt;replaceregexp file="test.properties"
* match="MyProperty=(.*)"
* replace="NewProperty=$$1"
* byline="true" /&gt;
*
* </pre>
*
* @author <a href="mailto:mattinger@mindless.com">Matthew Inger</a>
*/
public class ReplaceRegExp extends Task
{
// Don't extend SedonaTaskContainer until we can delay building of
// the subtasks so variable of the current token works.

private File file;
private String flags;
private boolean byline;
private Vector filesets; // Keep jdk 1.1 compliant so others can use this
private RegularExpression regex;
private Substitution subs;

/***
* Default Constructor
*/
public ReplaceRegExp()
{
super();
this.file = null;
this.filesets = new Vector();
this.flags = "";
this.byline = false;

this.regex = null;
this.subs = null;
}

public void setFile(File file)
{
this.file = file;
}

public void setMatch(String match)
{
if (regex != null)
throw new BuildException("Only one regular expression is allowed");

regex = new RegularExpression();
regex.setPattern(match);
}

public void setReplace(String replace)
{
if (subs != null)
throw new BuildException("Only one substitution expression is allowed");

subs = new Substitution();
subs.setExpression(replace);
}

public void setFlags(String flags)
{
this.flags = flags;
}

public void setByLine(String byline)
{
Boolean res = Boolean.valueOf(byline);
if (res == null)
res = Boolean.FALSE;
this.byline = res.booleanValue();
}

public void addFileset(FileSet set)
{
filesets.add(set);
}

public RegularExpression createRegularExpression()
{
if (regex != null)
throw new BuildException("Only one regular expression is allowed.");

regex = new RegularExpression();
return regex;
}

public Substitution createSubstitution()
{
if (subs != null)
throw new BuildException("Only one substitution expression is allowed");

subs = new Substitution();
return subs;
}

protected String doReplace(RegularExpression r,
Substitution s,
String input,
int options)
{
String res = input;
Regexp regexp = r.getRegexp(project);

if (regexp.matches(input, options))
{
res = regexp.substitute(input, s.getExpression(project), options);
}

return res;
}

/***
* Perform the replace on the entire file
*/
protected void doReplace(File f, int options)
throws IOException
{
File parentDir = new File(f.getAbsolutePath()).getParentFile();
File temp = File.createTempFile("replace", ".txt", parentDir);

FileReader r = null;
FileWriter w = null;

try
{
r = new FileReader(f);
w = new FileWriter(temp);

BufferedReader br = new BufferedReader(r);
BufferedWriter bw = new BufferedWriter(w);
PrintWriter pw = new PrintWriter(bw);

boolean changes = false;

log("Replacing pattern '" + regex.getPattern(project) + "' with '" + subs.getExpression(project) +
"' in '" + f.getPath() + "'" +
(byline ? " by line" : "") +
(flags.length() > 0 ? " with flags: '" + flags + "'" : "") +
".",
Project.MSG_WARN);

if (byline)
{
LineNumberReader lnr = new LineNumberReader(br);
String line = null;
while ((line = lnr.readLine()) != null)
{
String res = doReplace(regex, subs, line, options);
if (! res.equals(line))
changes = true;

pw.println(res);
}
pw.flush();
}
else
{
int flen = (int)(f.length());
char tmpBuf[] = new char[flen];
int numread = 0;
int totread = 0;
while (numread != -1 && totread < flen)
{
numread = br.read(tmpBuf, totread, flen);
totread += numread;
}

String buf = new String(tmpBuf);
String res = doReplace(regex, subs, buf, options);
if (! res.equals(buf))
changes = true;

pw.println(res);
pw.flush();
}

r.close();
r = null;
w.close();
w = null;

if (changes)
{
f.delete();
temp.renameTo(f);
}
else
{
temp.delete();
}
}
finally
{
try { if (r != null) r.close(); }
catch (Exception e) { };

try { if (w != null) r.close(); }
catch (Exception e) { };
}
}

public void execute()
throws BuildException
{
if (regex == null)
throw new BuildException("No expression to match.");
if (subs == null)
throw new BuildException("Nothing to replace expression with.");

if (file != null && filesets.size() > 0)
throw new BuildException("You cannot supply the 'file' attribute and filesets at the same time.");


int options = 0;
if (flags.indexOf('g') != -1)
options |= Regexp.REPLACE_ALL;

if (flags.indexOf('i') != -1)
options |= Regexp.MATCH_CASE_INSENSITIVE;

if (flags.indexOf('m') != -1)
options |= Regexp.MATCH_MULTILINE;

if (flags.indexOf('s') != -1)
options |= Regexp.MATCH_SINGLELINE;

if (file != null && file.exists())
{
try
{
doReplace(file, options);
}
catch (IOException e)
{
log("An error occurred processing file: '" + file.getAbsolutePath() + "': " + e.toString(),
Project.MSG_ERR);
}
}
else if (file != null)
{
log("The following file is missing: '" + file.getAbsolutePath() + "'",
Project.MSG_ERR);
}

int sz = filesets.size();
for (int i=0;i<sz;i++)
{
FileSet fs = (FileSet)(filesets.elementAt(i));
DirectoryScanner ds = fs.getDirectoryScanner(getProject());
String files[] = ds.getIncludedFiles();
for (int j=0;j<files.length;j++)
{
File f = new File(files[j]);
if (f.exists())
{
try
{
doReplace(f, options);
}
catch (Exception e)
{
log("An error occurred processing file: '" + f.getAbsolutePath() + "': " + e.toString(),
Project.MSG_ERR);
}
}
else
{
log("The following file is missing: '" + file.getAbsolutePath() + "'",
Project.MSG_ERR);
}
}
}
}
}



+ 161
- 0
src/main/org/apache/tools/ant/types/RegularExpression.java View File

@@ -0,0 +1,161 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.types;

import java.util.Hashtable;
import java.util.Stack;
import org.apache.tools.ant.BuildException;
import org.apache.tools.ant.Project;
import org.apache.tools.ant.util.regexp.Regexp;
import org.apache.tools.ant.util.regexp.RegexpFactory;

/***
* A regular expression datatype. Keeps an instance of the
* compiled expression for speed purposes. This compiled
* expression is lazily evaluated (it is compiled the first
* time it is needed). The syntax is the dependent on which
* regular expression type you are using. The system property
* "ant.regexp.regexpimpl" will be the classname of the implementation
* that will be used.
*
* <pre>
* For jdk <= 1.3, there are two available implementations:
* org.apache.tools.ant.util.regexp.JakartaOroRegexp (the default)
* Based on the jakarta-oro package
*
* org.apache.tools.ant.util.regexp.JakartaRegexpRegexp
* Based on the jakarta-regexp package
*
* For jdk <= 1.4, and additional implementation is available:
* org.apache.tools.ant.util.regexp.Jdk14RegexpRegexp
* Based on the jdk 1.4 built in regular expression package.
* </pre>
*
* @see org.apache.oro.regex.Perl5Compiler
* @see org.apache.regexp.RE
* @see java.util.regex.Pattern
*
* <pre>
* &lt;regularexpression [ [id="id"] pattern="expression" | refid="id" ]
* /&gt;
* </pre>
*
* @see org.apache.tools.ant.util.regexp.Regexp
* @author Matthew Inger <a href="mailto:mattinger@mindless.com">mattinger@mindless.com</a>
*/
public class RegularExpression extends DataType
{
public static final String DATA_TYPE_NAME = "regularexpression";

// The regular expression factory
private static final RegexpFactory factory = new RegexpFactory();

private Regexp regexp;

public RegularExpression()
{
this.regexp = factory.newRegexp();
}

public void setPattern(String pattern)
{
this.regexp.setPattern(pattern);
}

/***
* Gets the pattern string for this RegularExpression in the
* given project.
*/
public String getPattern(Project p)
{
if (isReference())
return getRef(p).getPattern(p);

return regexp.getPattern();
}

public Regexp getRegexp(Project p)
{
if (isReference())
return getRef(p).getRegexp(p);
return this.regexp;
}

/***
* Get the RegularExpression this reference refers to in
* the given project. Check for circular references too
*/
public RegularExpression getRef(Project p)
{
if (!checked)
{
Stack stk = new Stack();
stk.push(this);
dieOnCircularReference(stk, p);
}

Object o = ref.getReferencedObject(p);
if (!(o instanceof RegularExpression))
{
String msg = ref.getRefId() + " doesn\'t denote a regularexpression";
throw new BuildException(msg);
}
else
{
return (RegularExpression) o;
}
}

}

+ 129
- 0
src/main/org/apache/tools/ant/types/Substitution.java View File

@@ -0,0 +1,129 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.types;

import java.util.Hashtable;
import java.util.Stack;
import org.apache.tools.ant.BuildException;
import org.apache.tools.ant.Project;
import org.apache.tools.ant.types.DataType;

/***
* A regular expression substitution datatype. It is an expression
* that is meant to replace a regular expression. The syntax is the
* same as Perl5.
* @see org.apache.oro.text.regex.Perl5Substitition
*
* <pre>
* &lt;substitition [ [id="id"] expression="expression" | refid="id" ]
* /&gt;
* </pre>
*
* @author Matthew Inger <a href="mailto:mattinger@mindless.com">mattinger@mindless.com</a>
*/
public class Substitution extends DataType
{
public static final String DATA_TYPE_NAME = "substitition";

private String expression;

public Substitution()
{
this.expression = null;
}

public void setExpression(String expression)
{
this.expression = expression;
}

/***
* Gets the pattern string for this RegularExpression in the
* given project.
*/
public String getExpression(Project p)
{
if (isReference())
return getRef(p).getExpression(p);

return expression;
}

/***
* Get the RegularExpression this reference refers to in
* the given project. Check for circular references too
*/
public Substitution getRef(Project p)
{
if (!checked)
{
Stack stk = new Stack();
stk.push(this);
dieOnCircularReference(stk, p);
}

Object o = ref.getReferencedObject(p);
if (!(o instanceof Substitution))
{
String msg = ref.getRefId() + " doesn\'t denote a substitution";
throw new BuildException(msg);
}
else
{
return (Substitution) o;
}
}

}

+ 80
- 18
src/main/org/apache/tools/ant/util/regexp/JakartaOroMatcher.java View File

@@ -54,45 +54,77 @@

package org.apache.tools.ant.util.regexp;

import org.apache.oro.text.regex.*;

import org.apache.tools.ant.BuildException;
import org.apache.oro.text.regex.MatchResult;
import org.apache.oro.text.regex.Pattern;
import org.apache.oro.text.regex.Perl5Compiler;
import org.apache.oro.text.regex.Perl5Matcher;
import org.apache.oro.text.regex.Perl5Pattern;
import org.apache.oro.text.regex.Util;

import java.util.Vector;

/**
* Implementation of RegexpMatcher for Jakarta-ORO.
*
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
* @author <a href="mailto:mattinger@mindless.com">Matthew Inger</a>
*/
public class JakartaOroMatcher implements RegexpMatcher {

protected Perl5Matcher reg = new Perl5Matcher();
protected Perl5Compiler comp = new Perl5Compiler();
private Pattern pattern;
private String pattern;
protected final Perl5Compiler compiler = new Perl5Compiler();
protected final Perl5Matcher matcher = new Perl5Matcher();

public JakartaOroMatcher() {}

/**
* Set the regexp pattern from the String description.
*/
public void setPattern(String pattern) throws BuildException {
try {
this.pattern = comp.compile(pattern);
} catch (MalformedPatternException e) {
throw new BuildException(e);
}
public void setPattern(String pattern) {
this.pattern = pattern;
}

/**
* Get a String representation of the regexp pattern
*/
public String getPattern() {
return pattern.getPattern();
return this.pattern;
}

/**
* Get a compiled representation of the regexp pattern
*/
protected Pattern getCompiledPattern(int options)
throws BuildException
{
try
{
// compute the compiler options based on the input options first
Pattern p = compiler.compile(pattern, getCompilerOptions(options));
return p;
}
catch (Exception e)
{
throw new BuildException(e);
}
}

/**
* Does the given argument match the pattern?
*/
public boolean matches(String argument) {
return reg.contains(argument, pattern);
public boolean matches(String argument) throws BuildException {
return matches(argument, MATCH_DEFAULT);
}

/**
* Does the given argument match the pattern?
*/
public boolean matches(String input, int options)
throws BuildException
{
Pattern p = getCompiledPattern(options);
return matcher.contains(input, p);
}

/**
@@ -101,16 +133,46 @@ public class JakartaOroMatcher implements RegexpMatcher {
* <p>Group 0 will be the full match, the rest are the
* parenthesized subexpressions</p>.
*/
public Vector getGroups(String argument) {
if (!matches(argument)) {
public Vector getGroups(String argument) throws BuildException {
return getGroups(argument, MATCH_DEFAULT);
}

/**
* Returns a Vector of matched groups found in the argument.
*
* <p>Group 0 will be the full match, the rest are the
* parenthesized subexpressions</p>.
*/
public Vector getGroups(String input, int options)
throws BuildException
{
if (!matches(input, options)) {
return null;
}
Vector v = new Vector();
MatchResult mr = reg.getMatch();
for (int i=0; i<mr.groups(); i++) {
MatchResult mr = matcher.getMatch();
int cnt = mr.groups();
for (int i=0; i<cnt; i++) {
v.addElement(mr.group(i));
}
return v;
}

protected int getCompilerOptions(int options)
{
int cOptions = Perl5Compiler.DEFAULT_MASK;

if (RegexpUtil.hasFlag(options, MATCH_CASE_INSENSITIVE)) {
cOptions |= Perl5Compiler.CASE_INSENSITIVE_MASK;
}
if (RegexpUtil.hasFlag(options, MATCH_MULTILINE)) {
cOptions |= Perl5Compiler.MULTILINE_MASK;
}
if (RegexpUtil.hasFlag(options, MATCH_SINGLELINE)) {
cOptions |= Perl5Compiler.SINGLELINE_MASK;
}
return cOptions;
}

}

+ 99
- 0
src/main/org/apache/tools/ant/util/regexp/JakartaOroRegexp.java View File

@@ -0,0 +1,99 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.util.regexp;

import org.apache.tools.ant.BuildException;
import org.apache.oro.text.regex.Perl5Substitution;
import org.apache.oro.text.regex.Substitution;
import org.apache.oro.text.regex.Util;

import java.util.Vector;

/***
* Regular expression implementation using the Jakarta Oro package
* @author Matthew Inger <a href="mailto:mattinger@mindless.com">mattinger@mindless.com</a>
*/
public class JakartaOroRegexp extends JakartaOroMatcher implements Regexp
{

public JakartaOroRegexp()
{
super();
}

public String substitute(String input, String argument, int options)
throws BuildException
{
// Determine replacement Type
int sOptions = getSubsOptions(options);

// Do the substitution
Substitution s = new Perl5Substitution(argument, sOptions);
return Util.substitute(matcher,
getCompiledPattern(options),
s,
input);
}

protected int getSubsOptions(int options)
{
boolean replaceAll = RegexpUtil.hasFlag(options, REPLACE_ALL);
int subsOptions = 1;
if (replaceAll) {
subsOptions = Util.SUBSTITUTE_ALL;
}
return subsOptions;
}

}

+ 59
- 13
src/main/org/apache/tools/ant/util/regexp/JakartaRegexpMatcher.java View File

@@ -63,22 +63,17 @@ import java.util.Vector;
* Implementation of RegexpMatcher for Jakarta-Regexp.
*
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
* @author Matthew Inger <a href="mailto:mattinger@mindless.com">mattinger@mindless.com</a>
*/
public class JakartaRegexpMatcher implements RegexpMatcher {

protected RE reg = null;
private String pattern;

/**
* Set the regexp pattern from the String description.
*/
public void setPattern(String pattern) throws BuildException {
try {
this.pattern = pattern;
reg = new RE(pattern);
} catch (RESyntaxException e) {
throw new BuildException(e);
}
public void setPattern(String pattern) {
this.pattern = pattern;
}

/**
@@ -88,11 +83,40 @@ public class JakartaRegexpMatcher implements RegexpMatcher {
return pattern;
}

protected RE getCompiledPattern(int options)
throws BuildException
{
int cOptions = getCompilerOptions(options);
try
{
RE reg = new RE(pattern);
reg.setMatchFlags(cOptions);
return reg;
}
catch (RESyntaxException e)
{
throw new BuildException(e);
}
}

/**
* Does the given argument match the pattern?
*/
public boolean matches(String argument) throws BuildException {
return matches(argument, MATCH_DEFAULT);
}

/**
* Does the given argument match the pattern?
*/
public boolean matches(String argument) {
return reg.match(argument);
public boolean matches(String input, int options)
throws BuildException
{
return matches(input, getCompiledPattern(options));
}

private boolean matches(String input, RE reg) {
return reg.match(input);
}

/**
@@ -101,15 +125,37 @@ public class JakartaRegexpMatcher implements RegexpMatcher {
* <p>Group 0 will be the full match, the rest are the
* parenthesized subexpressions</p>.
*/
public Vector getGroups(String argument) {
if (!matches(argument)) {
public Vector getGroups(String argument) throws BuildException {
return getGroups(argument, MATCH_DEFAULT);
}

public Vector getGroups(String input, int options)
throws BuildException
{
RE reg = getCompiledPattern(options);
if (!matches(input, reg)) {
return null;
}
Vector v = new Vector();
for (int i=0; i<reg.getParenCount(); i++) {
int cnt = reg.getParenCount();
for (int i=0; i<cnt; i++) {
v.addElement(reg.getParen(i));
}
return v;
}

protected int getCompilerOptions(int options)
{
int cOptions = RE.MATCH_NORMAL;

if (RegexpUtil.hasFlag(options, MATCH_CASE_INSENSITIVE))
cOptions |= RE.MATCH_CASEINDEPENDENT;
if (RegexpUtil.hasFlag(options, MATCH_MULTILINE))
cOptions |= RE.MATCH_MULTILINE;
if (RegexpUtil.hasFlag(options, MATCH_SINGLELINE))
cOptions |= RE.MATCH_SINGLELINE;

return cOptions;
}

}

+ 88
- 0
src/main/org/apache/tools/ant/util/regexp/JakartaRegexpRegexp.java View File

@@ -0,0 +1,88 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.util.regexp;


import org.apache.tools.ant.BuildException;
import org.apache.regexp.*;
import java.util.Vector;

/***
* Regular expression implementation using the Jakarta Regexp package
* @author Matthew Inger <a href="mailto:mattinger@mindless.com">mattinger@mindless.com</a>
*/
public class JakartaRegexpRegexp extends JakartaRegexpMatcher implements Regexp
{

public JakartaRegexpRegexp()
{
super();
}

protected int getSubsOptions(int options)
{
int subsOptions = RE.REPLACE_FIRSTONLY;
if (RegexpUtil.hasFlag(options, REPLACE_ALL))
subsOptions = RE.REPLACE_ALL;
return subsOptions;
}

public String substitute(String input, String argument, int options)
throws BuildException
{
int sOptions = getSubsOptions(options);
RE reg = getCompiledPattern(options);
return reg.subst(input, argument, sOptions);
}
}

+ 73
- 14
src/main/org/apache/tools/ant/util/regexp/Jdk14RegexpMatcher.java View File

@@ -54,46 +54,77 @@

package org.apache.tools.ant.util.regexp;

import java.util.Vector;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.regex.PatternSyntaxException;

import org.apache.tools.ant.BuildException;
import java.util.Vector;

/**
* Implementation of RegexpMatcher for the built-in regexp matcher of
* JDK 1.4.
*
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
* @author Matthew Inger <a href="mailto:mattinger@mindless.com">mattinger@mindless.com</a>
*/
public class Jdk14RegexpMatcher implements RegexpMatcher {

private Pattern pattern;
private String pattern;

public Jdk14RegexpMatcher() {}

/**
* Set the regexp pattern from the String description.
*/
public void setPattern(String pattern) throws BuildException {
try {
this.pattern = Pattern.compile(pattern);
} catch (PatternSyntaxException e) {
throw new BuildException(e);
}
public void setPattern(String pattern) {
this.pattern = pattern;
}

/**
* Get a String representation of the regexp pattern
*/
public String getPattern() {
return pattern.pattern();
return pattern;
}

protected Pattern getCompiledPattern(int options)
throws BuildException
{
int cOptions = getCompilerOptions(options);
try
{
Pattern p = Pattern.compile(this.pattern, cOptions);
return p;
}
catch (PatternSyntaxException e)
{
throw new BuildException(e);
}
}

/**
* Does the given argument match the pattern?
*/
public boolean matches(String argument) throws BuildException {
return matches(argument, MATCH_DEFAULT);
}

/**
* Does the given argument match the pattern?
*/
public boolean matches(String argument) {
return pattern.matcher(argument).find();
public boolean matches(String input, int options)
throws BuildException
{
try
{
Pattern p = getCompiledPattern(options);
return p.matcher(input).find();
}
catch (Exception e)
{
throw new BuildException(e);
}
}

/**
@@ -102,16 +133,44 @@ public class Jdk14RegexpMatcher implements RegexpMatcher {
* <p>Group 0 will be the full match, the rest are the
* parenthesized subexpressions</p>.
*/
public Vector getGroups(String argument) {
Matcher matcher = pattern.matcher(argument);
public Vector getGroups(String argument) throws BuildException {
return getGroups(argument, MATCH_DEFAULT);
}

/**
* Returns a Vector of matched groups found in the argument.
*
* <p>Group 0 will be the full match, the rest are the
* parenthesized subexpressions</p>.
*/
public Vector getGroups(String input, int options)
throws BuildException
{
Pattern p = getCompiledPattern(options);
Matcher matcher = p.matcher(input);
if (!matcher.find()) {
return null;
}
Vector v = new Vector();
for (int i=0; i<=matcher.groupCount(); i++) {
int cnt = matcher.groupCount();
for (int i=0; i<=cnt; i++) {
v.addElement(matcher.group(i));
}
return v;
}

protected int getCompilerOptions(int options)
{
int cOptions = 0;

if (RegexpUtil.hasFlag(options, MATCH_CASE_INSENSITIVE))
cOptions |= Pattern.CASE_INSENSITIVE;
if (RegexpUtil.hasFlag(options, MATCH_MULTILINE))
cOptions |= Pattern.MULTILINE;
if (RegexpUtil.hasFlag(options, MATCH_SINGLELINE))
cOptions |= Pattern.DOTALL;

return cOptions;
}

}

+ 106
- 0
src/main/org/apache/tools/ant/util/regexp/Jdk14RegexpRegexp.java View File

@@ -0,0 +1,106 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.util.regexp;


import org.apache.tools.ant.BuildException;
import java.util.Vector;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.regex.PatternSyntaxException;

/***
* Regular expression implementation using the JDK 1.4 regular expression package
* @author Matthew Inger <a href="mailto:mattinger@mindless.com">mattinger@mindless.com</a>
*/
public class Jdk14RegexpRegexp extends Jdk14RegexpMatcher implements Regexp
{

public Jdk14RegexpRegexp()
{
super();
}

protected int getSubsOptions(int options)
{
int subsOptions = REPLACE_FIRST;
if (RegexpUtil.hasFlag(options, REPLACE_ALL))
subsOptions = REPLACE_ALL;
return subsOptions;
}

public String substitute(String input, String argument, int options)
throws BuildException
{
int sOptions = getSubsOptions(options);
Pattern p = getCompiledPattern(options);
StringBuffer sb = new StringBuffer();

Matcher m = p.matcher(input);
if (RegexpUtil.hasFlag(sOptions, REPLACE_ALL))
{
sb.append(m.replaceAll(argument));
}
else
{
boolean res = m.find();
if (res)
m.appendReplacement(sb, argument);
else
sb.append(input);
}

return sb.toString();
}
}

+ 75
- 0
src/main/org/apache/tools/ant/util/regexp/Regexp.java View File

@@ -0,0 +1,75 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.util.regexp;

import org.apache.tools.ant.BuildException;

/***
* Interface which represents a regular expression, and the operations
* that can be performed on it.
*
* @author <a href="mailto:mattinger@mindless.com">Matthew Inger</a>
*/
public interface Regexp extends RegexpMatcher
{
/**
* Perform a substitution on the regular expression.
* @param input The string to substitute on
* @param argument The string which defines the substitution
* @param options The list of options for the match and replace. See the
* MATCH_ and REPLACE_ constants above.
*/
String substitute(String input, String argument, int options)
throws BuildException;
}

+ 113
- 0
src/main/org/apache/tools/ant/util/regexp/RegexpFactory.java View File

@@ -0,0 +1,113 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.util.regexp;

import org.apache.tools.ant.BuildException;
import org.apache.tools.ant.Project;

/***
* Regular expression factory, which will create Regexp objects. The
* actual implementation class depends on the System or Ant Property:
* <code>ant.regexp.regexpimpl</code>.
*
* @author Matthew Inger <a href="mailto:mattinger@mindless.com">mattinger@mindless.com</a>
*/
public class RegexpFactory extends RegexpMatcherFactory
{
public RegexpFactory()
{
}

/***
* Create a new regular expression matcher instance.
*/
public Regexp newRegexp() throws BuildException {
return (Regexp) newRegexp(null);
}

/***
* Create a new regular expression matcher instance.
*
* @param p Project whose ant.regexp.regexpimpl property will be used.
*/
public Regexp newRegexp(Project p) throws BuildException {
String systemDefault = null;
if (p == null) {
systemDefault = System.getProperty("ant.regexp.regexpimpl");
} else {
systemDefault = (String) p.getProperties().get("ant.regexp.regexpimpl");
}
if (systemDefault != null) {
return (Regexp)createInstance(systemDefault);
// XXX should we silently catch possible exceptions and try to
// load a different implementation?
}

try {
return (Regexp)createInstance("org.apache.tools.ant.util.regexp.Jdk14RegexpRegexp");
} catch (BuildException be) {}
try {
return (Regexp)createInstance("org.apache.tools.ant.util.regexp.JakartaOroRegexp");
} catch (BuildException be) {}
try {
return (Regexp)createInstance("org.apache.tools.ant.util.regexp.JakartaRegexpRegexp");
} catch (BuildException be) {}

throw new BuildException("No supported regular expression matcher found");
}

}

+ 55
- 3
src/main/org/apache/tools/ant/util/regexp/RegexpMatcher.java View File

@@ -61,9 +61,42 @@ import java.util.Vector;
* Interface describing a regular expression matcher.
*
* @author <a href="mailto:stefan.bodewig@epost.de">Stefan Bodewig</a>
* @author <a href="mailto:mattinger@mindless.com">Matthew Inger</a>
*/
public interface RegexpMatcher {

/***
* Replace only the first occurance of the regular expression
*/
int REPLACE_FIRST = 0x00000001;

/***
* Replace all occurances of the regular expression
*/
int REPLACE_ALL = 0x00000010;

/***
* Default Mask (case insensitive, neither multiline nor
* singleline specified).
*/
int MATCH_DEFAULT = 0x00000000;

/***
* Perform a case insenstive match
*/
int MATCH_CASE_INSENSITIVE = 0x00000100;
/***
* Treat the input as a multiline input
*/
int MATCH_MULTILINE = 0x00001000;

/***
* Treat the input as singleline input ('.' matches newline)
*/
int MATCH_SINGLELINE = 0x00010000;


/**
* Set the regexp pattern from the String description.
*/
@@ -72,12 +105,12 @@ public interface RegexpMatcher {
/**
* Get a String representation of the regexp pattern
*/
String getPattern();
String getPattern() throws BuildException;

/**
* Does the given argument match the pattern?
*/
boolean matches(String argument);
boolean matches(String argument) throws BuildException;

/**
* Returns a Vector of matched groups found in the argument.
@@ -85,5 +118,24 @@ public interface RegexpMatcher {
* <p>Group 0 will be the full match, the rest are the
* parenthesized subexpressions</p>.
*/
Vector getGroups(String argument);
Vector getGroups(String argument) throws BuildException;

/***
* Does this regular expression match the input, given
* certain options
* @param input The string to check for a match
* @param options The list of options for the match. See the
* MATCH_ constants above.
*/
boolean matches(String input, int options) throws BuildException;

/***
* Get the match groups from this regular expression. The return
* type of the elements is always String.
* @param input The string to check for a match
* @param options The list of options for the match. See the
* MATCH_ constants above.
*/
Vector getGroups(String input, int options) throws BuildException;

}

+ 22
- 2
src/main/org/apache/tools/ant/util/regexp/RegexpMatcherFactory.java View File

@@ -55,6 +55,7 @@
package org.apache.tools.ant.util.regexp;

import org.apache.tools.ant.BuildException;
import org.apache.tools.ant.Project;

/**
* Simple Factory Class that produces an implementation of
@@ -71,11 +72,30 @@ public class RegexpMatcherFactory {

public RegexpMatcherFactory() {}

/***
* Create a new regular expression instance.
*/
public RegexpMatcher newRegexpMatcher() throws BuildException {
String systemDefault = System.getProperty("ant.regexp.matcherimpl");
return newRegexpMatcher(null);
}

/***
* Create a new regular expression instance.
*
* @param p Project whose ant.regexp.regexpimpl property will be used.
*/
public RegexpMatcher newRegexpMatcher(Project p)
throws BuildException {
String systemDefault = null;
if (p == null) {
systemDefault = System.getProperty("ant.regexp.regexpimpl");
} else {
systemDefault = (String) p.getProperties().get("ant.regexp.regexpimpl");
}
if (systemDefault != null) {
return createInstance(systemDefault);
// XXX should we silently possible exceptions and try to
// XXX should we silently catch possible exceptions and try to
// load a different implementation?
}



+ 72
- 0
src/main/org/apache/tools/ant/util/regexp/RegexpUtil.java View File

@@ -0,0 +1,72 @@
/*
* The Apache Software License, Version 1.1
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
* any, must include the following acknowlegement:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowlegement may appear in the software itself,
* if and wherever such third-party acknowlegements normally appear.
*
* 4. The names "The Jakarta Project", "Ant", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
* from this software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
* permission of the Apache Group.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
package org.apache.tools.ant.util.regexp;

/***
* Regular expression utilities class which handles flag operations
*
* @author <a href="mailto:mattinger@mindless.com">Matthew Inger</a>
*/
public class RegexpUtil extends Object
{
public static final boolean hasFlag(int options, int flag)
{
return ((options & flag) > 0);
}

public static final int removeFlag(int options, int flag)
{
return (options & (0xFFFFFFFF - flag));
}
}

Loading…
Cancel
Save