src/share/jaxws_classes/com/sun/xml/internal/ws/message/source/SourceUtils.java

Thu, 31 Aug 2017 15:18:52 +0800

author
aoqi
date
Thu, 31 Aug 2017 15:18:52 +0800
changeset 637
9c07ef4934dd
parent 368
0989ad8c0860
parent 0
373ffda63c9a
permissions
-rw-r--r--

merge

     1 /*
     2  * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.  Oracle designates this
     8  * particular file as subject to the "Classpath" exception as provided
     9  * by Oracle in the LICENSE file that accompanied this code.
    10  *
    11  * This code is distributed in the hope that it will be useful, but WITHOUT
    12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
    13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
    14  * version 2 for more details (a copy is included in the LICENSE file that
    15  * accompanied this code).
    16  *
    17  * You should have received a copy of the GNU General Public License version
    18  * 2 along with this work; if not, write to the Free Software Foundation,
    19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
    20  *
    21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
    22  * or visit www.oracle.com if you need additional information or have any
    23  * questions.
    24  */
    26 package com.sun.xml.internal.ws.message.source;
    28 import com.sun.xml.internal.ws.message.RootElementSniffer;
    29 import com.sun.xml.internal.ws.streaming.SourceReaderFactory;
    30 import com.sun.xml.internal.ws.util.xml.XmlUtil;
    31 import org.w3c.dom.Document;
    32 import org.w3c.dom.Node;
    34 import javax.xml.namespace.QName;
    35 import javax.xml.stream.XMLStreamConstants;
    36 import javax.xml.stream.XMLStreamException;
    37 import javax.xml.stream.XMLStreamReader;
    38 import javax.xml.stream.XMLStreamWriter;
    39 import javax.xml.transform.Source;
    40 import javax.xml.transform.Transformer;
    41 import javax.xml.transform.TransformerConfigurationException;
    42 import javax.xml.transform.TransformerException;
    43 import javax.xml.transform.dom.DOMSource;
    44 import javax.xml.transform.sax.SAXResult;
    45 import javax.xml.transform.sax.SAXSource;
    46 import javax.xml.transform.stream.StreamSource;
    47 import javax.xml.ws.WebServiceException;
    49 /**
    50  *
    51  * @author Vivek Pandey
    52  */
    53 final class SourceUtils {
    55     int srcType;
    57     private static final int domSource = 1;
    58     private static final int streamSource = 2;
    59     private static final int saxSource=4;
    61     public SourceUtils(Source src) {
    62         if(src instanceof StreamSource){
    63             srcType = streamSource;
    64         }else if(src instanceof DOMSource){
    65             srcType = domSource;
    66         }else if(src instanceof SAXSource){
    67             srcType = saxSource;
    68         }
    69     }
    71     public boolean isDOMSource(){
    72         return (srcType&domSource) == domSource;
    73     }
    75     public boolean isStreamSource(){
    76         return (srcType&streamSource) == streamSource;
    77     }
    79     public boolean isSaxSource(){
    80         return (srcType&saxSource) == saxSource;
    81     }
    83     /**
    84      * This would peek into the Source (DOMSource and SAXSource) for the localName and NamespaceURI
    85      * of the top-level element.
    86      * @param src
    87      * @return QName of the payload
    88      */
    89     public QName sniff(Source src) {
    90         return sniff(src, new RootElementSniffer());
    91     }
    93     public QName sniff(Source src, RootElementSniffer sniffer){
    94         String localName = null;
    95         String namespaceUri = null;
    97         if(isDOMSource()){
    98             DOMSource domSrc = (DOMSource)src;
    99             Node n = domSrc.getNode();
   100             if(n.getNodeType()== Node.DOCUMENT_NODE) {
   101                 n = ((Document)n).getDocumentElement();
   102             }
   103             localName = n.getLocalName();
   104             namespaceUri = n.getNamespaceURI();
   105         }else if(isSaxSource()){
   106             SAXSource saxSrc = (SAXSource)src;
   107             SAXResult saxResult = new SAXResult(sniffer);
   108             try {
   109                 Transformer tr = XmlUtil.newTransformer();
   110                 tr.transform(saxSrc, saxResult);
   111             } catch (TransformerConfigurationException e) {
   112                 throw new WebServiceException(e);
   113             } catch (TransformerException e) {
   114                 // if it's due to aborting the processing after the first element,
   115                 // we can safely ignore this exception.
   116                 //
   117                 // if it's due to error in the object, the same error will be reported
   118                 // when the readHeader() method is used, so we don't have to report
   119                 // an error right now.
   120                 localName = sniffer.getLocalName();
   121                 namespaceUri = sniffer.getNsUri();
   122             }
   123         }
   124         return new QName(namespaceUri, localName);
   125     }
   127     public static void serializeSource(Source src, XMLStreamWriter writer) throws XMLStreamException {
   128         XMLStreamReader reader = SourceReaderFactory.createSourceReader(src, true);
   129         int state;
   130         do {
   131             state = reader.next();
   132             switch (state) {
   133                 case XMLStreamConstants.START_ELEMENT:
   134                     /*
   135                      * TODO: Is this necessary, shouldn't zephyr return "" instead of
   136                      * null for getNamespaceURI() and getPrefix()?
   137                      */
   138                     String uri = reader.getNamespaceURI();
   139                     String prefix = reader.getPrefix();
   140                     String localName = reader.getLocalName();
   142                     if (prefix == null) {
   143                         if (uri == null) {
   144                             writer.writeStartElement(localName);
   145                         } else {
   146                             writer.writeStartElement(uri, localName);
   147                         }
   148                     } else {
   149 //                        assert uri != null;
   151                         if(prefix.length() > 0){
   152                             /**
   153                              * Before we write the
   154                              */
   155                             String writerURI = null;
   156                             if (writer.getNamespaceContext() != null) {
   157                                 writerURI = writer.getNamespaceContext().getNamespaceURI(prefix);
   158                             }
   159                             String writerPrefix = writer.getPrefix(uri);
   160                             if(declarePrefix(prefix, uri, writerPrefix, writerURI)){
   161                                 writer.writeStartElement(prefix, localName, uri);
   162                                 writer.setPrefix(prefix, uri != null ? uri : "");
   163                                 writer.writeNamespace(prefix, uri);
   164                             }else{
   165                                 writer.writeStartElement(prefix, localName, uri);
   166                             }
   167                         }else{
   168                             writer.writeStartElement(prefix, localName, uri);
   169                         }
   170                     }
   172                     int n = reader.getNamespaceCount();
   173                     // Write namespace declarations
   174                     for (int i = 0; i < n; i++) {
   175                         String nsPrefix = reader.getNamespacePrefix(i);
   176                         if (nsPrefix == null) {
   177                             nsPrefix = "";
   178                         }
   179                         // StAX returns null for default ns
   180                         String writerURI = null;
   181                         if (writer.getNamespaceContext() != null) {
   182                             writerURI = writer.getNamespaceContext().getNamespaceURI(nsPrefix);
   183                         }
   185                         // Zephyr: Why is this returning null?
   186                         // Compare nsPrefix with prefix because of [1] (above)
   187                         String readerURI = reader.getNamespaceURI(i);
   189                         /**
   190                          * write the namespace in 3 conditions
   191                          *  - when the namespace URI is not bound to the prefix in writer(writerURI == 0)
   192                          *  - when the readerPrefix and writerPrefix are ""
   193                          *  - when readerPrefix and writerPrefix are not equal and the URI bound to them
   194                          *    are different
   195                          */
   196                         if (writerURI == null || ((nsPrefix.length() == 0) || (prefix.length() == 0)) ||
   197                                 (!nsPrefix.equals(prefix) && !writerURI.equals(readerURI))) {
   198                             writer.setPrefix(nsPrefix, readerURI != null ? readerURI : "");
   199                             writer.writeNamespace(nsPrefix, readerURI != null ? readerURI : "");
   200                         }
   201                     }
   203                     // Write attributes
   204                     n = reader.getAttributeCount();
   205                     for (int i = 0; i < n; i++) {
   206                         String attrPrefix = reader.getAttributePrefix(i);
   207                         String attrURI = reader.getAttributeNamespace(i);
   209                         writer.writeAttribute(attrPrefix != null ? attrPrefix : "",
   210                             attrURI != null ? attrURI : "",
   211                             reader.getAttributeLocalName(i),
   212                             reader.getAttributeValue(i));
   213                         // if the attribute prefix is undeclared in current writer scope then declare it
   214                         setUndeclaredPrefix(attrPrefix, attrURI, writer);
   215                     }
   216                     break;
   217                 case XMLStreamConstants.END_ELEMENT:
   218                     writer.writeEndElement();
   219                     break;
   220                 case XMLStreamConstants.CHARACTERS:
   221                     writer.writeCharacters(reader.getText());
   222                     break;
   223                 default:
   224                     break;
   225             }
   226         } while (state != XMLStreamConstants.END_DOCUMENT);
   227         reader.close();
   228     }
   230     /**
   231      * sets undeclared prefixes on the writer
   232      * @param prefix
   233      * @param writer
   234      * @throws XMLStreamException
   235      */
   236     private static void setUndeclaredPrefix(String prefix, String readerURI, XMLStreamWriter writer) throws XMLStreamException {
   237         String writerURI = null;
   238         if (writer.getNamespaceContext() != null) {
   239             writerURI = writer.getNamespaceContext().getNamespaceURI(prefix);
   240         }
   242         if (writerURI == null) {
   243             writer.setPrefix(prefix, readerURI != null ? readerURI : "");
   244             writer.writeNamespace(prefix, readerURI != null ? readerURI : "");
   245         }
   246     }
   248     /**
   249      * check if we need to declare
   250      * @param rPrefix
   251      * @param rUri
   252      * @param wPrefix
   253      * @param wUri
   254      */
   255     private static boolean declarePrefix(String rPrefix, String rUri, String wPrefix, String wUri){
   256         if (wUri == null ||((wPrefix != null) && !rPrefix.equals(wPrefix))||
   257                 (rUri != null && !wUri.equals(rUri))) {
   258             return true;
   259         }
   260         return false;
   261     }
   262 }

mercurial