KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > jboss > axis > message > SOAPElementAxisImpl


1 /*
2  * Copyright 2001-2004 The Apache Software Foundation.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */

16 package org.jboss.axis.message;
17
18 // $Id: SOAPElementAxisImpl.java,v 1.1.2.6 2005/06/16 12:23:38 tdiesler Exp $
19

20 import org.jboss.axis.AxisFault;
21 import org.jboss.axis.Constants;
22 import org.jboss.axis.MessageContext;
23 import org.jboss.axis.MessagePart;
24 import org.jboss.axis.encoding.DeserializationContext;
25 import org.jboss.axis.encoding.DeserializationContextImpl;
26 import org.jboss.axis.encoding.Deserializer;
27 import org.jboss.axis.encoding.SerializationContext;
28 import org.jboss.axis.encoding.SerializationContextImpl;
29 import org.jboss.axis.enums.Style;
30 import org.jboss.axis.soap.SOAPConstants;
31 import org.jboss.axis.utils.Mapping;
32 import org.jboss.axis.utils.Messages;
33 import org.jboss.axis.utils.XMLUtils;
34 import org.jboss.logging.Logger;
35 import org.w3c.dom.Attr JavaDoc;
36 import org.w3c.dom.DOMException JavaDoc;
37 import org.w3c.dom.Document JavaDoc;
38 import org.w3c.dom.Element JavaDoc;
39 import org.w3c.dom.NamedNodeMap JavaDoc;
40 import org.w3c.dom.Node JavaDoc;
41 import org.w3c.dom.NodeList JavaDoc;
42 import org.w3c.dom.Text JavaDoc;
43 import org.xml.sax.Attributes JavaDoc;
44 import org.xml.sax.ContentHandler JavaDoc;
45 import org.xml.sax.InputSource JavaDoc;
46 import org.xml.sax.SAXException JavaDoc;
47 import org.xml.sax.helpers.AttributesImpl JavaDoc;
48
49 import javax.xml.namespace.QName JavaDoc;
50 import javax.xml.rpc.JAXRPCException JavaDoc;
51 import javax.xml.rpc.encoding.TypeMapping JavaDoc;
52 import javax.xml.soap.Name JavaDoc;
53 import javax.xml.soap.SOAPElement JavaDoc;
54 import javax.xml.soap.SOAPException JavaDoc;
55 import java.io.PrintWriter JavaDoc;
56 import java.io.Reader JavaDoc;
57 import java.io.StringReader JavaDoc;
58 import java.io.StringWriter JavaDoc;
59 import java.util.ArrayList JavaDoc;
60 import java.util.Collections JavaDoc;
61 import java.util.Iterator JavaDoc;
62 import java.util.List JavaDoc;
63 import java.util.Vector JavaDoc;
64
65 /**
66  * SOAPElementImpl is the base type of nodes of the SOAP message parse tree.
67  */

