Tue, 09 Apr 2013 14:51:13 +0100
8010393: Update JAX-WS RI to 2.2.9-b12941
Reviewed-by: alanb, erikj
Contributed-by: miroslav.kos@oracle.com, martin.grebac@oracle.com
alanb@368 | 1 | /* |
alanb@368 | 2 | * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved. |
alanb@368 | 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
alanb@368 | 4 | * |
alanb@368 | 5 | * This code is free software; you can redistribute it and/or modify it |
alanb@368 | 6 | * under the terms of the GNU General Public License version 2 only, as |
alanb@368 | 7 | * published by the Free Software Foundation. Oracle designates this |
alanb@368 | 8 | * particular file as subject to the "Classpath" exception as provided |
alanb@368 | 9 | * by Oracle in the LICENSE file that accompanied this code. |
alanb@368 | 10 | * |
alanb@368 | 11 | * This code is distributed in the hope that it will be useful, but WITHOUT |
alanb@368 | 12 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
alanb@368 | 13 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License |
alanb@368 | 14 | * version 2 for more details (a copy is included in the LICENSE file that |
alanb@368 | 15 | * accompanied this code). |
alanb@368 | 16 | * |
alanb@368 | 17 | * You should have received a copy of the GNU General Public License version |
alanb@368 | 18 | * 2 along with this work; if not, write to the Free Software Foundation, |
alanb@368 | 19 | * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. |
alanb@368 | 20 | * |
alanb@368 | 21 | * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA |
alanb@368 | 22 | * or visit www.oracle.com if you need additional information or have any |
alanb@368 | 23 | * questions. |
alanb@368 | 24 | */ |
alanb@368 | 25 | |
alanb@368 | 26 | package com.sun.xml.internal.ws.model; |
alanb@368 | 27 | |
alanb@368 | 28 | import com.oracle.xmlns.internal.webservices.jaxws_databinding.JavaMethod; |
alanb@368 | 29 | import com.oracle.xmlns.internal.webservices.jaxws_databinding.JavaParam; |
alanb@368 | 30 | import com.oracle.xmlns.internal.webservices.jaxws_databinding.JavaWsdlMappingType; |
alanb@368 | 31 | import com.oracle.xmlns.internal.webservices.jaxws_databinding.ObjectFactory; |
alanb@368 | 32 | import com.sun.xml.internal.bind.api.JAXBRIContext; |
alanb@368 | 33 | import com.sun.xml.internal.ws.streaming.XMLStreamReaderUtil; |
alanb@368 | 34 | import com.sun.xml.internal.ws.util.xml.XmlUtil; |
alanb@368 | 35 | import org.w3c.dom.Element; |
alanb@368 | 36 | import org.xml.sax.SAXException; |
alanb@368 | 37 | |
alanb@368 | 38 | import javax.xml.bind.JAXBContext; |
alanb@368 | 39 | import javax.xml.bind.JAXBElement; |
alanb@368 | 40 | import javax.xml.bind.JAXBException; |
alanb@368 | 41 | import javax.xml.bind.Unmarshaller; |
alanb@368 | 42 | import javax.xml.bind.util.JAXBResult; |
alanb@368 | 43 | import javax.xml.stream.XMLInputFactory; |
alanb@368 | 44 | import javax.xml.stream.XMLStreamException; |
alanb@368 | 45 | import javax.xml.stream.XMLStreamReader; |
alanb@368 | 46 | import javax.xml.transform.Source; |
alanb@368 | 47 | import javax.xml.transform.Transformer; |
alanb@368 | 48 | import javax.xml.transform.TransformerException; |
alanb@368 | 49 | import javax.xml.transform.TransformerFactory; |
alanb@368 | 50 | import javax.xml.transform.stream.StreamSource; |
alanb@368 | 51 | import javax.xml.validation.Schema; |
alanb@368 | 52 | import javax.xml.validation.SchemaFactory; |
alanb@368 | 53 | import java.io.*; |
alanb@368 | 54 | import java.lang.annotation.Annotation; |
alanb@368 | 55 | import java.lang.reflect.Method; |
alanb@368 | 56 | import java.net.URL; |
alanb@368 | 57 | import java.util.*; |
alanb@368 | 58 | |
alanb@368 | 59 | import static com.oracle.xmlns.internal.webservices.jaxws_databinding.ExistingAnnotationsType.MERGE; |
alanb@368 | 60 | |
alanb@368 | 61 | /** |
alanb@368 | 62 | * Metadata Reader able to read from either class annotations or external metadata files or combine both, |
alanb@368 | 63 | * depending on configuration provided in xml file itself. |
alanb@368 | 64 | * |
alanb@368 | 65 | * @author shih-chang.chen@oracle.com, miroslav.kos@oracle.com |
alanb@368 | 66 | */ |
alanb@368 | 67 | public class ExternalMetadataReader extends ReflectAnnotationReader { |
alanb@368 | 68 | |
alanb@368 | 69 | private static final String NAMESPACE_WEBLOGIC_WSEE_DATABINDING = "http://xmlns.oracle.com/weblogic/weblogic-wsee-databinding"; |
alanb@368 | 70 | private static final String NAMESPACE_JAXWS_RI_EXTERNAL_METADATA = "http://xmlns.oracle.com/webservices/jaxws-databinding"; |
alanb@368 | 71 | |
alanb@368 | 72 | /** |
alanb@368 | 73 | * map of readers for defined java types |
alanb@368 | 74 | */ |
alanb@368 | 75 | private Map<String, JavaWsdlMappingType> readers = new HashMap<String, JavaWsdlMappingType>(); |
alanb@368 | 76 | |
alanb@368 | 77 | public ExternalMetadataReader(Collection<File> files, Collection<String> resourcePaths, ClassLoader classLoader, |
alanb@368 | 78 | boolean xsdValidation, boolean disableSecureXmlProcessing) { |
alanb@368 | 79 | |
alanb@368 | 80 | if (files != null) { |
alanb@368 | 81 | for (File file : files) { |
alanb@368 | 82 | try { |
alanb@368 | 83 | String namespace = Util.documentRootNamespace(newSource(file), disableSecureXmlProcessing); |
alanb@368 | 84 | JavaWsdlMappingType externalMapping = parseMetadata(xsdValidation, newSource(file), namespace, disableSecureXmlProcessing); |
alanb@368 | 85 | readers.put(externalMapping.getJavaTypeName(), externalMapping); |
alanb@368 | 86 | } catch (Exception e) { |
alanb@368 | 87 | throw new RuntimeModelerException("runtime.modeler.external.metadata.unable.to.read", file.getAbsolutePath()); |
alanb@368 | 88 | } |
alanb@368 | 89 | } |
alanb@368 | 90 | } |
alanb@368 | 91 | |
alanb@368 | 92 | if (resourcePaths != null) { |
alanb@368 | 93 | for (String resourcePath : resourcePaths) { |
alanb@368 | 94 | try { |
alanb@368 | 95 | String namespace = Util.documentRootNamespace(newSource(resourcePath, classLoader), disableSecureXmlProcessing); |
alanb@368 | 96 | JavaWsdlMappingType externalMapping = parseMetadata(xsdValidation, newSource(resourcePath, classLoader), namespace, disableSecureXmlProcessing); |
alanb@368 | 97 | readers.put(externalMapping.getJavaTypeName(), externalMapping); |
alanb@368 | 98 | } catch (Exception e) { |
alanb@368 | 99 | throw new RuntimeModelerException("runtime.modeler.external.metadata.unable.to.read", resourcePath); |
alanb@368 | 100 | } |
alanb@368 | 101 | } |
alanb@368 | 102 | } |
alanb@368 | 103 | } |
alanb@368 | 104 | |
alanb@368 | 105 | private StreamSource newSource(String resourcePath, ClassLoader classLoader) { |
alanb@368 | 106 | InputStream is = classLoader.getResourceAsStream(resourcePath); |
alanb@368 | 107 | return new StreamSource(is); |
alanb@368 | 108 | } |
alanb@368 | 109 | |
alanb@368 | 110 | private JavaWsdlMappingType parseMetadata(boolean xsdValidation, StreamSource source, String namespace, boolean disableSecureXmlProcessing) throws JAXBException, IOException, TransformerException { |
alanb@368 | 111 | if (NAMESPACE_WEBLOGIC_WSEE_DATABINDING.equals(namespace)) { |
alanb@368 | 112 | return Util.transformAndRead(source, disableSecureXmlProcessing); |
alanb@368 | 113 | } if (NAMESPACE_JAXWS_RI_EXTERNAL_METADATA.equals(namespace)) { |
alanb@368 | 114 | return Util.read(source, xsdValidation, disableSecureXmlProcessing); |
alanb@368 | 115 | } else { |
alanb@368 | 116 | throw new RuntimeModelerException("runtime.modeler.external.metadata.unsupported.schema", namespace, Arrays.asList(NAMESPACE_WEBLOGIC_WSEE_DATABINDING, NAMESPACE_JAXWS_RI_EXTERNAL_METADATA).toString()); |
alanb@368 | 117 | } |
alanb@368 | 118 | } |
alanb@368 | 119 | |
alanb@368 | 120 | private StreamSource newSource(File file) { |
alanb@368 | 121 | try { |
alanb@368 | 122 | return new StreamSource(new FileInputStream(file)); |
alanb@368 | 123 | } catch (FileNotFoundException e) { |
alanb@368 | 124 | throw new RuntimeModelerException("runtime.modeler.external.metadata.unable.to.read", file.getAbsolutePath()); |
alanb@368 | 125 | } |
alanb@368 | 126 | } |
alanb@368 | 127 | |
alanb@368 | 128 | public <A extends Annotation> A getAnnotation(Class<A> annType, Class<?> cls) { |
alanb@368 | 129 | JavaWsdlMappingType r = reader(cls); |
alanb@368 | 130 | return r == null ? super.getAnnotation(annType, cls) : Util.annotation(r, annType); |
alanb@368 | 131 | } |
alanb@368 | 132 | |
alanb@368 | 133 | private JavaWsdlMappingType reader(Class<?> cls) { |
alanb@368 | 134 | return readers.get(cls.getName()); |
alanb@368 | 135 | } |
alanb@368 | 136 | |
alanb@368 | 137 | Annotation[] getAnnotations(List<Object> objects) { |
alanb@368 | 138 | ArrayList<Annotation> list = new ArrayList<Annotation>(); |
alanb@368 | 139 | for (Object a : objects) { |
alanb@368 | 140 | if (Annotation.class.isInstance(a)) { |
alanb@368 | 141 | list.add(Annotation.class.cast(a)); |
alanb@368 | 142 | } |
alanb@368 | 143 | } |
alanb@368 | 144 | return list.toArray(new Annotation[list.size()]); |
alanb@368 | 145 | } |
alanb@368 | 146 | |
alanb@368 | 147 | public Annotation[] getAnnotations(final Class<?> c) { |
alanb@368 | 148 | |
alanb@368 | 149 | Merger<Annotation[]> merger = new Merger<Annotation[]>(reader(c)) { |
alanb@368 | 150 | Annotation[] reflection() { |
alanb@368 | 151 | return ExternalMetadataReader.super.getAnnotations(c); |
alanb@368 | 152 | } |
alanb@368 | 153 | |
alanb@368 | 154 | Annotation[] external() { |
alanb@368 | 155 | return getAnnotations(reader.getClassAnnotation()); |
alanb@368 | 156 | } |
alanb@368 | 157 | }; |
alanb@368 | 158 | return merger.merge(); |
alanb@368 | 159 | } |
alanb@368 | 160 | |
alanb@368 | 161 | public Annotation[] getAnnotations(final Method m) { |
alanb@368 | 162 | Merger<Annotation[]> merger = new Merger<Annotation[]>(reader(m.getDeclaringClass())) { |
alanb@368 | 163 | Annotation[] reflection() { |
alanb@368 | 164 | return ExternalMetadataReader.super.getAnnotations(m); |
alanb@368 | 165 | } |
alanb@368 | 166 | |
alanb@368 | 167 | Annotation[] external() { |
alanb@368 | 168 | JavaMethod jm = getJavaMethod(m, reader); |
alanb@368 | 169 | return (jm == null) ? new Annotation[0] : getAnnotations(jm.getMethodAnnotation()); |
alanb@368 | 170 | } |
alanb@368 | 171 | }; |
alanb@368 | 172 | return merger.merge(); |
alanb@368 | 173 | } |
alanb@368 | 174 | |
alanb@368 | 175 | @SuppressWarnings("unchecked") |
alanb@368 | 176 | public <A extends Annotation> A getAnnotation(final Class<A> annType, final Method m) { |
alanb@368 | 177 | Merger<Annotation> merger = new Merger<Annotation>(reader(m.getDeclaringClass())) { |
alanb@368 | 178 | Annotation reflection() { |
alanb@368 | 179 | return ExternalMetadataReader.super.getAnnotation(annType, m); |
alanb@368 | 180 | } |
alanb@368 | 181 | |
alanb@368 | 182 | Annotation external() { |
alanb@368 | 183 | JavaMethod jm = getJavaMethod(m, reader); |
alanb@368 | 184 | return Util.annotation(jm, annType); |
alanb@368 | 185 | } |
alanb@368 | 186 | }; |
alanb@368 | 187 | return (A) merger.merge(); |
alanb@368 | 188 | } |
alanb@368 | 189 | |
alanb@368 | 190 | public Annotation[][] getParameterAnnotations(final Method m) { |
alanb@368 | 191 | Merger<Annotation[][]> merger = new Merger<Annotation[][]>(reader(m.getDeclaringClass())) { |
alanb@368 | 192 | Annotation[][] reflection() { |
alanb@368 | 193 | return ExternalMetadataReader.super.getParameterAnnotations(m); |
alanb@368 | 194 | } |
alanb@368 | 195 | |
alanb@368 | 196 | Annotation[][] external() { |
alanb@368 | 197 | JavaMethod jm = getJavaMethod(m, reader); |
alanb@368 | 198 | Annotation[][] a = m.getParameterAnnotations(); |
alanb@368 | 199 | for (int i = 0; i < m.getParameterTypes().length; i++) { |
alanb@368 | 200 | if (jm == null) continue; |
alanb@368 | 201 | JavaParam jp = jm.getJavaParams().getJavaParam().get(i); |
alanb@368 | 202 | a[i] = getAnnotations(jp.getParamAnnotation()); |
alanb@368 | 203 | } |
alanb@368 | 204 | return a; |
alanb@368 | 205 | } |
alanb@368 | 206 | }; |
alanb@368 | 207 | return merger.merge(); |
alanb@368 | 208 | } |
alanb@368 | 209 | |
alanb@368 | 210 | public void getProperties(final Map<String, Object> prop, final Class<?> cls) { |
alanb@368 | 211 | |
alanb@368 | 212 | JavaWsdlMappingType r = reader(cls); |
alanb@368 | 213 | |
alanb@368 | 214 | // no external reader or it requires annotations merging ... |
alanb@368 | 215 | if (r == null || MERGE.equals(r.getExistingAnnotations())) { |
alanb@368 | 216 | super.getProperties(prop, cls); |
alanb@368 | 217 | } |
alanb@368 | 218 | |
alanb@368 | 219 | } |
alanb@368 | 220 | |
alanb@368 | 221 | public void getProperties(final Map<String, Object> prop, final Method m) { |
alanb@368 | 222 | |
alanb@368 | 223 | JavaWsdlMappingType r = reader(m.getDeclaringClass()); |
alanb@368 | 224 | |
alanb@368 | 225 | // no external reader or it requires annotations merging ... |
alanb@368 | 226 | if (r == null || MERGE.equals(r.getExistingAnnotations())) { |
alanb@368 | 227 | super.getProperties(prop, m); |
alanb@368 | 228 | } |
alanb@368 | 229 | |
alanb@368 | 230 | if (r != null) { |
alanb@368 | 231 | JavaMethod jm = getJavaMethod(m, r); |
alanb@368 | 232 | Element[] e = Util.annotation(jm); |
alanb@368 | 233 | prop.put("eclipselink-oxm-xml.xml-element", findXmlElement(e)); |
alanb@368 | 234 | } |
alanb@368 | 235 | |
alanb@368 | 236 | } |
alanb@368 | 237 | |
alanb@368 | 238 | public void getProperties(final Map<String, Object> prop, final Method m, int pos) { |
alanb@368 | 239 | |
alanb@368 | 240 | JavaWsdlMappingType r = reader(m.getDeclaringClass()); |
alanb@368 | 241 | |
alanb@368 | 242 | // no external reader or it requires annotations merging ... |
alanb@368 | 243 | if (r == null || MERGE.equals(r.getExistingAnnotations())) { |
alanb@368 | 244 | super.getProperties(prop, m, pos); |
alanb@368 | 245 | } |
alanb@368 | 246 | |
alanb@368 | 247 | if (r != null) { |
alanb@368 | 248 | JavaMethod jm = getJavaMethod(m, r); |
alanb@368 | 249 | if (jm == null) return; |
alanb@368 | 250 | JavaParam jp = jm.getJavaParams().getJavaParam().get(pos); |
alanb@368 | 251 | Element[] e = Util.annotation(jp); |
alanb@368 | 252 | prop.put("eclipselink-oxm-xml.xml-element", findXmlElement(e)); |
alanb@368 | 253 | } |
alanb@368 | 254 | } |
alanb@368 | 255 | |
alanb@368 | 256 | JavaMethod getJavaMethod(Method method, JavaWsdlMappingType r) { |
alanb@368 | 257 | |
alanb@368 | 258 | JavaWsdlMappingType.JavaMethods javaMethods = r.getJavaMethods(); |
alanb@368 | 259 | if (javaMethods == null) { |
alanb@368 | 260 | return null; |
alanb@368 | 261 | } |
alanb@368 | 262 | |
alanb@368 | 263 | List<JavaMethod> sameName = new ArrayList<JavaMethod>(); |
alanb@368 | 264 | for (JavaMethod jm : javaMethods.getJavaMethod()) { |
alanb@368 | 265 | if (method.getName().equals(jm.getName())) { |
alanb@368 | 266 | sameName.add(jm); |
alanb@368 | 267 | } |
alanb@368 | 268 | } |
alanb@368 | 269 | |
alanb@368 | 270 | if (sameName.isEmpty()) { |
alanb@368 | 271 | return null; |
alanb@368 | 272 | } else { |
alanb@368 | 273 | if (sameName.size() == 1) { |
alanb@368 | 274 | return sameName.get(0); |
alanb@368 | 275 | } else { |
alanb@368 | 276 | Class<?>[] argCls = method.getParameterTypes(); |
alanb@368 | 277 | for (JavaMethod jm : sameName) { |
alanb@368 | 278 | JavaMethod.JavaParams params = jm.getJavaParams(); |
alanb@368 | 279 | if (params != null && params.getJavaParam() != null && params.getJavaParam().size() == argCls.length) { |
alanb@368 | 280 | int count = 0; |
alanb@368 | 281 | for (int i = 0; i < argCls.length; i++) { |
alanb@368 | 282 | JavaParam jp = params.getJavaParam().get(i); |
alanb@368 | 283 | if (argCls[i].getName().equals(jp.getJavaType())) { |
alanb@368 | 284 | count++; |
alanb@368 | 285 | } |
alanb@368 | 286 | } |
alanb@368 | 287 | if (count == argCls.length) { |
alanb@368 | 288 | return jm; |
alanb@368 | 289 | } |
alanb@368 | 290 | } |
alanb@368 | 291 | } |
alanb@368 | 292 | } |
alanb@368 | 293 | } |
alanb@368 | 294 | return null; |
alanb@368 | 295 | } |
alanb@368 | 296 | |
alanb@368 | 297 | Element findXmlElement(Element[] xa) { |
alanb@368 | 298 | if (xa == null) return null; |
alanb@368 | 299 | for (Element e : xa) { |
alanb@368 | 300 | if (e.getLocalName().equals("java-type")) return e; |
alanb@368 | 301 | if (e.getLocalName().equals("xml-element")) return e; |
alanb@368 | 302 | } |
alanb@368 | 303 | return null; |
alanb@368 | 304 | } |
alanb@368 | 305 | |
alanb@368 | 306 | /** |
alanb@368 | 307 | * Helper class to merge two different arrays of annotation objects. It merges annotations based on attribute |
alanb@368 | 308 | * <code>existing-annotations</code> in external customization file. |
alanb@368 | 309 | * <p/> |
alanb@368 | 310 | * We suppose that in the result array there wouldn't be two annotations of same type: |
alanb@368 | 311 | * annotation.annotationType().getName(); if there are found such annotations the one from reflection is |
alanb@368 | 312 | * considered overriden and is thrown away. |
alanb@368 | 313 | * <p/> |
alanb@368 | 314 | * The helper can work either with one and two dimensional array, but it can be used for two single Annotation |
alanb@368 | 315 | * objects; |
alanb@368 | 316 | */ |
alanb@368 | 317 | static abstract class Merger<T> { |
alanb@368 | 318 | |
alanb@368 | 319 | JavaWsdlMappingType reader; |
alanb@368 | 320 | |
alanb@368 | 321 | Merger(JavaWsdlMappingType r) { |
alanb@368 | 322 | this.reader = r; |
alanb@368 | 323 | } |
alanb@368 | 324 | |
alanb@368 | 325 | abstract T reflection(); |
alanb@368 | 326 | |
alanb@368 | 327 | abstract T external(); |
alanb@368 | 328 | |
alanb@368 | 329 | @SuppressWarnings("unchecked") |
alanb@368 | 330 | T merge() { |
alanb@368 | 331 | T reflection = reflection(); |
alanb@368 | 332 | if (reader == null) { |
alanb@368 | 333 | return reflection; |
alanb@368 | 334 | } |
alanb@368 | 335 | |
alanb@368 | 336 | T external = external(); |
alanb@368 | 337 | if (!MERGE.equals(reader.getExistingAnnotations())) { |
alanb@368 | 338 | return external; |
alanb@368 | 339 | } |
alanb@368 | 340 | |
alanb@368 | 341 | if (reflection instanceof Annotation) { |
alanb@368 | 342 | return (T) doMerge((Annotation) reflection, (Annotation) external); |
alanb@368 | 343 | } else if (reflection instanceof Annotation[][]) { |
alanb@368 | 344 | return (T) doMerge((Annotation[][]) reflection, (Annotation[][]) external); |
alanb@368 | 345 | } else { |
alanb@368 | 346 | return (T) doMerge((Annotation[]) reflection, (Annotation[]) external); |
alanb@368 | 347 | } |
alanb@368 | 348 | } |
alanb@368 | 349 | |
alanb@368 | 350 | private Annotation doMerge(Annotation reflection, Annotation external) { |
alanb@368 | 351 | return external != null ? external : reflection; |
alanb@368 | 352 | } |
alanb@368 | 353 | |
alanb@368 | 354 | private Annotation[][] doMerge(Annotation[][] reflection, Annotation[][] external) { |
alanb@368 | 355 | for (int i = 0; i < reflection.length; i++) { |
alanb@368 | 356 | reflection[i] = doMerge(reflection[i], external.length > i ? external[i] : null); |
alanb@368 | 357 | } |
alanb@368 | 358 | return reflection; |
alanb@368 | 359 | } |
alanb@368 | 360 | |
alanb@368 | 361 | private Annotation[] doMerge(Annotation[] annotations, Annotation[] externalAnnotations) { |
alanb@368 | 362 | HashMap<String, Annotation> mergeMap = new HashMap<String, Annotation>(); |
alanb@368 | 363 | if (annotations != null) { |
alanb@368 | 364 | for (Annotation reflectionAnnotation : annotations) { |
alanb@368 | 365 | mergeMap.put(reflectionAnnotation.annotationType().getName(), reflectionAnnotation); |
alanb@368 | 366 | } |
alanb@368 | 367 | } |
alanb@368 | 368 | |
alanb@368 | 369 | // overriding happens here, based on annotationType().getName() ... |
alanb@368 | 370 | if (externalAnnotations != null) { |
alanb@368 | 371 | for (Annotation externalAnnotation : externalAnnotations) { |
alanb@368 | 372 | mergeMap.put(externalAnnotation.annotationType().getName(), externalAnnotation); |
alanb@368 | 373 | } |
alanb@368 | 374 | } |
alanb@368 | 375 | Collection<Annotation> values = mergeMap.values(); |
alanb@368 | 376 | int size = values.size(); |
alanb@368 | 377 | return size == 0 ? null : values.toArray(new Annotation[size]); |
alanb@368 | 378 | } |
alanb@368 | 379 | |
alanb@368 | 380 | } |
alanb@368 | 381 | |
alanb@368 | 382 | static class Util { |
alanb@368 | 383 | |
alanb@368 | 384 | //private static final String DATABINDING_XSD = "com/sun/xml/internal/ws/model/jaxws-databinding.xsd"; |
alanb@368 | 385 | private static final String DATABINDING_XSD = "jaxws-databinding.xsd"; |
alanb@368 | 386 | //private static final String TRANSLATE_NAMESPACES_XSL = "/com/sun/xml/internal/ws/model/jaxws-databinding-translate-namespaces.xml"; |
alanb@368 | 387 | private static final String TRANSLATE_NAMESPACES_XSL = "jaxws-databinding-translate-namespaces.xml"; |
alanb@368 | 388 | |
alanb@368 | 389 | static Schema schema; |
alanb@368 | 390 | static JAXBContext jaxbContext; |
alanb@368 | 391 | |
alanb@368 | 392 | static { |
alanb@368 | 393 | SchemaFactory sf = SchemaFactory.newInstance("http://www.w3.org/2001/XMLSchema"); |
alanb@368 | 394 | try { |
alanb@368 | 395 | URL xsdUrl = getResource(); |
alanb@368 | 396 | if (xsdUrl != null) { |
alanb@368 | 397 | schema = sf.newSchema(xsdUrl); |
alanb@368 | 398 | } |
alanb@368 | 399 | } catch (SAXException e1) { |
alanb@368 | 400 | // e1.printStackTrace(); |
alanb@368 | 401 | } |
alanb@368 | 402 | |
alanb@368 | 403 | jaxbContext = createJaxbContext(false); |
alanb@368 | 404 | } |
alanb@368 | 405 | |
alanb@368 | 406 | private static URL getResource() { |
alanb@368 | 407 | ClassLoader classLoader = Util.class.getClassLoader(); |
alanb@368 | 408 | return classLoader != null ? classLoader.getResource(DATABINDING_XSD) : ClassLoader.getSystemResource(DATABINDING_XSD); |
alanb@368 | 409 | } |
alanb@368 | 410 | |
alanb@368 | 411 | private static JAXBContext createJaxbContext(boolean disableXmlSecurity) { |
alanb@368 | 412 | Class[] cls = {ObjectFactory.class}; |
alanb@368 | 413 | try { |
alanb@368 | 414 | if (disableXmlSecurity) { |
alanb@368 | 415 | Map<String, Object> properties = new HashMap<String, Object>(); |
alanb@368 | 416 | properties.put(JAXBRIContext.DISABLE_XML_SECURITY, disableXmlSecurity); |
alanb@368 | 417 | return JAXBContext.newInstance(cls, properties); |
alanb@368 | 418 | } else { |
alanb@368 | 419 | return JAXBContext.newInstance(cls); |
alanb@368 | 420 | } |
alanb@368 | 421 | } catch (JAXBException e) { |
alanb@368 | 422 | e.printStackTrace(); |
alanb@368 | 423 | return null; |
alanb@368 | 424 | } |
alanb@368 | 425 | } |
alanb@368 | 426 | |
alanb@368 | 427 | @SuppressWarnings("unchecked") |
alanb@368 | 428 | public static JavaWsdlMappingType read(Source src, boolean xsdValidation, boolean disableSecureXmlProcessing) throws IOException, JAXBException { |
alanb@368 | 429 | JAXBContext ctx = jaxbContext(disableSecureXmlProcessing); |
alanb@368 | 430 | try { |
alanb@368 | 431 | Unmarshaller um = ctx.createUnmarshaller(); |
alanb@368 | 432 | if (xsdValidation) { |
alanb@368 | 433 | if (schema == null) { |
alanb@368 | 434 | //TODO 0 warning for schema == null |
alanb@368 | 435 | } |
alanb@368 | 436 | um.setSchema(schema); |
alanb@368 | 437 | } |
alanb@368 | 438 | Object o = um.unmarshal(src); |
alanb@368 | 439 | return getJavaWsdlMapping(o); |
alanb@368 | 440 | } catch (JAXBException e) { |
alanb@368 | 441 | // throw new |
alanb@368 | 442 | // WebServiceException(WsDatabindingMessages.mappingFileCannotRead |
alanb@368 | 443 | // (src.getSystemId()), e); |
alanb@368 | 444 | URL url = new URL(src.getSystemId()); |
alanb@368 | 445 | Source s = new StreamSource(url.openStream()); |
alanb@368 | 446 | Unmarshaller um = ctx.createUnmarshaller(); |
alanb@368 | 447 | if (xsdValidation) { |
alanb@368 | 448 | if (schema == null) { |
alanb@368 | 449 | //TODO 0 warning for schema == null |
alanb@368 | 450 | } |
alanb@368 | 451 | um.setSchema(schema); |
alanb@368 | 452 | } |
alanb@368 | 453 | Object o = um.unmarshal(s); |
alanb@368 | 454 | return getJavaWsdlMapping(o); |
alanb@368 | 455 | } |
alanb@368 | 456 | } |
alanb@368 | 457 | |
alanb@368 | 458 | private static JAXBContext jaxbContext(boolean disableSecureXmlProcessing) { |
alanb@368 | 459 | // as it is supposed to have security enabled in most cases, we create and don't cache |
alanb@368 | 460 | // "insecure" JAXBContext - these should be corner cases |
alanb@368 | 461 | return disableSecureXmlProcessing ? createJaxbContext(true) : jaxbContext; |
alanb@368 | 462 | } |
alanb@368 | 463 | |
alanb@368 | 464 | public static JavaWsdlMappingType transformAndRead(Source src, boolean disableSecureXmlProcessing) throws TransformerException, JAXBException { |
alanb@368 | 465 | Source xsl = new StreamSource(Util.class.getResourceAsStream(TRANSLATE_NAMESPACES_XSL)); |
alanb@368 | 466 | JAXBResult result = new JAXBResult(jaxbContext(disableSecureXmlProcessing)); |
alanb@368 | 467 | TransformerFactory tf = XmlUtil.newTransformerFactory(!disableSecureXmlProcessing); |
alanb@368 | 468 | Transformer transformer = tf.newTemplates(xsl).newTransformer(); |
alanb@368 | 469 | transformer.transform(src, result); |
alanb@368 | 470 | return getJavaWsdlMapping(result.getResult()); |
alanb@368 | 471 | } |
alanb@368 | 472 | |
alanb@368 | 473 | |
alanb@368 | 474 | static JavaWsdlMappingType getJavaWsdlMapping(Object o) { |
alanb@368 | 475 | Object val = (o instanceof JAXBElement) ? ((JAXBElement) o).getValue() : o; |
alanb@368 | 476 | if (val instanceof JavaWsdlMappingType) return (JavaWsdlMappingType) val; |
alanb@368 | 477 | // else if (val instanceof JavaWsdlMappings) |
alanb@368 | 478 | // for (JavaWsdlMappingType m: ((JavaWsdlMappings) val).getJavaWsdlMapping()) |
alanb@368 | 479 | // if (seiName.equals(m.javaTypeName)) return m; |
alanb@368 | 480 | return null; |
alanb@368 | 481 | } |
alanb@368 | 482 | |
alanb@368 | 483 | static <T> T findInstanceOf(Class<T> type, List<Object> objects) { |
alanb@368 | 484 | for (Object o : objects) { |
alanb@368 | 485 | if (type.isInstance(o)) { |
alanb@368 | 486 | return type.cast(o); |
alanb@368 | 487 | } |
alanb@368 | 488 | } |
alanb@368 | 489 | return null; |
alanb@368 | 490 | } |
alanb@368 | 491 | |
alanb@368 | 492 | static public <T> T annotation(JavaWsdlMappingType jwse, Class<T> anntype) { |
alanb@368 | 493 | if (jwse == null || jwse.getClassAnnotation() == null) { |
alanb@368 | 494 | return null; |
alanb@368 | 495 | } |
alanb@368 | 496 | return findInstanceOf(anntype, jwse.getClassAnnotation()); |
alanb@368 | 497 | } |
alanb@368 | 498 | |
alanb@368 | 499 | static public <T> T annotation(JavaMethod jm, Class<T> anntype) { |
alanb@368 | 500 | if (jm == null || jm.getMethodAnnotation() == null) { |
alanb@368 | 501 | return null; |
alanb@368 | 502 | } |
alanb@368 | 503 | return findInstanceOf(anntype, jm.getMethodAnnotation()); |
alanb@368 | 504 | } |
alanb@368 | 505 | |
alanb@368 | 506 | static public <T> T annotation(JavaParam jp, Class<T> anntype) { |
alanb@368 | 507 | if (jp == null || jp.getParamAnnotation() == null) { |
alanb@368 | 508 | return null; |
alanb@368 | 509 | } |
alanb@368 | 510 | return findInstanceOf(anntype, jp.getParamAnnotation()); |
alanb@368 | 511 | } |
alanb@368 | 512 | |
alanb@368 | 513 | static public Element[] annotation(JavaMethod jm) { |
alanb@368 | 514 | if (jm == null || jm.getMethodAnnotation() == null) { |
alanb@368 | 515 | return null; |
alanb@368 | 516 | } |
alanb@368 | 517 | return findElements(jm.getMethodAnnotation()); |
alanb@368 | 518 | } |
alanb@368 | 519 | |
alanb@368 | 520 | static public Element[] annotation(JavaParam jp) { |
alanb@368 | 521 | if (jp == null || jp.getParamAnnotation() == null) { |
alanb@368 | 522 | return null; |
alanb@368 | 523 | } |
alanb@368 | 524 | return findElements(jp.getParamAnnotation()); |
alanb@368 | 525 | } |
alanb@368 | 526 | |
alanb@368 | 527 | private static Element[] findElements(List<Object> objects) { |
alanb@368 | 528 | List<Element> elems = new ArrayList<Element>(); |
alanb@368 | 529 | for (Object o : objects) { |
alanb@368 | 530 | if (o instanceof Element) { |
alanb@368 | 531 | elems.add((Element) o); |
alanb@368 | 532 | } |
alanb@368 | 533 | } |
alanb@368 | 534 | return elems.toArray(new Element[elems.size()]); |
alanb@368 | 535 | } |
alanb@368 | 536 | |
alanb@368 | 537 | static String documentRootNamespace(Source src, boolean disableSecureXmlProcessing) throws XMLStreamException { |
alanb@368 | 538 | XMLInputFactory factory; |
alanb@368 | 539 | factory = XmlUtil.newXMLInputFactory(!disableSecureXmlProcessing); |
alanb@368 | 540 | XMLStreamReader streamReader = factory.createXMLStreamReader(src); |
alanb@368 | 541 | XMLStreamReaderUtil.nextElementContent(streamReader); |
alanb@368 | 542 | String namespaceURI = streamReader.getName().getNamespaceURI(); |
alanb@368 | 543 | XMLStreamReaderUtil.close(streamReader); |
alanb@368 | 544 | return namespaceURI; |
alanb@368 | 545 | } |
alanb@368 | 546 | } |
alanb@368 | 547 | |
alanb@368 | 548 | |
alanb@368 | 549 | } |