com.caucho.xml.QNode Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of resin-kernel Show documentation
Show all versions of resin-kernel Show documentation
Kernel for Resin Java Application Server
The newest version!
/*
* Copyright (c) 1998-2012 Caucho Technology -- all rights reserved
*
* This file is part of Resin(R) Open Source
*
* Each copy or derived work must preserve the copyright notice and this
* notice unmodified.
*
* Resin Open Source 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.
*
* Resin Open Source 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, or any warranty
* of NON-INFRINGEMENT. See the GNU General Public License for more
* details.
*
* You should have received a copy of the GNU General Public License
* along with Resin Open Source; if not, write to the
* Free SoftwareFoundation, Inc.
* 59 Temple Place, Suite 330
* Boston, MA 02111-1307 USA
*
* @author Scott Ferguson
*/
package com.caucho.xml;
// import com.caucho.xpath.pattern.NodeListIterator;
import org.w3c.dom.DOMException;
import org.w3c.dom.NamedNodeMap;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import java.util.Iterator;
/**
* QNode represents any node that can have children.
*/
public abstract class QNode extends QAbstractNode {
protected QAbstractNode _firstChild;
protected QAbstractNode _lastChild;
protected QNode()
{
}
protected QNode(QDocument owner)
{
super(owner);
}
public String getNodeValue() { return null; }
public void setNodeValue(String value) {}
/**
* Returns a node list of the children.
*/
public NodeList getChildNodes()
{
return new ChildNodeList();
}
public Node getFirstChild()
{
return _firstChild;
}
public Node getLastChild()
{
return _lastChild;
}
public Node getPreviousSibling()
{
return _previous;
}
public Node getNextSibling()
{
return _next;
}
public NamedNodeMap getAttributes() { return null; }
public Node insertBefore(Node newChild, Node refChild)
throws DOMException
{
QAbstractNode qNewChild = (QAbstractNode) newChild;
QAbstractNode qRefChild = (QAbstractNode) refChild;
if (qNewChild._owner != _owner && qNewChild._owner != this)
throw new QDOMException(DOMException.WRONG_DOCUMENT_ERR,
"insertBefore new child from wrong document");
qNewChild.remove();
if (qRefChild != null && qRefChild._parent != this)
throw new QDOMException(DOMException.NOT_FOUND_ERR, "insertBefore has no such child");
if (qNewChild instanceof QDocumentFragment) {
QDocumentFragment frag = (QDocumentFragment) qNewChild;
QAbstractNode first = frag._firstChild;
QAbstractNode next = null;
for (QAbstractNode ptr = first; ptr != null; ptr = next) {
next = ptr._next;
insertBefore(ptr, refChild);
}
return first;
}
qNewChild._parent = this;
if (refChild == null) {
if (_firstChild == null) {
qNewChild._previous = null;
qNewChild._next = null;
_firstChild = _lastChild = qNewChild;
} else {
_lastChild._next = qNewChild;
qNewChild._previous = _lastChild;
_lastChild = qNewChild;
qNewChild._next = null;
}
return qNewChild;
}
qNewChild._previous = qRefChild._previous;
qNewChild._next = qRefChild;
if (qRefChild._previous == null)
_firstChild = qNewChild;
else
qRefChild._previous._next = qNewChild;
qRefChild._previous = qNewChild;
return qNewChild;
}
public Node replaceChild(Node newChild, Node refChild)
throws DOMException
{
QAbstractNode qNewChild = (QAbstractNode) newChild;
QAbstractNode qRefChild = (QAbstractNode) refChild;
if (qRefChild == null || qRefChild._parent != this)
throw new QDOMException(DOMException.NOT_FOUND_ERR, "ref is not child");
if (qNewChild == null || qNewChild._owner != _owner)
throw new QDOMException(DOMException.WRONG_DOCUMENT_ERR,
"wrong document");
if (_owner != null)
_owner._changeCount++;
qNewChild._previous = qRefChild._previous;
qNewChild._next = qRefChild._next;
qNewChild._parent = this;
if (qNewChild._previous == null)
_firstChild = qNewChild;
else
qNewChild._previous._next = qNewChild;
if (qNewChild._next == null)
_lastChild = qNewChild;
else
qNewChild._next._previous = qNewChild;
qRefChild._previous = null;
qRefChild._next = null;
qRefChild._parent = null;
return qRefChild;
}
public Node removeChild(Node oldChild) throws DOMException
{
QAbstractNode qOldChild = (QAbstractNode) oldChild;
if (qOldChild != null && qOldChild._parent != this) {
throw new QDOMException(DOMException.NOT_FOUND_ERR,
"removeChild has no such child");
}
if (_owner != null)
_owner._changeCount++;
if (qOldChild._previous == null)
_firstChild = qOldChild._next;
else
qOldChild._previous._next = qOldChild._next;
if (qOldChild._next == null)
_lastChild = qOldChild._previous;
else
qOldChild._next._previous = qOldChild._previous;
qOldChild._parent = null;
qOldChild._next = null;
qOldChild._previous = null;
return qOldChild;
}
private static void setOwner(QAbstractNode node, QDocument owner)
{
if (node._owner == null) {
node._owner = owner;
String namespace = node.getNamespaceURI();
if (namespace != "")
owner.addNamespace(node.getPrefix(), namespace);
for (QAbstractNode child = (QAbstractNode) node.getFirstChild();
child != null;
child = (QAbstractNode) child.getNextSibling())
{
setOwner(child, owner);
}
}
}
public Node appendChild(Node newNode) throws DOMException
{
QAbstractNode qNewNode = (QAbstractNode) newNode;
setOwner(qNewNode, _owner);
if (qNewNode._owner != _owner && qNewNode._owner != this) {
throw new QDOMException(DOMException.WRONG_DOCUMENT_ERR,
"can't appendChild from different document");
}
qNewNode.remove();
if (qNewNode instanceof QDocumentFragment) {
QDocumentFragment frag = (QDocumentFragment) qNewNode;
QAbstractNode first = frag._firstChild;
QAbstractNode next = null;
for (QAbstractNode ptr = first; ptr != null; ptr = next) {
next = ptr._next;
appendChild(ptr);
}
return first;
}
qNewNode._parent = this;
qNewNode._next = null;
qNewNode._previous = _lastChild;
if (_lastChild == null) {
_lastChild = qNewNode;
_firstChild = qNewNode;
}
else {
_lastChild._next = qNewNode;
_lastChild = qNewNode;
}
return qNewNode;
}
public boolean hasChildNodes()
{
return _firstChild != null;
}
public void setTextContent(String content)
{
QText text = new QText(content);
text._owner = _owner;
_firstChild = _lastChild = text;
}
public void normalize()
{
}
public boolean checkValid()
throws Exception
{
if (! super.checkValid())
throw new Exception("super bad: " + this);
if (_firstChild != null && _firstChild._previous != null)
throw new Exception("first child bad: " + this);
if (_lastChild != null && _lastChild._next != null)
throw new Exception("last child bad:" + this);
QAbstractNode ptr = _firstChild;
for (; ptr != null; ptr = ptr._next) {
if (ptr._parent != this)
throw new Exception("child parent bad:" + this + " " + ptr);
if (ptr._owner != _owner && ptr._owner != this)
throw new Exception("child owner bad:" + this + " " + ptr + " " +
ptr._owner + " " + _owner);
if (ptr._next != null && ptr._next._previous != ptr)
throw new Exception("child links bad:" + this + " " + ptr);
}
ptr = _lastChild;
for (; ptr != null; ptr = ptr._previous) {
if (ptr._parent != this)
throw new Exception("child parent bad:" + this + " " + ptr);
if (ptr._owner != _owner && ptr._owner != this)
throw new Exception("child owner bad:" + this + " " + ptr);
if (ptr._previous != null && ptr._previous._next != ptr)
throw new Exception("child links bad:" + this + " " + ptr);
}
return true;
}
public QAbstractNode getNextPreorder()
{
if (_firstChild != null)
return _firstChild;
else if (_next != null)
return _next;
for (QNode ptr = _parent; ptr != null; ptr = ptr._parent) {
if (ptr._next != null)
return ptr._next;
}
return null;
}
public boolean equals(Object arg)
{
return this == arg;
}
public boolean equals(Node arg, boolean deep)
{
return this == arg;
}
// NodeList methods
public class ChildNodeList implements NodeList {
/**
* Returns the child with the given index.
*/
public Node item(int index)
{
QAbstractNode ptr = _firstChild;
for (; ptr != null && index > 0; index--) {
ptr = ptr._next;
}
return ptr;
}
/**
* Returns the number of children.
*/
public int getLength()
{
int index = 0;
for (QAbstractNode ptr = _firstChild; ptr != null; ptr = ptr._next)
index++;
return index;
}
/*
// for quercus
public Iterator iterator()
{
return new NodeListIterator(null, this);
}
*/
}
}