68 public class SOAPElementAxisImpl extends SOAPElementImpl implements SOAPElement JavaDoc, Cloneable JavaDoc
69 {
70    private static Logger log = Logger.getLogger(SOAPElementAxisImpl.class.getName());
71
72    protected String JavaDoc name;
73    protected String JavaDoc prefix;
74    protected String JavaDoc namespaceURI;
75    protected transient Attributes JavaDoc attributes = NullAttributes.singleton;
76    protected String JavaDoc id;
77    protected String JavaDoc href;
78    protected boolean _isRoot = true;
79    protected SOAPEnvelopeAxisImpl message;
80
81    protected transient DeserializationContext context;
82
83    protected transient QName JavaDoc typeQName;
84
85    protected Vector JavaDoc qNameAttrs;
86
87    // Some message representations - as recorded SAX events...
88
protected transient SAX2EventRecorder recorder;
89    protected int startEventIndex;
90    protected int startContentsIndex;
91    protected int endEventIndex = -1;
92
93    // ...or as DOM
94
protected Element JavaDoc elementRep;
95
96    private SOAPElementAxisImpl parent;
97
98    public ArrayList JavaDoc namespaces;
99
100    /**
101     * Our encoding style, if any
102     */

103    protected String JavaDoc encodingStyle;
104
105    /**
106     * Object value, possibly supplied by subclass
107     */

108    protected Object JavaDoc objectValue;
109
110    // The children of this MessageElement
111
private ChildElementList children = new ChildElementList();
112
113    protected MessagePart soapPart;
114
115    // Set this flag to prevent clients from modifying this element
116
// eg. ws4ee handlers are not allowed to change the name of every element in the response
117
// TDI 15-Jun-2004
118
private boolean immutable;
119
120    /**
121     * No-arg constructor for building messages?
122     */

123    public SOAPElementAxisImpl()
124    {
125       super("unqualified-element");
126    }
127
128    public SOAPElementAxisImpl(String JavaDoc localPart)
129    {
130       super(localPart);
131       namespaceURI = "";
132       name = localPart;
133    }
134
135    public SOAPElementAxisImpl(String JavaDoc namespace, String JavaDoc localPart)
136    {
137       super(localPart, null, namespace);
138       namespaceURI = namespace;
139       name = localPart;
140    }
141
142    public SOAPElementAxisImpl(String JavaDoc localPart, String JavaDoc prefix, String JavaDoc namespace)
143    {
144       super(localPart, prefix, namespace);
145       this.namespaceURI = namespace;
146       this.name = localPart;
147       this.prefix = prefix;
148       if (prefix != null && prefix.length() > 0)
149          addMapping(new Mapping(namespace, prefix));
150    }
151
152    public SOAPElementAxisImpl(Name JavaDoc eltName)
153    {
154       super(eltName);
155       this.namespaceURI = eltName.getURI();
156       this.name = eltName.getLocalName();
157       this.prefix = eltName.getPrefix();
158       if (prefix != null && prefix.length() > 0)
159          addMapping(new Mapping(namespaceURI, prefix));
160    }
161
162    public SOAPElementAxisImpl(String JavaDoc namespace, String JavaDoc localPart, Object JavaDoc value)
163    {
164       super(localPart, "", namespace);
165       this.namespaceURI = namespace;
166       this.name = localPart;
167       objectValue = value;
168    }
169
170    public SOAPElementAxisImpl(QName JavaDoc name, Object JavaDoc value)
171    {
172       super(name.getLocalPart(), name.getPrefix(), name.getNamespaceURI());
173       this.namespaceURI = name.getNamespaceURI();
174       this.prefix = name.getPrefix();
175       this.name = name.getLocalPart();
176       objectValue = value;
177    }
178
179    public SOAPElementAxisImpl(Element JavaDoc elem)
180    {
181       super(elem);
182       namespaceURI = elem.getNamespaceURI();
183       prefix = elem.getPrefix();
184       name = elem.getLocalName();
185       elementRep = elem;
186    }
187
188    public SOAPElementAxisImpl(String JavaDoc namespace, String JavaDoc localPart, String JavaDoc prefix, Attributes JavaDoc attributes, DeserializationContext context)
189            throws AxisFault
190    {
191
192       super(localPart, prefix, namespace);
193       this.namespaceURI = namespace;
194       this.name = localPart;
195       this.prefix = prefix;
196
197       if (log.isDebugEnabled())
198       {
199          log.debug(Messages.getMessage("newElem00", super.toString(),
200                  "{" + prefix + "}" + localPart));
201          for (int i = 0; attributes != null && i < attributes.getLength(); i++)
202          {
203             log.debug(" " + attributes.getQName(i) + " = '" + attributes.getValue(i) + "'");
204          }
205       }
206
207       this.context = context;
208       this.startEventIndex = context.getStartOfMappingsPos();
209
210       setNSMappings(context.getCurrentNSMappings());
211
212       this.recorder = context.getRecorder();
213
214       if (attributes != null && attributes.getLength() > 0)
215       {
216          this.attributes = attributes;
217
218          typeQName = context.getTypeFromAttributes(namespace,
219                  localPart,
220                  attributes);
221
222          String JavaDoc rootVal = attributes.getValue(Constants.URI_DEFAULT_SOAP_ENC, Constants.ATTR_ROOT);
223          if (rootVal != null)
224             _isRoot = rootVal.equals("1");
225
226          id = attributes.getValue(Constants.ATTR_ID);
227          // Register this ID with the context.....
228
if (id != null)
229          {
230             context.registerElementByID(id, this);
231             if (recorder == null)
232             {
233                recorder = new SAX2EventRecorder();
234                context.setRecorder(recorder);
235             }
236          }
237
238          // Set the encoding style to the attribute value. If null,
239
// we just automatically use our parent's (see getEncodingStyle)
240
MessageContext mc = context.getMessageContext();
241          SOAPConstants sc = (mc != null) ?
242                  mc.getSOAPConstants() :
243                  SOAPConstants.SOAP11_CONSTANTS;
244
245          href = attributes.getValue(sc.getAttrHref());
246
247          // If there's an arrayType attribute, we can pretty well guess that we're an Array???
248
if (attributes.getValue(Constants.URI_DEFAULT_SOAP_ENC, Constants.ATTR_ARRAY_TYPE) != null)
249             typeQName = Constants.SOAP_ARRAY;
250
251
252          encodingStyle =
253                  attributes.getValue(sc.getEncodingURI(),
254                          Constants.ATTR_ENCODING_STYLE);
255
256          // if no-encoding style was defined, we don't define as well
257
if (Constants.URI_SOAP12_NOENC.equals(encodingStyle))
258             encodingStyle = null;
259
260          // If we have an encoding style, and are not a MESSAGE style
261
// operation (in other words - we're going to do some data
262
// binding), AND we're SOAP 1.2, check the encoding style against
263
// the ones we've got type mappings registered for. If it isn't
264
// registered, throw a DataEncodingUnknown fault as per the
265
// SOAP 1.2 spec.
266
if (encodingStyle != null &&
267                  sc.equals(SOAPConstants.SOAP12_CONSTANTS) &&
268                  (mc.getOperationStyle() != Style.MESSAGE))
269          {
270             TypeMapping JavaDoc tm = mc.getTypeMappingRegistry().
271                     getTypeMapping(encodingStyle);
272             if (tm == null ||
273                     (tm.equals(mc.getTypeMappingRegistry().
274                     getDefaultTypeMapping())))
275             {
276                AxisFault badEncodingFault = new AxisFault(Constants.FAULT_SOAP12_DATAENCODINGUNKNOWN,
277                        "bad encoding style", null, null);
278                throw badEncodingFault;
279             }
280          }
281
282       }
283    }
284
285    /**
286     * !!! TODO : Make sure this handles multiple targets
287     */

288    Deserializer fixupDeserializer;
289
290    public void setFixupDeserializer(Deserializer dser)
291    {
292       // !!! Merge targets here if already set?
293
fixupDeserializer = dser;
294    }
295
296    public Deserializer getFixupDeserializer()
297    {
298       return fixupDeserializer;
299    }
300
301    public void setEndIndex(int endIndex)
302    {
303       endEventIndex = endIndex;
304       //context.setRecorder(null);
305
}
306
307    /**
308     * For ws4ee we should explicitly turn replay of the SAX events of.
309     * This is a bad performance hit, but better than a inconsistent soap tree
310     * [tdi 05-June-2004]
311     */

312    private boolean isDirty;
313
314    public boolean isDirty()
315    {
316       return isDirty;
317       //return true;
318
}
319
320    public void setDirty(boolean dirty)
321    {
322       isDirty = dirty;
323    }
324
325    public boolean isRoot()
326    {
327       return _isRoot;
328    }
329
330    public String JavaDoc getID()
331    {
332       return id;
333    }
334
335    public String JavaDoc getHref()
336    {
337       return href;
338    }
339
340    public Attributes JavaDoc getAttributesEx()
341    {
342       return attributes;
343    }
344
345    public Node JavaDoc getFirstChild()
346    {
347       if (children != null && !children.isEmpty())
348       {
349          return (Node JavaDoc)children.get(0);
350       }
351       else
352       {
353          return null;
354       }
355    }
356
357    public Node JavaDoc getLastChild()
358    {
359       List JavaDoc children = getChildren();
360       if (children != null)
361          return (Node JavaDoc)children.get(children.size() - 1);
362       else
363          return null;
364    }
365
366    public Node JavaDoc getNextSibling()
367    {
368       SOAPElement JavaDoc parent = getParentElement();
369       if (parent == null)
370       {
371          return null;
372       }
373       Iterator JavaDoc iter = parent.getChildElements();
374       Node JavaDoc nextSibling = null;
375       while (iter.hasNext())
376       {
377          if (iter.next().equals(this))
378          {
379             if (iter.hasNext())
380             {
381                return (Node JavaDoc)iter.next();
382             }
383             else
384             {
385                return null;
386             }
387          }
388       }
389       return nextSibling; // should be null.
390
}
391
392    public Node JavaDoc getParentNode()
393    {
394       return parent;
395    }
396
397    public Node JavaDoc getPreviousSibling()
398    {
399       SOAPElement JavaDoc parent = getParentElement();
400       Iterator JavaDoc iter = parent.getChildElements();
401       Node JavaDoc previousSibling = null;
402       while (iter.hasNext())
403       {
404          if (iter.next().equals(this))
405          {
406             return previousSibling;
407          }
408       }
409       return previousSibling; // should be null.
410
}
411
412    public Node JavaDoc cloneNode(boolean deep)
413    {
414       try
415       {
416          SOAPElementAxisImpl clonedSelf = (SOAPElementAxisImpl)this.clonning();
417
418          if (deep == true)
419          {
420             if (children != null)
421             {
422                for (int i = 0; i < children.size(); i++)
423                {
424                   SOAPElementAxisImpl child = (SOAPElementAxisImpl)children.get(i);
425                   if (child != null)
426                   { // why child can be null?
427
SOAPElementAxisImpl clonedChild = (SOAPElementAxisImpl)child.cloneNode(deep); // deep == true
428
clonedChild.setParent(clonedSelf);
429                      clonedChild.setOwnerDocument(soapPart);
430                   }
431                }
432             }
433          }
434          return clonedSelf;
435       }
436       catch (Exception JavaDoc e)
437       {
438          return null;
439       }
440    }
441
442    /**
443     * protected clone method (not public)
444     * <p/>
445     * copied status
446     * -------------------
447     * protected String name ; Y
448     * protected String prefix ; Y
449     * protected String namespaceURI ; Y
450     * protected transient Attributes attributes Y
451     * protected String id; Y?
452     * protected String href; Y?
453     * protected boolean _isRoot = true; Y?
454     * protected SOAPEnvelope message = null; N?
455     * protected boolean _isDirty = false; Y?
456     * protected transient DeserializationContext context; Y?
457     * protected transient QName typeQName = null; Y?
458     * protected Vector qNameAttrs = null; Y?
459     * protected transient SAX2EventRecorder recorder = null; N?
460     * protected int startEventIndex = 0; N?
461     * protected int startContentsIndex = 0; N?
462     * protected int endEventIndex = -1; N?
463     * protected Element elementRep = null; N?
464     * protected MessageElement parent = null; N
465     * public ArrayList namespaces = null; Y
466     * protected String encodingStyle = null; N?
467     * private Object objectValue = null; N?
468     *
469     * @return
470     * @throws CloneNotSupportedException
471     */

472    protected Object JavaDoc clonning() throws CloneNotSupportedException JavaDoc
473    {
474       try
475       {
476          SOAPElementAxisImpl clonedME = null;
477          clonedME = (SOAPElementAxisImpl)this.clone();
478
479          clonedME.setName(name);
480          clonedME.setNamespaceURI(namespaceURI);
481          clonedME.setPrefix(prefix);
482
483          // new AttributesImpl will copy all data not set referencing only
484
clonedME.setAllAttributes(new AttributesImpl JavaDoc(attributes));
485          // clonedME.addNamespaceDeclaration((namespaces.clone()); // cannot do this. since we cannot access the namepace arraylist
486

487          clonedME.namespaces = new ArrayList JavaDoc();
488          if (namespaces != null)
489          {
490             for (int i = 0; i < namespaces.size(); i++)
491             {
492                // jeus.util.Logger.directLog( " Debug : namspace.size() = " + namespaces.size());
493
Mapping namespace = (Mapping)namespaces.get(i);
494                clonedME.addNamespaceDeclaration(namespace.getPrefix(), namespace.getNamespaceURI()); // why exception here!!
495
}
496          }
497          // clear reference to old children
498
clonedME.detachAllChildren();
499
500          // clear parents relationship to old parent
501
clonedME.setParent(null);
502          // clonedME.setObjectValue(objectValue); // how to copy this???
503
clonedME.setDirty(isDirty());
504          if (encodingStyle != null)
505          {
506             clonedME.setEncodingStyle(new String JavaDoc(encodingStyle));
507          }
508          clonedME.setRecorder(recorder);
509          return clonedME;
510       }
511       catch (Exception JavaDoc ex)
512       {
513          return null;
514       }
515    }
516
517    // called in MESerialaizationContext
518
public void setAllAttributes(Attributes JavaDoc attrs)
519    {
520       attributes = attrs;
521    }
522
523    public void detachAllChildren()
524    {
525       children.clear();
526    }
527
528    public NodeList JavaDoc getChildNodes()
529    {
530       NodeListImpl nodeList = new NodeListImpl();
531       for (int i = 0; i < children.size(); i++)
532       {
533          Node JavaDoc node = (Node JavaDoc)children.get(i);
534          nodeList.addNode(node);
535       }
536       return nodeList;
537    }
538
539    public boolean isSupported(String JavaDoc feature, String JavaDoc version)
540    {
541       return false; //TODO: Fix this for SAAJ 1.2 Implementation
542
}
543
544    public Node JavaDoc appendChild(Node JavaDoc newChild) throws DOMException JavaDoc
545    {
546       super.appendChild(newChild);
547       children.add(newChild);
548       return newChild;
549    }
550
551    /**
552     * Note that this method will log a error and no-op if there is
553     * a value (set using setObjectValue) in the MessageElement.
554     */

555    public void addChild(SOAPElementAxisImpl el) throws SOAPException JavaDoc
556    {
557
558       assertImmutable();
559
560       el.parent = this;
561       children.add(el);
562    }
563
564    /**
565     * Throws an JAXRPCException if an attempt is made to modifty this immutable element while
566     * RPCProcessing is going on.
567     */

568    private void assertImmutable()
569    {
570       SOAPEnvelopeAxisImpl env = getSOAPEnvelope();
571       if (env != null && env.isProcessingRPCInvocation() && immutable)
572          throw new JAXRPCException JavaDoc("Cannot modify an immutable element");
573    }
574
575    public Node JavaDoc removeChild(Node JavaDoc oldChild) throws DOMException JavaDoc
576    {
577
578       int position = children.indexOf(oldChild);
579       if (position < 0)
580          throw new DOMException JavaDoc(DOMException.NOT_FOUND_ERR, "MessageElement Not found");
581
582       // Remove all occurrences in case it has been added multiple times.
583
Iterator JavaDoc it = children.iterator();
584       while (it.hasNext())
585       {
586          Node JavaDoc node = (Node JavaDoc)it.next();
587          if (node.equals(oldChild))
588          {
589             log.debug("Remove child node: " + node.getNodeName());
590             it.remove();
591          }
592       }
593
594       setDirty(true);
595       return oldChild;
596    }
597
598    public Node JavaDoc insertBefore(Node JavaDoc newChild, Node JavaDoc refChild) throws DOMException JavaDoc
599    {
600       int position = children.indexOf(refChild);
601       if (position < 0) position = 0;
602       children.add(position, newChild);
603       setDirty(true);
604       return newChild;
605    }
606
607    public Node JavaDoc replaceChild(Node JavaDoc newChild, Node JavaDoc oldChild) throws DOMException JavaDoc
608    {
609       int position = children.indexOf(oldChild);
610       if (position < 0)
611          throw new DOMException JavaDoc(DOMException.NOT_FOUND_ERR, "MessageElement Not found");
612
613       children.remove(position);
614       children.add(position, newChild);
615       setDirty(true);
616       return oldChild;
617    }
618
619    /**
620     * Obtain an Attributes collection consisting of all attributes
621     * for this MessageElement, including namespace declarations.
622     *
623     * @return Attributes collection
624     */

625    public Attributes JavaDoc getCompleteAttributes()
626    {
627       if (namespaces == null)
628          return attributes;
629
630       AttributesImpl JavaDoc attrs = null;
631       if (attributes == NullAttributes.singleton)
632          attrs = new AttributesImpl JavaDoc();
633       else
634          attrs = new AttributesImpl JavaDoc(attributes);
635
636       for (Iterator JavaDoc iterator = namespaces.iterator(); iterator.hasNext();)
637       {
638          Mapping mapping = (Mapping)iterator.next();
639          String JavaDoc prefix = mapping.getPrefix();
640          String JavaDoc nsURI = mapping.getNamespaceURI();
641          attrs.addAttribute(Constants.NS_URI_XMLNS, prefix,
642                  "xmlns:" + prefix, nsURI, "CDATA");
643       }
644       return attrs;
645    }
646
647    public String JavaDoc getName()
648    {
649       return (name);
650    }
651
652    public void setName(String JavaDoc name)
653    {
654       this.name = name;
655    }
656
657    public QName JavaDoc getQName()
658    {
659       return new QName JavaDoc(namespaceURI, name);
660    }
661
662    public void setQName(QName JavaDoc qName)
663    {
664       this.name = qName.getLocalPart();
665       this.namespaceURI = qName.getNamespaceURI();
666    }
667
668    public String JavaDoc getPrefix()
669    {
670       return (prefix);
671    }
672
673    public void setPrefix(String JavaDoc prefix)
674    {
675       this.prefix = prefix;
676    }
677
678    public Document JavaDoc getOwnerDocument()
679    {
680       return soapPart;
681    }
682
683    public NamedNodeMap JavaDoc getAttributes()
684    {
685       // make first it is editable.
686
makeAttributesEditable();
687       return convertAttrSAXtoDOM();
688    }
689
690    /**
691     * [todo] In order to be compatible SAAJ Spec(ver 1.2),
692     * The internal representation of Attributes cannot help being changed
693     * It is because Attribute is not immutible Type, so if we keep out value and
694     * just return it in another form, the application may chnae it, which we cannot
695     * detect without some kind back track method (call back notifying the chnage.)
696     * I am not sure which approach is better.
697     */

698
699    private NamedNodeMap JavaDoc convertAttrSAXtoDOM()
700    {
701       try
702       {
703          org.w3c.dom.Document JavaDoc doc = org.jboss.axis.utils.XMLUtils.newDocument();
704
705          AttributesImpl JavaDoc saxAttrs = (AttributesImpl JavaDoc)attributes;
706          NamedNodeMap JavaDoc domAttributes = new NamedNodeMapImpl();
707          for (int i = 0; i < saxAttrs.getLength(); i++)
708          {
709             String JavaDoc uri = saxAttrs.getURI(i);
710             String JavaDoc qname = saxAttrs.getQName(i);
711             String JavaDoc value = saxAttrs.getValue(i);
712
713             if (uri != null && uri.trim().length() > 0)
714             {
715                // filterring out the tricky method to differentiate the null namespace
716
// -ware case
717
if (uri.equals("intentionalNullURI"))
718                {
719                   uri = null;
720                }
721                
722                if (uri.equals(Constants.NS_URI_XMLNS) && qname.startsWith("xmlns:") == false)
723                   qname = "xmlns:" + qname;
724
725                if (uri.equals(Constants.URI_DEFAULT_SCHEMA_XSI) && qname.startsWith("xsi:") == false)
726                   qname = "xsi:" + qname;
727
728                Attr JavaDoc attr = doc.createAttributeNS(uri, qname);
729                attr.setValue(value);
730                domAttributes.setNamedItemNS(attr);
731             }
732             else
733             {
734
735                Attr JavaDoc attr = doc.createAttribute(qname);
736                attr.setValue(value);
737                domAttributes.setNamedItem(attr);
738             }
739          }
740          return domAttributes;
741
742       }
743       catch (Exception JavaDoc ex)
744       {
745          log.error("Cannot convert SAX to DOM attributes", ex);
746          return null;
747       }
748
749    }
750
751    public short getNodeType()
752    {
753       if (false)
754       {
755          return DOCUMENT_FRAGMENT_NODE;
756       }
757       else if (false)
758       {
759          return Node.ELEMENT_NODE;
760       }
761       else
762       { // most often but we cannot give prioeity now
763
return Node.ELEMENT_NODE;
764       }
765    }
766
767    public void normalize()
768    {
769       //TODO: Fix this for SAAJ 1.2 Implementation
770
}
771
772    public boolean hasAttributes()
773    {
774       return attributes.getLength() > 0;
775    }
776
777    public boolean hasChildNodes()
778    {
779       return children.size() > 0;
780    }
781
782    public String JavaDoc getLocalName()
783    {
784       return name;
785    }
786
787    public String JavaDoc getNamespaceURI()
788    {
789       return (namespaceURI);
790    }
791
792    public String JavaDoc getNodeValue() throws DOMException JavaDoc
793    {
794       throw new DOMException JavaDoc(DOMException.NO_DATA_ALLOWED_ERR,
795               "Cannot use TextNode.get in " + this);
796    }
797
798    public void setNamespaceURI(String JavaDoc nsURI)
799    {
800       namespaceURI = nsURI;
801    }
802
803    public QName JavaDoc getType()
804    {
805       // Try to get the type from our target if we're a reference...
806
if (typeQName == null && href != null && context != null)
807       {
808          SOAPElementAxisImpl referent = context.getElementByID(href);
809          if (referent != null)
810          {
811             typeQName = referent.getType();
812          }
813       }
814       return typeQName;
815    }
816
817    public void setType(QName JavaDoc qname)
818    {
819       typeQName = qname;
820    }
821
822    public SAX2EventRecorder getRecorder()
823    {
824       return recorder;
825    }
826
827    public void setRecorder(SAX2EventRecorder rec)
828    {
829       recorder = rec;
830    }
831
832    /**
833     * Get the encoding style. If ours is null, walk up the hierarchy
834     * and use our parent's. Default if we're the root is "".
835     *
836     * @return the currently in-scope encoding style
837     */

838    public String JavaDoc getEncodingStyle()
839    {
840       if (encodingStyle == null)
841       {
842          if (parent == null)
843             return "";
844          return parent.getEncodingStyle();
845       }
846       return encodingStyle;
847    }
848
849    public void removeContents()
850    {
851       // unlink
852
if (children != null)
853       {
854          for (int i = 0; i < children.size(); i++)
855          {
856             try
857             {
858                ((SOAPElementAxisImpl)children.get(i)).setParent(null);
859             }
860             catch (Exception JavaDoc e)
861             {
862             }
863          }
864          // empty the collection
865
children.clear();
866       }
867    }
868
869    public Iterator JavaDoc getVisibleNamespacePrefixes()
870    {
871       Vector JavaDoc prefixes = new Vector JavaDoc();
872
873       // Add all parents namespace definitions
874
if (parent != null)
875       {
876          Iterator JavaDoc parentsPrefixes = parent.getVisibleNamespacePrefixes();
877          if (parentsPrefixes != null)
878          {
879             while (parentsPrefixes.hasNext())
880             {
881                prefixes.add(parentsPrefixes.next());
882             }
883          }
884       }
885       Iterator JavaDoc mine = getNamespacePrefixes();
886       if (mine != null)
887       {
888          while (mine.hasNext())
889          {
890             prefixes.add(mine.next());
891          }
892       }
893       return prefixes.iterator();
894    }
895
896    /**
897     * Sets the encoding style for this <CODE>SOAPElement</CODE>
898     * object to one specified. The semantics of a null value,
899     * as above in getEncodingStyle() are to just use the parent's value,
900     * but null here means set to "".
901     *
902     * @param encodingStyle a <CODE>String</CODE>
903     * giving the encoding style
904     * @throws java.lang.IllegalArgumentException
905     * if
906     * there was a problem in the encoding style being set.
907     * @see #getEncodingStyle() getEncodingStyle()
908     */

909    public void setEncodingStyle(String JavaDoc encodingStyle) throws SOAPException JavaDoc
910    {
911       if (encodingStyle == null)
912       {
913          encodingStyle = "";
914       }
915
916       this.encodingStyle = encodingStyle;
917
918       // Add the encoding style as an attribute
919
// According to the BP-1.0/4.1.7 we should not do that but the s1as interop tests fail otherwise
920
// [TDI 11-Sep-2004]
921
if (encodingStyle.equals("") == false)
922       {
923          SOAPConstants soapConstants = SOAPConstants.SOAP11_CONSTANTS;
924          addAttribute(getPrefix(soapConstants.getEnvelopeURI()), soapConstants.getEnvelopeURI(), Constants.ATTR_ENCODING_STYLE, encodingStyle);
925       }
926    }
927
928    private SOAPElementAxisImpl getParent()
929    {
930       return parent;
931    }
932
933    private void setParent(SOAPElementAxisImpl parent) throws SOAPException JavaDoc
934    {
935       this.parent = parent;
936       if (parent != null && !parent.children.contains(this))
937       {
938          parent.addChild(this);
939       }
940    }
941
942    /**
943     * Remove all child elements
944     */

945    void removeChildren()
946    {
947       while (children.isEmpty() == false)
948       {
949          removeChild((SOAPElementAxisImpl)children.get(0));
950       }
951    }
952
953    public void setContentsIndex(int index)
954    {
955       startContentsIndex = index;
956    }
957
958    public void setNSMappings(ArrayList JavaDoc namespaces)
959    {
960       this.namespaces = namespaces;
961    }
962
963    public String JavaDoc getPrefix(String JavaDoc namespaceURI)
964    {
965       if ((namespaceURI == null) || (namespaceURI.equals("")))
966          return null;
967
968       if (href != null && getRealElement() != null)
969       {
970          return getRealElement().getPrefix(namespaceURI);
971       }
972
973       for (int i = 0; namespaces != null && i < namespaces.size(); i++)
974       {
975          Mapping map = (Mapping)namespaces.get(i);
976          if (map.getNamespaceURI().equals(namespaceURI))
977             return map.getPrefix();
978       }
979
980       if (parent != null)
981          return parent.getPrefix(namespaceURI);
982
983       return null;
984    }
985
986    public String JavaDoc getNamespaceURI(String JavaDoc prefix)
987    {
988       if (prefix == null)
989          prefix = "";
990
991       if (href != null && getRealElement() != null)
992       {
993          return getRealElement().getNamespaceURI(prefix);
994       }
995
996       for (int i = 0; namespaces != null && i < namespaces.size(); i++)
997       {
998          Mapping map = (Mapping)namespaces.get(i);
999          if (map.getPrefix().equals(prefix))
1000         {
1001            return map.getNamespaceURI();
1002         }
1003      }
1004
1005      if (parent != null)
1006         return parent.getNamespaceURI(prefix);
1007
1008      if (log.isDebugEnabled())
1009      {
1010         log.debug(Messages.getMessage("noPrefix00", "" + this, prefix));
1011      }
1012
1013      return null;
1014   }
1015
1016   /**
1017    * Returns value of the node as an object of registered type.
1018    *
1019    * @return Object of proper type, or null if no mapping could be found.
1020    */

1021   public Object JavaDoc getObjectValue()
1022   {
1023      Object JavaDoc obj = null;
1024      try
1025      {
1026         obj = getObjectValue(null);
1027      }
1028      catch (Exception JavaDoc e)
1029      {
1030         log.debug("getValue()", e);
1031      }
1032      return obj;
1033   }
1034
1035   /**
1036    * Returns value of the node as an object of registered type.
1037    *
1038    * @param cls Class that contains top level deserializer metadata
1039    * @return Object of proper type, or null if no mapping could be found.
1040    */

1041   public Object JavaDoc getObjectValue(Class JavaDoc cls) throws Exception JavaDoc
1042   {
1043      if (objectValue == null)
1044      {
1045         objectValue = getValueAsType(getType(), cls);
1046      }
1047      return objectValue;
1048   }
1049
1050   /**
1051    * Sets value of this node to an Object.
1052    * A serializer needs to be registered for this object class for proper
1053    * operation.
1054    * <p/>
1055    * Note that this method will log an error and no-op if there are
1056    * any children in the MessageElement or if the MessageElement was
1057    * constructed from XML.
1058    *
1059    * @param newValue node's value or null.
1060    */

1061   public void setObjectValue(Object JavaDoc newValue) throws SOAPException JavaDoc
1062   {
1063      if (children != null && !children.isEmpty())
1064      {
1065         SOAPException JavaDoc exc = new SOAPException JavaDoc(Messages.getMessage("childPresent"));
1066         log.error(Messages.getMessage("childPresent"), exc);
1067         throw exc;
1068      }
1069      if (elementRep != null)
1070      {
1071         SOAPException JavaDoc exc = new SOAPException JavaDoc(Messages.getMessage("xmlPresent"));
1072         log.error(Messages.getMessage("xmlPresent"), exc);
1073         throw exc;
1074      }
1075      this.objectValue = newValue;
1076   }
1077
1078   public Object JavaDoc getValueAsType(QName JavaDoc type) throws Exception JavaDoc
1079   {
1080      return getValueAsType(type, null);
1081   }
1082
1083   public Object JavaDoc getValueAsType(QName JavaDoc type, Class JavaDoc cls) throws Exception JavaDoc
1084   {
1085      if (context == null)
1086         throw new Exception JavaDoc(Messages.getMessage("noContext00"));
1087
1088      Deserializer dser = null;
1089      if (cls == null)
1090      {
1091         dser = context.getDeserializerForType(type);
1092      }
1093      else
1094      {
1095         // TODO Port from saaj1.2
1096
// throw new IllegalArgumentException("MessageElement.getValueAsType(): JBoss does not support not null cls now.");
1097
dser = context.getDeserializerForClass(cls);
1098      }
1099      if (dser == null)
1100         throw new Exception JavaDoc(Messages.getMessage("noDeser00", "" + type));
1101
1102      boolean oldVal = context.isDoneParsing();
1103      ((DeserializationContextImpl)context).deserializing(true);
1104      context.pushElementHandler(new EnvelopeHandler((SOAPHandler)dser));
1105
1106      publishToHandler((org.xml.sax.ContentHandler JavaDoc)context);
1107
1108      ((DeserializationContextImpl)context).deserializing(oldVal);
1109
1110      return dser.getValue();
1111   }
1112
1113   protected static class QNameAttr
1114   {
1115      QName JavaDoc name;
1116      QName JavaDoc value;
1117   }
1118
1119   public void addAttribute(String JavaDoc namespace, String JavaDoc localName,
1120                            QName JavaDoc value)
1121   {
1122      if (qNameAttrs == null)
1123         qNameAttrs = new Vector JavaDoc();
1124
1125      QNameAttr attr = new QNameAttr();
1126      attr.name = new QName JavaDoc(namespace, localName);
1127      attr.value = value;
1128
1129      qNameAttrs.addElement(attr);
1130      // !!! Add attribute to attributes!
1131
}
1132
1133   protected AttributesImpl JavaDoc makeAttributesEditable()
1134   {
1135      if (attributes == null || attributes instanceof NullAttributes)
1136      {
1137         attributes = new AttributesImpl JavaDoc();
1138      }
1139      else if (!(attributes instanceof AttributesImpl JavaDoc))
1140      {
1141         attributes = new AttributesImpl JavaDoc(attributes);
1142      }
1143
1144      return (AttributesImpl JavaDoc)attributes;
1145   }
1146
1147   public void addAttribute(String JavaDoc namespace, String JavaDoc localName, String JavaDoc value)
1148   {
1149      AttributesImpl JavaDoc attrs = makeAttributesEditable();
1150      attrs.addAttribute(namespace, localName, localName, "CDATA", value);
1151   }
1152
1153   public void addAttribute(String JavaDoc prefix, String JavaDoc namespace, String JavaDoc localName, String JavaDoc value)
1154   {
1155      AttributesImpl JavaDoc attrs = makeAttributesEditable();
1156      String JavaDoc attrName = localName;
1157      if (prefix != null && prefix.length() > 0)
1158      {
1159         attrName = prefix + ":" + localName;
1160      }
1161      attrs.addAttribute(namespace, localName, attrName, "CDATA", value);
1162   }
1163
1164   /**
1165    * Set an attribute, adding the attribute if it isn't already present
1166    * in this element, and changing the value if it is. Passing null as the
1167    * value will cause any pre-existing attribute by this name to go away.
1168    */

1169   public void setAttribute(String JavaDoc namespace, String JavaDoc localName, String JavaDoc value)
1170   {
1171      AttributesImpl JavaDoc attrs = makeAttributesEditable();
1172      int idx = attrs.getIndex(namespace, localName);
1173      if (idx > -1)
1174      {
1175         // Got it, so replace it's value.
1176
if (value != null)
1177         {
1178            attrs.setValue(idx, value);
1179         }
1180         else
1181         {
1182            attrs.removeAttribute(idx);
1183         }
1184         return;
1185      }
1186
1187      addAttribute(namespace, localName, value);
1188   }
1189
1190   public String JavaDoc getAttributeValue(String JavaDoc localName)
1191   {
1192      if (attributes == null)
1193      {
1194         return null;
1195      }
1196      return attributes.getValue(localName);
1197   }
1198
1199   public void setEnvelope(SOAPEnvelopeAxisImpl env)
1200   {
1201      env.setDirty(true);
1202      message = env;
1203   }
1204
1205   public SOAPEnvelopeAxisImpl getEnvelope()
1206   {
1207      return message;
1208   }
1209
1210   public SOAPElementAxisImpl getRealElement()
1211   {
1212      if (href == null)
1213         return this;
1214
1215      Object JavaDoc obj = context.getObjectByRef(href);
1216      if (obj == null)
1217         return null;
1218
1219      if (!(obj instanceof SOAPElementAxisImpl))
1220         return null;
1221
1222      return (SOAPElementAxisImpl)obj;
1223   }
1224
1225   public Element JavaDoc getAsDOM()
1226   {
1227      try
1228      {
1229         return getAsDocument().getDocumentElement();
1230      }
1231      catch (Exception JavaDoc e)
1232      {
1233         log.error("Cannot get element as DOM: " + getElementName(), e);
1234         return null;
1235      }
1236   }
1237
1238   public Document JavaDoc getAsDocument()
1239   {
1240
1241      Document JavaDoc doc = null;
1242      try
1243      {
1244         String JavaDoc elementString = getAsString();
1245         Reader JavaDoc reader = new StringReader JavaDoc(elementString);
1246         doc = XMLUtils.newDocument(new InputSource JavaDoc(reader));
1247      }
1248      catch (Exception JavaDoc e)
1249      {
1250         log.error("Cannot serialize element", e);
1251         throw new IllegalStateException JavaDoc(e.toString());
1252      }
1253
1254      return doc;
1255   }
1256
1257   public String JavaDoc getAsString()
1258   {
1259      SerializationContext serializeContext = null;
1260      StringWriter JavaDoc writer = new StringWriter JavaDoc();
1261
1262      try
1263      {
1264         MessageContext msgContext;
1265         if (context != null)
1266         {
1267            msgContext = context.getMessageContext();
1268         }
1269         else
1270         {
1271            msgContext = MessageContext.getCurrentContext();
1272         }
1273         serializeContext = new SerializationContextImpl(writer, msgContext);
1274         serializeContext.setSendDecl(false);
1275         output(serializeContext);
1276         writer.close();
1277      }
1278      catch (Exception JavaDoc e)
1279      {
1280         log.error("Cannot serialize element", e);
1281         throw new IllegalStateException JavaDoc(e.toString());
1282      }
1283
1284      return writer.getBuffer().toString();
1285   }
1286
1287   /**
1288    * Get a string representation from the internal structure.
1289    * This should not go on the wire, but is for debugging only.
1290    */

1291   public String JavaDoc getAsStringFromInternal()
1292   {
1293      try
1294      {
1295         StringWriter JavaDoc sw = new StringWriter JavaDoc(1024);
1296         printFromInternal(new PrintWriter JavaDoc(sw), this);
1297         return sw.toString();
1298      }
1299      catch (Exception JavaDoc e)
1300      {
1301         log.error("Cannot parser internal element representation", e);
1302         return null;
1303      }
1304   }
1305
1306   /**
1307    * Print the given element from the internal representation
1308    * This should not go on the wire, but is for debugging only.
1309    */

1310   public static void printFromInternal(PrintWriter JavaDoc out, NodeImpl node) throws Exception JavaDoc
1311   {
1312      if (node instanceof Text JavaDoc)
1313      {
1314         out.print(node.getNodeValue());
1315         return;
1316      }
1317
1318      SOAPElementAxisImpl el = (SOAPElementAxisImpl)node;
1319      if (el.getChildren().size() == 0)
1320      {
1321         printStartElement(out, el);
1322         printEndElement(out, el);
1323         return;
1324      }
1325      else if (el.getChildren().size() == 1 && el.getFirstChild() instanceof Text JavaDoc)
1326      {
1327         printStartElement(out, el);
1328         out.print(el.getValue());
1329         printEndElement(out, el);
1330         return;
1331      }
1332      else
1333      {
1334         printStartElement(out, el);
1335
1336         Iterator JavaDoc it = el.getChildren().iterator();
1337         while (it.hasNext())
1338         {
1339            NodeImpl child = (NodeImpl)it.next();
1340            printFromInternal(out, child);
1341         }
1342         printEndElement(out, el);
1343      }
1344   }
1345
1346   private static void printStartElement(PrintWriter JavaDoc out, SOAPElementAxisImpl el)
1347   {
1348      if (el.prefix != null && el.prefix.length() > 0)
1349         out.print("<" + el.prefix + ":" + el.name);
1350      else
1351         out.print("<" + el.name);
1352
1353      for (int i = 0; i < el.attributes.getLength(); i++)
1354      {
1355         out.print(" " + el.attributes.getQName(i) + "='" + el.attributes.getValue(i) + "'");
1356      }
1357
1358      if (el.namespaces != null)
1359      {
1360         for (Iterator JavaDoc i = el.namespaces.iterator(); i.hasNext();)
1361         {
1362            Mapping mapping = (Mapping)i.next();
1363            out.print(" xmlns:" + mapping.getPrefix() + "='" + mapping.getNamespaceURI() + "'");
1364         }
1365      }
1366
1367      if (el.getChildren().size() > 0)
1368         out.print(">");
1369      else
1370         out.print("/>");
1371   }
1372
1373   private static void printEndElement(PrintWriter JavaDoc out, SOAPElementAxisImpl el)
1374   {
1375      if (el.getChildren().size() > 0)
1376      {
1377         if (el.prefix != null && el.prefix.length() > 0)
1378            out.print("</" + el.prefix + ":" + el.name + ">");
1379         else
1380            out.print("</" + el.name + ">");
1381      }
1382   }
1383
1384   public void publishToHandler(ContentHandler JavaDoc handler) throws SAXException JavaDoc
1385   {
1386      if (recorder == null)
1387         throw new SAXException JavaDoc(Messages.getMessage("noRecorder00"));
1388
1389      recorder.replay(startEventIndex, endEventIndex, handler);
1390   }
1391
1392   public void publishContents(ContentHandler JavaDoc handler) throws SAXException JavaDoc
1393   {
1394      if (recorder == null)
1395         throw new SAXException JavaDoc(Messages.getMessage("noRecorder00"));
1396
1397      recorder.replay(startContentsIndex, endEventIndex - 1, handler);
1398   }
1399
1400   /**
1401    * This is the public output() method, which will always simply use
1402    * the recorded SAX stream for this element if it is available. If
1403    * not, this method calls outputImpl() to allow subclasses and
1404    * programmatically created messages to serialize themselves.
1405    *
1406    * @param context the SerializationContext we will write to.
1407    */

1408   public final void output(SerializationContext context) throws Exception JavaDoc
1409   {
1410
1411      if ((recorder != null) && (isDirty() == false))
1412      {
1413         recorder.replay(startEventIndex, endEventIndex, new SAXOutputter(context));
1414         return;
1415      }
1416
1417      // Turn QName attributes into strings
1418
if (qNameAttrs != null)
1419      {
1420         for (int i = 0; i < qNameAttrs.size(); i++)
1421         {
1422            QNameAttr attr = (QNameAttr)qNameAttrs.get(i);
1423            QName JavaDoc attrName = attr.name;
1424            setAttribute(attrName.getNamespaceURI(), attrName.getLocalPart(), context.qName2String(attr.value));
1425         }
1426      }
1427
1428      /**
1429       * Write the encoding style attribute IF it's different from
1430       * whatever encoding style is in scope....
1431       */

1432      if (encodingStyle != null)
1433      {
1434         MessageContext mc = context.getMessageContext();
1435         SOAPConstants soapConstants = (mc != null) ?
1436                 mc.getSOAPConstants() :
1437                 SOAPConstants.SOAP11_CONSTANTS;
1438         if (parent == null)
1439         {
1440            // don't emit an encoding style if its "" (literal)
1441
if (!encodingStyle.equals(""))
1442            {
1443               setAttribute(soapConstants.getEnvelopeURI(), Constants.ATTR_ENCODING_STYLE, encodingStyle);
1444            }
1445         }
1446         else if (!encodingStyle.equals(parent.getEncodingStyle()))
1447         {
1448            setAttribute(soapConstants.getEnvelopeURI(), Constants.ATTR_ENCODING_STYLE, encodingStyle);
1449         }
1450      }
1451
1452      outputImpl(context);
1453   }
1454
1455   /**
1456    * Subclasses can override
1457    */

1458   protected void outputImpl(SerializationContext context) throws Exception JavaDoc
1459   {
1460      if (elementRep != null)
1461      {
1462         boolean oldPretty = context.getPretty();
1463         context.setPretty(false);
1464         context.writeDOMElement(elementRep);
1465         context.setPretty(oldPretty);
1466         return;
1467      }
1468
1469      if (prefix != null && prefix.length() > 0)
1470         context.registerPrefixForURI(prefix, namespaceURI);
1471
1472      if (namespaces != null)
1473      {
1474         for (Iterator JavaDoc i = namespaces.iterator(); i.hasNext();)
1475         {
1476            Mapping mapping = (Mapping)i.next();
1477            context.registerPrefixForURI(mapping.getPrefix(), mapping.getNamespaceURI());
1478         }
1479      }
1480
1481      if (objectValue != null)
1482      {
1483         context.serialize(new QName JavaDoc(namespaceURI, name),
1484                 attributes,
1485                 objectValue, null, false, null);
1486         return;
1487      }
1488
1489      context.startElement(new QName JavaDoc(namespaceURI, name), attributes);
1490      for (Iterator JavaDoc it = children.iterator(); it.hasNext();)
1491      {
1492         Node JavaDoc childNode = (Node JavaDoc)it.next();
1493         if (childNode instanceof SOAPElementAxisImpl)
1494            ((SOAPElementAxisImpl)childNode).output(context);
1495         else if (childNode instanceof TextImpl)
1496            context.writeString(childNode.getNodeValue());
1497      }
1498
1499      context.endElement();
1500   }
1501
1502   public void addMapping(Mapping map)
1503   {
1504      if (namespaces == null)
1505         namespaces = new ArrayList JavaDoc();
1506      namespaces.add(map);
1507   }
1508
1509   // JAXM Node methods...
1510

1511   public void setParentElement(SOAPElement JavaDoc parent) throws SOAPException JavaDoc
1512   {
1513      if (parent == null)
1514         throw new IllegalArgumentException JavaDoc(Messages.getMessage("nullParent00"));
1515      try
1516      {
1517         setParent((SOAPElementAxisImpl)parent);
1518      }
1519      catch (Throwable JavaDoc t)
1520      {
1521         throw new SOAPException JavaDoc(t);
1522      }
1523   }
1524
1525   public SOAPElement JavaDoc getParentElement()
1526   {
1527      return getParent();
1528   }
1529
1530   /**
1531    * Break the relationship between this element and its parent, if any.
1532    */

1533   public void detachNode()
1534   {
1535
1536      assertImmutable();
1537
1538      super.detachNode();
1539      if (parent != null)
1540      {
1541         parent.removeChild(this);
1542         parent = null;
1543      }
1544   }
1545
1546   public boolean isImmutable()
1547   {
1548      return immutable;
1549   }
1550
1551   public void setImmutable(boolean immutable)
1552   {
1553      this.immutable = immutable;
1554   }
1555
1556   public void setAllImmutable(boolean immutable)
1557   {
1558      this.immutable = immutable;
1559
1560      Iterator JavaDoc it = children.iterator();
1561      while (it.hasNext())
1562      {
1563         Node JavaDoc node = (Node JavaDoc)it.next();
1564         if (node instanceof SOAPElementAxisImpl)
1565            ((SOAPElementAxisImpl)node).setAllImmutable(true);
1566      }
1567   }
1568
1569   // JAXM SOAPElement methods...
1570

1571   public SOAPElement JavaDoc addChildElement(Name JavaDoc name) throws SOAPException JavaDoc
1572   {
1573      SOAPElementAxisImpl child = new SOAPElementAxisImpl(name.getLocalName(),
1574              name.getPrefix(),
1575              name.getURI());
1576      addChild(child);
1577      return child;
1578   }
1579
1580   public SOAPElement JavaDoc addChildElement(String JavaDoc localName) throws SOAPException JavaDoc
1581   {
1582      // Inherit parent's namespace
1583
SOAPElementAxisImpl child = new SOAPElementAxisImpl(getNamespaceURI(),
1584              localName);
1585      addChild(child);
1586      return child;
1587   }
1588
1589   public SOAPElement JavaDoc addChildElement(String JavaDoc localName,
1590                                      String JavaDoc prefix) throws SOAPException JavaDoc
1591   {
1592      SOAPElementAxisImpl child = new SOAPElementAxisImpl(getNamespaceURI(prefix),
1593              localName);
1594      child.setPrefix(prefix);
1595      addChild(child);
1596      return child;
1597   }
1598
1599   public SOAPElement JavaDoc addChildElement(String JavaDoc localName,
1600                                      String JavaDoc prefix,
1601                                      String JavaDoc uri) throws SOAPException JavaDoc
1602   {
1603      SOAPElementAxisImpl child = new SOAPElementAxisImpl(uri, localName);
1604      child.setPrefix(prefix);
1605      child.addNamespaceDeclaration(prefix, uri);
1606      addChild(child);
1607      return child;
1608   }
1609
1610   /**
1611    * The added child must be an instance of MessageElement rather than
1612    * an abitrary SOAPElement otherwise a (wrapped) ClassCastException
1613    * will be thrown.
1614    */

1615   public SOAPElement JavaDoc addChildElement(SOAPElement JavaDoc element)
1616           throws SOAPException JavaDoc
1617   {
1618      try
1619      {
1620         addChild((SOAPElementAxisImpl)element);
1621         return element;
1622      }
1623      catch (ClassCastException JavaDoc e)
1624      {
1625         throw new SOAPException JavaDoc(e);
1626      }
1627   }
1628
1629   /**
1630    * Text nodes are not supported.
1631    */

1632   public SOAPElement JavaDoc addTextNode(String JavaDoc value) throws SOAPException JavaDoc
1633   {
1634      org.w3c.dom.Text JavaDoc domText = domNode.getOwnerDocument().createTextNode(value);
1635      javax.xml.soap.Text JavaDoc soapText = new TextImpl(domText);
1636      appendChild(soapText);
1637      return this;
1638   }
1639
1640   public SOAPElement JavaDoc addAttribute(Name JavaDoc name, String JavaDoc value)
1641           throws SOAPException JavaDoc
1642   {
1643      try
1644      {
1645         addAttribute(name.getPrefix(), name.getURI(), name.getLocalName(), value);
1646      }
1647      catch (RuntimeException JavaDoc t)
1648      {
1649         throw new SOAPException JavaDoc(t);
1650      }
1651      return this;
1652   }
1653
1654   public SOAPElement JavaDoc addNamespaceDeclaration(String JavaDoc prefix, String JavaDoc uri)
1655           throws SOAPException JavaDoc
1656   {
1657      try
1658      {
1659         Mapping map = new Mapping(uri, prefix);
1660         addMapping(map);
1661      }
1662      catch (RuntimeException JavaDoc t)
1663      {
1664         throw new SOAPException JavaDoc(t);
1665      }
1666      return this;
1667   }
1668
1669   public String JavaDoc getAttributeValue(Name JavaDoc name)
1670   {
1671      return attributes.getValue(name.getURI(), name.getLocalName());
1672   }
1673
1674   public Iterator JavaDoc getAllAttributes()
1675   {
1676      int num = attributes.getLength();
1677      Vector JavaDoc attrs = new Vector JavaDoc(num);
1678      for (int i = 0; i < num; i++)
1679      {
1680         String JavaDoc q = attributes.getQName(i);
1681         String JavaDoc prefix = "";
1682         if (q != null)
1683         {
1684            int idx = q.indexOf(":");
1685            if (idx > 0)
1686            {
1687               prefix = q.substring(0, idx);
1688            }
1689            else
1690            {
1691               prefix = "";
1692            }
1693         }
1694
1695         attrs.add(new NameImpl(attributes.getLocalName(i), prefix, attributes.getURI(i)));
1696      }
1697      return attrs.iterator();
1698   }
1699
1700   // getNamespaceURI implemented above
1701

1702   public Iterator JavaDoc getNamespacePrefixes()
1703   {
1704      Vector JavaDoc prefixes = new Vector JavaDoc();
1705      for (int i = 0; namespaces != null && i < namespaces.size(); i++)
1706      {
1707         prefixes.add(((Mapping)namespaces.get(i)).getPrefix());
1708      }
1709      return prefixes.iterator();
1710   }
1711
1712   public Name JavaDoc getElementName()
1713   {
1714      return new NameImpl(getName(), getPrefix(), getNamespaceURI());
1715   }
1716
1717   public boolean removeAttribute(Name JavaDoc name)
1718   {
1719      AttributesImpl JavaDoc attrs = makeAttributesEditable();
1720      boolean removed = false;
1721
1722      for (int i = 0; i < attrs.getLength() && !removed; i++)
1723      {
1724         if (attrs.getURI(i).equals(name.getURI()) &&
1725                 attrs.getLocalName(i).equals(name.getLocalName()))
1726         {
1727            attrs.removeAttribute(i);
1728            removed = true;
1729         }
1730      }
1731      return removed;
1732   }
1733
1734   public boolean removeNamespaceDeclaration(String JavaDoc prefix)
1735   {
1736      makeAttributesEditable();
1737      boolean removed = false;
1738
1739      for (int i = 0; namespaces != null && i < namespaces.size() && !removed; i++)
1740      {
1741         if (((Mapping)namespaces.get(i)).getPrefix().equals(prefix))
1742         {
1743            namespaces.remove(i);
1744            removed = true;
1745         }
1746      }
1747      return removed;
1748   }
1749
1750   public Iterator JavaDoc getChildElements()
1751   {
1752      return children.iterator();
1753   }
1754
1755   public Iterator JavaDoc getChildElements(Name JavaDoc name)
1756   {
1757      ArrayList JavaDoc list = new ArrayList JavaDoc();
1758      Iterator JavaDoc it = getChildElements();
1759      while (it.hasNext())
1760      {
1761         Node JavaDoc node = (Node JavaDoc)it.next();
1762         if (name.getURI().equals(node.getNamespaceURI()) && name.getLocalName().equals(node.getLocalName()))
1763            list.add(node);
1764      }
1765      return list.iterator();
1766   }
1767
1768   public String JavaDoc getTagName()
1769   {
1770      return prefix == null ? name : prefix + ":" + name;
1771   }
1772
1773   public void removeAttribute(String JavaDoc name) throws DOMException JavaDoc
1774   {
1775      AttributesImpl JavaDoc impl = (AttributesImpl JavaDoc)attributes;
1776      int index = impl.getIndex(name);
1777      if (index >= 0)
1778      {
1779         AttributesImpl JavaDoc newAttrs = new AttributesImpl JavaDoc();
1780         // copy except the removed attribute
1781
for (int i = 0; i < impl.getLength(); i++)
1782         { // shift after removal
1783
if (i != index)
1784            {
1785               String JavaDoc uri = impl.getURI(i);
1786               String JavaDoc local = impl.getLocalName(i);
1787               String JavaDoc qname = impl.getQName(i);
1788               String JavaDoc type = impl.getType(i);
1789               String JavaDoc value = impl.getValue(i);
1790               newAttrs.addAttribute(uri, local, qname, type, value);
1791            }
1792         }
1793         // replace it
1794
attributes = newAttrs;
1795      }
1796   }
1797
1798   public boolean hasAttribute(String JavaDoc name)
1799   {
1800      if (name == null) // Do I have to send an exception?
1801
name = "";
1802
1803      for (int i = 0; i < attributes.getLength(); i++)
1804      {
1805         if (name.equals(attributes.getQName(i)))
1806            return true;
1807      }
1808      return false;
1809   }
1810
1811   public String JavaDoc getAttribute(String JavaDoc name)
1812   {
1813      return attributes.getValue(name);
1814   }
1815
1816   public void removeAttributeNS(String JavaDoc namespaceURI, String JavaDoc localName) throws DOMException JavaDoc
1817   {
1818      makeAttributesEditable();
1819      Name JavaDoc name = new NameImpl(localName, null, namespaceURI);
1820      removeAttribute(name);
1821   }
1822
1823   public void setAttribute(String JavaDoc name, String JavaDoc value) throws DOMException JavaDoc
1824   {
1825      if (value == null)
1826         throw new IllegalArgumentException JavaDoc("Cannot set null attribute");
1827
1828      AttributesImpl JavaDoc attrs = makeAttributesEditable();
1829      int index = attrs.getIndex(name);
1830      if (index < 0)
1831      { // not found
1832
String JavaDoc uri = "";
1833         String JavaDoc localname = name;
1834         String JavaDoc qname = name;
1835         String JavaDoc type = "CDDATA";
1836         attrs.addAttribute(uri, localname, qname, type, value);
1837      }
1838      else
1839      { // found
1840
attrs.setLocalName(index, value);
1841      }
1842   }
1843
1844   public boolean hasAttributeNS(String JavaDoc namespaceURI, String JavaDoc localName)
1845   {
1846      if (namespaceURI == null)
1847         namespaceURI = "";
1848      if (localName == null) // Do I have to send an exception? or just return false
1849
localName = "";
1850
1851      for (int i = 0; i < attributes.getLength(); i++)
1852      {
1853         if (namespaceURI.equals(attributes.getURI(i))
1854                 && localName.equals(attributes.getLocalName(i)))
1855            return true;
1856      }
1857      return false;
1858   }
1859
1860   public Attr JavaDoc getAttributeNode(String JavaDoc name)
1861   {
1862      return null; //TODO: Fix this for SAAJ 1.2 Implementation
1863
}
1864
1865   public Attr JavaDoc removeAttributeNode(Attr JavaDoc oldAttr) throws DOMException JavaDoc
1866   {
1867      makeAttributesEditable();
1868      Name JavaDoc name = new NameImpl(oldAttr.getLocalName(), oldAttr.getPrefix(), oldAttr.getNamespaceURI());
1869      removeAttribute(name);
1870      return oldAttr;
1871   }
1872
1873   public Attr JavaDoc setAttributeNode(Attr JavaDoc newAttr) throws DOMException JavaDoc
1874   {
1875      return newAttr;
1876   }
1877
1878   public Attr JavaDoc setAttributeNodeNS(Attr JavaDoc newAttr) throws DOMException JavaDoc
1879   {
1880      //attributes.
1881
AttributesImpl JavaDoc attrs = makeAttributesEditable();
1882      // how to convert to DOM ATTR
1883
attrs.addAttribute(newAttr.getNamespaceURI(),
1884              newAttr.getLocalName(),
1885              newAttr.getLocalName(),
1886              "CDATA",
1887              newAttr.getValue());
1888      return null;
1889   }
1890
1891   public NodeList JavaDoc getElementsByTagName(String JavaDoc name)
1892   {
1893      //use this MessageElement class for Nodelist store
1894
NodeListImpl nodelist = new NodeListImpl();
1895      if (children != null)
1896      {
1897         // add 2nd Generation
1898
for (int i = 0; i < children.size(); i++)
1899         {
1900            Node JavaDoc child = children.get(i);
1901            if ("*".equals(name) || child.getNodeName().equals(name))
1902               nodelist.addNode(child);
1903         }
1904         // add 3rd Generation
1905
for (int i = 0; i < children.size(); i++)
1906         {
1907            if (children.get(i).getNodeType() == Node.ELEMENT_NODE)
1908            {
1909               Element JavaDoc child = (Element JavaDoc)children.get(i);
1910               NodeList JavaDoc grandsons = child.getElementsByTagName(name);
1911               for (int j = 0; j < grandsons.getLength(); j++)
1912               {
1913                  nodelist.addNode(grandsons.item(j));
1914               }
1915            }
1916         }
1917      }
1918      return nodelist;
1919   }
1920
1921   public String JavaDoc getAttributeNS(String JavaDoc namespaceURI, String JavaDoc localName)
1922   {
1923      for (int i = 0; i < attributes.getLength(); i++)
1924      {
1925         if (attributes.getURI(i).equals(namespaceURI) && attributes.getLocalName(i).equals(localName))
1926         {
1927            return attributes.getValue(i);
1928         }
1929      }
1930      return null;
1931   }
1932
1933   public void setAttributeNS(String JavaDoc namespaceURI, String JavaDoc qualifiedName, String JavaDoc value) throws DOMException JavaDoc
1934   {
1935      AttributesImpl JavaDoc attrs = makeAttributesEditable();
1936      String JavaDoc localName = qualifiedName.substring(qualifiedName.indexOf(":") + 1, qualifiedName.length());
1937
1938      if (namespaceURI == null)
1939      {
1940         namespaceURI = "intentionalNullURI";
1941      }
1942      attrs.addAttribute(namespaceURI, localName, qualifiedName, "CDATA", value);
1943   }
1944
1945   public Attr JavaDoc getAttributeNodeNS(String JavaDoc namespaceURI, String JavaDoc localName)
1946   {
1947      return null; //TODO: Fix this for SAAJ 1.2 Implementation
1948
}
1949
1950   public NodeList JavaDoc getElementsByTagNameNS(String JavaDoc namespaceURI, String JavaDoc localName)
1951   {
1952      return getElementsNS(this, namespaceURI, localName);
1953   }
1954
1955   /**
1956    * helper method for recusively getting the element that has namespace URI and localname
1957    */

1958   protected NodeList JavaDoc getElementsNS(org.w3c.dom.Element JavaDoc parent,
1959                                    String JavaDoc namespaceURI, String JavaDoc localName)
1960   {
1961      NodeList JavaDoc children = parent.getChildNodes();
1962      NodeListImpl matches = new NodeListImpl();
1963      // Add first the imediate child
1964
for (int i = 0; i < children.getLength(); i++)
1965      {
1966
1967         Node JavaDoc c = (Node JavaDoc)children.item(i);
1968         if (c instanceof Element JavaDoc)
1969         {
1970            Element JavaDoc child = (Element JavaDoc)c;
1971            if (namespaceURI.equals(child.getNamespaceURI()) &&
1972                    localName.equals(child.getLocalName()))
1973            {
1974               matches.addNode(child);
1975            }
1976            // search the grand-children.
1977
matches.addNodeList(child.getElementsByTagNameNS(namespaceURI, localName));
1978         }
1979      }
1980      return matches;
1981   }
1982
1983   public void setOwnerDocument(org.jboss.axis.MessagePart sp)
1984   {
1985      soapPart = sp;
1986   }
1987
1988   /**
1989    * Mark the SOAPEnvelope as modified, this should invalidate the SAX event cache
1990    */

1991   private void setElementAsModified()
1992   {
1993      SOAPEnvelopeAxisImpl env = getSOAPEnvelope();
1994      if (env != null) env.setModified(true);
1995   }
1996
1997   /**
1998    * Get the SOAPEnvelope for this element
1999    */

2000   private SOAPEnvelopeAxisImpl getSOAPEnvelope()
2001   {
2002      SOAPEnvelopeAxisImpl env = null;
2003      SOAPElementAxisImpl el = this;
2004      while (env == null && el != null)
2005      {
2006         if (el instanceof SOAPEnvelopeAxisImpl)
2007         {
2008            env = (SOAPEnvelopeAxisImpl)el;
2009         }
2010         el = el.getParent();
2011      }
2012      return env;
2013   }
2014
2015   public List JavaDoc getChildren()
2016   {
2017      return children.getUnmodifieableList();
2018   }
2019
2020   /**
2021    * Wraps the child list maintained by this class to get better control of who
2022    * is doing what with respect to children. Eventually this should go all together
2023    * and the list be maintained by the NodeImpl.
2024    */

2025   class ChildElementList
2026   {
2027      private ArrayList JavaDoc children = new ArrayList JavaDoc();
2028
2029      // WRITE operations
2030

2031      public void clear()
2032      {
2033         log.debug("Clear the child list");
2034         children.clear();
2035         setElementAsModified();
2036      }
2037
2038      public void add(Node JavaDoc child)
2039      {
2040         log.debug("Adding child: " + getDebugStr(child));
2041         children.add(child);
2042         setElementAsModified();
2043      }
2044
2045      public void add(int pos, Node JavaDoc child)
2046      {
2047         log.debug("Adding child at position: " + pos + "," + getDebugStr(child));
2048         children.add(pos, child);
2049         setElementAsModified();
2050      }
2051
2052      public void remove(int pos)
2053      {
2054         log.debug("Remove child at position: " + pos);
2055         children.remove(pos);
2056         setElementAsModified();
2057      }
2058
2059      // READ operations
2060

2061      public List JavaDoc getUnmodifieableList()
2062      {
2063         return Collections.unmodifiableList(children);
2064      }
2065
2066      public boolean contains(Node JavaDoc child)
2067      {
2068         return children.contains(child);
2069      }
2070
2071      public boolean isEmpty()
2072      {
2073         return children.isEmpty();
2074      }
2075
2076      public Node JavaDoc get(int pos)
2077      {
2078         return (NodeImpl)children.get(pos);
2079      }
2080
2081      public int size()
2082      {
2083         return children.size();
2084      }
2085
2086      public int indexOf(Node JavaDoc child)
2087      {
2088         return children.indexOf(child);
2089      }
2090
2091      public Iterator JavaDoc iterator()
2092      {
2093         return children.iterator();
2094      }
2095
2096      private String JavaDoc getDebugStr(Node JavaDoc child)
2097      {
2098         String JavaDoc nodeStr = child.getNodeName();
2099         if (child.getNodeType() == Node.TEXT_NODE)
2100            nodeStr += " [" + child.getNodeValue() + "]";
2101         return nodeStr;
2102      }
2103   }
2104}
2105
Popular Tags