1 16 17 package org.enhydra.shark.asap.util; 18 19 import org.apache.axis.AxisFault; 20 import org.apache.axis.Constants; 21 import org.apache.axis.components.logger.LogFactory; 22 import org.apache.axis.description.FieldDesc; 23 import org.apache.axis.description.TypeDesc; 24 import org.apache.axis.encoding.SerializationContext; 25 import org.apache.axis.encoding.Serializer; 26 import org.apache.axis.message.MessageElement; 27 import org.apache.axis.utils.BeanPropertyDescriptor; 28 import org.apache.axis.utils.BeanUtils; 29 import org.apache.axis.utils.Messages; 30 import org.apache.axis.utils.FieldPropertyDescriptor; 31 import org.apache.axis.wsdl.fromJava.Types; 32 import org.apache.axis.wsdl.symbolTable.SchemaUtils; 33 import org.apache.commons.logging.Log; 34 import org.w3c.dom.Element ; 35 import org.xml.sax.Attributes ; 36 import org.xml.sax.helpers.AttributesImpl ; 37 import org.apache.axis.encoding.ser.*; 38 39 import javax.xml.namespace.QName ; 40 import java.io.IOException ; 41 import java.io.Serializable ; 42 import java.lang.reflect.InvocationTargetException ; 43 import java.lang.reflect.Modifier ; 44 import java.util.List ; 45 import java.lang.reflect.InvocationTargetException ; 46 import java.lang.reflect.Method ; 47 48 55 public class BeanSerializerShark implements Serializer, Serializable { 56 57 protected static Log log = 58 LogFactory.getLog(BeanSerializerShark.class.getName()); 59 60 QName xmlType; 61 Class javaType; 62 63 protected BeanPropertyDescriptor[] propertyDescriptor = null; 64 protected TypeDesc typeDesc = null; 65 66 67 public BeanSerializerShark(Class javaType, QName xmlType) { 69 this(javaType, xmlType, TypeDesc.getTypeDescForClass(javaType)); 70 } 71 72 public BeanSerializerShark(Class javaType, QName xmlType, TypeDesc typeDesc) { 74 this(javaType, xmlType, typeDesc, null); 75 76 if (typeDesc != null) { 77 propertyDescriptor = typeDesc.getPropertyDescriptors(); 78 } else { 79 propertyDescriptor = BeanUtils.getPd(javaType, null); 80 } 81 } 82 83 public BeanSerializerShark(Class javaType, QName xmlType, TypeDesc typeDesc, 85 BeanPropertyDescriptor[] propertyDescriptor) { 86 this.xmlType = xmlType; 87 this.javaType = javaType; 88 this.typeDesc = typeDesc; 89 this.propertyDescriptor = propertyDescriptor; 90 } 91 92 99 public void serialize(QName name, Attributes attributes, 100 Object value, SerializationContext context) 101 throws IOException 102 { 103 Attributes beanAttrs = getObjectAttributes(value, attributes, context); 107 108 String encodingStyle = context.getEncodingStyle(); 110 boolean isEncoded = Constants.isSOAP_ENC(encodingStyle); 111 112 boolean suppressElement = !context.isEncoded() && 114 name.getNamespaceURI().equals("") && 115 name.getLocalPart().equals("any"); 116 117 boolean grpElement = name.toString().endsWith("Group"); 118 suppressElement |= grpElement; 119 120 if (!suppressElement) 121 context.startElement(name, beanAttrs); 122 123 try { 124 for (int i=0; i<propertyDescriptor.length; i++) { 126 String propName = propertyDescriptor[i].getName(); 127 if (propName.equals("class")) 128 continue; 129 QName qname = null; 130 QName xmlType = null; 131 boolean isOmittable = false; 132 133 138 if (typeDesc != null) { 139 FieldDesc field = typeDesc.getFieldByName(propName); 140 if (field != null) { 141 if (!field.isElement()) 142 continue; 143 144 if (isEncoded) { 148 qname = new QName ( 149 field.getXmlName().getLocalPart()); 150 } else { 151 qname = field.getXmlName(); 152 } 153 isOmittable = field.isMinOccursZero(); 154 xmlType = field.getXmlType(); 155 } 156 } 157 158 if (qname == null) { 159 qname = new QName (isEncoded ? "" : name.getNamespaceURI(), 160 propName); 161 } 162 163 if (xmlType == null) { 164 xmlType = context.getQNameForClass(propertyDescriptor[i].getType()); 166 } 167 168 if(propertyDescriptor[i].isReadable()) { 170 if (!propertyDescriptor[i].isIndexed()) { 171 Object propValue = 173 propertyDescriptor[i].get(value); 174 if (propValue == null && 178 isOmittable && 179 !isEncoded) 180 continue; 181 182 if (null == propValue && qname.toString().endsWith("Group")) { 183 System.err.println("\telemQName:"+ qname +" contains 'Group' not appending nil"); 184 continue; 185 } 186 context.serialize(qname, 187 null, 188 propValue, 189 xmlType, 190 true, 191 null); 192 } else { 193 int j=0; 195 while(j >= 0) { 196 Object propValue = null; 197 try { 198 propValue = 199 propertyDescriptor[i].get(value, j); 200 j++; 201 } catch (Exception e) { 202 j = -1; 203 } 204 if (j >= 0) { 205 context.serialize(qname, null, 206 propValue, xmlType, 207 true, null); 208 } 209 } 210 } 211 } 212 } 213 214 BeanPropertyDescriptor anyDesc = typeDesc == null ? null : 215 typeDesc.getAnyDesc(); 216 if (anyDesc != null) { 217 Object anyVal = anyDesc.get(value); 220 if (anyVal != null && anyVal instanceof MessageElement[]) { 221 MessageElement [] anyContent = (MessageElement[])anyVal; 222 for (int i = 0; i < anyContent.length; i++) { 223 MessageElement element = anyContent[i]; 224 element.output(context); 225 } 226 } 227 } 228 } catch (InvocationTargetException ite) { 229 Throwable target = ite.getTargetException(); 230 log.error(Messages.getMessage("exception00"), target); 231 throw new IOException (target.toString()); 232 } catch (Exception e) { 233 log.error(Messages.getMessage("exception00"), e); 234 throw new IOException (e.toString()); 235 } 236 237 if (!suppressElement) 238 context.endElement(); 239 } 240 241 242 243 public String getMechanismType() { return Constants.AXIS_SAX; } 244 245 256 public Element writeSchema(Class javaType, Types types) throws Exception { 257 258 Element complexType = types.createElement("complexType"); 260 261 Element e = null; 263 Class superClass = javaType.getSuperclass(); 264 BeanPropertyDescriptor[] superPd = null; 265 List stopClasses = types.getStopClasses(); 266 if (superClass != null && 267 superClass != java.lang.Object .class && 268 superClass != java.lang.Exception .class && 269 superClass != java.lang.Throwable .class && 270 superClass != java.rmi.RemoteException .class && 271 superClass != org.apache.axis.AxisFault.class && 272 (stopClasses == null || 273 !(stopClasses.contains(superClass.getName()))) ) { 274 String base = types.writeType(superClass); 276 Element complexContent = types.createElement("complexContent"); 277 complexType.appendChild(complexContent); 278 Element extension = types.createElement("extension"); 279 complexContent.appendChild(extension); 280 extension.setAttribute("base", base); 281 e = extension; 282 TypeDesc superTypeDesc = TypeDesc.getTypeDescForClass(superClass); 284 if (superTypeDesc != null) { 285 superPd = superTypeDesc.getPropertyDescriptors(); 286 } else { 287 superPd = BeanUtils.getPd(superClass, null); 288 } 289 } else { 290 e = complexType; 291 } 292 293 Element all = types.createElement("sequence"); 301 e.appendChild(all); 302 303 if (Modifier.isAbstract(javaType.getModifiers())) { 304 complexType.setAttribute("abstract", "true"); 305 } 306 307 for (int i=0; i<propertyDescriptor.length; i++) { 309 String propName = propertyDescriptor[i].getName(); 310 311 boolean writeProperty = true; 313 if (propName.equals("class")) { 314 writeProperty = false; 315 } 316 317 if (superPd != null && writeProperty) { 320 for (int j=0; j<superPd.length && writeProperty; j++) { 321 if (propName.equals(superPd[j].getName())) { 322 writeProperty = false; 323 } 324 } 325 } 326 if (!writeProperty) { 327 continue; 328 } 329 330 335 if (typeDesc != null) { 336 Class fieldType = propertyDescriptor[i].getType(); 337 FieldDesc field = typeDesc.getFieldByName(propName); 338 339 if (field != null) { 340 QName qname = field.getXmlName(); 341 QName fieldXmlType = field.getXmlType(); 342 boolean isAnonymous = fieldXmlType != null && fieldXmlType.getLocalPart().startsWith(">"); 343 344 if (qname != null) { 345 350 propName = qname.getLocalPart(); 352 } 353 if (!field.isElement()) { 354 writeAttribute(types, 355 propName, 356 fieldType, 357 fieldXmlType, 358 complexType); 359 } else { 360 writeField(types, 361 propName, 362 fieldXmlType, 363 fieldType, 364 propertyDescriptor[i].isIndexed(), 365 field.isMinOccursZero(), 366 all, isAnonymous); 367 } 368 } else { 369 writeField(types, 370 propName, 371 null, 372 fieldType, 373 propertyDescriptor[i].isIndexed(), false, all, false); 374 } 375 } else { 376 boolean done = false; 377 if(propertyDescriptor[i] instanceof FieldPropertyDescriptor){ 378 FieldPropertyDescriptor fpd = (FieldPropertyDescriptor) propertyDescriptor[i]; 379 Class clazz = fpd.getField().getType(); 380 if(types.getTypeQName(clazz)!=null) { 381 writeField(types, 382 propName, 383 null, 384 clazz, 385 false, false, all, false); 386 387 done = true; 388 } 389 } 390 if(!done) { 391 writeField(types, 392 propName, 393 null, 394 propertyDescriptor[i].getType(), 395 propertyDescriptor[i].isIndexed(), false, all, false); 396 } 397 398 } 399 } 400 401 return complexType; 403 } 404 405 415 protected void writeField(Types types, 416 String fieldName, 417 QName xmlType, 418 Class fieldType, 419 boolean isUnbounded, 420 boolean isOmittable, 421 Element where, 422 boolean isAnonymous) throws Exception { 423 Element elem; 424 if (isAnonymous) { 425 elem = types.createElementWithAnonymousType(fieldName, 426 fieldType, isOmittable, where.getOwnerDocument()); 427 } else { 428 if (!SchemaUtils.isSimpleSchemaType(xmlType) && Types.isArray(fieldType)) { 429 xmlType = null; 430 } 431 432 String elementType = types.writeType(fieldType, xmlType); 433 434 if (elementType == null) { 435 QName anyQN = Constants.XSD_ANYTYPE; 437 String prefix = types.getNamespaces().getCreatePrefix(anyQN.getNamespaceURI()); 438 elementType = prefix + ":" + anyQN.getLocalPart(); 439 } 440 441 elem = types.createElement(fieldName, 442 elementType, 443 types.isNullable(fieldType), 444 isOmittable, 445 where.getOwnerDocument()); 446 } 447 448 if (isUnbounded) { 449 elem.setAttribute("maxOccurs", "unbounded"); 450 } 451 452 where.appendChild(elem); 453 } 454 455 462 protected void writeAttribute(Types types, 463 String fieldName, 464 Class fieldType, 465 QName fieldXmlType, 466 Element where) throws Exception { 467 468 if (!types.isAcceptableAsAttribute(fieldType)) { 470 throw new AxisFault(Messages.getMessage("AttrNotSimpleType00", 471 fieldName, 472 fieldType.getName())); 473 } 474 Element elem = types.createAttributeElement(fieldName, 475 fieldType, fieldXmlType, 476 false, 477 where.getOwnerDocument()); 478 where.appendChild(elem); 479 } 480 481 489 protected Attributes getObjectAttributes(Object value, 490 Attributes attributes, 491 SerializationContext context) { 492 493 if (typeDesc == null || !typeDesc.hasAttributes()) 494 return attributes; 495 496 AttributesImpl attrs; 497 if (attributes == null) { 498 attrs = new AttributesImpl (); 499 } else if (attributes instanceof AttributesImpl ) { 500 attrs = (AttributesImpl )attributes; 501 } else { 502 attrs = new AttributesImpl (attributes); 503 } 504 505 try { 506 for (int i=0; i<propertyDescriptor.length; i++) { 509 String propName = propertyDescriptor[i].getName(); 510 if (propName.equals("class")) 511 continue; 512 513 FieldDesc field = typeDesc.getFieldByName(propName); 514 if (field == null || field.isElement()) 516 continue; 517 518 QName qname = field.getXmlName(); 519 if (qname == null) { 520 qname = new QName ("", propName); 521 } 522 523 if (propertyDescriptor[i].isReadable() && 524 !propertyDescriptor[i].isIndexed()) { 525 Object propValue = propertyDescriptor[i].get(value); 527 if (qname.equals(new QName (Constants.URI_SOAP11_ENV, Constants.ATTR_MUST_UNDERSTAND))) { 529 if (propValue.equals(Boolean.TRUE)) { 530 propValue = "1"; 531 } else if (propValue.equals(Boolean.FALSE)) { 532 propValue = "0"; 533 } 534 } 535 if (propValue != null) { 540 setAttributeProperty(propValue, 541 qname, 542 field.getXmlType(), 543 attrs, 544 context); 545 } 546 } 547 } 548 } catch (Exception e) { 549 return attrs; 551 } 552 553 return attrs; 554 } 555 556 private void setAttributeProperty(Object propValue, 557 QName qname, 558 QName xmlType, AttributesImpl attrs, 559 SerializationContext context) throws Exception { 560 561 String namespace = qname.getNamespaceURI(); 562 String localName = qname.getLocalPart(); 563 564 if (attrs.getIndex(namespace, localName) != -1) { 570 return; 571 } 572 573 String propString = context.getValueAsString(propValue, xmlType); 574 575 attrs.addAttribute(namespace, 576 localName, 577 context.attributeQName2String(qname), 578 "CDATA", 579 propString); 580 } 581 } 582 | Popular Tags |