KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > axis > wsdl > toJava > JavaBeanWriter


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.apache.axis.wsdl.toJava;
17
18 import org.apache.axis.Constants;
19 import org.apache.axis.utils.JavaUtils;
20 import org.apache.axis.utils.Messages;
21 import org.apache.axis.wsdl.symbolTable.ContainedAttribute;
22 import org.apache.axis.wsdl.symbolTable.ElementDecl;
23 import org.apache.axis.wsdl.symbolTable.SchemaUtils;
24 import org.apache.axis.wsdl.symbolTable.TypeEntry;
25 import org.apache.axis.wsdl.symbolTable.CollectionTE;
26 import org.apache.axis.wsdl.symbolTable.BaseType;
27 import org.apache.axis.wsdl.symbolTable.DefinedElement;
28 import org.w3c.dom.DOMException JavaDoc;
29 import org.w3c.dom.Node JavaDoc;
30
31 import java.io.IOException JavaDoc;
32 import java.io.PrintWriter JavaDoc;
33 import java.util.ArrayList JavaDoc;
34 import java.util.HashSet JavaDoc;
35 import java.util.Iterator JavaDoc;
36 import java.util.Set JavaDoc;
37 import java.util.Vector JavaDoc;
38
39 /**
40  * This is Wsdl2java's Complex Type Writer. It writes the <typeName>.java file.
41  */

