Initial revision
From-SVN: r102074
This commit is contained in:
@@ -0,0 +1,87 @@
|
||||
/* AndExpr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Logical and.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class AndExpr
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr lhs;
|
||||
final Expr rhs;
|
||||
|
||||
public AndExpr(Expr lhs, Expr rhs)
|
||||
{
|
||||
this.lhs = lhs;
|
||||
this.rhs = rhs;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object left = lhs.evaluate(context, pos, len);
|
||||
if (!_boolean(context, left))
|
||||
{
|
||||
return Boolean.FALSE;
|
||||
}
|
||||
Object right = rhs.evaluate(context, pos, len);
|
||||
return _boolean(context, right) ? Boolean.TRUE : Boolean.FALSE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new AndExpr(lhs.clone(context), rhs.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (lhs.references(var) || rhs.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return lhs + " and " + rhs;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,154 @@
|
||||
/* ArithmeticExpr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Binary arithmetic expression.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class ArithmeticExpr
|
||||
extends Expr
|
||||
{
|
||||
|
||||
static final int ADD = 0;
|
||||
static final int SUBTRACT = 1;
|
||||
static final int MULTIPLY = 2;
|
||||
static final int DIVIDE = 3;
|
||||
static final int MODULO = 4;
|
||||
|
||||
final Expr lhs;
|
||||
final Expr rhs;
|
||||
final int op;
|
||||
|
||||
ArithmeticExpr(Expr lhs, Expr rhs, int op)
|
||||
{
|
||||
this.lhs = lhs;
|
||||
this.rhs = rhs;
|
||||
switch (op)
|
||||
{
|
||||
case ADD:
|
||||
case SUBTRACT:
|
||||
case MULTIPLY:
|
||||
case DIVIDE:
|
||||
case MODULO:
|
||||
this.op = op;
|
||||
break;
|
||||
default:
|
||||
throw new IllegalArgumentException();
|
||||
}
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object left = lhs.evaluate(context, pos, len);
|
||||
Object right = rhs.evaluate(context, pos, len);
|
||||
|
||||
double ln = _number(context, left);
|
||||
double rn = _number(context, right);
|
||||
switch (op)
|
||||
{
|
||||
case ADD:
|
||||
return new Double(ln + rn);
|
||||
case SUBTRACT:
|
||||
return new Double(ln - rn);
|
||||
case MULTIPLY:
|
||||
return new Double(ln * rn);
|
||||
case DIVIDE:
|
||||
if (rn == 0.0d || rn == -0.0d)
|
||||
{
|
||||
return new Double(ln < 0.0d ?
|
||||
Double.NEGATIVE_INFINITY :
|
||||
Double.POSITIVE_INFINITY);
|
||||
}
|
||||
return new Double(ln / rn);
|
||||
case MODULO:
|
||||
if (rn == 0.0d || rn == -0.0d)
|
||||
{
|
||||
return new Double(ln < 0.0d ?
|
||||
Double.NEGATIVE_INFINITY :
|
||||
Double.POSITIVE_INFINITY);
|
||||
}
|
||||
return new Double(ln % rn);
|
||||
default:
|
||||
throw new IllegalStateException();
|
||||
}
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new ArithmeticExpr(lhs.clone(context), rhs.clone(context), op);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (lhs.references(var) || rhs.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
StringBuffer buf = new StringBuffer();
|
||||
buf.append(lhs);
|
||||
buf.append(' ');
|
||||
switch (op)
|
||||
{
|
||||
case ADD:
|
||||
buf.append('+');
|
||||
break;
|
||||
case SUBTRACT:
|
||||
buf.append('-');
|
||||
break;
|
||||
case MULTIPLY:
|
||||
buf.append('*');
|
||||
break;
|
||||
case DIVIDE:
|
||||
buf.append("div");
|
||||
break;
|
||||
case MODULO:
|
||||
buf.append("mod");
|
||||
break;
|
||||
}
|
||||
buf.append(' ');
|
||||
buf.append(rhs);
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,95 @@
|
||||
/* BooleanFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>boolean</code> function converts its argument to a boolean as
|
||||
* follows:
|
||||
* <ul>
|
||||
* <li>a number is true if and only if it is neither positive or negative
|
||||
* zero nor NaN</li>
|
||||
* <li>a node-set is true if and only if it is non-empty</li>
|
||||
* <li>a string is true if and only if its length is non-zero</li>
|
||||
* <li>an object of a type other than the four basic types is converted to a
|
||||
* boolean in a way that is dependent on that type</li>
|
||||
* </ul>
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class BooleanFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
BooleanFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
BooleanFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
return _boolean(context, val) ? Boolean.TRUE : Boolean.FALSE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new BooleanFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "boolean(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,89 @@
|
||||
/* CeilingFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>ceiling</code> function returns the smallest (closest to
|
||||
* negative infinity) number that is not less than the argument and that
|
||||
* is an integer.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class CeilingFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
CeilingFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
CeilingFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
double n = _number(context, val);
|
||||
return new Double(Math.ceil(n));
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new CeilingFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "ceiling(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,113 @@
|
||||
/* ConcatFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>concat</code> function returns the concatenation of its arguments.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class ConcatFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final List args;
|
||||
|
||||
ConcatFunction(List args)
|
||||
{
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
StringBuffer buf = new StringBuffer();
|
||||
for (Iterator i = args.iterator(); i.hasNext(); )
|
||||
{
|
||||
Expr arg = (Expr) i.next();
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
buf.append(_string(context, val));
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
int len = args.size();
|
||||
List args2 = new ArrayList(len);
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
args2.add(((Expr) args.get(i)).clone(context));
|
||||
}
|
||||
return new ConcatFunction(args2);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
for (Iterator i = args.iterator(); i.hasNext(); )
|
||||
{
|
||||
if (((Expr) i.next()).references(var))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
StringBuffer buf = new StringBuffer("concat(");
|
||||
int len = args.size();
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
if (i > 0)
|
||||
{
|
||||
buf.append(',');
|
||||
}
|
||||
buf.append(args.get(i));
|
||||
}
|
||||
buf.append(')');
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,98 @@
|
||||
/* Constant.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Constant value (string literal or number).
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class Constant
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Object value;
|
||||
|
||||
public Constant(Object value)
|
||||
{
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
return value;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new Constant(value);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
String ret = value.toString();
|
||||
if (value instanceof String)
|
||||
{
|
||||
if (ret.indexOf('\'') == -1)
|
||||
{
|
||||
return '\'' + ret + '\'';
|
||||
}
|
||||
else
|
||||
{
|
||||
return '"' + ret + '"';
|
||||
}
|
||||
}
|
||||
if (value instanceof Double)
|
||||
{
|
||||
if (ret.endsWith(".0"))
|
||||
{
|
||||
ret = ret.substring(0, ret.length() - 2);
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,92 @@
|
||||
/* ContainsFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>contains</code> function returns true if the first argument
|
||||
* string contains the second argument string, and otherwise returns false.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class ContainsFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg1;
|
||||
final Expr arg2;
|
||||
|
||||
ContainsFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0), (Expr) args.get(1));
|
||||
}
|
||||
|
||||
ContainsFunction(Expr arg1, Expr arg2)
|
||||
{
|
||||
this.arg1 = arg1;
|
||||
this.arg2 = arg2;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val1 = arg1.evaluate(context, pos, len);
|
||||
Object val2 = arg2.evaluate(context, pos, len);
|
||||
String s1 = _string(context, val1);
|
||||
String s2 = _string(context, val2);
|
||||
return (s1.indexOf(s2) != -1) ? Boolean.TRUE : Boolean.FALSE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new ContainsFunction(arg1.clone(context), arg2.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg1.references(var) || arg2.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "contains(" + arg1 + "," + arg2 + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,88 @@
|
||||
/* CountFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>count</code> function returns the number of nodes in the
|
||||
* argument node-set.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class CountFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
CountFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
CountFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
return new Double((double) ((Collection) val).size());
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new CountFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "count(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,63 @@
|
||||
/* DocumentOrderComparator.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Comparator;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Sorts nodes into document order.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public class DocumentOrderComparator
|
||||
implements Comparator
|
||||
{
|
||||
|
||||
public int compare(Object o1, Object o2)
|
||||
{
|
||||
if (o1 instanceof Node && o2 instanceof Node)
|
||||
{
|
||||
Node n1 = (Node)o1;
|
||||
Node n2 = (Node)o2;
|
||||
return (int) n1.compareDocumentPosition(n2);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,268 @@
|
||||
/* EqualityExpr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Boolean equality expression.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class EqualityExpr
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr lhs;
|
||||
final Expr rhs;
|
||||
final boolean invert;
|
||||
|
||||
EqualityExpr(Expr lhs, Expr rhs, boolean invert)
|
||||
{
|
||||
this.lhs = lhs;
|
||||
this.rhs = rhs;
|
||||
this.invert = invert;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
boolean val = evaluateImpl(context, pos, len);
|
||||
if (invert)
|
||||
{
|
||||
return val ? Boolean.FALSE : Boolean.TRUE;
|
||||
}
|
||||
else
|
||||
{
|
||||
return val ? Boolean.TRUE : Boolean.FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean evaluateImpl(Node context, int pos, int len)
|
||||
{
|
||||
Object left = lhs.evaluate(context, pos, len);
|
||||
Object right = rhs.evaluate(context, pos, len);
|
||||
|
||||
/*
|
||||
* If both objects to be compared are node-sets, then the comparison
|
||||
* will be true if and only if there is a node in the first node-set and
|
||||
* a node in the second node-set such that the result of performing the
|
||||
* comparison on the string-values of the two nodes is true.
|
||||
*/
|
||||
boolean flns = left instanceof Collection;
|
||||
boolean frns = right instanceof Collection;
|
||||
if (flns && frns)
|
||||
{
|
||||
Collection lns = (Collection) left;
|
||||
Collection rns = (Collection) right;
|
||||
if (lns.isEmpty())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
boolean all = true;
|
||||
for (Iterator i = lns.iterator(); i.hasNext(); )
|
||||
{
|
||||
Node ltest = (Node) i.next();
|
||||
for (Iterator j = rns.iterator(); j.hasNext(); )
|
||||
{
|
||||
Node rtest = (Node) j.next();
|
||||
if (ltest == rtest || ltest.equals(rtest))
|
||||
{
|
||||
// much shorter
|
||||
if (!invert)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else if (stringValue(ltest).equals(stringValue(rtest)))
|
||||
{
|
||||
if (!invert)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
all = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return all;
|
||||
}
|
||||
/*
|
||||
* If one object to be compared is a node-set and the other is a number,
|
||||
* then the comparison will be true if and only if there is a node in
|
||||
* the node-set such that the result of performing the comparison on the
|
||||
* number to be compared and on the result of converting the
|
||||
* string-value of that node to a number using the number function is
|
||||
* true.
|
||||
*/
|
||||
boolean fln = left instanceof Double;
|
||||
boolean frn = right instanceof Double;
|
||||
if ((flns && frn) || (frns && fln))
|
||||
{
|
||||
Collection ns = flns ? (Collection) left : (Collection) right;
|
||||
double n = fln ? ((Double) left).doubleValue() :
|
||||
((Double) right).doubleValue();
|
||||
boolean all = true;
|
||||
for (Iterator i = ns.iterator(); i.hasNext(); )
|
||||
{
|
||||
Node test = (Node) i.next();
|
||||
double nn = _number(context, stringValue(test));
|
||||
if (nn == n)
|
||||
{
|
||||
if (!invert)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
all = false;
|
||||
}
|
||||
}
|
||||
return invert ? all : false;
|
||||
}
|
||||
/*
|
||||
* If one object to be compared is a node-set and the other is a
|
||||
* string, then the comparison will be true if and only if there is a
|
||||
* node in the node-set such that the result of performing the
|
||||
* comparison on the string-value of the node and the other string is
|
||||
* true.
|
||||
*/
|
||||
boolean fls = left instanceof String;
|
||||
boolean frs = right instanceof String;
|
||||
if ((flns && frs) || (frns && fls))
|
||||
{
|
||||
Collection ns = flns ? (Collection) left : (Collection) right;
|
||||
String s = fls ? (String) left : (String) right;
|
||||
boolean all = true;
|
||||
for (Iterator i = ns.iterator(); i.hasNext(); )
|
||||
{
|
||||
Node test = (Node) i.next();
|
||||
if (stringValue(test).equals(s))
|
||||
{
|
||||
if (!invert)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
all = false;
|
||||
}
|
||||
}
|
||||
return invert ? all : false;
|
||||
}
|
||||
/*
|
||||
* If one object to be compared is a node-set and the other is a
|
||||
* boolean, then the comparison will be true if and only if the result
|
||||
* of performing the comparison on the boolean and on the result of
|
||||
* converting the node-set to a boolean using the boolean function is
|
||||
* true.
|
||||
*/
|
||||
boolean flb = left instanceof Boolean;
|
||||
boolean frb = right instanceof Boolean;
|
||||
if ((flns && frb) || (frns && flb))
|
||||
{
|
||||
Collection ns = flns ? (Collection) left : (Collection) right;
|
||||
boolean b = flb ? ((Boolean) left).booleanValue() :
|
||||
((Boolean) right).booleanValue();
|
||||
return _boolean(context, ns) == b;
|
||||
}
|
||||
/*
|
||||
* If at least one object to be compared is a boolean, then each object
|
||||
* to be compared is converted to a boolean as if by applying the
|
||||
* boolean function.
|
||||
*/
|
||||
if (flb || frb)
|
||||
{
|
||||
boolean lb = flb ? ((Boolean) left).booleanValue() :
|
||||
_boolean(context, left);
|
||||
boolean rb = frb ? ((Boolean) right).booleanValue() :
|
||||
_boolean(context, right);
|
||||
return lb == rb;
|
||||
}
|
||||
/*
|
||||
* Otherwise, if at least one object to be compared is
|
||||
* a number, then each object to be compared is converted to a number as
|
||||
* if by applying the number function.
|
||||
*/
|
||||
if (fln || frn)
|
||||
{
|
||||
double ln = fln ? ((Double) left).doubleValue() :
|
||||
_number(context, left);
|
||||
double rn = frn ? ((Double) right).doubleValue() :
|
||||
_number(context, right);
|
||||
return ln == rn;
|
||||
}
|
||||
/*
|
||||
* Otherwise, both objects to be
|
||||
* compared are converted to strings as if by applying the string
|
||||
* function.
|
||||
*/
|
||||
String ls = fls ? (String) left : _string(context, left);
|
||||
String rs = frs ? (String) right : _string(context, right);
|
||||
return ls.equals(rs);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new EqualityExpr(lhs.clone(context), rhs.clone(context), invert);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (lhs.references(var) || rhs.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
if (invert)
|
||||
{
|
||||
return lhs + " != " + rhs;
|
||||
}
|
||||
else
|
||||
{
|
||||
return lhs + " = " + rhs;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,476 @@
|
||||
/* Expr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.text.DecimalFormat;
|
||||
import java.text.DecimalFormatSymbols;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.Comparator;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Set;
|
||||
import java.util.StringTokenizer;
|
||||
import javax.xml.namespace.QName;
|
||||
import javax.xml.parsers.DocumentBuilder;
|
||||
import javax.xml.parsers.DocumentBuilderFactory;
|
||||
import javax.xml.parsers.ParserConfigurationException;
|
||||
import javax.xml.xpath.XPathConstants;
|
||||
import javax.xml.xpath.XPathExpression;
|
||||
import javax.xml.xpath.XPathExpressionException;
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.Node;
|
||||
import org.xml.sax.InputSource;
|
||||
import org.xml.sax.SAXException;
|
||||
|
||||
/**
|
||||
* An XPath expression.
|
||||
* This can be evaluated in the context of a node to produce a result.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public abstract class Expr
|
||||
implements XPathExpression
|
||||
{
|
||||
|
||||
protected static final Comparator documentOrderComparator =
|
||||
new DocumentOrderComparator();
|
||||
|
||||
protected static final DecimalFormat decimalFormat =
|
||||
new DecimalFormat("####################################################" +
|
||||
".####################################################",
|
||||
new DecimalFormatSymbols(Locale.US));
|
||||
|
||||
public Object evaluate(Object item, QName returnType)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
Object ret = null;
|
||||
Node context = null;
|
||||
if (item instanceof Node)
|
||||
{
|
||||
context = (Node) item;
|
||||
ret = evaluate(context, 1, 1);
|
||||
if (XPathConstants.STRING == returnType &&
|
||||
!(ret instanceof String))
|
||||
{
|
||||
ret = _string(context, ret);
|
||||
}
|
||||
else if (XPathConstants.NUMBER == returnType &&
|
||||
!(ret instanceof Double))
|
||||
{
|
||||
ret = new Double(_number(context, ret));
|
||||
}
|
||||
else if (XPathConstants.BOOLEAN == returnType &&
|
||||
!(ret instanceof Boolean))
|
||||
{
|
||||
ret = _boolean(context, ret) ? Boolean.TRUE : Boolean.FALSE;
|
||||
}
|
||||
else if (XPathConstants.NODE == returnType)
|
||||
{
|
||||
if (ret instanceof Collection)
|
||||
{
|
||||
Collection ns = (Collection) ret;
|
||||
switch (ns.size())
|
||||
{
|
||||
case 0:
|
||||
ret = null;
|
||||
break;
|
||||
case 1:
|
||||
ret = (Node) ns.iterator().next();
|
||||
break;
|
||||
default:
|
||||
throw new XPathExpressionException("multiple nodes in node-set");
|
||||
}
|
||||
}
|
||||
else if (ret != null)
|
||||
{
|
||||
throw new XPathExpressionException("return value is not a node-set");
|
||||
}
|
||||
}
|
||||
else if (XPathConstants.NODESET == returnType)
|
||||
{
|
||||
if (ret != null && !(ret instanceof Collection))
|
||||
{
|
||||
throw new XPathExpressionException("return value is not a node-set");
|
||||
}
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
public String evaluate(Object item)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
return (String) evaluate(item, XPathConstants.STRING);
|
||||
}
|
||||
|
||||
public Object evaluate(InputSource source, QName returnType)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
try
|
||||
{
|
||||
DocumentBuilderFactory factory =
|
||||
new gnu.xml.dom.JAXPFactory();
|
||||
DocumentBuilder builder = factory.newDocumentBuilder();
|
||||
Document doc = builder.parse(source);
|
||||
return evaluate(doc, returnType);
|
||||
}
|
||||
catch (ParserConfigurationException e)
|
||||
{
|
||||
throw new XPathExpressionException(e);
|
||||
}
|
||||
catch (SAXException e)
|
||||
{
|
||||
throw new XPathExpressionException(e);
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new XPathExpressionException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public String evaluate(InputSource source)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
return (String) evaluate(source, XPathConstants.STRING);
|
||||
}
|
||||
|
||||
public abstract Object evaluate(Node context, int pos, int len);
|
||||
|
||||
public abstract Expr clone(Object context);
|
||||
|
||||
public abstract boolean references(QName var);
|
||||
|
||||
/* -- 4.1 Node Set Functions -- */
|
||||
|
||||
/**
|
||||
* The id function selects elements by their unique ID.
|
||||
* When the argument to id is of type node-set, then the result is
|
||||
* the union of the result of applying id to the string-value of each of
|
||||
* the nodes in the argument node-set. When the argument to id is of any
|
||||
* other type, the argument is converted to a string as if by a call to
|
||||
* the string function; the string is split into a whitespace-separated
|
||||
* list of tokens (whitespace is any sequence of characters matching the
|
||||
* production S); the result is a node-set containing the elements in the
|
||||
* same document as the context node that have a unique ID equal to any of
|
||||
* the tokens in the list.
|
||||
*/
|
||||
public static Collection _id(Node context, Object object)
|
||||
{
|
||||
Set ret = new HashSet();
|
||||
if (object instanceof Collection)
|
||||
{
|
||||
Collection nodeSet = (Collection) object;
|
||||
for (Iterator i = nodeSet.iterator(); i.hasNext(); )
|
||||
{
|
||||
String string = stringValue((Node) i.next());
|
||||
ret.addAll(_id (context, string));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Document doc = (context instanceof Document) ? (Document) context :
|
||||
context.getOwnerDocument();
|
||||
String string = _string(context, object);
|
||||
StringTokenizer st = new StringTokenizer(string, " \t\r\n");
|
||||
while (st.hasMoreTokens())
|
||||
{
|
||||
Node element = doc.getElementById(st.nextToken());
|
||||
if (element != null)
|
||||
{
|
||||
ret.add(element);
|
||||
}
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
* The local-name function returns the local part of the expanded-name of
|
||||
* the node in the argument node-set that is first in document order. If
|
||||
* the argument node-set is empty or the first node has no expanded-name,
|
||||
* an empty string is returned. If the argument is omitted, it defaults to
|
||||
* a node-set with the context node as its only member.
|
||||
*/
|
||||
public static String _local_name(Node context, Collection nodeSet)
|
||||
{
|
||||
Node node = (nodeSet == null || nodeSet.size() == 0) ? context :
|
||||
firstNode(nodeSet);
|
||||
return node.getLocalName();
|
||||
}
|
||||
|
||||
/**
|
||||
* The namespace-uri function returns the namespace URI of the
|
||||
* expanded-name of the node in the argument node-set that is first in
|
||||
* document order. If the argument node-set is empty, the first node has
|
||||
* no expanded-name, or the namespace URI of the expanded-name is null, an
|
||||
* empty string is returned. If the argument is omitted, it defaults to a
|
||||
* node-set with the context node as its only member.
|
||||
*/
|
||||
public static String _namespace_uri(Node context, Collection nodeSet)
|
||||
{
|
||||
Node node = (nodeSet == null || nodeSet.size() == 0) ? context :
|
||||
firstNode(nodeSet);
|
||||
return node.getNamespaceURI();
|
||||
}
|
||||
|
||||
/**
|
||||
* The name function returns a string containing a QName representing the
|
||||
* expanded-name of the node in the argument node-set that is first in
|
||||
* document order. The QName must represent the expanded-name with respect
|
||||
* to the namespace declarations in effect on the node whose expanded-name
|
||||
* is being represented. Typically, this will be the QName that occurred
|
||||
* in the XML source. This need not be the case if there are namespace
|
||||
* declarations in effect on the node that associate multiple prefixes
|
||||
* with the same namespace. However, an implementation may include
|
||||
* information about the original prefix in its representation of nodes;
|
||||
* in this case, an implementation can ensure that the returned string is
|
||||
* always the same as the QName used in the XML source. If the argument
|
||||
* node-set is empty or the first node has no expanded-name, an empty
|
||||
* string is returned. If the argument it omitted, it defaults to a
|
||||
* node-set with the context node as its only member.
|
||||
*/
|
||||
public static String _name(Node context, Collection nodeSet)
|
||||
{
|
||||
Node node = (nodeSet == null || nodeSet.size() == 0) ? context :
|
||||
firstNode(nodeSet);
|
||||
switch (node.getNodeType())
|
||||
{
|
||||
case Node.ATTRIBUTE_NODE:
|
||||
case Node.ELEMENT_NODE:
|
||||
case Node.PROCESSING_INSTRUCTION_NODE:
|
||||
return node.getNodeName();
|
||||
default:
|
||||
return "";
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the first node in the set in document order.
|
||||
*/
|
||||
static Node firstNode(Collection nodeSet)
|
||||
{
|
||||
List list = new ArrayList(nodeSet);
|
||||
Collections.sort(list, documentOrderComparator);
|
||||
return (Node) list.get(0);
|
||||
}
|
||||
|
||||
/* -- 4.2 String Functions -- */
|
||||
|
||||
/**
|
||||
* Implementation of the XPath <code>string</code> function.
|
||||
*/
|
||||
public static String _string(Node context, Object object)
|
||||
{
|
||||
if (object == null)
|
||||
{
|
||||
return stringValue(context);
|
||||
}
|
||||
if (object instanceof String)
|
||||
{
|
||||
return (String) object;
|
||||
}
|
||||
if (object instanceof Boolean)
|
||||
{
|
||||
return object.toString();
|
||||
}
|
||||
if (object instanceof Double)
|
||||
{
|
||||
double d = ((Double) object).doubleValue();
|
||||
if (Double.isNaN(d))
|
||||
{
|
||||
return "NaN";
|
||||
}
|
||||
else if (d == 0.0d)
|
||||
{
|
||||
return "0";
|
||||
}
|
||||
else if (Double.isInfinite(d))
|
||||
{
|
||||
if (d < 0)
|
||||
{
|
||||
return "-Infinity";
|
||||
}
|
||||
else
|
||||
{
|
||||
return "Infinity";
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
String ret = decimalFormat.format(d);
|
||||
if (ret.endsWith (".0"))
|
||||
{
|
||||
ret = ret.substring(0, ret.length() - 2);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
if (object instanceof Collection)
|
||||
{
|
||||
Collection nodeSet = (Collection) object;
|
||||
if (nodeSet.isEmpty())
|
||||
{
|
||||
return "";
|
||||
}
|
||||
Node node = firstNode(nodeSet);
|
||||
return stringValue(node);
|
||||
}
|
||||
throw new IllegalArgumentException(object.toString());
|
||||
}
|
||||
|
||||
/* -- 4.3 Boolean Functions -- */
|
||||
|
||||
/**
|
||||
* Implementation of the XPath <code>boolean</code> function.
|
||||
*/
|
||||
public static boolean _boolean(Node context, Object object)
|
||||
{
|
||||
if (object instanceof Boolean)
|
||||
{
|
||||
return ((Boolean) object).booleanValue();
|
||||
}
|
||||
if (object instanceof Double)
|
||||
{
|
||||
return ((Double) object).doubleValue() != 0.0;
|
||||
}
|
||||
if (object instanceof String)
|
||||
{
|
||||
return ((String) object).length() != 0;
|
||||
}
|
||||
if (object instanceof Collection)
|
||||
{
|
||||
return ((Collection) object).size() != 0;
|
||||
}
|
||||
return false; // TODO user defined types
|
||||
}
|
||||
|
||||
/* -- 4.4 Number Functions -- */
|
||||
|
||||
/**
|
||||
* Implementation of the XPath <code>number</code> function.
|
||||
*/
|
||||
public static double _number(Node context, Object object)
|
||||
{
|
||||
if (object == null)
|
||||
{
|
||||
object = Collections.singleton(context);
|
||||
}
|
||||
if (object instanceof Double)
|
||||
{
|
||||
return ((Double) object).doubleValue();
|
||||
}
|
||||
if (object instanceof Boolean)
|
||||
{
|
||||
return ((Boolean) object).booleanValue() ? 1.0 : 0.0;
|
||||
}
|
||||
if (object instanceof Collection)
|
||||
{
|
||||
// Convert node-set to string
|
||||
object = stringValue((Collection) object);
|
||||
}
|
||||
if (object instanceof String)
|
||||
{
|
||||
String string = ((String) object).trim();
|
||||
try
|
||||
{
|
||||
return Double.parseDouble(string);
|
||||
}
|
||||
catch (NumberFormatException e)
|
||||
{
|
||||
return Double.NaN;
|
||||
}
|
||||
}
|
||||
return Double.NaN; // TODO user-defined types
|
||||
}
|
||||
|
||||
/**
|
||||
* Computes the XPath string-value of the specified node-set.
|
||||
*/
|
||||
public static String stringValue(Collection nodeSet)
|
||||
{
|
||||
StringBuffer buf = new StringBuffer();
|
||||
for (Iterator i = nodeSet.iterator(); i.hasNext(); )
|
||||
{
|
||||
buf.append(stringValue((Node) i.next()));
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* Computes the XPath string-value of the specified node.
|
||||
*/
|
||||
public static String stringValue(Node node)
|
||||
{
|
||||
return stringValue(node, false);
|
||||
}
|
||||
|
||||
static String stringValue(Node node, boolean elementMode)
|
||||
{
|
||||
switch (node.getNodeType())
|
||||
{
|
||||
case Node.DOCUMENT_NODE: // 5.1 Root Node
|
||||
case Node.DOCUMENT_FRAGMENT_NODE:
|
||||
case Node.ELEMENT_NODE: // 5.2 Element Nodes
|
||||
StringBuffer buf = new StringBuffer();
|
||||
for (Node ctx = node.getFirstChild(); ctx != null;
|
||||
ctx = ctx.getNextSibling())
|
||||
{
|
||||
buf.append(stringValue(ctx, true));
|
||||
}
|
||||
return buf.toString();
|
||||
case Node.TEXT_NODE: // 5.7 Text Nodes
|
||||
case Node.CDATA_SECTION_NODE:
|
||||
return node.getNodeValue();
|
||||
case Node.ATTRIBUTE_NODE: // 5.3 Attribute Nodes
|
||||
case Node.PROCESSING_INSTRUCTION_NODE: // 5.5 Processing Instruction
|
||||
case Node.COMMENT_NODE: // 5.6 Comment Nodes
|
||||
if (!elementMode)
|
||||
{
|
||||
return node.getNodeValue();
|
||||
}
|
||||
default:
|
||||
return "";
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
/* FalseFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>false</code> function returns false.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class FalseFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
return Boolean.FALSE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new FalseFunction();
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "false()";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,89 @@
|
||||
/* FloorFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>floor</code> function returns the largest (closest to positive
|
||||
* infinity) number that is not greater than the argument and that is an
|
||||
* integer.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class FloorFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
FloorFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
FloorFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
double n = _number(context, val);
|
||||
return new Double(Math.floor(n));
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new FloorFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "floor(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
/* Function.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Interface to be implemented by external functions that need to receive
|
||||
* parameter values.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public interface Function
|
||||
{
|
||||
|
||||
/**
|
||||
* Sets the list of expressions to evaluate as parameter values.
|
||||
*/
|
||||
void setArguments(List args);
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,163 @@
|
||||
/* FunctionCall.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import javax.xml.xpath.XPathFunction;
|
||||
import javax.xml.xpath.XPathFunctionException;
|
||||
import javax.xml.xpath.XPathFunctionResolver;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Executes an XPath core or extension function.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class FunctionCall
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final XPathFunctionResolver resolver;
|
||||
final String name;
|
||||
final List args;
|
||||
|
||||
public FunctionCall(XPathFunctionResolver resolver, String name)
|
||||
{
|
||||
this(resolver, name, Collections.EMPTY_LIST);
|
||||
}
|
||||
|
||||
public FunctionCall(XPathFunctionResolver resolver, String name, List args)
|
||||
{
|
||||
this.resolver = resolver;
|
||||
this.name = name;
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
if (resolver != null)
|
||||
{
|
||||
QName qname = QName.valueOf(name);
|
||||
int arity = args.size();
|
||||
XPathFunction function = resolver.resolveFunction(qname, arity);
|
||||
if (function != null)
|
||||
{
|
||||
//System.err.println("Calling "+toString()+" with "+values);
|
||||
if (function instanceof Expr)
|
||||
{
|
||||
if (function instanceof Function)
|
||||
{
|
||||
((Function) function).setArguments(args);
|
||||
}
|
||||
return ((Expr) function).evaluate(context, pos, len);
|
||||
}
|
||||
else
|
||||
{
|
||||
List values = new ArrayList(arity);
|
||||
for (int i = 0; i < arity; i++)
|
||||
{
|
||||
Expr arg = (Expr) args.get(i);
|
||||
values.add(arg.evaluate(context, pos, len));
|
||||
}
|
||||
try
|
||||
{
|
||||
return function.evaluate(values);
|
||||
}
|
||||
catch (XPathFunctionException e)
|
||||
{
|
||||
e.printStackTrace(System.err); // FIXME
|
||||
throw new RuntimeException(e.getMessage(), e);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
throw new IllegalArgumentException("Invalid function call: " +
|
||||
toString());
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
int len = args.size();
|
||||
List args2 = new ArrayList(len);
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
args2.add(((Expr) args.get(i)).clone(context));
|
||||
}
|
||||
XPathFunctionResolver r = resolver;
|
||||
if (context instanceof XPathFunctionResolver)
|
||||
{
|
||||
r = (XPathFunctionResolver) context;
|
||||
}
|
||||
return new FunctionCall(r, name, args2);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
for (Iterator i = args.iterator(); i.hasNext(); )
|
||||
{
|
||||
if (((Expr) i.next()).references(var))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
StringBuffer buf = new StringBuffer();
|
||||
buf.append(name);
|
||||
buf.append('(');
|
||||
int len = args.size();
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
if (i > 0)
|
||||
{
|
||||
buf.append(',');
|
||||
}
|
||||
buf.append(args.get(i));
|
||||
}
|
||||
buf.append(')');
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,102 @@
|
||||
/* IdFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>id</code> function selects elements by their unique ID.
|
||||
* When the argument to id is of type node-set, then the result is
|
||||
* the union of the result of applying id to the string-value of each of the
|
||||
* nodes in the argument node-set. When the argument to id is of any other
|
||||
* type, the argument is converted to a string as if by a call to the string
|
||||
* function; the string is split into a whitespace-separated list of tokens
|
||||
* (whitespace is any sequence of characters matching the production S); the
|
||||
* result is a node-set containing the elements in the same document as the
|
||||
* context node that have a unique ID equal to any of the tokens in the
|
||||
* list.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class IdFunction
|
||||
extends Pattern
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
IdFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
public IdFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public boolean matches(Node context)
|
||||
{
|
||||
Object ret = evaluate(context, 1, 1);
|
||||
return !((Collection) ret).isEmpty();
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
return _id(context, val);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new IdFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "id(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,116 @@
|
||||
/* LangFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Element;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>lang</code> function returns true or false depending on whether
|
||||
* the language of the context node as specified by xml:lang attributes is
|
||||
* the same as or is a sublanguage of the language specified by the argument
|
||||
* string. The language of the context node is determined by the value of
|
||||
* the xml:lang attribute on the context node, or, if the context node has
|
||||
* no xml:lang attribute, by the value of the xml:lang attribute on the
|
||||
* nearest ancestor of the context node that has an xml:lang attribute. If
|
||||
* there is no such attribute, then lang returns false. If there is such an
|
||||
* attribute, then lang returns true if the attribute value is equal to the
|
||||
* argument ignoring case, or if there is some suffix starting with - such
|
||||
* that the attribute value is equal to the argument ignoring that suffix of
|
||||
* the attribute value and ignoring case.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class LangFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
LangFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
LangFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
String lang = _string(context, val);
|
||||
String clang = getLang(context);
|
||||
while (clang == null && context != null)
|
||||
{
|
||||
context = context.getParentNode();
|
||||
clang = getLang(context);
|
||||
}
|
||||
boolean ret = (clang == null) ? false :
|
||||
clang.toLowerCase().startsWith(lang.toLowerCase());
|
||||
return ret ? Boolean.TRUE : Boolean.FALSE;
|
||||
}
|
||||
|
||||
String getLang(Node node)
|
||||
{
|
||||
if (node.getNodeType() == Node.ELEMENT_NODE)
|
||||
{
|
||||
return ((Element) node).getAttribute("xml:lang");
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new IdFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "lang(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,73 @@
|
||||
/* LastFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>last</code> function returns a number equal to the context
|
||||
* size from the expression evaluation context.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class LastFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
return new Double((double) len);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new LastFunction();
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "last()";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,93 @@
|
||||
/* LocalNameFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>local-name</code> function returns the local part of the
|
||||
* expanded-name of the node in the argument node-set that is first in
|
||||
* document order.
|
||||
* If the argument node-set is empty or the first node has no expanded-name,
|
||||
* an empty string is returned. If the argument is omitted, it defaults to a
|
||||
* node-set with the context node as its only member.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class LocalNameFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
LocalNameFunction(List args)
|
||||
{
|
||||
this(args.size() > 0 ? (Expr) args.get(0) : null);
|
||||
}
|
||||
|
||||
LocalNameFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = (arg == null) ? null : arg.evaluate(context, pos, len);
|
||||
return _local_name(context, (Collection) val);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new LocalNameFunction((arg == null) ? null :
|
||||
arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg == null) ? false : arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return (arg == null) ? "local-name()" : "local-name(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,101 @@
|
||||
/* NameFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>name</code> function returns a string containing a QName
|
||||
* representing the expanded-name of the node in the argument node-set that
|
||||
* is first in document order. The QName must represent the expanded-name
|
||||
* with respect to the namespace declarations in effect on the node whose
|
||||
* expanded-name is being represented. Typically, this will be the QName
|
||||
* that occurred in the XML source. This need not be the case if there are
|
||||
* namespace declarations in effect on the node that associate multiple
|
||||
* prefixes with the same namespace. However, an implementation may include
|
||||
* information about the original prefix in its representation of nodes; in
|
||||
* this case, an implementation can ensure that the returned string is
|
||||
* always the same as the QName used in the XML source. If the argument
|
||||
* node-set is empty or the first node has no expanded-name, an empty string
|
||||
* is returned. If the argument it omitted, it defaults to a node-set with
|
||||
* the context node as its only member.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class NameFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
NameFunction(List args)
|
||||
{
|
||||
this(args.size() > 0 ? (Expr) args.get(0) : null);
|
||||
}
|
||||
|
||||
NameFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = (arg == null) ? null : arg.evaluate(context, pos, len);
|
||||
return _name(context, (Collection) val);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new NameFunction((arg == null) ? null :
|
||||
arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg == null) ? false : arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return (arg == null) ? "name()" : "name(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,142 @@
|
||||
/* NameTest.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.XMLConstants;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Tests whether a node has the specified name.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class NameTest
|
||||
extends Test
|
||||
{
|
||||
|
||||
final QName qName;
|
||||
final boolean anyLocalName;
|
||||
final boolean any;
|
||||
|
||||
public NameTest(QName qName, boolean anyLocalName, boolean any)
|
||||
{
|
||||
this.anyLocalName = anyLocalName;
|
||||
this.any = any;
|
||||
this.qName = qName;
|
||||
}
|
||||
|
||||
public boolean matchesAny()
|
||||
{
|
||||
return any;
|
||||
}
|
||||
|
||||
public boolean matchesAnyLocalName()
|
||||
{
|
||||
return anyLocalName;
|
||||
}
|
||||
|
||||
public boolean matches(Node node, int pos, int len)
|
||||
{
|
||||
switch (node.getNodeType())
|
||||
{
|
||||
case Node.ATTRIBUTE_NODE:
|
||||
// Do not match namespace attributes
|
||||
String uri = node.getNamespaceURI();
|
||||
if (XMLConstants.XMLNS_ATTRIBUTE_NS_URI.equals(uri) ||
|
||||
XMLConstants.XMLNS_ATTRIBUTE.equals(node.getPrefix()) ||
|
||||
XMLConstants.XMLNS_ATTRIBUTE.equals(node.getNodeName()))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
// Fall through
|
||||
case Node.ELEMENT_NODE:
|
||||
break;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
if (any)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
String uri = qName.getNamespaceURI();
|
||||
String nodeUri = node.getNamespaceURI();
|
||||
String nodeLocalName = node.getLocalName();
|
||||
if (nodeLocalName != null && !equal(uri, nodeUri))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (anyLocalName)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
String localName = qName.getLocalPart();
|
||||
if (nodeLocalName != null)
|
||||
{
|
||||
nodeLocalName = node.getNodeName();
|
||||
}
|
||||
return (localName.equals(nodeLocalName));
|
||||
}
|
||||
|
||||
final boolean equal(String s1, String s2)
|
||||
{
|
||||
return (((s1 == null || s1.length() == 0) &&
|
||||
(s2 == null || s2.length() == 0)) ||
|
||||
s1 != null && s1.equals(s2));
|
||||
}
|
||||
|
||||
public Test clone(Object context)
|
||||
{
|
||||
return new NameTest(qName, anyLocalName, any);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString ()
|
||||
{
|
||||
if (any)
|
||||
{
|
||||
return "*";
|
||||
}
|
||||
return qName.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,128 @@
|
||||
/* NamespaceTest.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.XMLConstants;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Tests whether a namespace attribute has the specified name.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class NamespaceTest
|
||||
extends Test
|
||||
{
|
||||
|
||||
final QName qName;
|
||||
final boolean anyLocalName;
|
||||
final boolean any;
|
||||
|
||||
public NamespaceTest(QName qName, boolean anyLocalName, boolean any)
|
||||
{
|
||||
this.anyLocalName = anyLocalName;
|
||||
this.any = any;
|
||||
this.qName = qName;
|
||||
}
|
||||
|
||||
public boolean matchesAny()
|
||||
{
|
||||
return any;
|
||||
}
|
||||
|
||||
public boolean matchesAnyLocalName()
|
||||
{
|
||||
return anyLocalName;
|
||||
}
|
||||
|
||||
public boolean matches(Node node, int pos, int len)
|
||||
{
|
||||
switch (node.getNodeType())
|
||||
{
|
||||
case Node.ATTRIBUTE_NODE:
|
||||
// Only match namespace attributes
|
||||
String uri = node.getNamespaceURI();
|
||||
if (XMLConstants.XMLNS_ATTRIBUTE_NS_URI.equals(uri) ||
|
||||
XMLConstants.XMLNS_ATTRIBUTE.equals(node.getPrefix()) ||
|
||||
XMLConstants.XMLNS_ATTRIBUTE.equals(node.getNodeName()))
|
||||
{
|
||||
break;
|
||||
}
|
||||
// Fall through
|
||||
default:
|
||||
// Only process namespace attributes
|
||||
return false;
|
||||
}
|
||||
if (any)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
if (anyLocalName)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
String localName = qName.getLocalPart();
|
||||
String nodeLocalName = node.getLocalName();
|
||||
if (nodeLocalName == null)
|
||||
{
|
||||
nodeLocalName = node.getNodeName();
|
||||
}
|
||||
return (localName.equals(nodeLocalName));
|
||||
}
|
||||
|
||||
public Test clone(Object context)
|
||||
{
|
||||
return new NamespaceTest(qName, anyLocalName, any);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString ()
|
||||
{
|
||||
if (any)
|
||||
{
|
||||
return "*";
|
||||
}
|
||||
return qName.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,93 @@
|
||||
/* NamespaceUriFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>namespace-uri</code> function returns the namespace URI of the
|
||||
* expanded-name of the node in the argument node-set that is first in
|
||||
* document order. If the argument node-set is empty, the first node has no
|
||||
* expanded-name, or the namespace URI of the expanded-name is null, an
|
||||
* empty string is returned. If the argument is omitted, it defaults to a
|
||||
* node-set with the context node as its only member.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class NamespaceUriFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
NamespaceUriFunction(List args)
|
||||
{
|
||||
this(args.size() > 0 ? (Expr) args.get(0) : null);
|
||||
}
|
||||
|
||||
NamespaceUriFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = (arg == null) ? null : arg.evaluate(context, pos, len);
|
||||
return _namespace_uri(context, (Collection) val);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new NamespaceUriFunction((arg == null) ? null :
|
||||
arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg == null) ? false : arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return (arg == null) ? "namespace-uri()" : "namespace-uri(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,81 @@
|
||||
/* NegativeExpr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Unary negative.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class NegativeExpr
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr expr;
|
||||
|
||||
NegativeExpr(Expr expr)
|
||||
{
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = expr.evaluate(context, pos, len);
|
||||
double n = _number(context, val);
|
||||
return new Double(-n);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new NegativeExpr(expr.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return expr.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "-" + expr;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,136 @@
|
||||
/* NodeTypeTest.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Tests whether a node is of a given type.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class NodeTypeTest
|
||||
extends Test
|
||||
{
|
||||
|
||||
final short type;
|
||||
final String data;
|
||||
|
||||
public NodeTypeTest(short type)
|
||||
{
|
||||
this(type, null);
|
||||
}
|
||||
|
||||
public NodeTypeTest(short type, String data)
|
||||
{
|
||||
this.type = type;
|
||||
this.data = data;
|
||||
}
|
||||
|
||||
public short getNodeType()
|
||||
{
|
||||
return type;
|
||||
}
|
||||
|
||||
public String getData()
|
||||
{
|
||||
return data;
|
||||
}
|
||||
|
||||
public boolean matches(Node node, int pos, int len)
|
||||
{
|
||||
short nodeType = node.getNodeType();
|
||||
switch (nodeType)
|
||||
{
|
||||
case Node.ELEMENT_NODE:
|
||||
case Node.ATTRIBUTE_NODE:
|
||||
case Node.TEXT_NODE:
|
||||
case Node.CDATA_SECTION_NODE:
|
||||
case Node.COMMENT_NODE:
|
||||
case Node.PROCESSING_INSTRUCTION_NODE:
|
||||
if (type > 0)
|
||||
{
|
||||
if (nodeType != type)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (data != null && !data.equals(node.getNodeValue()))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
default:
|
||||
// Not part of XPath data model
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public Test clone(Object context)
|
||||
{
|
||||
return new NodeTypeTest(type, data);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case 0:
|
||||
return "node()";
|
||||
case Node.TEXT_NODE:
|
||||
return "text()";
|
||||
case Node.COMMENT_NODE:
|
||||
return "comment()";
|
||||
case Node.PROCESSING_INSTRUCTION_NODE:
|
||||
if (data != null)
|
||||
{
|
||||
return "processing-instruction('" + data + "')";
|
||||
}
|
||||
return "processing-instruction()";
|
||||
default:
|
||||
throw new IllegalStateException();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,105 @@
|
||||
/* NormalizeSpaceFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.StringTokenizer;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>normalize-space</code> function returns the argument string
|
||||
* with whitespace normalized by stripping leading and trailing whitespace
|
||||
* and replacing sequences of whitespace characters by a single space.
|
||||
* Whitespace characters are the same as those allowed by the S production
|
||||
* in XML. If the argument is omitted, it defaults to the context node
|
||||
* converted to a string, in other words the string-value of the context
|
||||
* node.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class NormalizeSpaceFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
NormalizeSpaceFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
NormalizeSpaceFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = (arg == null) ? null : arg.evaluate(context, pos, len);
|
||||
String s = _string(context, val);
|
||||
StringTokenizer st = new StringTokenizer(s, " \t\r\n");
|
||||
StringBuffer buf = new StringBuffer();
|
||||
if (st.hasMoreTokens())
|
||||
{
|
||||
buf.append(st.nextToken());
|
||||
while (st.hasMoreTokens())
|
||||
{
|
||||
buf.append(' ');
|
||||
buf.append(st.nextToken());
|
||||
}
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new NormalizeSpaceFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg == null) ? false : arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return (arg == null) ? "normalize-space()" : "normalize-space(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
/* NotFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>not</code> function returns true if its argument is false,
|
||||
* and false otherwise.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class NotFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
NotFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
NotFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
return _boolean(context, val) ? Boolean.FALSE : Boolean.TRUE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new NotFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "not(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,102 @@
|
||||
/* NumberFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>number</code> function converts its argument to a number as
|
||||
* follows:
|
||||
* <ul>
|
||||
* <li>a string that consists of optional whitespace followed by an optional
|
||||
* minus sign followed by a Number followed by whitespace is converted to
|
||||
* the IEEE 754 number that is nearest (according to the IEEE 754
|
||||
* round-to-nearest rule) to the mathematical value represented by the
|
||||
* string; any other string is converted to NaN</li>
|
||||
* <li>boolean true is converted to 1; boolean false is converted to 0</li>
|
||||
* <li>a node-set is first converted to a string as if by a call to the
|
||||
* string function and then converted in the same way as a string
|
||||
* argument</li>
|
||||
* <li>an object of a type other than the four basic types is converted to a
|
||||
* number in a way that is dependent on that type</li>
|
||||
* </ul>
|
||||
* If the argument is omitted, it defaults to a node-set with the context
|
||||
* node as its only member.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class NumberFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
NumberFunction(List args)
|
||||
{
|
||||
this(args.size() > 0 ? (Expr) args.get(0) : null);
|
||||
}
|
||||
|
||||
NumberFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = (arg == null) ? null : arg.evaluate(context, pos, len);
|
||||
return new Double(_number(context, val));
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new NumberFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "number(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
/* OrExpr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Logical or.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class OrExpr
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr lhs;
|
||||
final Expr rhs;
|
||||
|
||||
public OrExpr(Expr lhs, Expr rhs)
|
||||
{
|
||||
this.lhs = lhs;
|
||||
this.rhs = rhs;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object left = lhs.evaluate(context, pos, len);
|
||||
if (_boolean(context, left))
|
||||
{
|
||||
return Boolean.TRUE;
|
||||
}
|
||||
Object right = rhs.evaluate(context, pos, len);
|
||||
return _boolean(context, right) ? Boolean.TRUE : Boolean.FALSE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new OrExpr(lhs.clone(context), rhs.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (lhs.references(var) || rhs.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return lhs + " or " + rhs;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,90 @@
|
||||
/* ParenthesizedExpr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Simple subexpression.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class ParenthesizedExpr
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr expr;
|
||||
|
||||
ParenthesizedExpr(Expr expr)
|
||||
{
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object ret = expr.evaluate(context, pos, len);
|
||||
if (ret instanceof Collection)
|
||||
{
|
||||
List list = new ArrayList((Collection) ret);
|
||||
Collections.sort(list, documentOrderComparator);
|
||||
ret = list;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new ParenthesizedExpr(expr.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return expr.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "(" + expr + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
/* Path.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* An XPath path component expression.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
abstract class Path
|
||||
extends Pattern
|
||||
{
|
||||
|
||||
abstract Collection evaluate(Node context, Collection nodeSet);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
/* Pattern.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Interface implemented by expressions that can form part of XSL patterns.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public abstract class Pattern
|
||||
extends Expr
|
||||
{
|
||||
|
||||
public abstract boolean matches(Node context);
|
||||
|
||||
}
|
||||
|
||||
@@ -0,0 +1,73 @@
|
||||
/* PositionFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>position</code> function returns a number equal to the context
|
||||
* position from the expression evaluation context.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class PositionFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
return new Double((double) pos);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new PositionFunction();
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "position()";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,85 @@
|
||||
/* Predicate.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Tests whether an expression matches against a given context node.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
class Predicate
|
||||
extends Test
|
||||
{
|
||||
|
||||
final Expr expr;
|
||||
|
||||
Predicate(Expr expr)
|
||||
{
|
||||
this.expr = expr;
|
||||
}
|
||||
|
||||
public boolean matches(Node node, int pos, int len)
|
||||
{
|
||||
Object ret = expr.evaluate(node, pos, len);
|
||||
if (ret instanceof Double)
|
||||
{
|
||||
// Same as [position() = x]
|
||||
return ((Double) ret).intValue() == pos;
|
||||
}
|
||||
return Expr._boolean(node, expr.evaluate(node, pos, len));
|
||||
}
|
||||
|
||||
public Test clone(Object context)
|
||||
{
|
||||
return new Predicate(expr.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return expr.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "[" + expr + "]";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,107 @@
|
||||
/* RelationalExpr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Numerical comparison expression.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class RelationalExpr
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr lhs;
|
||||
final Expr rhs;
|
||||
final boolean lt;
|
||||
final boolean eq;
|
||||
|
||||
RelationalExpr(Expr lhs, Expr rhs, boolean lt, boolean eq)
|
||||
{
|
||||
this.lhs = lhs;
|
||||
this.rhs = rhs;
|
||||
this.lt = lt;
|
||||
this.eq = eq;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object left = lhs.evaluate(context, pos, len);
|
||||
Object right = rhs.evaluate(context, pos, len);
|
||||
double ln = _number(context, left);
|
||||
double rn = _number(context, right);
|
||||
if (eq && ln == rn)
|
||||
{
|
||||
return Boolean.TRUE;
|
||||
}
|
||||
if (lt)
|
||||
{
|
||||
if (ln < rn || Double.isInfinite(rn))
|
||||
{
|
||||
return Boolean.TRUE;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ln > rn || Double.isInfinite(ln))
|
||||
{
|
||||
return Boolean.TRUE;
|
||||
}
|
||||
}
|
||||
return Boolean.FALSE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new RelationalExpr(lhs.clone(context), rhs.clone(context), lt, eq);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (lhs.references(var) || rhs.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return lhs + " " + (lt ? "<" : ">") + (eq ? "=" : "") + " " + rhs;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
/* Root.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* Expression that evaluates to the document root.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class Root
|
||||
extends Path
|
||||
{
|
||||
|
||||
public boolean matches(Node node)
|
||||
{
|
||||
return (node.getNodeType() == Node.DOCUMENT_NODE);
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
return evaluate(context, Collections.EMPTY_SET);
|
||||
}
|
||||
|
||||
Collection evaluate(Node context, Collection ns)
|
||||
{
|
||||
Document doc = (context instanceof Document) ? (Document) context :
|
||||
context.getOwnerDocument();
|
||||
return Collections.singleton(doc);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new Root();
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "/";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,96 @@
|
||||
/* RoundFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>round</code> function returns the number that is closest to the
|
||||
* argument and that is an integer. If there are two such numbers, then the
|
||||
* one that is closest to positive infinity is returned. If the argument is
|
||||
* NaN, then NaN is returned. If the argument is positive infinity, then
|
||||
* positive infinity is returned. If the argument is negative infinity, then
|
||||
* negative infinity is returned. If the argument is positive zero, then
|
||||
* positive zero is returned. If the argument is negative zero, then
|
||||
* negative zero is returned. If the argument is less than zero, but greater
|
||||
* than or equal to -0.5, then negative zero is returned.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class RoundFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
RoundFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
RoundFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
double n = _number(context, val);
|
||||
return (Double.isNaN(n) || Double.isInfinite(n)) ?
|
||||
new Double(n) : new Double(Math.round(n));
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new RoundFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "round(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,519 @@
|
||||
/* Selector.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import javax.xml.XMLConstants;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Attr;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* A single component of a location path.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class Selector
|
||||
extends Path
|
||||
{
|
||||
|
||||
public static final int ANCESTOR = 0;
|
||||
public static final int ANCESTOR_OR_SELF = 1;
|
||||
public static final int ATTRIBUTE = 2;
|
||||
public static final int CHILD = 3;
|
||||
public static final int DESCENDANT = 4;
|
||||
public static final int DESCENDANT_OR_SELF = 5;
|
||||
public static final int FOLLOWING = 6;
|
||||
public static final int FOLLOWING_SIBLING = 7;
|
||||
public static final int NAMESPACE = 8;
|
||||
public static final int PARENT = 9;
|
||||
public static final int PRECEDING = 10;
|
||||
public static final int PRECEDING_SIBLING = 11;
|
||||
public static final int SELF = 12;
|
||||
|
||||
/**
|
||||
* Axis to select nodes in.
|
||||
*/
|
||||
final int axis;
|
||||
|
||||
/**
|
||||
* List of tests to perform on candidates.
|
||||
*/
|
||||
final Test[] tests;
|
||||
|
||||
public Selector(int axis, List tests)
|
||||
{
|
||||
this.axis = axis;
|
||||
this.tests = new Test[tests.size()];
|
||||
tests.toArray(this.tests);
|
||||
if (axis == NAMESPACE &&
|
||||
this.tests.length > 0 &&
|
||||
this.tests[0] instanceof NameTest)
|
||||
{
|
||||
NameTest nt = (NameTest) this.tests[0];
|
||||
this.tests[0] = new NamespaceTest(nt.qName, nt.anyLocalName, nt.any);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the list of tests to perform on candidates.
|
||||
*/
|
||||
public Test[] getTests()
|
||||
{
|
||||
return tests;
|
||||
}
|
||||
|
||||
public boolean matches(Node context)
|
||||
{
|
||||
short nodeType = context.getNodeType();
|
||||
switch (axis)
|
||||
{
|
||||
case CHILD:
|
||||
if (nodeType == Node.ATTRIBUTE_NODE)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
case ATTRIBUTE:
|
||||
case NAMESPACE:
|
||||
if (nodeType != Node.ATTRIBUTE_NODE)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
break;
|
||||
case DESCENDANT_OR_SELF:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
int tlen = tests.length;
|
||||
if (tlen > 0)
|
||||
{
|
||||
int pos = getContextPosition(context);
|
||||
int len = getContextSize(context);
|
||||
for (int j = 0; j < tlen && len > 0; j++)
|
||||
{
|
||||
Test test = tests[j];
|
||||
if (!test.matches(context, pos, len))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private int getContextPosition(Node ctx)
|
||||
{
|
||||
int pos = 1;
|
||||
for (ctx = ctx.getPreviousSibling(); ctx != null;
|
||||
ctx = ctx.getPreviousSibling())
|
||||
{
|
||||
pos++;
|
||||
}
|
||||
return pos;
|
||||
}
|
||||
|
||||
private int getContextSize(Node ctx)
|
||||
{
|
||||
if (ctx.getNodeType() == Node.ATTRIBUTE_NODE)
|
||||
{
|
||||
Node parent = ((Attr) ctx).getOwnerElement();
|
||||
return parent.getAttributes().getLength();
|
||||
}
|
||||
Node parent = ctx.getParentNode();
|
||||
if (parent != null)
|
||||
{
|
||||
return parent.getChildNodes().getLength();
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Set acc = new LinkedHashSet();
|
||||
addCandidates(context, acc);
|
||||
List candidates = new ArrayList(acc);
|
||||
//Collections.sort(candidates, documentOrderComparator);
|
||||
List ret = filterCandidates(candidates, false);
|
||||
return ret;
|
||||
}
|
||||
|
||||
Collection evaluate(Node context, Collection ns)
|
||||
{
|
||||
Set acc = new LinkedHashSet();
|
||||
for (Iterator i = ns.iterator(); i.hasNext(); )
|
||||
{
|
||||
addCandidates((Node) i.next(), acc);
|
||||
}
|
||||
List candidates = new ArrayList(acc);
|
||||
//Collections.sort(candidates, documentOrderComparator);
|
||||
List ret = filterCandidates(candidates, true);
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
* Filter the given list of candidates according to the node tests.
|
||||
*/
|
||||
List filterCandidates(List candidates, boolean cascade)
|
||||
{
|
||||
int len = candidates.size();
|
||||
int tlen = tests.length;
|
||||
if (tlen > 0 && len > 0)
|
||||
{
|
||||
// Present the result of each successful generation to the next test
|
||||
for (int j = 0; j < tlen && len > 0; j++)
|
||||
{
|
||||
Test test = tests[j];
|
||||
List successful = new ArrayList(len);
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
Node node = (Node) candidates.get(i);
|
||||
if (cascade)
|
||||
{
|
||||
// Documents and DocumentFragments should be considered
|
||||
// if part of a location path where the axis involves
|
||||
// the SELF concept
|
||||
short nodeType = node.getNodeType();
|
||||
if ((nodeType == Node.DOCUMENT_NODE ||
|
||||
nodeType == Node.DOCUMENT_FRAGMENT_NODE) &&
|
||||
(axis == DESCENDANT_OR_SELF ||
|
||||
axis == ANCESTOR_OR_SELF ||
|
||||
axis == SELF) &&
|
||||
(tests.length == 1 &&
|
||||
tests[0] instanceof NodeTypeTest &&
|
||||
((NodeTypeTest) tests[0]).type == (short) 0))
|
||||
{
|
||||
successful.add(node);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
if (test.matches(node, i + 1, len))
|
||||
{
|
||||
successful.add(node);
|
||||
}
|
||||
/*
|
||||
System.err.println("Testing "+node);
|
||||
int p = getContextPosition(node);
|
||||
int l = getContextSize(node);
|
||||
if (test.matches(node, p, l))
|
||||
{
|
||||
successful.add(node);
|
||||
}*/
|
||||
}
|
||||
candidates = successful;
|
||||
len = candidates.size();
|
||||
}
|
||||
}
|
||||
return candidates;
|
||||
}
|
||||
|
||||
void addCandidates(Node context, Collection candidates)
|
||||
{
|
||||
// Build list of candidates
|
||||
switch (axis)
|
||||
{
|
||||
case CHILD:
|
||||
addChildNodes(context, candidates, false);
|
||||
break;
|
||||
case DESCENDANT:
|
||||
addChildNodes(context, candidates, true);
|
||||
break;
|
||||
case DESCENDANT_OR_SELF:
|
||||
candidates.add (context);
|
||||
addChildNodes(context, candidates, true);
|
||||
break;
|
||||
case PARENT:
|
||||
addParentNode(context, candidates, false);
|
||||
break;
|
||||
case ANCESTOR:
|
||||
addParentNode(context, candidates, true);
|
||||
break;
|
||||
case ANCESTOR_OR_SELF:
|
||||
candidates.add(context);
|
||||
addParentNode(context, candidates, true);
|
||||
break;
|
||||
case FOLLOWING_SIBLING:
|
||||
addFollowingNodes(context, candidates, false);
|
||||
break;
|
||||
case PRECEDING_SIBLING:
|
||||
addPrecedingNodes(context, candidates, false);
|
||||
break;
|
||||
case FOLLOWING:
|
||||
addFollowingNodes(context, candidates, true);
|
||||
break;
|
||||
case PRECEDING:
|
||||
addPrecedingNodes(context, candidates, true);
|
||||
break;
|
||||
case ATTRIBUTE:
|
||||
addAttributes(context, candidates);
|
||||
break;
|
||||
case NAMESPACE:
|
||||
addNamespaceAttributes(context, candidates);
|
||||
break;
|
||||
case SELF:
|
||||
candidates.add(context);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void addChildNodes(Node context, Collection acc, boolean recurse)
|
||||
{
|
||||
Node child = context.getFirstChild();
|
||||
while (child != null)
|
||||
{
|
||||
acc.add(child);
|
||||
if (recurse)
|
||||
{
|
||||
addChildNodes(child, acc, recurse);
|
||||
}
|
||||
child = child.getNextSibling();
|
||||
}
|
||||
}
|
||||
|
||||
void addParentNode(Node context, Collection acc, boolean recurse)
|
||||
{
|
||||
Node parent = (context.getNodeType() == Node.ATTRIBUTE_NODE) ?
|
||||
((Attr) context).getOwnerElement() : context.getParentNode();
|
||||
if (parent != null)
|
||||
{
|
||||
acc.add(parent);
|
||||
if (recurse)
|
||||
{
|
||||
addParentNode(parent, acc, recurse);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void addFollowingNodes(Node context, Collection acc, boolean recurse)
|
||||
{
|
||||
Node cur = context.getNextSibling();
|
||||
while (cur != null)
|
||||
{
|
||||
acc.add(cur);
|
||||
if (recurse)
|
||||
{
|
||||
addChildNodes(cur, acc, true);
|
||||
}
|
||||
cur = cur.getNextSibling();
|
||||
}
|
||||
if (recurse)
|
||||
{
|
||||
context = (context.getNodeType() == Node.ATTRIBUTE_NODE) ?
|
||||
((Attr) context).getOwnerElement() : context.getParentNode();
|
||||
if (context != null)
|
||||
{
|
||||
addFollowingNodes(context, acc, recurse);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void addPrecedingNodes(Node context, Collection acc, boolean recurse)
|
||||
{
|
||||
Node cur = context.getPreviousSibling();
|
||||
while (cur != null)
|
||||
{
|
||||
acc.add(cur);
|
||||
if (recurse)
|
||||
{
|
||||
addChildNodes(cur, acc, true);
|
||||
}
|
||||
cur = cur.getPreviousSibling();
|
||||
}
|
||||
if (recurse)
|
||||
{
|
||||
context = (context.getNodeType() == Node.ATTRIBUTE_NODE) ?
|
||||
((Attr) context).getOwnerElement() : context.getParentNode();
|
||||
if (context != null)
|
||||
{
|
||||
addPrecedingNodes(context, acc, recurse);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void addAttributes(Node context, Collection acc)
|
||||
{
|
||||
NamedNodeMap attrs = context.getAttributes();
|
||||
if (attrs != null)
|
||||
{
|
||||
int attrLen = attrs.getLength();
|
||||
for (int i = 0; i < attrLen; i++)
|
||||
{
|
||||
Node attr = attrs.item(i);
|
||||
if (!isNamespaceAttribute(attr))
|
||||
{
|
||||
acc.add(attr);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void addNamespaceAttributes(Node context, Collection acc)
|
||||
{
|
||||
NamedNodeMap attrs = context.getAttributes();
|
||||
if (attrs != null)
|
||||
{
|
||||
int attrLen = attrs.getLength();
|
||||
for (int i = 0; i < attrLen; i++)
|
||||
{
|
||||
Node attr = attrs.item(i);
|
||||
if (isNamespaceAttribute(attr))
|
||||
{
|
||||
acc.add(attr);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
final boolean isNamespaceAttribute(Node node)
|
||||
{
|
||||
String uri = node.getNamespaceURI();
|
||||
return (XMLConstants.XMLNS_ATTRIBUTE_NS_URI.equals(uri) ||
|
||||
XMLConstants.XMLNS_ATTRIBUTE.equals(node.getPrefix()) ||
|
||||
XMLConstants.XMLNS_ATTRIBUTE.equals(node.getNodeName()));
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
int len = tests.length;
|
||||
List tests2 = new ArrayList(len);
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
tests2.add(tests[i].clone(context));
|
||||
}
|
||||
return new Selector(axis, tests2);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
for (int i = 0; i < tests.length; i++)
|
||||
{
|
||||
if (tests[i].references(var))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
StringBuffer buf = new StringBuffer();
|
||||
switch (axis)
|
||||
{
|
||||
case ANCESTOR:
|
||||
buf.append("ancestor::");
|
||||
break;
|
||||
case ANCESTOR_OR_SELF:
|
||||
buf.append("ancestor-or-self::");
|
||||
break;
|
||||
case ATTRIBUTE:
|
||||
if (tests.length == 0 ||
|
||||
(tests[0] instanceof NameTest))
|
||||
{
|
||||
buf.append('@');
|
||||
}
|
||||
else
|
||||
{
|
||||
buf.append("attribute::");
|
||||
}
|
||||
break;
|
||||
case CHILD:
|
||||
//buf.append("child::");
|
||||
break;
|
||||
case DESCENDANT:
|
||||
buf.append("descendant::");
|
||||
break;
|
||||
case DESCENDANT_OR_SELF:
|
||||
buf.append("descendant-or-self::");
|
||||
break;
|
||||
case FOLLOWING:
|
||||
buf.append("following::");
|
||||
break;
|
||||
case FOLLOWING_SIBLING:
|
||||
buf.append("following-sibling::");
|
||||
break;
|
||||
case NAMESPACE:
|
||||
buf.append("namespace::");
|
||||
break;
|
||||
case PARENT:
|
||||
if (tests.length == 0 ||
|
||||
(tests[0] instanceof NodeTypeTest &&
|
||||
((NodeTypeTest) tests[0]).type == 0))
|
||||
{
|
||||
return "..";
|
||||
}
|
||||
buf.append("parent::");
|
||||
break;
|
||||
case PRECEDING:
|
||||
buf.append("preceding::");
|
||||
break;
|
||||
case PRECEDING_SIBLING:
|
||||
buf.append("preceding-sibling::");
|
||||
break;
|
||||
case SELF:
|
||||
if (tests.length == 0 ||
|
||||
(tests[0] instanceof NodeTypeTest &&
|
||||
((NodeTypeTest) tests[0]).type == 0))
|
||||
{
|
||||
return ".";
|
||||
}
|
||||
buf.append("self::");
|
||||
break;
|
||||
}
|
||||
if (tests.length == 0)
|
||||
{
|
||||
buf.append('*');
|
||||
}
|
||||
else
|
||||
{
|
||||
for (int i = 0; i < tests.length; i++)
|
||||
{
|
||||
buf.append(tests[i]);
|
||||
}
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,92 @@
|
||||
/* StartsWithFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>starts-with</code> function returns true if the first argument
|
||||
* string starts with the second argument string, and otherwise returns false.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class StartsWithFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg1;
|
||||
final Expr arg2;
|
||||
|
||||
StartsWithFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0), (Expr) args.get(1));
|
||||
}
|
||||
|
||||
StartsWithFunction(Expr arg1, Expr arg2)
|
||||
{
|
||||
this.arg1 = arg1;
|
||||
this.arg2 = arg2;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val1 = arg1.evaluate(context, pos, len);
|
||||
Object val2 = arg2.evaluate(context, pos, len);
|
||||
String s1 = _string(context, val1);
|
||||
String s2 = _string(context, val2);
|
||||
return s1.startsWith(s2) ? Boolean.TRUE : Boolean.FALSE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new StartsWithFunction(arg1.clone(context), arg2.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg1.references(var) || arg2.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "starts-with(" + arg1 + "," + arg2 + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,253 @@
|
||||
/* Steps.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.Iterator;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.LinkedList;
|
||||
import java.util.Set;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Attr;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* A list of transitions between components in a location path.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class Steps
|
||||
extends Path
|
||||
{
|
||||
|
||||
final LinkedList path;
|
||||
|
||||
public Steps()
|
||||
{
|
||||
this(new LinkedList());
|
||||
}
|
||||
|
||||
Steps(LinkedList path)
|
||||
{
|
||||
this.path = path;
|
||||
}
|
||||
|
||||
public boolean matches(Node context)
|
||||
{
|
||||
// Right to left
|
||||
return matches(context, path.size() - 1);
|
||||
}
|
||||
|
||||
boolean matches(Node context, int pos)
|
||||
{
|
||||
Pattern right = (Pattern) path.get(pos);
|
||||
if (!right.matches(context))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
if (pos > 0)
|
||||
{
|
||||
Pattern left = (Pattern) path.get(pos - 1);
|
||||
Iterator j = possibleContexts(right, context).iterator();
|
||||
while (j.hasNext())
|
||||
{
|
||||
Node candidate = (Node) j.next();
|
||||
if (left.matches(candidate) &&
|
||||
matches(candidate, pos - 1))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
// keep going, there may be another candidate
|
||||
}
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Essentially the reverse of Selector.addCandidates.
|
||||
* The idea is to determine possible context nodes for a match.
|
||||
*/
|
||||
Collection possibleContexts(Pattern pattern, Node context)
|
||||
{
|
||||
if (pattern instanceof Selector)
|
||||
{
|
||||
Selector s = (Selector) pattern;
|
||||
Collection candidates = new LinkedHashSet();
|
||||
switch (s.axis)
|
||||
{
|
||||
case Selector.PARENT:
|
||||
s.addChildNodes(context, candidates, false);
|
||||
break;
|
||||
case Selector.ANCESTOR:
|
||||
s.addChildNodes(context, candidates, true);
|
||||
break;
|
||||
case Selector.ANCESTOR_OR_SELF:
|
||||
candidates.add (context);
|
||||
s.addChildNodes(context, candidates, true);
|
||||
break;
|
||||
case Selector.CHILD:
|
||||
s.addParentNode(context, candidates, false);
|
||||
break;
|
||||
case Selector.DESCENDANT:
|
||||
s.addParentNode(context, candidates, true);
|
||||
break;
|
||||
case Selector.DESCENDANT_OR_SELF:
|
||||
candidates.add(context);
|
||||
s.addParentNode(context, candidates, true);
|
||||
break;
|
||||
case Selector.PRECEDING_SIBLING:
|
||||
s.addFollowingNodes(context, candidates, false);
|
||||
break;
|
||||
case Selector.FOLLOWING_SIBLING:
|
||||
s.addPrecedingNodes(context, candidates, false);
|
||||
break;
|
||||
case Selector.PRECEDING:
|
||||
s.addFollowingNodes(context, candidates, true);
|
||||
break;
|
||||
case Selector.FOLLOWING:
|
||||
s.addPrecedingNodes(context, candidates, true);
|
||||
break;
|
||||
case Selector.ATTRIBUTE:
|
||||
case Selector.NAMESPACE:
|
||||
if (context.getNodeType() == Node.ATTRIBUTE_NODE)
|
||||
{
|
||||
candidates.add(((Attr) context).getOwnerElement());
|
||||
}
|
||||
break;
|
||||
case Selector.SELF:
|
||||
candidates.add(context);
|
||||
break;
|
||||
}
|
||||
return candidates;
|
||||
}
|
||||
return Collections.EMPTY_SET;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
//System.err.println(toString()+" evaluate");
|
||||
// Left to right
|
||||
Iterator i = path.iterator();
|
||||
Expr lhs = (Expr) i.next();
|
||||
Object val = lhs.evaluate(context, pos, len);
|
||||
//System.err.println("\tevaluate "+lhs+" = "+val);
|
||||
while (val instanceof Collection && i.hasNext())
|
||||
{
|
||||
Path rhs = (Path) i.next();
|
||||
val = rhs.evaluate(context, (Collection) val);
|
||||
//System.err.println("\tevaluate "+rhs+" = "+val);
|
||||
}
|
||||
return val;
|
||||
}
|
||||
|
||||
Collection evaluate(Node context, Collection ns)
|
||||
{
|
||||
// Left to right
|
||||
Iterator i = path.iterator();
|
||||
Expr lhs = (Expr) i.next();
|
||||
if (lhs instanceof Path)
|
||||
{
|
||||
ns = ((Path) lhs).evaluate(context, ns);
|
||||
}
|
||||
else
|
||||
{
|
||||
Set acc = new LinkedHashSet();
|
||||
int pos = 1, len = ns.size();
|
||||
for (Iterator j = ns.iterator(); j.hasNext(); )
|
||||
{
|
||||
Node node = (Node) j.next();
|
||||
Object ret = lhs.evaluate(node, pos++, len);
|
||||
if (ret instanceof Collection)
|
||||
{
|
||||
acc.addAll((Collection) ret);
|
||||
}
|
||||
}
|
||||
ns = acc;
|
||||
}
|
||||
while (i.hasNext())
|
||||
{
|
||||
Path rhs = (Path) i.next();
|
||||
ns = rhs.evaluate(context, ns);
|
||||
}
|
||||
return ns;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
int len = path.size();
|
||||
LinkedList path2 = new LinkedList();
|
||||
for (int i = 0; i < len; i++)
|
||||
{
|
||||
path2.add(((Expr) path.get(i)).clone(context));
|
||||
}
|
||||
return new Steps(path2);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
for (Iterator i = path.iterator(); i.hasNext(); )
|
||||
{
|
||||
if (((Expr) i.next()).references(var))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
StringBuffer buf = new StringBuffer();
|
||||
Iterator i = path.iterator();
|
||||
Expr expr = (Expr) i.next();
|
||||
if (!(expr instanceof Root))
|
||||
{
|
||||
buf.append(expr);
|
||||
}
|
||||
while (i.hasNext())
|
||||
{
|
||||
expr = (Expr) i.next();
|
||||
buf.append('/');
|
||||
buf.append(expr);
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,119 @@
|
||||
/* StringFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>string function converts an object to a string as follows:
|
||||
* <ul>
|
||||
* <li>A node-set is converted to a string by returning the string-value of
|
||||
* the node in the node-set that is first in document order. If the node-set
|
||||
* is empty, an empty string is returned.</li>
|
||||
* <li>A number is converted to a string as follows
|
||||
* <ul>
|
||||
* <li>NaN is converted to the string NaN</li>
|
||||
* <li>positive zero is converted to the string 0</li>
|
||||
* <li>negative zero is converted to the string 0</li>
|
||||
* <li>positive infinity is converted to the string Infinity</li>
|
||||
* <li>negative infinity is converted to the string -Infinity</li>
|
||||
* <li>if the number is an integer, the number is represented in decimal
|
||||
* form as a Number with no decimal point and no leading zeros, preceded by
|
||||
* a minus sign (-) if the number is negative</li>
|
||||
* <li>otherwise, the number is represented in decimal form as a Number
|
||||
* including a decimal point with at least one digit before the decimal
|
||||
* point and at least one digit after the decimal point, preceded by a minus
|
||||
* sign (-) if the number is negative; there must be no leading zeros before
|
||||
* the decimal point apart possibly from the one required digit immediately
|
||||
* before the decimal point; beyond the one required digit after the decimal
|
||||
* point there must be as many, but only as many, more digits as are needed
|
||||
* to uniquely distinguish the number from all other IEEE 754 numeric
|
||||
* values.</li>
|
||||
* </ul>
|
||||
* </li>
|
||||
* <li>The boolean false value is converted to the string false. The boolean
|
||||
* true value is converted to the string true.</li>
|
||||
* <li>An object of a type other than the four basic types is converted to a
|
||||
* string in a way that is dependent on that type.</li>
|
||||
* </ul>
|
||||
* If the argument is omitted, it defaults to a node-set with the context
|
||||
* node as its only member.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class StringFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
StringFunction(List args)
|
||||
{
|
||||
this(args.size() > 0 ? (Expr) args.get(0) : null);
|
||||
}
|
||||
|
||||
StringFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = (arg == null) ? null : arg.evaluate(context, pos, len);
|
||||
return _string(context, val);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new StringFunction((arg == null) ? null :
|
||||
arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg == null) ? false : arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return (arg == null) ? "string()" : "string(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,91 @@
|
||||
/* StringLengthFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>string-length</code> function returns the number of characters
|
||||
* in the string.
|
||||
* If the argument is omitted, it defaults to the context node converted to
|
||||
* a string, in other words the string-value of the context node.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class StringLengthFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
StringLengthFunction(List args)
|
||||
{
|
||||
this(args.isEmpty() ? null : (Expr) args.get(0));
|
||||
}
|
||||
|
||||
StringLengthFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = (arg == null) ? null : arg.evaluate(context, pos, len);
|
||||
String s = _string(context, val);
|
||||
return new Double((double) s.length());
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new StringLengthFunction((arg == null) ? null :
|
||||
arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg == null) ? false : arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return (arg == null) ? "string-length()" : "string-length(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,98 @@
|
||||
/* SubstringAfterFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>substring-after</code> function returns the substring of the
|
||||
* first argument string that follows the first occurrence of the second
|
||||
* argument string in the first argument string, or the empty string if the
|
||||
* first argument string does not contain the second argument string. For
|
||||
* example, substring-after("1999/04/01","/") returns 04/01, and
|
||||
* substring-after("1999/04/01","19") returns 99/04/01.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class SubstringAfterFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg1;
|
||||
final Expr arg2;
|
||||
|
||||
SubstringAfterFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0), (Expr) args.get(1));
|
||||
}
|
||||
|
||||
SubstringAfterFunction(Expr arg1, Expr arg2)
|
||||
{
|
||||
this.arg1 = arg1;
|
||||
this.arg2 = arg2;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val1 = arg1.evaluate(context, pos, len);
|
||||
Object val2 = arg2.evaluate(context, pos, len);
|
||||
String s1 = _string(context, val1);
|
||||
String s2 = _string(context, val2);
|
||||
int index = s1.indexOf(s2);
|
||||
return (index == -1) ? "" : s1.substring(index + s2.length());
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new SubstringAfterFunction(arg1.clone(context),
|
||||
arg2.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg1.references(var) || arg2.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "substring-after(" + arg1 + "," + arg2 + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,97 @@
|
||||
/* SubstringBeforeFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>substring-before</code> function returns the substring of the
|
||||
* first argument string that precedes the first occurrence of the second
|
||||
* argument string in the first argument string, or the empty string if the
|
||||
* first argument string does not contain the second argument string. For
|
||||
* example, substring-before("1999/04/01","/") returns 1999.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class SubstringBeforeFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg1;
|
||||
final Expr arg2;
|
||||
|
||||
SubstringBeforeFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0), (Expr) args.get(1));
|
||||
}
|
||||
|
||||
SubstringBeforeFunction(Expr arg1, Expr arg2)
|
||||
{
|
||||
this.arg1 = arg1;
|
||||
this.arg2 = arg2;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val1 = arg1.evaluate(context, pos, len);
|
||||
Object val2 = arg2.evaluate(context, pos, len);
|
||||
String s1 = _string(context, val1);
|
||||
String s2 = _string(context, val2);
|
||||
int index = s1.indexOf(s2);
|
||||
return (index == -1) ? "" : s1.substring(0, index);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new SubstringBeforeFunction(arg1.clone(context),
|
||||
arg2.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg1.references(var) || arg2.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "substring-before(" + arg1 + "," + arg2 + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,129 @@
|
||||
/* SubstringFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The substring function returns the substring of the first argument
|
||||
* starting at the position specified in the second argument with length
|
||||
* specified in the third argument. For example, substring("12345",2,3)
|
||||
* returns "234". If the third argument is not specified, it returns the
|
||||
* substring starting at the position specified in the second argument and
|
||||
* continuing to the end of the string. For example, substring("12345",2)
|
||||
* returns "2345".
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class SubstringFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg1;
|
||||
final Expr arg2;
|
||||
final Expr arg3;
|
||||
|
||||
SubstringFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0), (Expr) args.get(1),
|
||||
(args.size() > 2) ? (Expr) args.get(2) : null);
|
||||
}
|
||||
|
||||
SubstringFunction(Expr arg1, Expr arg2, Expr arg3)
|
||||
{
|
||||
this.arg1 = arg1;
|
||||
this.arg2 = arg2;
|
||||
this.arg3 = arg3;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val1 = arg1.evaluate(context, pos, len);
|
||||
Object val2 = arg2.evaluate(context, pos, len);
|
||||
String s = _string(context, val1);
|
||||
int p = (val2 instanceof Double) ?
|
||||
((Double) val2).intValue() :
|
||||
(int) Math.round(_number(context, val2));
|
||||
p--;
|
||||
if (p < 0)
|
||||
{
|
||||
p = 0;
|
||||
}
|
||||
|
||||
int l = s.length() - p;
|
||||
if (l <= 0)
|
||||
{
|
||||
return "";
|
||||
}
|
||||
|
||||
if (arg3 != null)
|
||||
{
|
||||
Object val3 = arg3.evaluate(context, pos, len);
|
||||
int v3 = (val3 instanceof Double) ?
|
||||
((Double) val3).intValue() :
|
||||
(int) Math.round(_number(context, val3));
|
||||
if (v3 < l)
|
||||
{
|
||||
l = v3;
|
||||
}
|
||||
}
|
||||
|
||||
return s.substring(p, p + l);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new SubstringFunction(arg1.clone(context), arg2.clone(context),
|
||||
(arg3 == null) ? null : arg3.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg1.references(var) || arg2.references(var) ||
|
||||
(arg3 == null) ? false : arg3.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return (arg3 == null) ? "substring(" + arg1 + "," + arg2 + ")" :
|
||||
"substring(" + arg1 + "," + arg2 + "," + arg3 + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,100 @@
|
||||
/* SumFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>sum</code> function returns the sum, for each node in the
|
||||
* argument node-set, of the result of converting the string-values of the
|
||||
* node to a number.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class SumFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg;
|
||||
|
||||
SumFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0));
|
||||
}
|
||||
|
||||
SumFunction(Expr arg)
|
||||
{
|
||||
this.arg = arg;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val = arg.evaluate(context, pos, len);
|
||||
double sum = 0.0d;
|
||||
if (val instanceof Collection)
|
||||
{
|
||||
for (Iterator i = ((Collection) val).iterator(); i.hasNext(); )
|
||||
{
|
||||
Node node = (Node) i.next();
|
||||
String s = stringValue(node);
|
||||
sum += _number(context, s);
|
||||
}
|
||||
}
|
||||
return new Double(sum);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new SumFunction(arg.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return arg.references(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "sum(" + arg + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,58 @@
|
||||
/* Test.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* A test that can be performed on a node to determine whether to include it
|
||||
* in a selection.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public abstract class Test
|
||||
{
|
||||
|
||||
public abstract boolean matches(Node node, int pos, int len);
|
||||
|
||||
public abstract Test clone(Object context);
|
||||
|
||||
public abstract boolean references(QName var);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,133 @@
|
||||
/* TranslateFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.List;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>translate</code> function returns the first argument string
|
||||
* with occurrences of characters in the second argument string replaced by
|
||||
* the character at the corresponding position in the third argument string.
|
||||
* For example, translate("bar","abc","ABC") returns the string BAr. If
|
||||
* there is a character in the second argument string with no character at a
|
||||
* corresponding position in the third argument string (because the second
|
||||
* argument string is longer than the third argument string), then
|
||||
* occurrences of that character in the first argument string are removed.
|
||||
* For example, translate("--aaa--","abc-","ABC") returns "AAA". If a
|
||||
* character occurs more than once in the second argument string, then the
|
||||
* first occurrence determines the replacement character. If the third
|
||||
* argument string is longer than the second argument string, then excess
|
||||
* characters are ignored.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class TranslateFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final Expr arg1;
|
||||
final Expr arg2;
|
||||
final Expr arg3;
|
||||
|
||||
TranslateFunction(List args)
|
||||
{
|
||||
this((Expr) args.get(0), (Expr) args.get(1), (Expr) args.get(2));
|
||||
}
|
||||
|
||||
TranslateFunction(Expr arg1, Expr arg2, Expr arg3)
|
||||
{
|
||||
this.arg1 = arg1;
|
||||
this.arg2 = arg2;
|
||||
this.arg3 = arg3;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object val1 = arg1.evaluate(context, pos, len);
|
||||
Object val2 = arg2.evaluate(context, pos, len);
|
||||
Object val3 = arg3.evaluate(context, pos, len);
|
||||
String string = _string(context, val1);
|
||||
String search = _string(context, val2);
|
||||
String replace = _string(context, val3);
|
||||
StringBuffer buf = new StringBuffer();
|
||||
int l1 = string.length();
|
||||
int l2 = search.length();
|
||||
int l3 = replace.length();
|
||||
for (int i = 0; i < l1; i++)
|
||||
{
|
||||
char c = string.charAt(i);
|
||||
boolean replaced = false;
|
||||
for (int j = 0; j < l2; j++)
|
||||
{
|
||||
if (c == search.charAt(j))
|
||||
{
|
||||
if (j < l3)
|
||||
{
|
||||
buf.append(replace.charAt(j));
|
||||
}
|
||||
replaced = true;
|
||||
}
|
||||
}
|
||||
if (!replaced)
|
||||
{
|
||||
buf.append(c);
|
||||
}
|
||||
}
|
||||
return new String(buf);
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new TranslateFunction(arg1.clone(context), arg2.clone(context),
|
||||
arg3.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (arg1.references(var) || arg2.references(var) ||
|
||||
arg3.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "translate(" + arg1 + "," + arg2 + "," + arg3 + ")";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
/* TrueFunction.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The <code>true</code> function returns true.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
final class TrueFunction
|
||||
extends Expr
|
||||
{
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
return Boolean.TRUE;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new TrueFunction();
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return "true()";
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,108 @@
|
||||
/* UnionExpr.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import javax.xml.namespace.QName;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* The union of two node-sets.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public final class UnionExpr
|
||||
extends Pattern
|
||||
{
|
||||
|
||||
final Expr lhs;
|
||||
final Expr rhs;
|
||||
|
||||
public UnionExpr(Expr lhs, Expr rhs)
|
||||
{
|
||||
this.lhs = lhs;
|
||||
this.rhs = rhs;
|
||||
}
|
||||
|
||||
public boolean matches(Node context)
|
||||
{
|
||||
if (lhs instanceof Pattern && rhs instanceof Pattern)
|
||||
{
|
||||
return ((Pattern) lhs).matches(context) ||
|
||||
((Pattern) rhs).matches(context);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
Object left = lhs.evaluate(context, pos, len);
|
||||
Object right = rhs.evaluate(context, pos, len);
|
||||
if (left instanceof Collection && right instanceof Collection)
|
||||
{
|
||||
Set set = new HashSet();
|
||||
set.addAll ((Collection) left);
|
||||
set.addAll ((Collection) right);
|
||||
List list = new ArrayList(set);
|
||||
Collections.sort(list, documentOrderComparator);
|
||||
return list;
|
||||
}
|
||||
return Collections.EMPTY_SET;
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
return new UnionExpr(lhs.clone(context), rhs.clone(context));
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return (lhs.references(var) || rhs.references(var));
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return lhs + " | " + rhs;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,100 @@
|
||||
/* VariableReference.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.namespace.QName;
|
||||
import javax.xml.xpath.XPathVariableResolver;
|
||||
import org.w3c.dom.Node;
|
||||
import gnu.xml.transform.Bindings;
|
||||
|
||||
public class VariableReference
|
||||
extends Expr
|
||||
{
|
||||
|
||||
final XPathVariableResolver resolver;
|
||||
final QName name;
|
||||
|
||||
public VariableReference(XPathVariableResolver resolver, QName name)
|
||||
{
|
||||
this.resolver = resolver;
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public Object evaluate(Node context, int pos, int len)
|
||||
{
|
||||
if (resolver != null)
|
||||
{
|
||||
if (resolver instanceof Bindings)
|
||||
{
|
||||
// Needs context to operate properly
|
||||
return ((Bindings) resolver).get(name, context, pos, len);
|
||||
}
|
||||
return resolver.resolveVariable(name);
|
||||
}
|
||||
throw new IllegalStateException("no variable resolver");
|
||||
}
|
||||
|
||||
public Expr clone(Object context)
|
||||
{
|
||||
XPathVariableResolver r = resolver;
|
||||
if (context instanceof XPathVariableResolver)
|
||||
{
|
||||
r = (XPathVariableResolver) context;
|
||||
}
|
||||
return new VariableReference(r, name);
|
||||
}
|
||||
|
||||
public boolean references(QName var)
|
||||
{
|
||||
return name.equals(var);
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
StringBuffer buf = new StringBuffer("$");
|
||||
String prefix = name.getPrefix();
|
||||
if (prefix != null && !"".equals(prefix))
|
||||
{
|
||||
buf.append(prefix);
|
||||
buf.append(':');
|
||||
}
|
||||
buf.append(name.getLocalPart());
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,90 @@
|
||||
/* XPathFactoryImpl.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import javax.xml.xpath.XPath;
|
||||
import javax.xml.xpath.XPathFactory;
|
||||
import javax.xml.xpath.XPathFactoryConfigurationException;
|
||||
import javax.xml.xpath.XPathFunctionResolver;
|
||||
import javax.xml.xpath.XPathVariableResolver;
|
||||
|
||||
/**
|
||||
* GNU XPath factory implementation.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public class XPathFactoryImpl
|
||||
extends XPathFactory
|
||||
{
|
||||
|
||||
XPathVariableResolver variableResolver;
|
||||
XPathFunctionResolver functionResolver;
|
||||
|
||||
public boolean isObjectModelSupported(String objectModel)
|
||||
{
|
||||
return XPathFactory.DEFAULT_OBJECT_MODEL_URI.equals(objectModel);
|
||||
}
|
||||
|
||||
public void setFeature(String name, boolean value)
|
||||
throws XPathFactoryConfigurationException
|
||||
{
|
||||
throw new XPathFactoryConfigurationException(name);
|
||||
}
|
||||
|
||||
public boolean getFeature(String name)
|
||||
throws XPathFactoryConfigurationException
|
||||
{
|
||||
throw new XPathFactoryConfigurationException(name);
|
||||
}
|
||||
|
||||
public void setXPathVariableResolver(XPathVariableResolver resolver)
|
||||
{
|
||||
variableResolver = resolver;
|
||||
}
|
||||
|
||||
public void setXPathFunctionResolver(XPathFunctionResolver resolver)
|
||||
{
|
||||
functionResolver = resolver;
|
||||
}
|
||||
|
||||
public XPath newXPath()
|
||||
{
|
||||
return new XPathImpl(null, variableResolver, functionResolver);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,164 @@
|
||||
/* XPathImpl.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.io.IOException;
|
||||
import javax.xml.namespace.NamespaceContext;
|
||||
import javax.xml.namespace.QName;
|
||||
import javax.xml.xpath.XPath;
|
||||
import javax.xml.xpath.XPathExpression;
|
||||
import javax.xml.xpath.XPathExpressionException;
|
||||
import javax.xml.xpath.XPathFunctionResolver;
|
||||
import javax.xml.xpath.XPathVariableResolver;
|
||||
import org.xml.sax.InputSource;
|
||||
|
||||
/**
|
||||
* JAXP XPath implementation.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public class XPathImpl
|
||||
implements XPath
|
||||
{
|
||||
|
||||
XPathParser parser;
|
||||
NamespaceContext namespaceContext;
|
||||
XPathVariableResolver variableResolver;
|
||||
XPathFunctionResolver functionResolver;
|
||||
|
||||
XPathImpl(NamespaceContext namespaceContext,
|
||||
XPathVariableResolver variableResolver,
|
||||
XPathFunctionResolver functionResolver)
|
||||
{
|
||||
parser = new XPathParser();
|
||||
this.namespaceContext = namespaceContext;
|
||||
this.variableResolver = variableResolver;
|
||||
this.functionResolver = functionResolver;
|
||||
reset();
|
||||
}
|
||||
|
||||
public void reset()
|
||||
{
|
||||
parser.namespaceContext = namespaceContext;
|
||||
parser.variableResolver = variableResolver;
|
||||
parser.functionResolver = functionResolver;
|
||||
}
|
||||
|
||||
public void setXPathVariableResolver(XPathVariableResolver resolver)
|
||||
{
|
||||
parser.variableResolver = resolver;
|
||||
}
|
||||
|
||||
public XPathVariableResolver getXPathVariableResolver()
|
||||
{
|
||||
return parser.variableResolver;
|
||||
}
|
||||
|
||||
public void setXPathFunctionResolver(XPathFunctionResolver resolver)
|
||||
{
|
||||
parser.functionResolver = resolver;
|
||||
}
|
||||
|
||||
public XPathFunctionResolver getXPathFunctionResolver()
|
||||
{
|
||||
return parser.functionResolver;
|
||||
}
|
||||
|
||||
public void setNamespaceContext(NamespaceContext nsContext)
|
||||
{
|
||||
parser.namespaceContext = nsContext;
|
||||
}
|
||||
|
||||
public NamespaceContext getNamespaceContext()
|
||||
{
|
||||
return parser.namespaceContext;
|
||||
}
|
||||
|
||||
public XPathExpression compile(String expression)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
XPathTokenizer tokenizer = new XPathTokenizer(expression);
|
||||
try
|
||||
{
|
||||
return (Expr) parser.yyparse(tokenizer);
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new XPathExpressionException(e);
|
||||
}
|
||||
catch (XPathParser.yyException e)
|
||||
{
|
||||
throw new XPathExpressionException(expression);
|
||||
}
|
||||
}
|
||||
|
||||
public Object evaluate(String expression,
|
||||
Object item,
|
||||
QName returnType)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
XPathExpression expr = compile(expression);
|
||||
return expr.evaluate(item, returnType);
|
||||
}
|
||||
|
||||
public String evaluate(String expression,
|
||||
Object item)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
XPathExpression expr = compile(expression);
|
||||
return expr.evaluate(item);
|
||||
}
|
||||
|
||||
public Object evaluate(String expression,
|
||||
InputSource source,
|
||||
QName returnType)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
XPathExpression expr = compile(expression);
|
||||
return expr.evaluate(source, returnType);
|
||||
}
|
||||
|
||||
public String evaluate(String expression,
|
||||
InputSource source)
|
||||
throws XPathExpressionException
|
||||
{
|
||||
XPathExpression expr = compile(expression);
|
||||
return expr.evaluate(source);
|
||||
}
|
||||
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,784 @@
|
||||
%{
|
||||
/*
|
||||
* XPathParser.java
|
||||
* Copyright (C) 2004 The Free Software Foundation
|
||||
*
|
||||
* This file is part of GNU JAXP, a library.
|
||||
*
|
||||
* GNU JAXP is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* GNU JAXP is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*
|
||||
* Linking this library statically or dynamically with other modules is
|
||||
* making a combined work based on this library. Thus, the terms and
|
||||
* conditions of the GNU General Public License cover the whole
|
||||
* combination.
|
||||
*
|
||||
* As a special exception, the copyright holders of this library give you
|
||||
* permission to link this library with independent modules to produce an
|
||||
* executable, regardless of the license terms of these independent
|
||||
* modules, and to copy and distribute the resulting executable under
|
||||
* terms of your choice, provided that you also meet, for each linked
|
||||
* independent module, the terms and conditions of the license of that
|
||||
* module. An independent module is a module which is not derived from
|
||||
* or based on this library. If you modify this library, you may extend
|
||||
* this exception to your version of the library, but you are not
|
||||
* obliged to do so. If you do not wish to do so, delete this
|
||||
* exception statement from your version.
|
||||
*/
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import javax.xml.namespace.NamespaceContext;
|
||||
import javax.xml.namespace.QName;
|
||||
import javax.xml.xpath.XPathFunctionResolver;
|
||||
import javax.xml.xpath.XPathVariableResolver;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
/**
|
||||
* An XPath 1.0 parser.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public class XPathParser
|
||||
{
|
||||
|
||||
NamespaceContext namespaceContext;
|
||||
XPathVariableResolver variableResolver;
|
||||
XPathFunctionResolver functionResolver;
|
||||
|
||||
QName getQName(String name)
|
||||
{
|
||||
QName qName = QName.valueOf(name);
|
||||
if (namespaceContext != null)
|
||||
{
|
||||
String prefix = qName.getPrefix();
|
||||
String uri = qName.getNamespaceURI();
|
||||
if (prefix != null && (uri == null || uri.length() == 0))
|
||||
{
|
||||
uri = namespaceContext.getNamespaceURI(prefix);
|
||||
String localName = qName.getLocalPart();
|
||||
qName = new QName(uri, localName, prefix);
|
||||
}
|
||||
}
|
||||
return qName;
|
||||
}
|
||||
|
||||
Expr lookupFunction(String name, List args)
|
||||
{
|
||||
int arity = args.size();
|
||||
if ("position".equals(name) && arity == 0)
|
||||
{
|
||||
return new PositionFunction();
|
||||
}
|
||||
else if ("last".equals(name) && arity == 0)
|
||||
{
|
||||
return new LastFunction();
|
||||
}
|
||||
else if ("string".equals(name) && (arity == 1 || arity == 0))
|
||||
{
|
||||
return new StringFunction(args);
|
||||
}
|
||||
else if ("number".equals(name) && (arity == 1 || arity == 0))
|
||||
{
|
||||
return new NumberFunction(args);
|
||||
}
|
||||
else if ("boolean".equals(name) && arity == 1)
|
||||
{
|
||||
return new BooleanFunction(args);
|
||||
}
|
||||
else if ("count".equals(name) && arity == 1)
|
||||
{
|
||||
return new CountFunction(args);
|
||||
}
|
||||
else if ("not".equals(name) && arity == 1)
|
||||
{
|
||||
return new NotFunction(args);
|
||||
}
|
||||
else if ("id".equals(name) && arity == 1)
|
||||
{
|
||||
return new IdFunction(args);
|
||||
}
|
||||
else if ("concat".equals(name) && arity > 1)
|
||||
{
|
||||
return new ConcatFunction(args);
|
||||
}
|
||||
else if ("true".equals(name) && arity == 0)
|
||||
{
|
||||
return new TrueFunction();
|
||||
}
|
||||
else if ("false".equals(name) && arity == 0)
|
||||
{
|
||||
return new FalseFunction();
|
||||
}
|
||||
else if ("name".equals(name) && (arity == 1 || arity == 0))
|
||||
{
|
||||
return new NameFunction(args);
|
||||
}
|
||||
else if ("local-name".equals(name) && (arity == 1 || arity == 0))
|
||||
{
|
||||
return new LocalNameFunction(args);
|
||||
}
|
||||
else if ("namespace-uri".equals(name) && (arity == 1 || arity == 0))
|
||||
{
|
||||
return new NamespaceUriFunction(args);
|
||||
}
|
||||
else if ("starts-with".equals(name) && arity == 2)
|
||||
{
|
||||
return new StartsWithFunction(args);
|
||||
}
|
||||
else if ("contains".equals(name) && arity == 2)
|
||||
{
|
||||
return new ContainsFunction(args);
|
||||
}
|
||||
else if ("string-length".equals(name) && (arity == 1 || arity == 0))
|
||||
{
|
||||
return new StringLengthFunction(args);
|
||||
}
|
||||
else if ("translate".equals(name) && arity == 3)
|
||||
{
|
||||
return new TranslateFunction(args);
|
||||
}
|
||||
else if ("normalize-space".equals(name) && (arity == 1 || arity == 0))
|
||||
{
|
||||
return new NormalizeSpaceFunction(args);
|
||||
}
|
||||
else if ("substring".equals(name) && (arity == 2 || arity == 3))
|
||||
{
|
||||
return new SubstringFunction(args);
|
||||
}
|
||||
else if ("substring-before".equals(name) && arity == 2)
|
||||
{
|
||||
return new SubstringBeforeFunction(args);
|
||||
}
|
||||
else if ("substring-after".equals(name) && arity == 2)
|
||||
{
|
||||
return new SubstringAfterFunction(args);
|
||||
}
|
||||
else if ("lang".equals(name) && arity == 1)
|
||||
{
|
||||
return new LangFunction(args);
|
||||
}
|
||||
else if ("sum".equals(name) && arity == 1)
|
||||
{
|
||||
return new SumFunction(args);
|
||||
}
|
||||
else if ("floor".equals(name) && arity == 1)
|
||||
{
|
||||
return new FloorFunction(args);
|
||||
}
|
||||
else if ("ceiling".equals(name) && arity == 1)
|
||||
{
|
||||
return new CeilingFunction(args);
|
||||
}
|
||||
else if ("round".equals(name) && arity == 1)
|
||||
{
|
||||
return new RoundFunction(args);
|
||||
}
|
||||
else if (functionResolver != null)
|
||||
{
|
||||
QName qName = QName.valueOf(name);
|
||||
Object function = functionResolver.resolveFunction(qName, arity);
|
||||
if (function != null &&
|
||||
function instanceof Function &&
|
||||
function instanceof Expr)
|
||||
{
|
||||
Function f = (Function) function;
|
||||
f.setArguments(args);
|
||||
return (Expr) function;
|
||||
}
|
||||
}
|
||||
return new FunctionCall(functionResolver, name, args);
|
||||
}
|
||||
|
||||
%}
|
||||
|
||||
%token LITERAL
|
||||
%token DIGITS
|
||||
%token NAME
|
||||
|
||||
%token LP // '('
|
||||
%token RP // ')'
|
||||
%token LB // '['
|
||||
%token RB // ']'
|
||||
%token COMMA // ','
|
||||
%token PIPE // '|'
|
||||
%token SLASH // '/'
|
||||
%token DOUBLE_SLASH // '//'
|
||||
%token EQ // '='
|
||||
%token NE // '!='
|
||||
%token GT // '>'
|
||||
%token LT // '<'
|
||||
%token GTE // '>='
|
||||
%token LTE // '<='
|
||||
%token PLUS // '+'
|
||||
%token MINUS // '-'
|
||||
%token AT // '@'
|
||||
%token STAR // '*'
|
||||
%token DOLLAR // '$'
|
||||
%token COLON // ':'
|
||||
%token DOUBLE_COLON // '::'
|
||||
%token DOT // '.'
|
||||
%token DOUBLE_DOT // '..'
|
||||
|
||||
%token ANCESTOR
|
||||
%token ANCESTOR_OR_SELF
|
||||
%token ATTRIBUTE
|
||||
%token CHILD
|
||||
%token DESCENDANT
|
||||
%token DESCENDANT_OR_SELF
|
||||
%token FOLLOWING
|
||||
%token FOLLOWING_SIBLING
|
||||
%token NAMESPACE
|
||||
%token PARENT
|
||||
%token PRECEDING
|
||||
%token PRECEDING_SIBLING
|
||||
%token SELF
|
||||
%token DIV
|
||||
%token MOD
|
||||
%token OR
|
||||
%token AND
|
||||
%token COMMENT
|
||||
%token PROCESSING_INSTRUCTION
|
||||
%token TEXT
|
||||
%token NODE
|
||||
|
||||
%right UNARY
|
||||
|
||||
%start expr
|
||||
|
||||
%%
|
||||
|
||||
expr:
|
||||
or_expr
|
||||
;
|
||||
|
||||
location_path:
|
||||
relative_location_path
|
||||
| absolute_location_path
|
||||
;
|
||||
|
||||
absolute_location_path:
|
||||
SLASH
|
||||
{
|
||||
$$ = new Root();
|
||||
}
|
||||
| SLASH relative_location_path
|
||||
{
|
||||
Steps steps;
|
||||
if ($2 instanceof Steps)
|
||||
{
|
||||
steps = (Steps) $2;
|
||||
}
|
||||
else
|
||||
{
|
||||
steps = new Steps();
|
||||
steps.path.addFirst($2);
|
||||
}
|
||||
steps.path.addFirst(new Root());
|
||||
$$ = steps;
|
||||
//$$ = new Step(new Root(), (Path) $2);
|
||||
}
|
||||
| DOUBLE_SLASH relative_location_path
|
||||
{
|
||||
Test nt = new NodeTypeTest((short) 0);
|
||||
Selector s = new Selector(Selector.DESCENDANT_OR_SELF,
|
||||
Collections.singletonList (nt));
|
||||
Steps steps;
|
||||
if ($2 instanceof Steps)
|
||||
{
|
||||
steps = (Steps) $2;
|
||||
}
|
||||
else
|
||||
{
|
||||
steps = new Steps();
|
||||
steps.path.addFirst($2);
|
||||
}
|
||||
steps.path.addFirst(s);
|
||||
steps.path.addFirst(new Root());
|
||||
$$ = steps;
|
||||
//Step step = new Step(s, (Path) $2);
|
||||
//$$ = new Step(new Root(), step);
|
||||
}
|
||||
;
|
||||
|
||||
relative_location_path:
|
||||
step
|
||||
| relative_location_path SLASH step
|
||||
{
|
||||
Steps steps;
|
||||
if ($1 instanceof Steps)
|
||||
{
|
||||
steps = (Steps) $1;
|
||||
}
|
||||
else
|
||||
{
|
||||
steps = new Steps();
|
||||
steps.path.addFirst($1);
|
||||
}
|
||||
steps.path.addLast($3);
|
||||
$$ = steps;
|
||||
//$$ = new Step((Expr) $1, (Path) $3);
|
||||
}
|
||||
| relative_location_path DOUBLE_SLASH step
|
||||
{
|
||||
Test nt = new NodeTypeTest((short) 0);
|
||||
Selector s = new Selector(Selector.DESCENDANT_OR_SELF,
|
||||
Collections.singletonList (nt));
|
||||
Steps steps;
|
||||
if ($1 instanceof Steps)
|
||||
{
|
||||
steps = (Steps) $1;
|
||||
}
|
||||
else
|
||||
{
|
||||
steps = new Steps();
|
||||
steps.path.addFirst($1);
|
||||
}
|
||||
steps.path.addLast(s);
|
||||
steps.path.addLast($3);
|
||||
$$ = steps;
|
||||
//Step step = new Step(s, (Path) $3);
|
||||
//$$ = new Step((Expr) $1, step);
|
||||
}
|
||||
;
|
||||
|
||||
step:
|
||||
step_node_test
|
||||
{
|
||||
$$ = new Selector (Selector.CHILD, (List) $1);
|
||||
}
|
||||
| AT step_node_test
|
||||
{
|
||||
$$ = new Selector (Selector.ATTRIBUTE, (List) $2);
|
||||
}
|
||||
| axis_name DOUBLE_COLON step_node_test
|
||||
{
|
||||
$$ = new Selector (((Integer) $1).intValue (), (List) $3);
|
||||
}
|
||||
| DOT
|
||||
{
|
||||
$$ = new Selector (Selector.SELF, Collections.EMPTY_LIST);
|
||||
}
|
||||
| DOUBLE_DOT
|
||||
{
|
||||
$$ = new Selector (Selector.PARENT, Collections.EMPTY_LIST);
|
||||
}
|
||||
;
|
||||
|
||||
step_node_test:
|
||||
node_test
|
||||
{
|
||||
List list = new ArrayList();
|
||||
list.add($1);
|
||||
$$ = list;
|
||||
}
|
||||
| step_node_test predicate
|
||||
{
|
||||
List list = (List)$1;
|
||||
list.add($2);
|
||||
$$ = list;
|
||||
}
|
||||
;
|
||||
|
||||
/*predicate_list:
|
||||
predicate
|
||||
{
|
||||
List list = new ArrayList ();
|
||||
list.add ($1);
|
||||
$$ = list;
|
||||
}
|
||||
| predicate predicate_list
|
||||
{
|
||||
List list = (List) $3;
|
||||
list.add (0, $1);
|
||||
$$ = list;
|
||||
}
|
||||
;*/
|
||||
|
||||
axis_name:
|
||||
ANCESTOR
|
||||
{
|
||||
$$ = new Integer(Selector.ANCESTOR);
|
||||
}
|
||||
| ANCESTOR_OR_SELF
|
||||
{
|
||||
$$ = new Integer(Selector.ANCESTOR_OR_SELF);
|
||||
}
|
||||
| ATTRIBUTE
|
||||
{
|
||||
$$ = new Integer(Selector.ATTRIBUTE);
|
||||
}
|
||||
| CHILD
|
||||
{
|
||||
$$ = new Integer(Selector.CHILD);
|
||||
}
|
||||
| DESCENDANT
|
||||
{
|
||||
$$ = new Integer(Selector.DESCENDANT);
|
||||
}
|
||||
| DESCENDANT_OR_SELF
|
||||
{
|
||||
$$ = new Integer(Selector.DESCENDANT_OR_SELF);
|
||||
}
|
||||
| FOLLOWING
|
||||
{
|
||||
$$ = new Integer(Selector.FOLLOWING);
|
||||
}
|
||||
| FOLLOWING_SIBLING
|
||||
{
|
||||
$$ = new Integer(Selector.FOLLOWING_SIBLING);
|
||||
}
|
||||
| NAMESPACE
|
||||
{
|
||||
$$ = new Integer(Selector.NAMESPACE);
|
||||
}
|
||||
| PARENT
|
||||
{
|
||||
$$ = new Integer(Selector.PARENT);
|
||||
}
|
||||
| PRECEDING
|
||||
{
|
||||
$$ = new Integer(Selector.PRECEDING);
|
||||
}
|
||||
| PRECEDING_SIBLING
|
||||
{
|
||||
$$ = new Integer(Selector.PRECEDING_SIBLING);
|
||||
}
|
||||
| SELF
|
||||
{
|
||||
$$ = new Integer(Selector.SELF);
|
||||
}
|
||||
;
|
||||
|
||||
node_test:
|
||||
name_test
|
||||
/*| PROCESSING_INSTRUCTION LP LITERAL RP*/
|
||||
| PROCESSING_INSTRUCTION LITERAL RP
|
||||
{
|
||||
$$ = new NodeTypeTest(Node.PROCESSING_INSTRUCTION_NODE, (String) $2);
|
||||
}
|
||||
/*| node_type LP RP*/
|
||||
| node_type RP
|
||||
{
|
||||
$$ = new NodeTypeTest(((Short) $1).shortValue());
|
||||
}
|
||||
;
|
||||
|
||||
predicate:
|
||||
LB expr RB
|
||||
{
|
||||
$$ = new Predicate((Expr) $2);
|
||||
}
|
||||
;
|
||||
|
||||
primary_expr:
|
||||
variable_reference
|
||||
| LP expr RP
|
||||
{
|
||||
$$ = new ParenthesizedExpr((Expr) $2);
|
||||
}
|
||||
| LITERAL
|
||||
{
|
||||
$$ = new Constant($1);
|
||||
}
|
||||
| number
|
||||
{
|
||||
$$ = new Constant($1);
|
||||
}
|
||||
| function_call
|
||||
;
|
||||
|
||||
function_call:
|
||||
function_name LP RP
|
||||
{
|
||||
$$ = lookupFunction((String) $1, Collections.EMPTY_LIST);
|
||||
}
|
||||
| function_name LP argument_list RP
|
||||
{
|
||||
$$ = lookupFunction((String) $1, (List) $3);
|
||||
}
|
||||
;
|
||||
|
||||
argument_list:
|
||||
expr
|
||||
{
|
||||
List list = new ArrayList();
|
||||
list.add($1);
|
||||
$$ = list;
|
||||
}
|
||||
| expr COMMA argument_list
|
||||
{
|
||||
List list = (List) $3;
|
||||
list.add(0, $1);
|
||||
$$ = list;
|
||||
}
|
||||
;
|
||||
|
||||
union_expr:
|
||||
path_expr
|
||||
| union_expr PIPE path_expr
|
||||
{
|
||||
$$ = new UnionExpr((Expr) $1, (Expr) $3);
|
||||
}
|
||||
;
|
||||
|
||||
path_expr:
|
||||
location_path
|
||||
| filter_expr
|
||||
| filter_expr SLASH relative_location_path
|
||||
{
|
||||
Steps steps;
|
||||
if ($3 instanceof Steps)
|
||||
{
|
||||
steps = (Steps) $3;
|
||||
}
|
||||
else
|
||||
{
|
||||
steps = new Steps();
|
||||
steps.path.addFirst($3);
|
||||
}
|
||||
steps.path.addFirst($1);
|
||||
$$ = steps;
|
||||
//$$ = new Step ((Expr) $1, (Path) $3);
|
||||
}
|
||||
| filter_expr DOUBLE_SLASH relative_location_path
|
||||
{
|
||||
Test nt = new NodeTypeTest((short) 0);
|
||||
Selector s = new Selector(Selector.DESCENDANT_OR_SELF,
|
||||
Collections.singletonList(nt));
|
||||
Steps steps;
|
||||
if ($3 instanceof Steps)
|
||||
{
|
||||
steps = (Steps) $3;
|
||||
}
|
||||
else
|
||||
{
|
||||
steps = new Steps();
|
||||
steps.path.addFirst($3);
|
||||
}
|
||||
steps.path.addFirst(s);
|
||||
steps.path.addFirst($1);
|
||||
$$ = steps;
|
||||
//Step step = new Step (s, (Path) $3);
|
||||
//$$ = new Step ((Expr) $1, step);
|
||||
}
|
||||
;
|
||||
|
||||
filter_expr:
|
||||
primary_expr
|
||||
| filter_expr predicate
|
||||
{
|
||||
Predicate filter = (Predicate) $2;
|
||||
Selector s = new Selector(Selector.SELF,
|
||||
Collections.singletonList(filter));
|
||||
Steps steps;
|
||||
if ($1 instanceof Steps)
|
||||
{
|
||||
steps = (Steps) $1;
|
||||
}
|
||||
else
|
||||
{
|
||||
steps = new Steps();
|
||||
steps.path.addFirst($1);
|
||||
}
|
||||
steps.path.addLast(s);
|
||||
$$ = steps;
|
||||
//$$ = new Step ((Expr) $1, s);
|
||||
}
|
||||
;
|
||||
|
||||
or_expr:
|
||||
and_expr
|
||||
| or_expr OR and_expr
|
||||
{
|
||||
$$ = new OrExpr((Expr) $1, (Expr) $3);
|
||||
}
|
||||
;
|
||||
|
||||
and_expr:
|
||||
equality_expr
|
||||
| and_expr AND equality_expr
|
||||
{
|
||||
$$ = new AndExpr((Expr) $1, (Expr) $3);
|
||||
}
|
||||
;
|
||||
|
||||
equality_expr:
|
||||
relational_expr
|
||||
| equality_expr EQ relational_expr
|
||||
{
|
||||
$$ = new EqualityExpr((Expr) $1, (Expr) $3, false);
|
||||
}
|
||||
| equality_expr NE relational_expr
|
||||
{
|
||||
$$ = new EqualityExpr((Expr) $1, (Expr) $3, true);
|
||||
}
|
||||
;
|
||||
|
||||
relational_expr:
|
||||
additive_expr
|
||||
| relational_expr LT additive_expr
|
||||
{
|
||||
$$ = new RelationalExpr((Expr) $1, (Expr) $3, true, false);
|
||||
}
|
||||
| relational_expr GT additive_expr
|
||||
{
|
||||
$$ = new RelationalExpr((Expr) $1, (Expr) $3, false, false);
|
||||
}
|
||||
| relational_expr LTE additive_expr
|
||||
{
|
||||
$$ = new RelationalExpr((Expr) $1, (Expr) $3, true, true);
|
||||
}
|
||||
| relational_expr GTE additive_expr
|
||||
{
|
||||
$$ = new RelationalExpr((Expr) $1, (Expr) $3, false, true);
|
||||
}
|
||||
;
|
||||
|
||||
additive_expr:
|
||||
multiplicative_expr
|
||||
| additive_expr PLUS multiplicative_expr
|
||||
{
|
||||
$$ = new ArithmeticExpr((Expr) $1, (Expr) $3, ArithmeticExpr.ADD);
|
||||
}
|
||||
| additive_expr MINUS multiplicative_expr
|
||||
{
|
||||
$$ = new ArithmeticExpr((Expr) $1, (Expr) $3, ArithmeticExpr.SUBTRACT);
|
||||
}
|
||||
;
|
||||
|
||||
multiplicative_expr:
|
||||
unary_expr
|
||||
| multiplicative_expr STAR unary_expr
|
||||
{
|
||||
$$ = new ArithmeticExpr((Expr) $1, (Expr) $3, ArithmeticExpr.MULTIPLY);
|
||||
}
|
||||
| multiplicative_expr DIV unary_expr
|
||||
{
|
||||
$$ = new ArithmeticExpr((Expr) $1, (Expr) $3, ArithmeticExpr.DIVIDE);
|
||||
}
|
||||
| multiplicative_expr MOD unary_expr
|
||||
{
|
||||
$$ = new ArithmeticExpr((Expr) $1, (Expr) $3, ArithmeticExpr.MODULO);
|
||||
}
|
||||
;
|
||||
|
||||
unary_expr:
|
||||
union_expr
|
||||
| MINUS unary_expr %prec UNARY
|
||||
{
|
||||
$$ = new NegativeExpr((Expr) $2);
|
||||
}
|
||||
;
|
||||
|
||||
number:
|
||||
DIGITS
|
||||
{
|
||||
$$ = new Double((String) $1 + ".0");
|
||||
}
|
||||
| DIGITS DOT
|
||||
{
|
||||
$$ = new Double((String) $1 + ".0");
|
||||
}
|
||||
| DIGITS DOT DIGITS
|
||||
{
|
||||
$$ = new Double((String) $1 + "." + (String) $3);
|
||||
}
|
||||
| DOT DIGITS
|
||||
{
|
||||
$$ = new Double("0." + (String) $2);
|
||||
}
|
||||
;
|
||||
|
||||
function_name:
|
||||
qname
|
||||
/* | node_type
|
||||
{
|
||||
switch (((Short) $1).shortValue ())
|
||||
{
|
||||
case Node.COMMENT_NODE:
|
||||
$$ = "comment";
|
||||
break;
|
||||
case Node.TEXT_NODE:
|
||||
$$ = "text";
|
||||
break;
|
||||
case Node.PROCESSING_INSTRUCTION_NODE:
|
||||
$$ = "processing-instruction";
|
||||
break;
|
||||
default:
|
||||
$$ = "node";
|
||||
break;
|
||||
}
|
||||
}*/
|
||||
;
|
||||
|
||||
variable_reference:
|
||||
DOLLAR qname
|
||||
{
|
||||
String name = (String) $2;
|
||||
$$ = new VariableReference(variableResolver, getQName(name));
|
||||
}
|
||||
;
|
||||
|
||||
name_test:
|
||||
STAR
|
||||
{
|
||||
$$ = new NameTest(null, true, true);
|
||||
}
|
||||
| NAME COLON STAR
|
||||
{
|
||||
QName qName = getQName((String) $1);
|
||||
$$ = new NameTest(qName, true, false);
|
||||
}
|
||||
| qname
|
||||
{
|
||||
QName qName = getQName((String) $1);
|
||||
$$ = new NameTest(qName, false, false);
|
||||
}
|
||||
;
|
||||
|
||||
qname:
|
||||
NAME
|
||||
| NAME COLON NAME
|
||||
{
|
||||
$$ = (String) $1 + ':' + (String) $3;
|
||||
}
|
||||
;
|
||||
|
||||
node_type:
|
||||
COMMENT
|
||||
{
|
||||
$$ = new Short(Node.COMMENT_NODE);
|
||||
}
|
||||
| TEXT
|
||||
{
|
||||
$$ = new Short(Node.TEXT_NODE);
|
||||
}
|
||||
| PROCESSING_INSTRUCTION
|
||||
{
|
||||
$$ = new Short(Node.PROCESSING_INSTRUCTION_NODE);
|
||||
}
|
||||
| NODE
|
||||
{
|
||||
$$ = new Short((short) 0);
|
||||
}
|
||||
;
|
||||
|
||||
%%
|
||||
|
||||
}
|
||||
@@ -0,0 +1,592 @@
|
||||
/* XPathTokenizer.java --
|
||||
Copyright (C) 2004 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GNU Classpath.
|
||||
|
||||
GNU Classpath is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GNU Classpath is distributed in the hope that it will be useful, but
|
||||
WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GNU Classpath; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
|
||||
02110-1301 USA.
|
||||
|
||||
Linking this library statically or dynamically with other modules is
|
||||
making a combined work based on this library. Thus, the terms and
|
||||
conditions of the GNU General Public License cover the whole
|
||||
combination.
|
||||
|
||||
As a special exception, the copyright holders of this library give you
|
||||
permission to link this library with independent modules to produce an
|
||||
executable, regardless of the license terms of these independent
|
||||
modules, and to copy and distribute the resulting executable under
|
||||
terms of your choice, provided that you also meet, for each linked
|
||||
independent module, the terms and conditions of the license of that
|
||||
module. An independent module is a module which is not derived from
|
||||
or based on this library. If you modify this library, you may extend
|
||||
this exception to your version of the library, but you are not
|
||||
obligated to do so. If you do not wish to do so, delete this
|
||||
exception statement from your version. */
|
||||
|
||||
package gnu.xml.xpath;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.IOException;
|
||||
import java.io.Reader;
|
||||
import java.io.StringReader;
|
||||
import java.util.Map;
|
||||
import java.util.TreeMap;
|
||||
|
||||
/*import antlr.Token;
|
||||
import antlr.TokenStream;
|
||||
import antlr.TokenStreamException;
|
||||
import antlr.TokenStreamIOException;*/
|
||||
|
||||
/**
|
||||
* XPath 1.0 expression tokenizer.
|
||||
*
|
||||
* @author <a href='mailto:dog@gnu.org'>Chris Burdess</a>
|
||||
*/
|
||||
public class XPathTokenizer
|
||||
implements XPathParser.yyInput
|
||||
//implements TokenStream
|
||||
{
|
||||
|
||||
static class XPathToken
|
||||
//extends Token
|
||||
{
|
||||
|
||||
int type;
|
||||
String val;
|
||||
|
||||
XPathToken (int type)
|
||||
{
|
||||
this (type, null);
|
||||
}
|
||||
|
||||
XPathToken (int type, String val)
|
||||
{
|
||||
//super (type);
|
||||
this.type = type;
|
||||
this.val = val;
|
||||
}
|
||||
|
||||
public String getText ()
|
||||
{
|
||||
return val;
|
||||
}
|
||||
|
||||
public String toString ()
|
||||
{
|
||||
return val;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static final Map keywords = new TreeMap ();
|
||||
static
|
||||
{
|
||||
keywords.put ("ancestor", new Integer (XPathParser.ANCESTOR));
|
||||
keywords.put ("ancestor-or-self", new Integer (XPathParser.ANCESTOR_OR_SELF));
|
||||
keywords.put ("attribute", new Integer (XPathParser.ATTRIBUTE));
|
||||
keywords.put ("child", new Integer (XPathParser.CHILD));
|
||||
keywords.put ("descendant", new Integer (XPathParser.DESCENDANT));
|
||||
keywords.put ("descendant-or-self", new Integer (XPathParser.DESCENDANT_OR_SELF));
|
||||
keywords.put ("following", new Integer (XPathParser.FOLLOWING));
|
||||
keywords.put ("following-sibling", new Integer (XPathParser.FOLLOWING_SIBLING));
|
||||
keywords.put ("namespace", new Integer (XPathParser.NAMESPACE));
|
||||
keywords.put ("parent", new Integer (XPathParser.PARENT));
|
||||
keywords.put ("preceding", new Integer (XPathParser.PRECEDING));
|
||||
keywords.put ("preceding-sibling", new Integer (XPathParser.PRECEDING_SIBLING));
|
||||
keywords.put ("self", new Integer (XPathParser.SELF));
|
||||
keywords.put ("div", new Integer (XPathParser.DIV));
|
||||
keywords.put ("mod", new Integer (XPathParser.MOD));
|
||||
keywords.put ("or", new Integer (XPathParser.OR));
|
||||
keywords.put ("and", new Integer (XPathParser.AND));
|
||||
keywords.put ("comment", new Integer (XPathParser.COMMENT));
|
||||
keywords.put ("processing-instruction", new Integer (XPathParser.PROCESSING_INSTRUCTION));
|
||||
keywords.put ("text", new Integer (XPathParser.TEXT));
|
||||
keywords.put ("node", new Integer (XPathParser.NODE));
|
||||
}
|
||||
|
||||
Reader in;
|
||||
XPathToken token;
|
||||
XPathToken lastToken;
|
||||
|
||||
public XPathTokenizer (String expr)
|
||||
{
|
||||
this (new StringReader (expr));
|
||||
}
|
||||
|
||||
XPathTokenizer (Reader in)
|
||||
{
|
||||
this.in = in.markSupported () ? in : new BufferedReader (in);
|
||||
}
|
||||
|
||||
/* Begin ANTLR specific *
|
||||
|
||||
public Token nextToken ()
|
||||
throws TokenStreamException
|
||||
{
|
||||
try
|
||||
{
|
||||
if (!advance ())
|
||||
{
|
||||
throw new TokenStreamException ("eof");
|
||||
}
|
||||
token ();
|
||||
return token;
|
||||
}
|
||||
catch (IOException e)
|
||||
{
|
||||
throw new TokenStreamIOException (e);
|
||||
}
|
||||
}
|
||||
|
||||
* End ANTLR specific */
|
||||
|
||||
public boolean advance ()
|
||||
throws IOException
|
||||
{
|
||||
lastToken = token;
|
||||
int c = in.read ();
|
||||
switch (c)
|
||||
{
|
||||
case -1: // eof
|
||||
return false;
|
||||
case 0x20:
|
||||
case 0x09:
|
||||
case 0x0d:
|
||||
case 0x0a: // skip whitespace
|
||||
return advance ();
|
||||
case 0x22: // "
|
||||
case 0x27: // '
|
||||
token = consume_literal (c);
|
||||
break;
|
||||
case 0x28: // (
|
||||
token = new XPathToken (XPathParser.LP);
|
||||
break;
|
||||
case 0x29: // )
|
||||
token = new XPathToken (XPathParser.RP);
|
||||
break;
|
||||
case 0x5b: // [
|
||||
token = new XPathToken (XPathParser.LB);
|
||||
break;
|
||||
case 0x5d: // ]
|
||||
token = new XPathToken (XPathParser.RB);
|
||||
break;
|
||||
case 0x2c: // ,
|
||||
token = new XPathToken (XPathParser.COMMA);
|
||||
break;
|
||||
case 0x7c: // |
|
||||
token = new XPathToken (XPathParser.PIPE);
|
||||
break;
|
||||
case 0x2f: // /
|
||||
in.mark (1);
|
||||
int d1 = in.read ();
|
||||
if (d1 == 0x2f)
|
||||
{
|
||||
token = new XPathToken (XPathParser.DOUBLE_SLASH);
|
||||
}
|
||||
else
|
||||
{
|
||||
in.reset ();
|
||||
token = new XPathToken (XPathParser.SLASH);
|
||||
}
|
||||
break;
|
||||
case 0x3d: // =
|
||||
token = new XPathToken (XPathParser.EQ);
|
||||
break;
|
||||
case 0x21: // !
|
||||
in.mark (1);
|
||||
int d2 = in.read ();
|
||||
if (d2 == 0x3d) // =
|
||||
{
|
||||
token = new XPathToken (XPathParser.NE);
|
||||
}
|
||||
else
|
||||
{
|
||||
in.reset ();
|
||||
token = new XPathToken (XPathParser.yyErrorCode);
|
||||
}
|
||||
break;
|
||||
case 0x3e: // >
|
||||
in.mark (1);
|
||||
int d3 = in.read ();
|
||||
if (d3 == 0x3d) // =
|
||||
{
|
||||
token = new XPathToken (XPathParser.GTE);
|
||||
}
|
||||
else
|
||||
{
|
||||
in.reset ();
|
||||
token = new XPathToken (XPathParser.GT);
|
||||
}
|
||||
break;
|
||||
case 0x3c: // <
|
||||
in.mark (1);
|
||||
int d4 = in.read ();
|
||||
if (d4 == 0x3d) // =
|
||||
{
|
||||
token = new XPathToken (XPathParser.LTE);
|
||||
}
|
||||
else
|
||||
{
|
||||
in.reset ();
|
||||
token = new XPathToken (XPathParser.LT);
|
||||
}
|
||||
break;
|
||||
case 0x2b: // +
|
||||
token = new XPathToken (XPathParser.PLUS);
|
||||
break;
|
||||
case 0x2d: // -
|
||||
token = new XPathToken (XPathParser.MINUS);
|
||||
break;
|
||||
case 0x40: // @
|
||||
token = new XPathToken (XPathParser.AT);
|
||||
break;
|
||||
case 0x2a: // *
|
||||
token = new XPathToken (XPathParser.STAR);
|
||||
break;
|
||||
case 0x24: // $
|
||||
token = new XPathToken (XPathParser.DOLLAR);
|
||||
break;
|
||||
case 0x3a: // :
|
||||
in.mark (1);
|
||||
int d5 = in.read ();
|
||||
if (d5 == 0x3a)
|
||||
{
|
||||
token = new XPathToken (XPathParser.DOUBLE_COLON);
|
||||
}
|
||||
else
|
||||
{
|
||||
in.reset ();
|
||||
token = new XPathToken (XPathParser.COLON);
|
||||
}
|
||||
break;
|
||||
case 0x2e: // .
|
||||
in.mark (1);
|
||||
int d6 = in.read ();
|
||||
if (d6 == 0x2e)
|
||||
{
|
||||
token = new XPathToken (XPathParser.DOUBLE_DOT);
|
||||
}
|
||||
else
|
||||
{
|
||||
in.reset ();
|
||||
token = new XPathToken (XPathParser.DOT);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
if (c >= 0x30 && c <= 0x39)
|
||||
{
|
||||
token = consume_digits (c);
|
||||
}
|
||||
else if (c == 0x5f || Character.isLetter ((char) c))
|
||||
{
|
||||
token = consume_name (c);
|
||||
}
|
||||
else
|
||||
{
|
||||
token = new XPathToken (XPathParser.yyErrorCode);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
public int token ()
|
||||
{
|
||||
return token.type;
|
||||
}
|
||||
|
||||
public Object value ()
|
||||
{
|
||||
return token.val;
|
||||
}
|
||||
|
||||
XPathToken consume_literal (int delimiter)
|
||||
throws IOException
|
||||
{
|
||||
StringBuffer buf = new StringBuffer ();
|
||||
while (true)
|
||||
{
|
||||
int c = in.read ();
|
||||
if (c == -1)
|
||||
{
|
||||
return new XPathToken (XPathParser.yyErrorCode);
|
||||
}
|
||||
else if (c == delimiter)
|
||||
{
|
||||
return new XPathToken (XPathParser.LITERAL, buf.toString ());
|
||||
}
|
||||
else
|
||||
{
|
||||
buf.append ((char) c);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
XPathToken consume_digits (int c)
|
||||
throws IOException
|
||||
{
|
||||
StringBuffer buf = new StringBuffer ();
|
||||
buf.append ((char) c);
|
||||
while (true)
|
||||
{
|
||||
in.mark (1);
|
||||
c = in.read ();
|
||||
if (c >= 0x30 && c <= 0x39)
|
||||
{
|
||||
buf.append ((char) c);
|
||||
}
|
||||
else
|
||||
{
|
||||
in.reset ();
|
||||
return new XPathToken (XPathParser.DIGITS, buf.toString ());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
XPathToken consume_name (int c)
|
||||
throws IOException
|
||||
{
|
||||
StringBuffer buf = new StringBuffer ();
|
||||
buf.append ((char) c);
|
||||
while (true)
|
||||
{
|
||||
in.mark (1);
|
||||
c = in.read ();
|
||||
if (isNameChar (c))
|
||||
{
|
||||
buf.append ((char) c);
|
||||
}
|
||||
else
|
||||
{
|
||||
in.reset ();
|
||||
String name = buf.toString ();
|
||||
Integer keyword = (Integer) keywords.get (name);
|
||||
if (keyword == null)
|
||||
{
|
||||
return new XPathToken (XPathParser.NAME, name);
|
||||
}
|
||||
else
|
||||
{
|
||||
int val = keyword.intValue ();
|
||||
switch (val)
|
||||
{
|
||||
case XPathParser.NODE:
|
||||
case XPathParser.COMMENT:
|
||||
case XPathParser.TEXT:
|
||||
case XPathParser.PROCESSING_INSTRUCTION:
|
||||
// Consume subsequent (
|
||||
in.mark (1);
|
||||
do
|
||||
{
|
||||
c = in.read ();
|
||||
}
|
||||
while (c == 0x20 || c == 0x09);
|
||||
if (c != 0x28)
|
||||
{
|
||||
in.reset ();
|
||||
return new XPathToken (XPathParser.NAME, name);
|
||||
}
|
||||
break;
|
||||
case XPathParser.CHILD:
|
||||
case XPathParser.PARENT:
|
||||
case XPathParser.SELF:
|
||||
case XPathParser.DESCENDANT:
|
||||
case XPathParser.ANCESTOR:
|
||||
case XPathParser.DESCENDANT_OR_SELF:
|
||||
case XPathParser.ANCESTOR_OR_SELF:
|
||||
case XPathParser.ATTRIBUTE:
|
||||
case XPathParser.NAMESPACE:
|
||||
case XPathParser.FOLLOWING:
|
||||
case XPathParser.FOLLOWING_SIBLING:
|
||||
case XPathParser.PRECEDING:
|
||||
case XPathParser.PRECEDING_SIBLING:
|
||||
// Check that this is an axis specifier
|
||||
in.mark(1);
|
||||
do
|
||||
{
|
||||
c = in.read();
|
||||
}
|
||||
while (c == 0x20 || c == 0x09);
|
||||
if (c == 0x3a)
|
||||
{
|
||||
c = in.read();
|
||||
if (c == 0x3a)
|
||||
{
|
||||
in.reset();
|
||||
return new XPathToken(val);
|
||||
}
|
||||
}
|
||||
in.reset();
|
||||
return new XPathToken(XPathParser.NAME, name);
|
||||
case XPathParser.DIV:
|
||||
case XPathParser.MOD:
|
||||
// May be a name
|
||||
if (lastToken == null)
|
||||
{
|
||||
return new XPathToken(XPathParser.NAME, name);
|
||||
}
|
||||
switch (lastToken.type)
|
||||
{
|
||||
case XPathParser.LP:
|
||||
case XPathParser.LB:
|
||||
case XPathParser.COMMA:
|
||||
case XPathParser.PIPE:
|
||||
case XPathParser.EQ:
|
||||
case XPathParser.NE:
|
||||
case XPathParser.GT:
|
||||
case XPathParser.LT:
|
||||
case XPathParser.GTE:
|
||||
case XPathParser.LTE:
|
||||
case XPathParser.PLUS:
|
||||
case XPathParser.MINUS:
|
||||
case XPathParser.STAR:
|
||||
case XPathParser.AT:
|
||||
case XPathParser.DOLLAR:
|
||||
case XPathParser.COLON:
|
||||
case XPathParser.DOUBLE_COLON:
|
||||
case XPathParser.DIV:
|
||||
case XPathParser.MOD:
|
||||
case XPathParser.OR:
|
||||
case XPathParser.AND:
|
||||
case XPathParser.SLASH:
|
||||
return new XPathToken(XPathParser.NAME, name);
|
||||
}
|
||||
break;
|
||||
}
|
||||
return new XPathToken (val);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
boolean isNameChar (int c)
|
||||
{
|
||||
/* Name */
|
||||
return (c == 0x5f
|
||||
|| c == 0x2d
|
||||
|| c == 0x2e
|
||||
|| (c >= 0x30 && c <= 0x39)
|
||||
/* CombiningChar */
|
||||
|| (c >= 0x0300 && c <= 0x0345)
|
||||
|| (c >= 0x0360 && c <= 0x0361)
|
||||
|| (c >= 0x0483 && c <= 0x0486)
|
||||
|| (c >= 0x0591 && c <= 0x05A1)
|
||||
|| (c >= 0x05A3 && c <= 0x05B9)
|
||||
|| (c >= 0x05BB && c <= 0x05BD)
|
||||
|| c == 0x05BF
|
||||
|| (c >= 0x05C1 && c <= 0x05C2)
|
||||
|| c == 0x05C4
|
||||
|| (c >= 0x064B && c <= 0x0652)
|
||||
|| c == 0x0670
|
||||
|| (c >= 0x06D6 && c <= 0x06DC)
|
||||
|| (c >= 0x06DD && c <= 0x06DF)
|
||||
|| (c >= 0x06E0 && c <= 0x06E4)
|
||||
|| (c >= 0x06E7 && c <= 0x06E8)
|
||||
|| (c >= 0x06EA && c <= 0x06ED)
|
||||
|| (c >= 0x0901 && c <= 0x0903)
|
||||
|| c == 0x093C
|
||||
|| (c >= 0x093E && c <= 0x094C)
|
||||
|| c == 0x094D
|
||||
|| (c >= 0x0951 && c <= 0x0954)
|
||||
|| (c >= 0x0962 && c <= 0x0963)
|
||||
|| (c >= 0x0981 && c <= 0x0983)
|
||||
|| c == 0x09BC
|
||||
|| c == 0x09BE
|
||||
|| c == 0x09BF
|
||||
|| (c >= 0x09C0 && c <= 0x09C4)
|
||||
|| (c >= 0x09C7 && c <= 0x09C8)
|
||||
|| (c >= 0x09CB && c <= 0x09CD)
|
||||
|| c == 0x09D7
|
||||
|| (c >= 0x09E2 && c <= 0x09E3)
|
||||
|| c == 0x0A02
|
||||
|| c == 0x0A3C
|
||||
|| c == 0x0A3E
|
||||
|| c == 0x0A3F
|
||||
|| (c >= 0x0A40 && c <= 0x0A42)
|
||||
|| (c >= 0x0A47 && c <= 0x0A48)
|
||||
|| (c >= 0x0A4B && c <= 0x0A4D)
|
||||
|| (c >= 0x0A70 && c <= 0x0A71)
|
||||
|| (c >= 0x0A81 && c <= 0x0A83)
|
||||
|| c == 0x0ABC
|
||||
|| (c >= 0x0ABE && c <= 0x0AC5)
|
||||
|| (c >= 0x0AC7 && c <= 0x0AC9)
|
||||
|| (c >= 0x0ACB && c <= 0x0ACD)
|
||||
|| (c >= 0x0B01 && c <= 0x0B03)
|
||||
|| c == 0x0B3C
|
||||
|| (c >= 0x0B3E && c <= 0x0B43)
|
||||
|| (c >= 0x0B47 && c <= 0x0B48)
|
||||
|| (c >= 0x0B4B && c <= 0x0B4D)
|
||||
|| (c >= 0x0B56 && c <= 0x0B57)
|
||||
|| (c >= 0x0B82 && c <= 0x0B83)
|
||||
|| (c >= 0x0BBE && c <= 0x0BC2)
|
||||
|| (c >= 0x0BC6 && c <= 0x0BC8)
|
||||
|| (c >= 0x0BCA && c <= 0x0BCD)
|
||||
|| c == 0x0BD7
|
||||
|| (c >= 0x0C01 && c <= 0x0C03)
|
||||
|| (c >= 0x0C3E && c <= 0x0C44)
|
||||
|| (c >= 0x0C46 && c <= 0x0C48)
|
||||
|| (c >= 0x0C4A && c <= 0x0C4D)
|
||||
|| (c >= 0x0C55 && c <= 0x0C56)
|
||||
|| (c >= 0x0C82 && c <= 0x0C83)
|
||||
|| (c >= 0x0CBE && c <= 0x0CC4)
|
||||
|| (c >= 0x0CC6 && c <= 0x0CC8)
|
||||
|| (c >= 0x0CCA && c <= 0x0CCD)
|
||||
|| (c >= 0x0CD5 && c <= 0x0CD6)
|
||||
|| (c >= 0x0D02 && c <= 0x0D03)
|
||||
|| (c >= 0x0D3E && c <= 0x0D43)
|
||||
|| (c >= 0x0D46 && c <= 0x0D48)
|
||||
|| (c >= 0x0D4A && c <= 0x0D4D)
|
||||
|| c == 0x0D57
|
||||
|| c == 0x0E31
|
||||
|| (c >= 0x0E34 && c <= 0x0E3A)
|
||||
|| (c >= 0x0E47 && c <= 0x0E4E)
|
||||
|| c == 0x0EB1
|
||||
|| (c >= 0x0EB4 && c <= 0x0EB9)
|
||||
|| (c >= 0x0EBB && c <= 0x0EBC)
|
||||
|| (c >= 0x0EC8 && c <= 0x0ECD)
|
||||
|| (c >= 0x0F18 && c <= 0x0F19)
|
||||
|| c == 0x0F35
|
||||
|| c == 0x0F37
|
||||
|| c == 0x0F39
|
||||
|| c == 0x0F3E
|
||||
|| c == 0x0F3F
|
||||
|| (c >= 0x0F71 && c <= 0x0F84)
|
||||
|| (c >= 0x0F86 && c <= 0x0F8B)
|
||||
|| (c >= 0x0F90 && c <= 0x0F95)
|
||||
|| c == 0x0F97
|
||||
|| (c >= 0x0F99 && c <= 0x0FAD)
|
||||
|| (c >= 0x0FB1 && c <= 0x0FB7)
|
||||
|| c == 0x0FB9
|
||||
|| (c >= 0x20D0 && c <= 0x20DC)
|
||||
|| c == 0x20E1
|
||||
|| (c >= 0x302A && c <= 0x302F)
|
||||
|| c == 0x3099
|
||||
|| c == 0x309A
|
||||
/* Extender */
|
||||
|| c == 0x00B7
|
||||
|| c == 0x02D0
|
||||
|| c == 0x02D1
|
||||
|| c == 0x0387
|
||||
|| c == 0x0640
|
||||
|| c == 0x0E46
|
||||
|| c == 0x0EC6
|
||||
|| c == 0x3005
|
||||
|| (c >= 0x3031 && c <= 0x3035)
|
||||
|| (c >= 0x309D && c <= 0x309E)
|
||||
|| (c >= 0x30FC && c <= 0x30FE)
|
||||
/* Name */
|
||||
|| Character.isLetter ((char) c));
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user