OSDN Git Service

original
[gb-231r1-is01/Gingerbread_2.3.3_r1_IS01.git] / libcore / luni / src / main / java / org / apache / xml / dtm / ref / dom2dtm / DOM2DTMdefaultNamespaceDeclarationNode.java
1 /*
2  * Licensed to the Apache Software Foundation (ASF) under one
3  * or more contributor license agreements. See the NOTICE file
4  * distributed with this work for additional information
5  * regarding copyright ownership. The ASF licenses this file
6  * to you under the Apache License, Version 2.0 (the  "License");
7  * you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  *     http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing, software
13  * distributed under the License is distributed on an "AS IS" BASIS,
14  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15  * See the License for the specific language governing permissions and
16  * limitations under the License.
17  */
18 /*
19  * $Id: DOM2DTMdefaultNamespaceDeclarationNode.java 468653 2006-10-28 07:07:05Z minchau $
20  */
21
22 package org.apache.xml.dtm.ref.dom2dtm;
23
24 import org.apache.xml.dtm.DTMException;
25
26 import org.w3c.dom.Attr;
27 import org.w3c.dom.Document;
28 import org.w3c.dom.Element;
29 import org.w3c.dom.NamedNodeMap;
30 import org.w3c.dom.Node;
31 import org.w3c.dom.NodeList;
32 import org.w3c.dom.TypeInfo;
33 import org.w3c.dom.UserDataHandler;
34 import org.w3c.dom.DOMException;
35
36 /** This is a kluge to let us shove a declaration for xml: into the
37  * DOM2DTM model.  Basically, it creates a proxy node in DOM space to
38  * carry the additional information. This is _NOT_ a full DOM
39  * implementation, and shouldn't be one since it sits alongside the
40  * DOM rather than becoming part of the DOM model.
41  * 
42  * (This used to be an internal class within DOM2DTM. Moved out because
43  * I need to perform an instanceof operation on it to support a temporary
44  * workaround in DTMManagerDefault.)
45  * 
46  * %REVIEW% What if the DOM2DTM was built around a DocumentFragment and
47  * there isn't a single root element? I think this fails that case...
48  * 
49  * %REVIEW% An alternative solution would be to create the node _only_
50  * in DTM space, but given how DOM2DTM is currently written I think
51  * this is simplest.
52  * */
53 public class DOM2DTMdefaultNamespaceDeclarationNode implements Attr,TypeInfo
54 {
55   final String NOT_SUPPORTED_ERR="Unsupported operation on pseudonode";
56   
57   Element pseudoparent;
58   String prefix,uri,nodename;
59   int handle;
60   DOM2DTMdefaultNamespaceDeclarationNode(Element pseudoparent,String prefix,String uri,int handle)
61   {
62     this.pseudoparent=pseudoparent;
63     this.prefix=prefix;
64     this.uri=uri;
65     this.handle=handle;
66     this.nodename="xmlns:"+prefix;
67   }
68   public String getNodeName() {return nodename;}
69   public String getName() {return nodename;}
70   public String getNamespaceURI() {return "http://www.w3.org/2000/xmlns/";}
71   public String getPrefix() {return prefix;}
72   public String getLocalName() {return prefix;}
73   public String getNodeValue() {return uri;}
74   public String getValue() {return uri;}
75   public Element getOwnerElement() {return pseudoparent;}
76   
77   public boolean isSupported(String feature, String version) {return false;}
78   public boolean hasChildNodes() {return false;}
79   public boolean hasAttributes() {return false;}
80   public Node getParentNode() {return null;}
81   public Node getFirstChild() {return null;}
82   public Node getLastChild() {return null;}
83   public Node getPreviousSibling() {return null;}
84   public Node getNextSibling() {return null;}
85   public boolean getSpecified() {return false;}
86   public void normalize() {return;}
87   public NodeList getChildNodes() {return null;}
88   public NamedNodeMap getAttributes() {return null;}
89   public short getNodeType() {return Node.ATTRIBUTE_NODE;}
90   public void setNodeValue(String value) {throw new DTMException(NOT_SUPPORTED_ERR);}
91   public void setValue(String value) {throw new DTMException(NOT_SUPPORTED_ERR);}
92   public void setPrefix(String value) {throw new DTMException(NOT_SUPPORTED_ERR);}
93   public Node insertBefore(Node a, Node b) {throw new DTMException(NOT_SUPPORTED_ERR);}
94   public Node replaceChild(Node a, Node b) {throw new DTMException(NOT_SUPPORTED_ERR);}
95   public Node appendChild(Node a) {throw new DTMException(NOT_SUPPORTED_ERR);}
96   public Node removeChild(Node a) {throw new DTMException(NOT_SUPPORTED_ERR);}
97   public Document getOwnerDocument() {return pseudoparent.getOwnerDocument();}
98   public Node cloneNode(boolean deep) {throw new DTMException(NOT_SUPPORTED_ERR);}
99         
100     /** Non-DOM method, part of the temporary kluge
101      * %REVIEW% This would be a pruning problem, but since it will always be
102      * added to the root element and we prune on elements, we shouldn't have 
103      * to worry.
104      */
105     public int getHandleOfNode()                
106     {
107         return handle;
108     }
109
110     //RAMESH: PENDING=> Add proper implementation for the below DOM L3 additions
111
112     /**
113      * @see org.w3c.dom.TypeInfo#getTypeName()
114      */
115     public String getTypeName() {return null; }
116      
117     /**
118      * @see org.w3c.dom.TypeInfo#getTypeNamespace()
119      */
120     public String getTypeNamespace() { return null;}
121     
122     /**
123      * @see or.gw3c.dom.TypeInfo#isDerivedFrom(String,String,int)
124      */
125     public boolean isDerivedFrom( String ns, String localName, int derivationMethod ) {
126         return false;
127     }
128
129     public TypeInfo getSchemaTypeInfo() { return this; }
130     
131     public boolean isId( ) { return false; }
132
133     /**
134      * Associate an object to a key on this node. The object can later be
135      * retrieved from this node by calling <code>getUserData</code> with the
136      * same key.
137      * @param key The key to associate the object to.
138      * @param data The object to associate to the given key, or
139      *   <code>null</code> to remove any existing association to that key.
140      * @param handler The handler to associate to that key, or
141      *   <code>null</code>.
142      * @return Returns the <code>DOMObject</code> previously associated to
143      *   the given key on this node, or <code>null</code> if there was none.
144      * @since DOM Level 3
145      */
146     public Object setUserData(String key,
147                               Object data,
148                               UserDataHandler handler) {
149         return getOwnerDocument().setUserData( key, data, handler);
150     }
151
152     /**
153      * Retrieves the object associated to a key on a this node. The object
154      * must first have been set to this node by calling
155      * <code>setUserData</code> with the same key.
156      * @param key The key the object is associated to.
157      * @return Returns the <code>DOMObject</code> associated to the given key
158      *   on this node, or <code>null</code> if there was none.
159      * @since DOM Level 3
160      */
161     public Object getUserData(String key) {
162         return getOwnerDocument().getUserData( key);
163     } 
164
165     /**
166      *  This method returns a specialized object which implements the
167      * specialized APIs of the specified feature and version. The
168      * specialized object may also be obtained by using binding-specific
169      * casting methods but is not necessarily expected to, as discussed in Mixed DOM implementations.
170      * @param feature The name of the feature requested (case-insensitive).
171      * @param version  This is the version number of the feature to test. If
172      *   the version is <code>null</code> or the empty string, supporting
173      *   any version of the feature will cause the method to return an
174      *   object that supports at least one version of the feature.
175      * @return  Returns an object which implements the specialized APIs of
176      *   the specified feature and version, if any, or <code>null</code> if
177      *   there is no object which implements interfaces associated with that
178      *   feature. If the <code>DOMObject</code> returned by this method
179      *   implements the <code>Node</code> interface, it must delegate to the
180      *   primary core <code>Node</code> and not return results inconsistent
181      *   with the primary core <code>Node</code> such as attributes,
182      *   childNodes, etc.
183      * @since DOM Level 3
184      */
185     public Object getFeature(String feature, String version) {
186         // we don't have any alternate node, either this node does the job
187         // or we don't have anything that does
188         return isSupported(feature, version) ? this : null;
189     }
190
191     /**
192      * Tests whether two nodes are equal.
193      * <br>This method tests for equality of nodes, not sameness (i.e.,
194      * whether the two nodes are references to the same object) which can be
195      * tested with <code>Node.isSameNode</code>. All nodes that are the same
196      * will also be equal, though the reverse may not be true.
197      * <br>Two nodes are equal if and only if the following conditions are
198      * satisfied: The two nodes are of the same type.The following string
199      * attributes are equal: <code>nodeName</code>, <code>localName</code>,
200      * <code>namespaceURI</code>, <code>prefix</code>, <code>nodeValue</code>
201      * , <code>baseURI</code>. This is: they are both <code>null</code>, or
202      * they have the same length and are character for character identical.
203      * The <code>attributes</code> <code>NamedNodeMaps</code> are equal.
204      * This is: they are both <code>null</code>, or they have the same
205      * length and for each node that exists in one map there is a node that
206      * exists in the other map and is equal, although not necessarily at the
207      * same index.The <code>childNodes</code> <code>NodeLists</code> are
208      * equal. This is: they are both <code>null</code>, or they have the
209      * same length and contain equal nodes at the same index. This is true
210      * for <code>Attr</code> nodes as for any other type of node. Note that
211      * normalization can affect equality; to avoid this, nodes should be
212      * normalized before being compared.
213      * <br>For two <code>DocumentType</code> nodes to be equal, the following
214      * conditions must also be satisfied: The following string attributes
215      * are equal: <code>publicId</code>, <code>systemId</code>,
216      * <code>internalSubset</code>.The <code>entities</code>
217      * <code>NamedNodeMaps</code> are equal.The <code>notations</code>
218      * <code>NamedNodeMaps</code> are equal.
219      * <br>On the other hand, the following do not affect equality: the
220      * <code>ownerDocument</code> attribute, the <code>specified</code>
221      * attribute for <code>Attr</code> nodes, the
222      * <code>isWhitespaceInElementContent</code> attribute for
223      * <code>Text</code> nodes, as well as any user data or event listeners
224      * registered on the nodes.
225      * @param arg The node to compare equality with.
226      * @param deep If <code>true</code>, recursively compare the subtrees; if
227      *   <code>false</code>, compare only the nodes themselves (and its
228      *   attributes, if it is an <code>Element</code>).
229      * @return If the nodes, and possibly subtrees are equal,
230      *   <code>true</code> otherwise <code>false</code>.
231      * @since DOM Level 3
232      */
233     public boolean isEqualNode(Node arg) {
234         if (arg == this) {
235             return true;
236         }
237         if (arg.getNodeType() != getNodeType()) {
238             return false;
239         }
240         // in theory nodeName can't be null but better be careful
241         // who knows what other implementations may be doing?...
242         if (getNodeName() == null) {
243             if (arg.getNodeName() != null) {
244                 return false;
245             }
246         }
247         else if (!getNodeName().equals(arg.getNodeName())) {
248             return false;
249         }
250
251         if (getLocalName() == null) {
252             if (arg.getLocalName() != null) {
253                 return false;
254             }
255         }
256         else if (!getLocalName().equals(arg.getLocalName())) {
257             return false;
258         }
259
260         if (getNamespaceURI() == null) {
261             if (arg.getNamespaceURI() != null) {
262                 return false;
263             }
264         }
265         else if (!getNamespaceURI().equals(arg.getNamespaceURI())) {
266             return false;
267         }
268
269         if (getPrefix() == null) {
270             if (arg.getPrefix() != null) {
271                 return false;
272             }
273         }
274         else if (!getPrefix().equals(arg.getPrefix())) {
275             return false;
276         }
277
278         if (getNodeValue() == null) {
279             if (arg.getNodeValue() != null) {
280                 return false;
281             }
282         }
283         else if (!getNodeValue().equals(arg.getNodeValue())) {
284             return false;
285         }
286     /*
287         if (getBaseURI() == null) {
288             if (((NodeImpl) arg).getBaseURI() != null) {
289                 return false;
290             }
291         }
292         else if (!getBaseURI().equals(((NodeImpl) arg).getBaseURI())) {
293             return false;
294         }
295 */
296
297              return true;
298     }
299
300     /**
301      * DOM Level 3 - Experimental:
302      * Look up the namespace URI associated to the given prefix, starting from this node.
303      * Use lookupNamespaceURI(null) to lookup the default namespace
304      *
305      * @param namespaceURI
306      * @return th URI for the namespace
307      * @since DOM Level 3
308      */
309     public String lookupNamespaceURI(String specifiedPrefix) {
310         short type = this.getNodeType();
311         switch (type) {
312         case Node.ELEMENT_NODE : {
313
314                 String namespace = this.getNamespaceURI();
315                 String prefix = this.getPrefix();
316                 if (namespace !=null) {
317                     // REVISIT: is it possible that prefix is empty string?
318                     if (specifiedPrefix== null && prefix==specifiedPrefix) {
319                         // looking for default namespace
320                         return namespace;
321                     } else if (prefix != null && prefix.equals(specifiedPrefix)) {
322                         // non default namespace
323                         return namespace;
324                     }
325                 }
326                 if (this.hasAttributes()) {
327                     NamedNodeMap map = this.getAttributes();
328                     int length = map.getLength();
329                     for (int i=0;i<length;i++) {
330                         Node attr = map.item(i);
331                         String attrPrefix = attr.getPrefix();
332                         String value = attr.getNodeValue();
333                         namespace = attr.getNamespaceURI();
334                         if (namespace !=null && namespace.equals("http://www.w3.org/2000/xmlns/")) {
335                             // at this point we are dealing with DOM Level 2 nodes only
336                             if (specifiedPrefix == null &&
337                                 attr.getNodeName().equals("xmlns")) {
338                                 // default namespace
339                                 return value;
340                             } else if (attrPrefix !=null &&
341                                        attrPrefix.equals("xmlns") &&
342                                        attr.getLocalName().equals(specifiedPrefix)) {
343                  // non default namespace
344                                 return value;
345                             }
346                         }
347                     }
348                 }
349                 /*
350                 NodeImpl ancestor = (NodeImpl)getElementAncestor(this);
351                 if (ancestor != null) {
352                     return ancestor.lookupNamespaceURI(specifiedPrefix);
353                 }
354                 */
355
356                 return null;
357
358
359             }
360 /*
361         case Node.DOCUMENT_NODE : {
362                 return((NodeImpl)((Document)this).getDocumentElement()).lookupNamespaceURI(specifiedPrefix) ;
363             }
364 */
365         case Node.ENTITY_NODE :
366         case Node.NOTATION_NODE:
367         case Node.DOCUMENT_FRAGMENT_NODE:
368         case Node.DOCUMENT_TYPE_NODE:
369             // type is unknown
370             return null;
371         case Node.ATTRIBUTE_NODE:{
372                 if (this.getOwnerElement().getNodeType() == Node.ELEMENT_NODE) {
373                     return getOwnerElement().lookupNamespaceURI(specifiedPrefix);
374
375                 }
376                 return null;
377             }
378         default:{
379            /*
380                 NodeImpl ancestor = (NodeImpl)getElementAncestor(this);
381                 if (ancestor != null) {
382                     return ancestor.lookupNamespaceURI(specifiedPrefix);
383                 }
384              */
385                 return null;
386             }
387
388         }
389     }
390     
391     /**
392      *  DOM Level 3: Experimental
393      *  This method checks if the specified <code>namespaceURI</code> is the
394      *  default namespace or not.
395      *  @param namespaceURI The namespace URI to look for.
396      *  @return  <code>true</code> if the specified <code>namespaceURI</code>
397      *   is the default namespace, <code>false</code> otherwise.
398      * @since DOM Level 3
399      */
400     public boolean isDefaultNamespace(String namespaceURI){
401        /*
402         // REVISIT: remove casts when DOM L3 becomes REC.
403         short type = this.getNodeType();
404         switch (type) {
405         case Node.ELEMENT_NODE: {
406             String namespace = this.getNamespaceURI();
407             String prefix = this.getPrefix();
408
409             // REVISIT: is it possible that prefix is empty string?
410             if (prefix == null || prefix.length() == 0) {
411                 if (namespaceURI == null) {
412                     return (namespace == namespaceURI);
413                 }
414                 return namespaceURI.equals(namespace);
415             }
416             if (this.hasAttributes()) {
417                 ElementImpl elem = (ElementImpl)this;
418                 NodeImpl attr = (NodeImpl)elem.getAttributeNodeNS("http://www.w3.org/2000/xmlns/", "xmlns");
419                 if (attr != null) {
420                     String value = attr.getNodeValue();
421                     if (namespaceURI == null) {
422                         return (namespace == value);
423                     }
424                     return namespaceURI.equals(value);
425                 }
426             }
427
428             NodeImpl ancestor = (NodeImpl)getElementAncestor(this);
429             if (ancestor != null) {
430                 return ancestor.isDefaultNamespace(namespaceURI);
431             }
432             return false;
433         }
434         case Node.DOCUMENT_NODE:{
435                 return((NodeImpl)((Document)this).getDocumentElement()).isDefaultNamespace(namespaceURI);
436             }
437
438         case Node.ENTITY_NODE :
439           case Node.NOTATION_NODE:
440         case Node.DOCUMENT_FRAGMENT_NODE:
441         case Node.DOCUMENT_TYPE_NODE:
442             // type is unknown
443             return false;
444         case Node.ATTRIBUTE_NODE:{
445                 if (this.ownerNode.getNodeType() == Node.ELEMENT_NODE) {
446                     return ownerNode.isDefaultNamespace(namespaceURI);
447
448                 }
449                 return false;
450             }
451         default:{  
452                 NodeImpl ancestor = (NodeImpl)getElementAncestor(this);
453                 if (ancestor != null) {
454                     return ancestor.isDefaultNamespace(namespaceURI);
455                 }
456                 return false;
457             }
458
459         }
460 */
461         return false;
462
463
464     }
465
466     /**
467      *
468      * DOM Level 3 - Experimental:
469      * Look up the prefix associated to the given namespace URI, starting from this node.
470      *
471      * @param namespaceURI
472      * @return the prefix for the namespace
473      */
474     public String lookupPrefix(String namespaceURI){
475
476         // REVISIT: When Namespaces 1.1 comes out this may not be true
477         // Prefix can't be bound to null namespace
478         if (namespaceURI == null) {
479             return null;
480         }
481
482         short type = this.getNodeType();
483
484         switch (type) {
485 /*
486         case Node.ELEMENT_NODE: {
487
488                 String namespace = this.getNamespaceURI(); // to flip out children
489                 return lookupNamespacePrefix(namespaceURI, (ElementImpl)this);
490             }
491
492         case Node.DOCUMENT_NODE:{
493                 return((NodeImpl)((Document)this).getDocumentElement()).lookupPrefix(namespaceURI);
494             }
495 */
496         case Node.ENTITY_NODE :
497         case Node.NOTATION_NODE:
498         case Node.DOCUMENT_FRAGMENT_NODE:
499         case Node.DOCUMENT_TYPE_NODE:
500             // type is unknown
501             return null;
502         case Node.ATTRIBUTE_NODE:{
503                 if (this.getOwnerElement().getNodeType() == Node.ELEMENT_NODE) {
504                     return getOwnerElement().lookupPrefix(namespaceURI);
505
506                 }
507                 return null;
508             }
509         default:{ 
510 /*
511                 NodeImpl ancestor = (NodeImpl)getElementAncestor(this);
512                 if (ancestor != null) {
513                     return ancestor.lookupPrefix(namespaceURI);
514                 }
515 */
516                 return null;
517             }
518          }
519     }
520
521     /**
522      * Returns whether this node is the same node as the given one.
523      * <br>This method provides a way to determine whether two
524      * <code>Node</code> references returned by the implementation reference
525      * the same object. When two <code>Node</code> references are references
526      * to the same object, even if through a proxy, the references may be
527      * used completely interchangably, such that all attributes have the
528      * same values and calling the same DOM method on either reference
529      * always has exactly the same effect.
530      * @param other The node to test against.
531      * @return Returns <code>true</code> if the nodes are the same,
532      *   <code>false</code> otherwise.
533      * @since DOM Level 3
534      */
535     public boolean isSameNode(Node other) {
536         // we do not use any wrapper so the answer is obvious
537         return this == other;
538     }
539
540     /**
541      * This attribute returns the text content of this node and its
542      * descendants. When it is defined to be null, setting it has no effect.
543      * When set, any possible children this node may have are removed and
544      * replaced by a single <code>Text</code> node containing the string
545      * this attribute is set to. On getting, no serialization is performed,
546      * the returned string does not contain any markup. No whitespace
547      * normalization is performed, the returned string does not contain the
548      * element content whitespaces . Similarly, on setting, no parsing is
549      * performed either, the input string is taken as pure textual content.
550      * <br>The string returned is made of the text content of this node
551      * depending on its type, as defined below:
552      * <table border='1'>
553      * <tr>
554      * <th>Node type</th>
555      * <th>Content</th>
556      * </tr>
557      * <tr>
558      * <td valign='top' rowspan='1' colspan='1'>
559      * ELEMENT_NODE, ENTITY_NODE, ENTITY_REFERENCE_NODE,
560      * DOCUMENT_FRAGMENT_NODE</td>
561      * <td valign='top' rowspan='1' colspan='1'>concatenation of the <code>textContent</code>
562      * attribute value of every child node, excluding COMMENT_NODE and
563      * PROCESSING_INSTRUCTION_NODE nodes</td>
564      * </tr>
565      * <tr>
566      * <td valign='top' rowspan='1' colspan='1'>ATTRIBUTE_NODE, TEXT_NODE,
567      * CDATA_SECTION_NODE, COMMENT_NODE, PROCESSING_INSTRUCTION_NODE</td>
568      * <td valign='top' rowspan='1' colspan='1'>
569      * <code>nodeValue</code></td>
570      * </tr>
571      * <tr>
572      * <td valign='top' rowspan='1' colspan='1'>DOCUMENT_NODE, DOCUMENT_TYPE_NODE, NOTATION_NODE</td>
573      * <td valign='top' rowspan='1' colspan='1'>
574      * null</td>
575      * </tr>
576      * </table>
577      * @exception DOMException
578      *   NO_MODIFICATION_ALLOWED_ERR: Raised when the node is readonly.
579      * @exception DOMException
580      *   DOMSTRING_SIZE_ERR: Raised when it would return more characters than
581      *   fit in a <code>DOMString</code> variable on the implementation
582      *   platform.
583      * @since DOM Level 3
584      */
585     public void setTextContent(String textContent)
586         throws DOMException {
587         setNodeValue(textContent);
588     }
589     
590     /**
591      * This attribute returns the text content of this node and its
592      * descendants. When it is defined to be null, setting it has no effect.
593      * When set, any possible children this node may have are removed and
594      * replaced by a single <code>Text</code> node containing the string
595      * this attribute is set to. On getting, no serialization is performed,
596      * the returned string does not contain any markup. No whitespace
597      * normalization is performed, the returned string does not contain the
598      * element content whitespaces . Similarly, on setting, no parsing is
599      * performed either, the input string is taken as pure textual content.
600      * <br>The string returned is made of the text content of this node
601      * depending on its type, as defined below:
602      * <table border='1'>
603      * <tr>
604      * <th>Node type</th>
605      * <th>Content</th>
606      * </tr>
607      * <tr>
608      * <td valign='top' rowspan='1' colspan='1'>
609      * ELEMENT_NODE, ENTITY_NODE, ENTITY_REFERENCE_NODE,
610      * DOCUMENT_FRAGMENT_NODE</td>
611      * <td valign='top' rowspan='1' colspan='1'>concatenation of the <code>textContent</code>
612      * attribute value of every child node, excluding COMMENT_NODE and
613      * PROCESSING_INSTRUCTION_NODE nodes</td>
614      * </tr>
615      * <tr>
616      * <td valign='top' rowspan='1' colspan='1'>ATTRIBUTE_NODE, TEXT_NODE,
617      * CDATA_SECTION_NODE, COMMENT_NODE, PROCESSING_INSTRUCTION_NODE</td>
618      * <td valign='top' rowspan='1' colspan='1'>
619      * <code>nodeValue</code></td>
620      * </tr>
621      * <tr>
622      * <td valign='top' rowspan='1' colspan='1'>DOCUMENT_NODE, DOCUMENT_TYPE_NODE, NOTATION_NODE</td>
623      * <td valign='top' rowspan='1' colspan='1'>
624      * null</td>
625      * </tr>
626      * </table>
627      * @exception DOMException
628      *   NO_MODIFICATION_ALLOWED_ERR: Raised when the node is readonly.
629      * @exception DOMException
630      *   DOMSTRING_SIZE_ERR: Raised when it would return more characters than
631      *   fit in a <code>DOMString</code> variable on the implementation
632      *   platform.
633      * @since DOM Level 3
634      */
635     public String getTextContent() throws DOMException {
636         return getNodeValue();  // overriden in some subclasses
637     }
638
639     /**
640      * Compares a node with this node with regard to their position in the
641      * document.
642      * @param other The node to compare against this node.
643      * @return Returns how the given node is positioned relatively to this
644      *   node.
645      * @since DOM Level 3
646      */
647     public short compareDocumentPosition(Node other) throws DOMException {
648         return 0;
649     }
650
651     /**
652      * The absolute base URI of this node or <code>null</code> if undefined.
653      * This value is computed according to . However, when the
654      * <code>Document</code> supports the feature "HTML" , the base URI is
655      * computed using first the value of the href attribute of the HTML BASE
656      * element if any, and the value of the <code>documentURI</code>
657      * attribute from the <code>Document</code> interface otherwise.
658      * <br> When the node is an <code>Element</code>, a <code>Document</code>
659      * or a a <code>ProcessingInstruction</code>, this attribute represents
660      * the properties [base URI] defined in . When the node is a
661      * <code>Notation</code>, an <code>Entity</code>, or an
662      * <code>EntityReference</code>, this attribute represents the
663      * properties [declaration base URI] in the . How will this be affected
664      * by resolution of relative namespace URIs issue?It's not.Should this
665      * only be on Document, Element, ProcessingInstruction, Entity, and
666      * Notation nodes, according to the infoset? If not, what is it equal to
667      * on other nodes? Null? An empty string? I think it should be the
668      * parent's.No.Should this be read-only and computed or and actual
669      * read-write attribute?Read-only and computed (F2F 19 Jun 2000 and
670      * teleconference 30 May 2001).If the base HTML element is not yet
671      * attached to a document, does the insert change the Document.baseURI?
672      * Yes. (F2F 26 Sep 2001)
673      * @since DOM Level 3
674      */
675     public String getBaseURI() {
676         return null;
677     }
678 }
679