42 public class JavaBeanWriter extends JavaClassWriter {
43
44     /** Field type */
45     private TypeEntry type;
46
47     /** Field elements */
48     private Vector JavaDoc elements;
49
50     /** Field attributes */
51     private Vector JavaDoc attributes;
52
53     /** Field extendType */
54     private TypeEntry extendType;
55
56     /** Field helper */
57     protected JavaBeanHelperWriter helper;
58
59     /** Field names */
60     protected Vector JavaDoc names = new Vector JavaDoc(); // even indices: types, odd: vars
61

62     /** Field simpleValueTypes */
63     protected ArrayList JavaDoc simpleValueTypes =
64             new ArrayList JavaDoc(); // name of type of simple value
65

66     /** Field enumerationTypes */
67     protected Set JavaDoc enumerationTypes = new HashSet JavaDoc(); // name of enumerated types
68

69     /** Field pw */
70     protected PrintWriter JavaDoc pw;
71
72     // The following fields can be set by extended classes
73
// to control processing
74

75     /** Field enableDefaultConstructor */
76     protected boolean enableDefaultConstructor = true;
77
78     /** Field enableFullConstructor */
79     protected boolean enableFullConstructor = false;
80
81     /** Field enableSimpleConstructors */
82     protected boolean enableSimpleConstructors = false;
83
84     /** Field enableToString */
85     protected boolean enableToString = false;
86
87     /** Field enableSetters */
88     protected boolean enableSetters = true;
89
90     /** Field enableGetters */
91     protected boolean enableGetters = true;
92
93     /** Field enableEquals */
94     protected boolean enableEquals = true;
95
96     /** Field enableHashCode */
97     protected boolean enableHashCode = true;
98
99     /** Field enableMemberFields */
100     protected boolean enableMemberFields = true;
101
102     /** Field isAny */
103     protected boolean isAny = false;
104
105     /** Field isMixed */
106     protected boolean isMixed = false;
107     
108
109     /**
110      * Constructor.
111      *
112      * @param emitter
113      * @param type The type representing this class
114      * @param elements Vector containing the Type and name of each property
115      * @param extendType The type representing the extended class (or null)
116      * @param attributes Vector containing the attribute types and names
117      * @param helper Helper class writer
118      */

119     protected JavaBeanWriter(Emitter emitter, TypeEntry type, Vector JavaDoc elements,
120                              TypeEntry extendType, Vector JavaDoc attributes,
121                              JavaWriter helper) {
122
123         super(emitter, type.getName(), "complexType");
124
125         this.type = type;
126         this.elements = elements;
127         this.attributes = attributes;
128         this.extendType = extendType;
129         this.helper = (JavaBeanHelperWriter) helper;
130
131         if (type.isSimpleType()) {
132             enableSimpleConstructors = true;
133             enableToString = true;
134         } else {
135
136             // is this a complex type that is derived from other types
137
// by restriction? if so, do not emit instance variables
138
// or accessor/mutator pairs as those are inherited from
139
// the super type, which must be non-null.
140
if ((null != extendType)
141                     && (null
142                     != SchemaUtils.getComplexElementRestrictionBase(
143                             type.getNode(), emitter.getSymbolTable()))) {
144                 enableMemberFields = false;
145                 enableGetters = false;
146                 enableSetters = false;
147                 enableEquals = false;
148                 enableHashCode = false;
149             }
150         }
151     } // ctor
152

153     /**
154      * Write a common header, including the package name, the class
155      * declaration, and the opening curly brace.
156      * Prints javadoc from WSDL documentation. (Cannot pull up, type DOM not avail)
157      */

158     protected void writeFileHeader(PrintWriter JavaDoc pw) throws IOException JavaDoc {
159         writeHeaderComments(pw);
160         writePackage(pw);
161     
162         try
163         {
164             String JavaDoc comments = SchemaUtils.getAnnotationDocumentation(type.getNode());
165             comments = getJavadocDescriptionPart(comments, false);
166             if (comments != null && comments.trim().length() > 0)
167             {
168                 pw.println();
169                 pw.println("/**");
170                 pw.println(comments);
171                 pw.println(" */");
172             }
173         }
174         catch (DOMException JavaDoc e)
175         {
176             // no comment
177
}
178         // print class declaration
179
pw.println(getClassModifiers() + getClassText() + getClassName() + ' ' + getExtendsText() + getImplementsText() + "{");
180     } // writeFileHeader
181

182     /**
183      * Generate the binding for the given complex type.
184      *
185      * @param pw
186      * @throws IOException
187      */

188     protected void writeFileBody(PrintWriter JavaDoc pw) throws IOException JavaDoc {
189
190         this.pw = pw;
191
192         // Populate Names Vector with the names and types of the members.
193
// The write methods use the names vector whenever they need to get
194
// a member name or type. Moved to implements callback in order
195
// to set any interface
196
// preprocess();
197
// Write Member Fields
198
if (enableMemberFields) {
199             writeMemberFields();
200         }
201
202         // Write the default constructor
203
if (enableDefaultConstructor) {
204             writeDefaultConstructor();
205         }
206
207         // Write Full Constructor
208
if (enableFullConstructor) {
209             writeFullConstructor();
210         }
211
212         // Write SimpleConstructors
213
if (enableSimpleConstructors) {
214             writeSimpleConstructors();
215         }
216         
217         if(!enableFullConstructor && !enableSimpleConstructors && enableMemberFields) {
218             writeMinimalConstructor();
219         }
220
221         // Write ToString method
222
if (enableToString) {
223             writeToStringMethod();
224         }
225
226         // Write accessor methods
227
writeAccessMethods();
228
229         // Write general purpose equals and hashCode methods
230
if (enableEquals) {
231             writeEqualsMethod();
232         }
233
234         if (enableHashCode) {
235             writeHashCodeMethod();
236         }
237
238         // Write the meta data into a Helper class or
239
// embed it in the bean class
240
if (!emitter.isHelperWanted()) {
241
242             // Write the helper info into the bean class
243
helper.setPrintWriter(pw);
244         }
245
246         helper.generate();
247     } // writeFileBody
248

249     /**
250      * Builds the names String vector.
251      * The even indices are the java class names of the
252      * member fields. The odd indices are the member variable
253      * names.
254      * Also sets the simpleValueType variable to the
255      * java class name of the simple value if this bean represents
256      * a simple type
257      */

258     protected void preprocess() {
259         
260         // Add element names
261
if (elements != null) {
262             for (int i = 0; i < elements.size(); i++) {
263                 ElementDecl elem = (ElementDecl) elements.get(i);
264                 String JavaDoc typeName = elem.getType().getName();
265                 String JavaDoc variableName;
266
267                 if (elem.getAnyElement()) {
268                     typeName = "org.apache.axis.message.MessageElement []";
269                     variableName = Constants.ANYCONTENT;
270                     isAny = true;
271                 } else {
272                     variableName = elem.getName();
273                     if (elem.getType().getUnderlTypeNillable()
274                         || (elem.getNillable() && elem.getMaxOccursIsUnbounded())) {
275                     /*
276                      * Soapenc arrays with nillable underlying type or
277                      * nillable="true" maxOccurs="unbounded" elements
278                      * should be mapped to a wrapper type.
279                      */

280                         typeName = Utils.getWrapperType(elem.getType());
281             
282                     } else if (elem.getMinOccursIs0() && elem.getMaxOccursIsExactlyOne()
283                             || elem.getNillable() || elem.getOptional()) {
284                     /*
285                      * Quote from JAX-RPC 1.1, Section 4.2.1:
286                      * There are a number of cases in which a built-in simple
287                      * XML data type must be mapped to the corresponding Java
288                      * wrapper class for the Java primitive type:
289                      * * an element declaration with the nillable attribute
290                      * set to true;
291                      * * an element declaration with the minOccurs attribute
292                      * set to 0 (zero) and the maxOccurs attribute set
293                      * to 1 (one) or absent;
294                      * * an attribute declaration with the use attribute set
295                      * to optional or absent and carrying neither
296                      * the default nor the fixed attribute;
297                      */

298                         typeName = Utils.getWrapperType(typeName);
299                     }
300                 }
301
302                 // Make sure the property name is not reserved.
303
variableName = JavaUtils.getUniqueValue(
304                         helper.reservedPropNames, variableName);
305                 names.add(typeName);
306                 names.add(variableName);
307
308                 if (type.isSimpleType()
309                         && (variableName.endsWith("Value")
310                         || variableName.equals("_value"))) {
311                     simpleValueTypes.add(typeName);
312                 }
313
314                 // bug 19069: need to generate code that access member variables that
315
// are enum types through the class interface, not the constructor
316
// this util method returns non-null if the type at node is an enum
317
if (null != Utils.getEnumerationBaseAndValues(
318                         elem.getType().getNode(), emitter.getSymbolTable())) {
319                     enumerationTypes.add(typeName);
320                 }
321             }
322         }
323
324         if (enableMemberFields && SchemaUtils.isMixed(type.getNode())) {
325             isMixed = true;
326             if (!isAny) {
327                 names.add("org.apache.axis.message.MessageElement []");
328                 names.add(Constants.ANYCONTENT);
329             }
330         }
331
332         // Add attribute names
333
if (attributes != null) {
334
335             for (int i = 0; i < attributes.size(); i++) {
336                 ContainedAttribute attr = (ContainedAttribute) attributes.get(i);
337                 String JavaDoc typeName = attr.getType().getName();
338                 String JavaDoc variableName = attr.getName();
339
340         // TODO - What about MinOccurs and Nillable?
341
// Do they make sense here?
342
if (attr.getOptional()) {
343             typeName = Utils.getWrapperType(typeName);
344         }
345
346                 // Make sure the property name is not reserved.
347
variableName = JavaUtils.getUniqueValue(
348                         helper.reservedPropNames, variableName);
349
350                 names.add(typeName);
351                 names.add(variableName);
352
353                 if (type.isSimpleType()
354                         && (variableName.endsWith("Value")
355                         || variableName.equals("_value"))) {
356                     simpleValueTypes.add(typeName);
357                 }
358
359                 // bug 19069: need to generate code that access member variables that
360
// are enum types through the class interface, not the constructor
361
// this util method returns non-null if the type at node is an enum
362
if (null != Utils.getEnumerationBaseAndValues(attr.getType().getNode(),
363                         emitter.getSymbolTable())) {
364                     enumerationTypes.add(typeName);
365                 }
366             }
367         }
368
369         if ((extendType != null) && extendType.getDimensions().equals("[]")) {
370             String JavaDoc typeName = extendType.getName();
371             String JavaDoc elemName = extendType.getQName().getLocalPart();
372             String JavaDoc variableName = Utils.xmlNameToJava(elemName);
373
374             names.add(typeName);
375             names.add(variableName);
376         }
377
378         // Check for duplicate names and make them unique
379
// Start at index 2 and go by twos
380
for (int i = 1; i < names.size(); i +=2)
381         {
382             int suffix = 2; // the number we append to the name
383
String JavaDoc s = (String JavaDoc) names.elementAt(i);
384             if (i < names.size() - 2)
385             {
386                 int dup = names.indexOf(s, i+1);
387                 while (dup > 0)
388                 {
389                     // duplicate name, tack a number on the end
390
names.set(dup, names.get(dup) + Integer.toString(suffix));
391                     suffix++;
392                     // get out if we don't have more
393
if (i >= names.size() - 2)
394                         break;
395                     dup = names.indexOf(s, dup+1);
396                 }
397             }
398
399         }
400     }
401
402     /**
403      * Returns the class name that should be used to serialize and
404      * deserialize this binary element
405      */

406     protected String JavaDoc getBinaryTypeEncoderName(String JavaDoc elementName)
407     {
408         TypeEntry type = getElementDecl(elementName);
409     if (type != null)
410     {
411         String JavaDoc typeName = type.getQName().getLocalPart();
412
413         if (typeName.equals("base64Binary"))
414             return "org.apache.axis.encoding.Base64";
415         if (typeName.equals("hexBinary"))
416             return "org.apache.axis.types.HexBinary";
417
418         throw new java.lang.RuntimeException JavaDoc("Unknown binary type " +
419         typeName + " for element " + elementName);
420     }
421
422     throw new java.lang.RuntimeException JavaDoc("Unknown element " + elementName);
423     }
424
425     /**
426      * Returns the TypeEntry of the given element
427      */

428     protected TypeEntry getElementDecl(String JavaDoc elementName)
429     {
430         if (elements != null) {
431             for (int i = 0; i < elements.size(); i++) {
432                 ElementDecl elem = (ElementDecl) elements.get(i);
433                 String JavaDoc variableName;
434
435                 if (elem.getAnyElement()) {
436                     variableName = Constants.ANYCONTENT;
437                 } else {
438                     variableName = elem.getName();
439                 }
440
441                 if (variableName.equals(elementName))
442             return elem.getType();
443         }
444     }
445     return null;
446     }
447
448     /**
449      * Returns the appropriate extends text
450      *
451      * @return "" or "abstract "
452      */

453     protected String JavaDoc getClassModifiers() {
454
455         Node JavaDoc node = type.getNode();
456
457         if (node != null) {
458             if (JavaUtils.isTrueExplicitly(Utils.getAttribute(node,
459                     "abstract"))) {
460                 return super.getClassModifiers() + "abstract ";
461             }
462         }
463
464         return super.getClassModifiers();
465     } // getClassModifiers
466

467     /**
468      * Returns the appropriate extends text
469      *
470      * @return "" or " extends <class> "
471      */

472     protected String JavaDoc getExtendsText() {
473
474         // See if this class extends another class
475
String JavaDoc extendsText = "";
476
477         if ((extendType != null) && !type.isSimpleType()
478                 && (extendType.getDimensions().length() == 0)) {
479             extendsText = " extends " + extendType.getName() + " ";
480         }
481
482         return extendsText;
483     }
484
485     /**
486      * Returns the appropriate implements text
487      *
488      * @return " implements <classes> "
489      */

490     protected String JavaDoc getImplementsText() {
491
492         // See if this class extends another class
493
String JavaDoc implementsText = " implements java.io.Serializable";
494
495         if (type.isSimpleType()) {
496             implementsText += ", org.apache.axis.encoding.SimpleType";
497         }
498
499         // need to call this to find out whether the type contains any elements
500
preprocess();
501
502         if (isAny) {
503             implementsText += ", org.apache.axis.encoding.AnyContentType";
504         }
505
506         if (isMixed) {
507             implementsText += ", org.apache.axis.encoding.MixedContentType";
508         }
509
510         implementsText += " ";
511
512         return implementsText;
513     }
514
515     /**
516      * Writes the member fields.
517      */

518     protected void writeMemberFields() {
519
520         // Define the member element of the bean
521
if (isUnion()) {
522             pw.println(" private java.lang.String _value;");
523
524             return;
525         }
526
527         for (int i = 0; i < names.size(); i += 2) {
528             // get comments for this field
529
String JavaDoc comments = "";
530             if (elements != null)
531             {
532                 if (elements != null && i < (elements.size()*2))
533                 {
534                     ElementDecl elem = (ElementDecl)elements.get(i/2);
535                     comments = elem.getDocumentation();
536                 }
537             }
538             
539             String JavaDoc typeName = (String JavaDoc) names.get(i);
540             String JavaDoc variable = (String JavaDoc) names.get(i + 1);
541
542             // Declare the bean element
543
if (comments != null && comments.trim().length() > 0)
544             {
545                 String JavaDoc flatComments = getJavadocDescriptionPart(comments, false).substring(3);
546                 // it will be flat if it fits on one line
547
pw.println(" /** " + flatComments.trim() + " */");
548             }
549             pw.print(" private " + typeName + " " + variable + ";");
550
551             // label the attribute fields.
552
if ((elements == null) || (i >= (elements.size() * 2))) {
553                 pw.println(" // attribute");
554             } else {
555                 pw.println();
556             }
557         }
558
559         pw.println();
560     }
561
562     
563     /**
564      * Writes the default constructor.
565      */

566     protected void writeDefaultConstructor() {
567
568         // Define the default constructor
569
pw.println(" public " + className + "() {");
570         pw.println(" }");
571         pw.println();
572     }
573
574     protected void writeMinimalConstructor() {
575
576         if (isUnion() || names.size() == 0) {
577             return;
578         }
579
580         pw.println(" public " + className + "(");
581         for (int i = 0; i < names.size(); i += 2) {
582             String JavaDoc typeName = (String JavaDoc) names.get(i);
583             String JavaDoc variable = (String JavaDoc) names.get(i + 1);
584             pw.print(" " + typeName + " "
585                     + variable);
586             if (i >= names.size() - 2) {
587                 pw.println(") {");
588             } else {
589                 pw.println(",");
590             }
591         }
592         
593         for (int i = 0; i < names.size(); i += 2) {
594             String JavaDoc variable = (String JavaDoc) names.get(i + 1);
595             pw.println(" this." + variable + " = " + variable + ";");
596             if (i >= names.size() - 2) {
597                 break;
598             }
599         }
600         pw.println(" }");
601         pw.println();
602     }
603     
604     /**
605      * Writes the full constructor.
606      * Note that this class is not recommended for
607      * JSR 101 compliant beans, but is provided for
608      * extended classes which may wish to generate a full
609      * constructor.
610      */

611     protected void writeFullConstructor() {
612
613         if (type.isSimpleType()) {
614             return;
615         }
616
617         // The constructor needs to consider all extended types
618
Vector JavaDoc extendList = new Vector JavaDoc();
619
620         extendList.add(type);
621
622         TypeEntry parent = extendType;
623
624         while (parent != null) {
625             extendList.add(parent);
626
627             parent =
628                     SchemaUtils.getComplexElementExtensionBase(parent.getNode(),
629                             emitter.getSymbolTable());
630         }
631
632         // Now generate a list of names and types starting with
633
// the oldest parent. (Attrs are considered before elements).
634
Vector JavaDoc paramTypes = new Vector JavaDoc();
635         Vector JavaDoc paramNames = new Vector JavaDoc();
636
637         for (int i = extendList.size() - 1; i >= 0; i--) {
638             TypeEntry te = (TypeEntry) extendList.elementAt(i);
639
640             // The names of the inherited parms are mangled
641
// in case they interfere with local parms.
642
String JavaDoc mangle = "";
643
644             if (i > 0) {
645                 mangle = "_"
646                         + Utils.xmlNameToJava(te.getQName().getLocalPart())
647                         + "_";
648             }
649
650             // Process the attributes
651
Vector JavaDoc attributes = te.getContainedAttributes();
652             if (attributes != null) {
653                 for (int j = 0; j < attributes.size(); j += 1) {
654                     ContainedAttribute attr = (ContainedAttribute) attributes.get(j);
655                     paramTypes.add(attr.getType().getName());
656                     paramNames.add(JavaUtils.getUniqueValue(
657                             helper.reservedPropNames, attr.getName()));
658                 }
659             }
660
661             // Process the elements
662
Vector JavaDoc elements = te.getContainedElements();
663
664             if (elements != null) {
665                 for (int j = 0; j < elements.size(); j++) {
666                     ElementDecl elem = (ElementDecl) elements.get(j);
667                     paramTypes.add(elem.getType().getName());
668                     paramNames.add(JavaUtils.getUniqueValue(
669                             helper.reservedPropNames, elem.getName()));
670                 }
671             }
672         }
673
674         // Set the index where the local params start
675
int localParams = paramTypes.size() - names.size() / 2;
676
677         // Now write the constructor signature
678
if (paramTypes.size() > 0) {
679             pw.println(" public " + className + "(");
680
681             for (int i = 0; i < paramTypes.size(); i++) {
682                 pw.print(" " + paramTypes.elementAt(i) + " "
683                         + paramNames.elementAt(i));
684
685                 if ((i + 1) < paramTypes.size()) {
686                     pw.println(",");
687                 } else {
688                     pw.println(") {");
689                 }
690             }
691
692             // Call the extended constructor to set inherited fields
693
if ((extendType != null) && (localParams > 0)) {
694                 pw.println(" super(");
695
696                 for (int j = 0; j < localParams; j++) {
697                     pw.print(" " + paramNames.elementAt(j));
698
699                     if ((j + 1) < localParams) {
700                         pw.println(",");
701                     } else {
702                         pw.println(");");
703                     }
704                 }
705             }
706
707             // Set local fields directly
708
for (int j = localParams; j < paramNames.size(); j++) {
709                 pw.println(" this." + paramNames.elementAt(j) + " = "
710                         + paramNames.elementAt(j) + ";");
711             }
712
713             pw.println(" }");
714             pw.println();
715         }
716     }
717
718     /**
719      * Writes the constructors for SimpleTypes.
720      * Writes a constructor accepting a string and
721      * a constructor accepting the simple java type.
722      */

723     protected void writeSimpleConstructors() {
724
725         // If this is a simple type,need to emit a string
726
// constructor and a value construtor.
727
if (simpleValueTypes.size() == 0) {
728             return;
729         }
730
731         pw.println(" // " + Messages.getMessage("needStringCtor"));
732
733         if (isUnion() || simpleValueTypes.get(0).equals("java.lang.String")) {
734             pw.println(" public " + className
735                     + "(java.lang.String _value) {");
736             pw.println(" this._value = _value;");
737             pw.println(" }");
738             int i = 0;
739             for (Iterator JavaDoc iterator = simpleValueTypes.iterator();
740                  iterator.hasNext();) {
741                 String JavaDoc typeName = (String JavaDoc) iterator.next();
742
743                 if (typeName.equals("java.lang.String")) {
744                     i += 2;
745                     continue;
746                 }
747
748                 String JavaDoc capName = "_value";
749                 if (isUnion()) {
750                     // names and simpleValueTypes should match as
751
// union is over simple types
752
String JavaDoc name = (String JavaDoc) names.get(i + 1);
753                     capName = Utils.capitalizeFirstChar(name);
754                 }
755
756                 pw.println(" public " + className + "(" + typeName
757                         + " _value) {");
758                 pw.println(" set" + capName + "(_value);");
759                 pw.println(" }");
760                 pw.println();
761                 i += 2;
762             }
763         } else if (simpleValueTypes.size() == 1) {
764             pw.println(" public " + className + "("
765                     + simpleValueTypes.get(0) + " _value) {");
766             pw.println(" this._value = _value;");
767             pw.println(" }");
768             pw.println(" public " + className
769                     + "(java.lang.String _value) {");
770             writeSimpleTypeGetter((String JavaDoc) simpleValueTypes.get(0), null,
771                     "this._value =");
772             pw.println(" }");
773             pw.println();
774         }
775     }
776
777     /**
778      * Method writeSimpleTypeGetter
779      *
780      * @param simpleValueType
781      * @param name
782      * @param returnString
783      */

784     protected void writeSimpleTypeGetter(String JavaDoc simpleValueType, String JavaDoc name,
785                                          String JavaDoc returnString) {
786
787         // Make sure we wrap base types with its Object type
788
String JavaDoc wrapper = JavaUtils.getWrapper(simpleValueType);
789
790         if (wrapper != null) {
791             pw.println(" " + returnString + " new " + wrapper
792                     + "(_value)." + simpleValueType + "Value();");
793         } else {
794             if (simpleValueType.equals("byte[]")) {
795             String JavaDoc encoder = getBinaryTypeEncoderName ("_value");
796                 pw.println(" " + returnString
797                         + " " + encoder + ".decode(_value);");
798             } else if (simpleValueType.equals("org.apache.axis.types.URI")) {
799                 pw.println(" try {");
800                 pw.println(" " + returnString
801                         + " new org.apache.axis.types.URI(_value);");
802                 pw.println(" }");
803                 pw.println(
804                         " catch (org.apache.axis.types.URI.MalformedURIException mue) {");
805                 pw.println(
806                         " throw new java.lang.RuntimeException(mue.toString());");
807                 pw.println(" }");
808             } else if (simpleValueType.equals("java.util.Date")) {
809                 pw.println(" try {");
810                 pw.println(
811                         " " + returnString
812                         + " (java.text.DateFormat.getDateTimeInstance()).parse(_value);");
813                 pw.println(" }");
814                 pw.println(" catch (java.text.ParseException e){");
815                 pw.println(
816                         " throw new java.lang.RuntimeException(e.toString());");
817                 pw.println(" }");
818             } else if (simpleValueType.equals("java.util.Calendar")) {
819                 pw.println(" java.util.Calendar cal =");
820                 pw.println(
821                         " (java.util.Calendar) new org.apache.axis.encoding.ser.CalendarDeserializer(");
822                 pw.println(
823                         " java.lang.String.class, org.apache.axis.Constants.XSD_STRING).makeValue(_value);");
824                 pw.println(" " + returnString + " cal;");
825             } else if (enumerationTypes.contains(simpleValueType)) {
826
827                 // we're generating code that will obtain a reference to an enumeration: use the
828
// class forString interface, not the constructor. Bug 19069
829
pw.println(" " + returnString + " " + simpleValueType
830                         + ".fromString(_value);");
831             } else {
832                 pw.println(" " + returnString + " new "
833                         + simpleValueType + "(_value);");
834             }
835         }
836     }
837
838     /**
839      * Method isUnion
840      *
841      * @return
842      */

843     private boolean isUnion() {
844         return this.simpleValueTypes.size() > 1;
845     }
846
847     /**
848      * Writes the toString method
849      * Currently the toString method is only written for
850      * simpleTypes.
851      */

852     protected void writeToStringMethod() {
853
854         // If this is a simple type, emit a toString
855
if (simpleValueTypes.size() == 0) {
856             return;
857         }
858
859         pw.println(" // " + Messages.getMessage("needToString"));
860         pw.println(" public java.lang.String toString() {");
861
862         if (isUnion() || simpleValueTypes.get(0).equals("java.lang.String")) {
863             pw.println(" return _value;");
864         } else {
865             String JavaDoc wrapper =
866                     JavaUtils.getWrapper((String JavaDoc) simpleValueTypes.get(0));
867
868             if (wrapper != null) {
869                 pw.println(" return new " + wrapper
870                         + "(_value).toString();");
871             } else {
872                 String JavaDoc simpleValueType0 = (String JavaDoc)simpleValueTypes.get(0);
873                 if (simpleValueType0.equals("byte[]")) {
874                 String JavaDoc encoder = getBinaryTypeEncoderName ("_value");
875                     pw.println(
876                             " return _value == null ? null : " +
877                 encoder + ".encode(_value);");
878                 } else if (simpleValueType0.equals("java.util.Calendar")) {
879                     pw.println(
880                             " return _value == null ? null : new org.apache.axis.encoding.ser.CalendarSerializer().getValueAsString(_value, null);");
881                 } else {
882                     pw.println(
883                             " return _value == null ? null : _value.toString();");
884                 }
885             }
886         }
887
888         pw.println(" }");
889         pw.println();
890     }
891
892     /**
893      * Method writeSimpleTypeSetter
894      *
895      * @param simpleValueType
896      */

897     protected void writeSimpleTypeSetter(String JavaDoc simpleValueType) {
898
899         String JavaDoc wrapper = JavaUtils.getWrapper(simpleValueType);
900
901         if (wrapper != null) {
902             pw.println(" this._value = new " + wrapper
903                     + "(_value).toString();");
904         } else {
905             if (simpleValueType.equals("byte[]")) {
906         String JavaDoc encoder = getBinaryTypeEncoderName ("_value");
907                 pw.println(
908                         " this._value = _value == null ? null : " +
909             encoder + ".encode(_value);");
910             } else if (simpleValueType.equals("java.util.Calendar")) {
911                 pw.println(
912                         " this._value = _value == null ? null : new org.apache.axis.encoding.ser.CalendarSerializer().getValueAsString(_value, null);");
913             } else {
914                 pw.println(
915                         " this._value = _value == null ? null : _value.toString();");
916             }
917         }
918     }
919
920     /**
921      * Writes the setter and getter methods
922      */

923     protected void writeAccessMethods() {
924
925         int j = 0;
926
927         // Define getters and setters for the bean elements
928
for (int i = 0; i < names.size(); i += 2, j++) {
929             String JavaDoc typeName = (String JavaDoc) names.get(i);
930             String JavaDoc name = (String JavaDoc) names.get(i + 1);
931             String JavaDoc capName = Utils.capitalizeFirstChar(name);
932
933             String JavaDoc documentation = "";
934             if (elements != null)
935             {
936                 if (elements != null && i < (elements.size()*2))
937                 {
938                     ElementDecl elem = (ElementDecl)elements.get(i/2);
939                     documentation = elem.getDocumentation();
940                 }
941             }
942             
943             String JavaDoc get = "get";
944
945             if (typeName.equals("boolean")) {
946                 get = "is";
947             }
948
949             String JavaDoc comment = getJavadocDescriptionPart(documentation, false);
950             if (comment.length() > 3) {
951                 // remove the " *" at the front of the first line
952
comment = comment.substring(2);
953             }
954             if (enableGetters) {
955                 try {
956                     pw.println();
957                     pw.println(" /**");
958                     pw.println(" * Gets the " + name + " value for this " + getClassName() + ".");
959                     pw.println(" * ");
960                     pw.println(" * @return " + name + comment);
961                     pw.println(" */");
962                 } catch (DOMException JavaDoc e) {
963                     // no comment
964
}
965                 pw.println(" public " + typeName + " " + get + capName
966                         + "() {");
967
968                 if (isUnion()) {
969                     writeSimpleTypeGetter(typeName, name, "return");
970                 } else {
971                     pw.println(" return " + name + ";");
972                 }
973
974                 pw.println(" }");
975                 pw.println();
976             }
977
978             if (enableSetters) {
979                 try
980                 {
981                     String JavaDoc nm = (isUnion()) ? "_value" : name;
982                     pw.println();
983                     pw.println(" /**");
984                     pw.println(" * Sets the " + nm + " value for this " + getClassName() + ".");
985                     pw.println(" * ");
986                     pw.println(" * @param " + nm + comment);
987                     pw.println(" */");
988                 }
989                 catch (DOMException JavaDoc e)
990                 {
991                     // no comment
992
}
993                 if (isUnion()) {
994                     pw.println(" public void set" + capName + "(" + typeName
995                             + " _value) {");
996                     writeSimpleTypeSetter(typeName);
997                 } else {
998                     pw.println(" public void set" + capName + "(" + typeName
999                             + " " + name + ") {");
1000                    pw.println(" this." + name + " = " + name + ";");
1001                }
1002
1003                pw.println(" }");
1004                pw.println();
1005            }
1006
1007            // If this is a special collection type, insert extra
1008
// java code so that the serializer/deserializer can recognize
1009
// the class. This is not JAX-RPC, and will be replaced with
1010
// compliant code when JAX-RPC determines how to deal with this case.
1011
// These signatures comply with Bean Indexed Properties which seems
1012
// like the reasonable approach to take for collection types.
1013
// (It may be more efficient to handle this with an ArrayList...but
1014
// for the initial support it was easier to use an actual array.)
1015
if ((elements != null) && (j < elements.size())) {
1016                ElementDecl elem = (ElementDecl) elements.get(j);
1017
1018                if (elem.getType().getQName().getLocalPart().indexOf("[") > 0) {
1019                    String JavaDoc compName =
1020                            typeName.substring(0, typeName.lastIndexOf("["));
1021
1022                    if (enableGetters) {
1023                        pw.println(" public " + compName + " " + get
1024                                + capName + "(int i) {");
1025                        pw.println(" return this." + name + "[i];");
1026                        pw.println(" }");
1027                        pw.println();
1028                    }
1029
1030                    if (enableSetters) {
1031                        pw.println(" public void set" + capName + "(int i, "
1032                                + compName + " _value) {");
1033
1034                        // According to the section 7.2 of the JavaBeans
1035
// specification, the indexed setter should not
1036
// establish or grow the array. Thus the following
1037
// code is not generated for compliance purposes.
1038

1039                        /*
1040                         * int bracketIndex = typeName.indexOf("[");
1041                         * String newingName = typeName.substring(0, bracketIndex + 1);
1042                         * String newingSuffix = typeName.substring(bracketIndex + 1);
1043                         *
1044                         * pw.println(" if (this." + name + " == null ||");
1045                         * pw.println(" this." + name + ".length <= i) {");
1046                         * pw.println(" " + typeName + " a = new " +
1047                         * newingName + "i + 1" + newingSuffix + ";");
1048                         * pw.println(" if (this." + name + " != null) {");
1049                         * pw.println(" for(int j = 0; j < this." + name +
1050                         * ".length; j++)");
1051                         * pw.println(" a[j] = this." + name + "[j];");
1052                         * pw.println(" }");
1053                         * pw.println(" this." + name + " = a;");
1054                         * pw.println(" }");
1055                         */

1056                        pw.println(" this." + name + "[i] = _value;");
1057                        pw.println(" }");
1058                        pw.println();
1059                    }
1060                }
1061            }
1062        }
1063    }
1064
1065    /**
1066     * Writes a general purpose equals method
1067     */

1068    protected void writeEqualsMethod() {
1069
1070        // The __equalsCalc field and synchronized method are necessary
1071
// in case the object has direct or indirect references to itself.
1072
pw.println(" private java.lang.Object __equalsCalc = null;");
1073        pw.println(
1074                " public synchronized boolean equals(java.lang.Object obj) {");
1075
1076        // First do the general comparison checks
1077
pw.println(" if (!(obj instanceof " + className
1078                + ")) return false;");
1079        pw.println(" " + className + " other = (" + className
1080                + ") obj;");
1081        pw.println(" if (obj == null) return false;");
1082        pw.println(" if (this == obj) return true;");
1083
1084        // Have we been here before ? return true if yes otherwise false
1085
pw.println(" if (__equalsCalc != null) {");
1086        pw.println(" return (__equalsCalc == obj);");
1087        pw.println(" }");
1088        pw.println(" __equalsCalc = obj;");
1089
1090        // Before checking the elements, check equality of the super class
1091
String JavaDoc truth = "true";
1092
1093        if ((extendType != null) && !type.isSimpleType()) {
1094            truth = "super.equals(obj)";
1095        }
1096
1097        pw.println(" boolean _equals;");
1098
1099        if (names.size() == 0) {
1100            pw.println(" _equals = " + truth + ";");
1101        } else if (isUnion()) {
1102            pw.println(" _equals = " + truth + " && "
1103                    + " this.toString().equals(obj.toString());");
1104        } else {
1105            pw.println(" _equals = " + truth + " && ");
1106
1107            for (int i = 0; i < names.size(); i += 2) {
1108                String JavaDoc variableType = (String JavaDoc) names.get(i);
1109                String JavaDoc variable = (String JavaDoc) names.get(i + 1);
1110                String JavaDoc get = "get";
1111
1112                if (variableType.equals("boolean")) {
1113                    get = "is";
1114                }
1115
1116                if (variableType.equals("int") || variableType.equals("long")
1117                        || variableType.equals("short")
1118                        || variableType.equals("float")
1119                        || variableType.equals("double")
1120                        || variableType.equals("boolean")
1121                        || variableType.equals("byte")) {
1122                    pw.print(" this." + variable + " == other."
1123                            + get + Utils.capitalizeFirstChar(variable)
1124                            + "()");
1125                } else if (variableType.indexOf("[") >= 0) {
1126
1127                    // Use java.util.Arrays.equals to compare arrays.
1128
pw.println(" ((this." + variable
1129                            + "==null && other." + get
1130                            + Utils.capitalizeFirstChar(variable)
1131                            + "()==null) || ");
1132                    pw.println(" (this." + variable + "!=null &&");
1133                    pw.print(" java.util.Arrays.equals(this."
1134                            + variable + ", other." + get
1135                            + Utils.capitalizeFirstChar(variable) + "())))");
1136                } else {
1137                    pw.println(" ((this." + variable
1138                            + "==null && other." + get
1139                            + Utils.capitalizeFirstChar(variable)
1140                            + "()==null) || ");
1141                    pw.println(" (this." + variable + "!=null &&");
1142                    pw.print(" this." + variable
1143                            + ".equals(other." + get
1144                            + Utils.capitalizeFirstChar(variable) + "())))");
1145                }
1146
1147                if (i == (names.size() - 2)) {
1148                    pw.println(";");
1149                } else {
1150                    pw.println(" &&");
1151                }
1152            }
1153        }
1154
1155        pw.println(" __equalsCalc = null;");
1156        pw.println(" return _equals;");
1157        pw.println(" }");
1158        pw.println("");
1159    }
1160
1161    /**
1162     * Writes a general purpose hashCode method.
1163     */

1164    protected void writeHashCodeMethod() {
1165
1166        // The __hashCodeCalc field and synchronized method are necessary
1167
// in case the object has direct or indirect references to itself.
1168
pw.println(" private boolean __hashCodeCalc = false;");
1169        pw.println(" public synchronized int hashCode() {");
1170        pw.println(" if (__hashCodeCalc) {");
1171        pw.println(" return 0;");
1172        pw.println(" }");
1173        pw.println(" __hashCodeCalc = true;");
1174
1175        // Get the hashCode of the super class
1176
String JavaDoc start = "1";
1177
1178        if ((extendType != null) && !type.isSimpleType()) {
1179            start = "super.hashCode()";
1180        }
1181
1182        pw.println(" int _hashCode = " + start + ";");
1183
1184        if (isUnion()) {
1185            pw.println(" if (this._value != null) {");
1186            pw.println(" _hashCode += this._value.hashCode();");
1187            pw.println(" }");
1188        }
1189
1190        for (int i = 0; !isUnion() && (i < names.size()); i += 2) {
1191            String JavaDoc variableType = (String JavaDoc) names.get(i);
1192            String JavaDoc variable = (String JavaDoc) names.get(i + 1);
1193            String JavaDoc get = "get";
1194
1195            if (variableType.equals("boolean")) {
1196                get = "is";
1197            }
1198
1199            if (variableType.equals("int") || variableType.equals("short")
1200                    || variableType.equals("byte")) {
1201                pw.println(" _hashCode += " + get
1202                        + Utils.capitalizeFirstChar(variable) + "();");
1203            } else if (variableType.equals("boolean")) {
1204                pw.println(" _hashCode += (" + get
1205                        + Utils.capitalizeFirstChar(variable)
1206                        + "() ? Boolean.TRUE : Boolean.FALSE).hashCode();");
1207            } else if (variableType.equals("long")) {
1208                pw.println(" _hashCode += new Long(" + get
1209                        + Utils.capitalizeFirstChar(variable)
1210                        + "()).hashCode();");
1211            } else if (variableType.equals("float")) {
1212                pw.println(" _hashCode += new Float(" + get
1213                        + Utils.capitalizeFirstChar(variable)
1214                        + "()).hashCode();");
1215            } else if (variableType.equals("double")) {
1216                pw.println(" _hashCode += new Double(" + get
1217                        + Utils.capitalizeFirstChar(variable)
1218                        + "()).hashCode();");
1219            } else if (variableType.indexOf("[") >= 0) {
1220
1221                // The hashCode calculation for arrays is complicated.
1222
// Wish there was a hashCode method in java.utils.Arrays !
1223
// Get the hashCode for each element of the array which is not an array.
1224
pw.println(" if (" + get
1225                        + Utils.capitalizeFirstChar(variable)
1226                        + "() != null) {");
1227                pw.println(" for (int i=0;");
1228                pw.println(
1229                        " i<java.lang.reflect.Array.getLength("
1230                        + get + Utils.capitalizeFirstChar(variable) + "());");
1231                pw.println(" i++) {");
1232                pw.println(
1233                        " java.lang.Object obj = java.lang.reflect.Array.get("
1234                        + get + Utils.capitalizeFirstChar(variable) + "(), i);");
1235                pw.println(" if (obj != null &&");
1236                pw.println(" !obj.getClass().isArray()) {");
1237                pw.println(" _hashCode += obj.hashCode();");
1238                pw.println(" }");
1239                pw.println(" }");
1240                pw.println(" }");
1241            } else {
1242                pw.println(" if (" + get
1243                        + Utils.capitalizeFirstChar(variable)
1244                        + "() != null) {");
1245                pw.println(" _hashCode += " + get
1246                        + Utils.capitalizeFirstChar(variable)
1247                        + "().hashCode();");
1248                pw.println(" }");
1249            }
1250        }
1251
1252        // Reset the __hashCodeCalc variable and return
1253
pw.println(" __hashCodeCalc = false;");
1254        pw.println(" return _hashCode;");
1255        pw.println(" }");
1256        pw.println("");
1257    }
1258    
1259    /** Generate a java source file and/or helper source file.
1260     * If the emitter works in deploy mode and the class already exists, only the helper is generated.
1261     * Otherwise, the java bean and helper source are generated.
1262     */

1263    public void generate() throws IOException JavaDoc {
1264        String JavaDoc fqcn = getPackage() + "." + getClassName();
1265        if (emitter.isDeploy() && emitter.doesExist(fqcn)) {
1266            if (emitter.isHelperWanted()) {
1267                helper.generate();
1268            }
1269        } else {
1270            super.generate();
1271        }
1272    }
1273} // class JavaBeanWriter
1274
Popular Tags