src/share/jaxws_classes/com/sun/tools/internal/xjc/reader/xmlschema/bindinfo/BindInfo.java

Tue, 09 Apr 2013 14:51:13 +0100

author
alanb
date
Tue, 09 Apr 2013 14:51:13 +0100
changeset 368
0989ad8c0860
parent 286
f50545b5e2f1
child 637
9c07ef4934dd
permissions
-rw-r--r--

8010393: Update JAX-WS RI to 2.2.9-b12941
Reviewed-by: alanb, erikj
Contributed-by: miroslav.kos@oracle.com, martin.grebac@oracle.com

ohair@286 1 /*
ohair@286 2 * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
ohair@286 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
ohair@286 4 *
ohair@286 5 * This code is free software; you can redistribute it and/or modify it
ohair@286 6 * under the terms of the GNU General Public License version 2 only, as
ohair@286 7 * published by the Free Software Foundation. Oracle designates this
ohair@286 8 * particular file as subject to the "Classpath" exception as provided
ohair@286 9 * by Oracle in the LICENSE file that accompanied this code.
ohair@286 10 *
ohair@286 11 * This code is distributed in the hope that it will be useful, but WITHOUT
ohair@286 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
ohair@286 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
ohair@286 14 * version 2 for more details (a copy is included in the LICENSE file that
ohair@286 15 * accompanied this code).
ohair@286 16 *
ohair@286 17 * You should have received a copy of the GNU General Public License version
ohair@286 18 * 2 along with this work; if not, write to the Free Software Foundation,
ohair@286 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
ohair@286 20 *
ohair@286 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
ohair@286 22 * or visit www.oracle.com if you need additional information or have any
ohair@286 23 * questions.
ohair@286 24 */
ohair@286 25
ohair@286 26 package com.sun.tools.internal.xjc.reader.xmlschema.bindinfo;
ohair@286 27
ohair@286 28 import java.io.FilterWriter;
ohair@286 29 import java.io.IOException;
ohair@286 30 import java.io.StringWriter;
ohair@286 31 import java.io.Writer;
ohair@286 32 import java.util.ArrayList;
ohair@286 33 import java.util.Iterator;
ohair@286 34 import java.util.List;
ohair@286 35
ohair@286 36 import javax.xml.bind.JAXBContext;
ohair@286 37 import javax.xml.bind.JAXBException;
alanb@368 38 import javax.xml.bind.Unmarshaller;
ohair@286 39 import javax.xml.bind.annotation.XmlAnyElement;
ohair@286 40 import javax.xml.bind.annotation.XmlElement;
ohair@286 41 import javax.xml.bind.annotation.XmlMixed;
ohair@286 42 import javax.xml.bind.annotation.XmlRootElement;
ohair@286 43 import javax.xml.bind.annotation.XmlType;
ohair@286 44 import javax.xml.transform.Transformer;
ohair@286 45 import javax.xml.transform.TransformerException;
ohair@286 46 import javax.xml.transform.dom.DOMSource;
ohair@286 47 import javax.xml.transform.stream.StreamResult;
ohair@286 48
ohair@286 49 import com.sun.codemodel.internal.JDocComment;
alanb@368 50 import com.sun.xml.internal.bind.v2.WellKnownNamespace;
ohair@286 51 import com.sun.tools.internal.xjc.SchemaCache;
ohair@286 52 import com.sun.tools.internal.xjc.model.CCustomizations;
ohair@286 53 import com.sun.tools.internal.xjc.model.CPluginCustomization;
ohair@286 54 import com.sun.tools.internal.xjc.model.Model;
ohair@286 55 import com.sun.tools.internal.xjc.reader.Ring;
ohair@286 56 import com.sun.tools.internal.xjc.reader.xmlschema.BGMBuilder;
ohair@286 57 import com.sun.xml.internal.bind.annotation.XmlLocation;
ohair@286 58 import com.sun.xml.internal.bind.marshaller.MinimumEscapeHandler;
ohair@286 59 import com.sun.xml.internal.xsom.XSComponent;
ohair@286 60
ohair@286 61 import org.w3c.dom.Element;
ohair@286 62 import org.xml.sax.Locator;
ohair@286 63
ohair@286 64 /**
ohair@286 65 * Container for customization declarations.
ohair@286 66 *
ohair@286 67 * We use JAXB ourselves and parse this object from "xs:annotation".
ohair@286 68 *
ohair@286 69 * @author
ohair@286 70 * Kohsuke Kawaguchi (kohsuke,kawaguchi@sun.com)
ohair@286 71 */
alanb@368 72 @XmlRootElement(namespace= WellKnownNamespace.XML_SCHEMA,name="annotation")
ohair@286 73 @XmlType(namespace=WellKnownNamespace.XML_SCHEMA,name="foobar")
ohair@286 74 public final class BindInfo implements Iterable<BIDeclaration> {
ohair@286 75
ohair@286 76 private BGMBuilder builder;
ohair@286 77
ohair@286 78 @XmlLocation
ohair@286 79 private Locator location;
ohair@286 80
ohair@286 81 /**
ohair@286 82 * Documentation taken from &lt;xs:documentation>s.
ohair@286 83 */
ohair@286 84 @XmlElement(namespace=WellKnownNamespace.XML_SCHEMA)
ohair@286 85 private Documentation documentation;
ohair@286 86
ohair@286 87 /**
ohair@286 88 * Returns true if this {@link BindInfo} doesn't contain any useful
ohair@286 89 * information.
ohair@286 90 *
ohair@286 91 * This flag is used to discard unused {@link BindInfo}s early to save memory footprint.
ohair@286 92 */
ohair@286 93 public boolean isPointless() {
ohair@286 94 if(size()>0) return false;
ohair@286 95 if(documentation!=null && !documentation.contents.isEmpty())
ohair@286 96 return false;
ohair@286 97
ohair@286 98 return true;
ohair@286 99 }
ohair@286 100
ohair@286 101 private static final class Documentation {
ohair@286 102 @XmlAnyElement
ohair@286 103 @XmlMixed
ohair@286 104 List<Object> contents = new ArrayList<Object>();
ohair@286 105
ohair@286 106 void addAll(Documentation rhs) {
ohair@286 107 if(rhs==null) return;
ohair@286 108
ohair@286 109 if(contents==null)
ohair@286 110 contents = new ArrayList<Object>();
ohair@286 111 if(!contents.isEmpty())
ohair@286 112 contents.add("\n\n");
ohair@286 113 contents.addAll(rhs.contents);
ohair@286 114 }
ohair@286 115 }
ohair@286 116
ohair@286 117 /** list of individual declarations. */
ohair@286 118 private final List<BIDeclaration> decls = new ArrayList<BIDeclaration>();
ohair@286 119
ohair@286 120 private static final class AppInfo {
ohair@286 121 /**
ohair@286 122 * Receives {@link BIDeclaration}s and other DOMs.
ohair@286 123 */
ohair@286 124 @XmlAnyElement(lax=true,value=DomHandlerEx.class)
ohair@286 125 List<Object> contents = new ArrayList<Object>();
ohair@286 126
ohair@286 127 public void addTo(BindInfo bi) {
ohair@286 128 if(contents==null) return;
ohair@286 129
ohair@286 130 for (Object o : contents) {
ohair@286 131 if(o instanceof BIDeclaration)
ohair@286 132 bi.addDecl((BIDeclaration)o);
ohair@286 133 // this is really PITA! I can't get the source location
ohair@286 134 if(o instanceof DomHandlerEx.DomAndLocation) {
ohair@286 135 DomHandlerEx.DomAndLocation e = (DomHandlerEx.DomAndLocation)o;
ohair@286 136 String nsUri = e.element.getNamespaceURI();
ohair@286 137 if(nsUri==null || nsUri.equals("")
ohair@286 138 || nsUri.equals(WellKnownNamespace.XML_SCHEMA))
ohair@286 139 continue; // this is definitely not a customization
ohair@286 140 bi.addDecl(new BIXPluginCustomization(e.element,e.loc));
ohair@286 141 }
ohair@286 142 }
ohair@286 143 }
ohair@286 144 }
ohair@286 145
ohair@286 146
ohair@286 147 // only used by JAXB
ohair@286 148 @XmlElement(namespace=WellKnownNamespace.XML_SCHEMA)
ohair@286 149 void setAppinfo(AppInfo aib) {
ohair@286 150 aib.addTo(this);
ohair@286 151 }
ohair@286 152
ohair@286 153
ohair@286 154
ohair@286 155 /**
ohair@286 156 * Gets the location of this annotation in the source file.
ohair@286 157 *
ohair@286 158 * @return
ohair@286 159 * If the declarations are in fact specified in the source
ohair@286 160 * code, a non-null valid object will be returned.
ohair@286 161 * If this BindInfo is generated internally by XJC, then
ohair@286 162 * null will be returned.
ohair@286 163 */
ohair@286 164 public Locator getSourceLocation() { return location; }
ohair@286 165
ohair@286 166
ohair@286 167 private XSComponent owner;
ohair@286 168 /**
ohair@286 169 * Sets the owner schema component and a reference to BGMBuilder.
ohair@286 170 * This method is called from the BGMBuilder before
ohair@286 171 * any BIDeclaration inside it is used.
ohair@286 172 */
ohair@286 173 public void setOwner( BGMBuilder _builder, XSComponent _owner ) {
ohair@286 174 this.owner = _owner;
ohair@286 175 this.builder = _builder;
ohair@286 176 for (BIDeclaration d : decls)
ohair@286 177 d.onSetOwner();
ohair@286 178 }
ohair@286 179 public XSComponent getOwner() { return owner; }
ohair@286 180
ohair@286 181 /**
ohair@286 182 * Back pointer to the BGMBuilder which is building
ohair@286 183 * a BGM from schema components including this customization.
ohair@286 184 */
ohair@286 185 public BGMBuilder getBuilder() { return builder; }
ohair@286 186
ohair@286 187 /** Adds a new declaration. */
ohair@286 188 public void addDecl( BIDeclaration decl ) {
ohair@286 189 if(decl==null) throw new IllegalArgumentException();
ohair@286 190 decl.setParent(this);
ohair@286 191 decls.add(decl);
ohair@286 192 }
ohair@286 193
ohair@286 194 /**
ohair@286 195 * Gets the first declaration with a given name, or null
ohair@286 196 * if none is found.
ohair@286 197 */
ohair@286 198 public <T extends BIDeclaration>
ohair@286 199 T get( Class<T> kind ) {
ohair@286 200 for( BIDeclaration decl : decls ) {
ohair@286 201 if( kind.isInstance(decl) )
ohair@286 202 return kind.cast(decl);
ohair@286 203 }
ohair@286 204 return null; // not found
ohair@286 205 }
ohair@286 206
ohair@286 207 /**
ohair@286 208 * Gets all the declarations
ohair@286 209 */
ohair@286 210 public BIDeclaration[] getDecls() {
ohair@286 211 return decls.toArray(new BIDeclaration[decls.size()]);
ohair@286 212 }
ohair@286 213
ohair@286 214 /**
ohair@286 215 * Gets the documentation parsed from &lt;xs:documentation>s.
ohair@286 216 * The returned collection is to be added to {@link JDocComment#append(Object)}.
ohair@286 217 * @return maybe null.
ohair@286 218 */
ohair@286 219 public String getDocumentation() {
ohair@286 220 // TODO: FIXME: correctly turn individual items to String including DOM
ohair@286 221 if(documentation==null || documentation.contents==null) return null;
ohair@286 222
ohair@286 223 StringBuilder buf = new StringBuilder();
ohair@286 224 for (Object c : documentation.contents) {
ohair@286 225 if(c instanceof String) {
ohair@286 226 buf.append(c.toString());
ohair@286 227 }
ohair@286 228 if(c instanceof Element) {
ohair@286 229 Transformer t = builder.getIdentityTransformer();
ohair@286 230 StringWriter w = new StringWriter();
ohair@286 231 try {
ohair@286 232 Writer fw = new FilterWriter(w) {
ohair@286 233 char[] buf = new char[1];
ohair@286 234
ohair@286 235 public void write(int c) throws IOException {
ohair@286 236 buf[0] = (char)c;
ohair@286 237 write(buf,0,1);
ohair@286 238 }
ohair@286 239
ohair@286 240 public void write(char[] cbuf, int off, int len) throws IOException {
ohair@286 241 MinimumEscapeHandler.theInstance.escape(cbuf,off,len,false,out);
ohair@286 242 }
ohair@286 243
ohair@286 244 public void write(String str, int off, int len) throws IOException {
ohair@286 245 write(str.toCharArray(),off,len);
ohair@286 246 }
ohair@286 247 };
ohair@286 248 t.transform(new DOMSource((Element)c),new StreamResult(fw));
ohair@286 249 } catch (TransformerException e) {
ohair@286 250 throw new Error(e); // impossible
ohair@286 251 }
ohair@286 252 buf.append("\n<pre>\n");
ohair@286 253 buf.append(w);
ohair@286 254 buf.append("\n</pre>\n");
ohair@286 255 }
ohair@286 256 }
ohair@286 257 return buf.toString();
ohair@286 258 }
ohair@286 259
ohair@286 260 /**
ohair@286 261 * Merges all the declarations inside the given BindInfo
ohair@286 262 * to this BindInfo.
ohair@286 263 */
ohair@286 264 public void absorb( BindInfo bi ) {
ohair@286 265 for( BIDeclaration d : bi )
ohair@286 266 d.setParent(this);
ohair@286 267 this.decls.addAll( bi.decls );
ohair@286 268
ohair@286 269 if(this.documentation==null)
ohair@286 270 this.documentation = bi.documentation;
ohair@286 271 else
ohair@286 272 this.documentation.addAll(bi.documentation);
ohair@286 273 }
ohair@286 274
ohair@286 275 /** Gets the number of declarations. */
ohair@286 276 public int size() { return decls.size(); }
ohair@286 277
ohair@286 278 public BIDeclaration get( int idx ) { return decls.get(idx); }
ohair@286 279
ohair@286 280 public Iterator<BIDeclaration> iterator() {
ohair@286 281 return decls.iterator();
ohair@286 282 }
ohair@286 283
ohair@286 284 /**
ohair@286 285 * Gets the list of {@link CPluginCustomization}s from this.
ohair@286 286 *
ohair@286 287 * <p>
ohair@286 288 * Note that calling this method marks all those plug-in customizations
ohair@286 289 * as 'used'. So call it only when it's really necessary.
ohair@286 290 */
ohair@286 291 public CCustomizations toCustomizationList() {
ohair@286 292 CCustomizations r=null;
ohair@286 293 for( BIDeclaration d : this ) {
ohair@286 294 if(d instanceof BIXPluginCustomization) {
ohair@286 295 BIXPluginCustomization pc = (BIXPluginCustomization) d;
ohair@286 296 pc.markAsAcknowledged();
ohair@286 297 if(!Ring.get(Model.class).options.pluginURIs.contains(pc.getName().getNamespaceURI()))
ohair@286 298 continue; // this isn't a plugin customization
ohair@286 299 if(r==null)
ohair@286 300 r = new CCustomizations();
ohair@286 301 r.add(new CPluginCustomization(pc.element,pc.getLocation()));
ohair@286 302 }
ohair@286 303 }
ohair@286 304
ohair@286 305 if(r==null) r = CCustomizations.EMPTY;
ohair@286 306 return new CCustomizations(r);
ohair@286 307 }
ohair@286 308 /** An instance with the empty contents. */
ohair@286 309 public final static BindInfo empty = new BindInfo();
ohair@286 310
ohair@286 311 /**
ohair@286 312 * Lazily prepared {@link JAXBContext}.
ohair@286 313 */
alanb@368 314 private static volatile JAXBContext customizationContext;
ohair@286 315
alanb@368 316 public static JAXBContext getCustomizationContext() {
alanb@368 317 try {
alanb@368 318 if (customizationContext == null) {
alanb@368 319 synchronized (BindInfo.class) {
alanb@368 320 if (customizationContext == null) {
alanb@368 321 customizationContext = JAXBContext.newInstance(
alanb@368 322 BindInfo.class, // for xs:annotation
alanb@368 323 BIClass.class,
alanb@368 324 BIConversion.User.class,
alanb@368 325 BIConversion.UserAdapter.class,
alanb@368 326 BIDom.class,
alanb@368 327 BIFactoryMethod.class,
alanb@368 328 BIInlineBinaryData.class,
alanb@368 329 BIXDom.class,
alanb@368 330 BIXSubstitutable.class,
alanb@368 331 BIEnum.class,
alanb@368 332 BIEnumMember.class,
alanb@368 333 BIGlobalBinding.class,
alanb@368 334 BIProperty.class,
alanb@368 335 BISchemaBinding.class);
alanb@368 336 }
alanb@368 337 }
ohair@286 338 }
alanb@368 339 return customizationContext;
alanb@368 340 } catch (JAXBException e) {
alanb@368 341 throw new AssertionError(e);
alanb@368 342 }
alanb@368 343 }
alanb@368 344
alanb@368 345 public static Unmarshaller getCustomizationUnmarshaller() {
alanb@368 346 try {
alanb@368 347 return getCustomizationContext().createUnmarshaller();
alanb@368 348 } catch (JAXBException e) {
alanb@368 349 throw new AssertionError(e);
ohair@286 350 }
ohair@286 351 }
ohair@286 352
ohair@286 353 /**
ohair@286 354 * Lazily parsed schema for the binding file.
ohair@286 355 */
ohair@286 356 public static final SchemaCache bindingFileSchema = new SchemaCache(BindInfo.class.getResource("binding.xsd"));
ohair@286 357 }

mercurial