View Javadoc

    1   /*
    2    * $Id: AbstractAdapterNode.java 471756 2006-11-06 15:01:43Z husted $
    3    *
    4    * Licensed to the Apache Software Foundation (ASF) under one
    5    * or more contributor license agreements.  See the NOTICE file
    6    * distributed with this work for additional information
    7    * regarding copyright ownership.  The ASF licenses this file
    8    * to you under the Apache License, Version 2.0 (the
    9    * "License"); you may not use this file except in compliance
    10   * with the License.  You may obtain a copy of the License at
    11   *
    12   *  http://www.apache.org/licenses/LICENSE-2.0
    13   *
    14   * Unless required by applicable law or agreed to in writing,
    15   * software distributed under the License is distributed on an
    16   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
    17   * KIND, either express or implied.  See the License for the
    18   * specific language governing permissions and limitations
    19   * under the License.
    20   */
    21  package org.apache.struts2.views.xslt;
    22
    23  import java.util.ArrayList;
    24  import java.util.LinkedList;
    25  import java.util.List;
    26
    27  import org.apache.commons.logging.Log;
    28  import org.apache.commons.logging.LogFactory;
    29  import org.apache.struts2.StrutsException;
    30  import org.w3c.dom.DOMException;
    31  import org.w3c.dom.Document;
    32  import org.w3c.dom.NamedNodeMap;
    33  import org.w3c.dom.Node;
    34  import org.w3c.dom.NodeList;
    35  import org.w3c.dom.UserDataHandler;
    36
    37  /***
    38   * AbstractAdapterNode is the base for childAdapters that expose a read-only view
    39   * of a Java object as a DOM Node.  This class implements the core parent-child
    40   * and sibling node traversal functionality shared by all adapter type nodes
    41   * and used in proxy node support.
    42   *
    43   * @see AbstractAdapterElement
    44   */
    45  public abstract class AbstractAdapterNode implements AdapterNode {
    46
    47      private static final NamedNodeMap EMPTY_NAMEDNODEMAP =
    48              new NamedNodeMap() {
    49                  public int getLength() {
    50                      return 0;
    51                  }
    52
    53                  public Node item(int index) {
    54                      return null;
    55                  }
    56
    57                  public Node getNamedItem(String name) {
    58                      return null;
    59                  }
    60
    61                  public Node removeNamedItem(String name) throws DOMException {
    62                      return null;
    63                  }
    64
    65                  public Node setNamedItem(Node arg) throws DOMException {
    66                      return null;
    67                  }
    68
    69                  public Node setNamedItemNS(Node arg) throws DOMException {
    70                      return null;
    71                  }
    72
    73                  public Node getNamedItemNS(String namespaceURI, String localName) {
    74                      return null;
    75                  }
    76
    77                  public Node removeNamedItemNS(String namespaceURI, String localName) throws DOMException {
    78                      return null;
    79                  }
    80              };
    81
    82      private List<Node> childAdapters;
    83      private Log log = LogFactory.getLog(this.getClass());
    84
    85      // The domain object that we are adapting
    86      private Object propertyValue;
    87      private String propertyName;
    88      private AdapterNode parent;
    89      private AdapterFactory adapterFactory;
    90
    91
    92      public AbstractAdapterNode() {
    93          if (LogFactory.getLog(getClass()).isDebugEnabled()) {
    94              LogFactory.getLog(getClass()).debug("Creating " + this);
    95          }
    96      }
    97
    98      /***
    99       *
    100      * @param adapterFactory
    101      * @param parent
    102      * @param propertyName
    103      * @param value
    104      */
    105     protected void setContext(AdapterFactory adapterFactory, AdapterNode parent, String propertyName, Object value) {
    106         setAdapterFactory(adapterFactory);
    107         setParent(parent);
    108         setPropertyName(propertyName);
    109         setPropertyValue(value);
    110     }
    111
    112     /***
    113      * subclasses override to produce their children
    114      *
    115      * @return List of child adapters.
    116      */
    117     protected List<Node> buildChildAdapters() {
    118         return new ArrayList<Node>();
    119     }
    120
    121     /***
    122      * Lazily initialize child childAdapters
    123      */
    124     protected List<Node> getChildAdapters() {
    125         if (childAdapters == null) {
    126             childAdapters = buildChildAdapters();
    127         }
    128         return childAdapters;
    129     }
    130
    131     public Node getChildBeforeOrAfter(Node child, boolean before) {
    132         log.debug("getChildBeforeOrAfter: ");
    133         List adapters = getChildAdapters();
    134         log.debug("childAdapters = " + adapters);
    135         log.debug("child = " + child);
    136         int index = adapters.indexOf(child);
    137         if (index < 0)
    138             throw new StrutsException(child + " is no child of " + this);
    139         int siblingIndex = before ? index - 1 : index + 1;
    140         return ((0 < siblingIndex) && (siblingIndex < adapters.size())) ?
    141                 ((Node) adapters.get(siblingIndex)) : null;
    142     }
    143
    144     public Node getChildAfter(Node child) {
    145         log.trace("getChildafter");
    146         return getChildBeforeOrAfter(child, false/*after*/);
    147     }
    148
    149     public Node getChildBefore(Node child) {
    150         log.trace("getchildbefore");
    151         return getChildBeforeOrAfter(child, true/*after*/);
    152     }
    153
    154     public NodeList getElementsByTagName(String tagName) {
    155         if (tagName.equals("*")) {
    156             return getChildNodes();
    157         } else {
    158             LinkedList<Node> filteredChildren = new LinkedList<Node>();
    159
    160             for (Node adapterNode : getChildAdapters()) {
    161                 if (adapterNode.getNodeName().equals(tagName)) {
    162                     filteredChildren.add(adapterNode);
    163                 }
    164             }
    165
    166             return new SimpleNodeList(filteredChildren);
    167         }
    168     }
    169
    170     public NodeList getElementsByTagNameNS(String string, String string1) {
    171         // TODO:
    172         return null;
    173     }
    174
    175     // Begin Node methods
    176
    177     public NamedNodeMap getAttributes() {
    178         return EMPTY_NAMEDNODEMAP;
    179     }
    180
    181     public NodeList getChildNodes() {
    182         NodeList nl = new SimpleNodeList(getChildAdapters());
    183         if (log.isDebugEnabled())
    184             log.debug("getChildNodes for tag: "
    185                     + getNodeName() + " num children: " + nl.getLength());
    186         return nl;
    187     }
    188
    189     public Node getFirstChild() {
    190         return (getChildNodes().getLength() > 0) ? getChildNodes().item(0) : null;
    191     }
    192
    193     public Node getLastChild() {
    194         return (getChildNodes().getLength() > 0) ? getChildNodes().item(getChildNodes().getLength() - 1) : null;
    195     }
    196
    197
    198     public String getLocalName() {
    199         return null;
    200     }
    201
    202     public String getNamespaceURI() {
    203         return null;
    204     }
    205
    206     public void setNodeValue(String string) throws DOMException {
    207         throw operationNotSupported();
    208     }
    209
    210     public String getNodeValue() throws DOMException {
    211         throw operationNotSupported();
    212     }
    213
    214     public Document getOwnerDocument() {
    215         return null;
    216     }
    217
    218     public Node getParentNode() {
    219         log.trace("getParentNode");
    220         return getParent();
    221     }
    222
    223     public AdapterNode getParent() {
    224         return parent;
    225     }
    226
    227     public void setParent(AdapterNode parent) {
    228         this.parent = parent;
    229     }
    230
    231     public Object getPropertyValue() {
    232         return propertyValue;
    233     }
    234
    235     public void setPropertyValue(Object prop) {
    236         this.propertyValue = prop;
    237     }
    238
    239     public void setPrefix(String string) throws DOMException {
    240         throw operationNotSupported();
    241     }
    242
    243     public String getPrefix() {
    244         return null;
    245     }
    246
    247     public Node getNextSibling() {
    248         Node next = getParent().getChildAfter(this);
    249         if (log.isTraceEnabled()) {
    250             log.trace("getNextSibling on " + getNodeName() + ": "
    251                     + ((next == null) ? "null" : next.getNodeName()));
    252         }
    253
    254         return getParent().getChildAfter(this);
    255     }
    256
    257     public Node getPreviousSibling() {
    258         return getParent().getChildBefore(this);
    259     }
    260
    261     public String getPropertyName() {
    262         return propertyName;
    263     }
    264
    265     public void setPropertyName(String name) {
    266         this.propertyName = name;
    267     }
    268
    269     public AdapterFactory getAdapterFactory() {
    270         return adapterFactory;
    271     }
    272
    273     public void setAdapterFactory(AdapterFactory adapterFactory) {
    274         this.adapterFactory = adapterFactory;
    275     }
    276
    277     public boolean isSupported(String string, String string1) {
    278         throw operationNotSupported();
    279     }
    280
    281     public Node appendChild(Node node) throws DOMException {
    282         throw operationNotSupported();
    283     }
    284
    285     public Node cloneNode(boolean b) {
    286         log.trace("cloneNode");
    287         throw operationNotSupported();
    288     }
    289
    290     public boolean hasAttributes() {
    291         return false;
    292     }
    293
    294     public boolean hasChildNodes() {
    295         return false;
    296     }
    297
    298     public Node insertBefore(Node node, Node node1) throws DOMException {
    299         throw operationNotSupported();
    300     }
    301
    302     public void normalize() {
    303         log.trace("normalize");
    304         throw operationNotSupported();
    305     }
    306
    307     public Node removeChild(Node node) throws DOMException {
    308         throw operationNotSupported();
    309     }
    310
    311     public Node replaceChild(Node node, Node node1) throws DOMException {
    312         throw operationNotSupported();
    313     }
    314
    315     // Begin DOM 3 methods
    316
    317     public boolean isDefaultNamespace(String string) {
    318         throw operationNotSupported();
    319     }
    320
    321     public String lookupNamespaceURI(String string) {
    322         throw operationNotSupported();
    323     }
    324
    325     public String getNodeName() {
    326         throw operationNotSupported();
    327     }
    328
    329     public short getNodeType() {
    330         throw operationNotSupported();
    331     }
    332
    333     public String getBaseURI() {
    334         throw operationNotSupported();
    335     }
    336
    337     public short compareDocumentPosition(Node node) throws DOMException {
    338         throw operationNotSupported();
    339     }
    340
    341     public String getTextContent() throws DOMException {
    342         throw operationNotSupported();
    343     }
    344
    345     public void setTextContent(String string) throws DOMException {
    346         throw operationNotSupported();
    347
    348     }
    349
    350     public boolean isSameNode(Node node) {
    351         throw operationNotSupported();
    352     }
    353
    354     public String lookupPrefix(String string) {
    355         throw operationNotSupported();
    356     }
    357
    358     public boolean isEqualNode(Node node) {
    359         throw operationNotSupported();
    360     }
    361
    362     public Object getFeature(String string, String string1) {
    363         throw operationNotSupported();
    364     }
    365
    366     public Object setUserData(String string, Object object, UserDataHandler userDataHandler) {
    367         throw operationNotSupported();
    368     }
    369
    370     public Object getUserData(String string) {
    371         throw operationNotSupported();
    372     }
    373
    374     // End node methods
    375
    376     protected StrutsException operationNotSupported() {
    377         return new StrutsException("Operation not supported.");
    378     }
    379
    380     public String toString() {
    381         return getClass() + ": " + getNodeName() + " parent=" + getParentNode();
    382     }
    383 }