axis-java-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From sc...@apache.org
Subject cvs commit: xml-axis/java/src/org/apache/axis/wsdlgen Emitter.java Java2Wsdl.java Namespaces.java Types.java todo.txt
Date Tue, 11 Dec 2001 15:13:56 GMT
scheu       01/12/11 07:13:56

  Added:       java/src/org/apache/axis/wsdl Java2WSDL.java
               java/src/org/apache/axis/wsdl/fromJava Emitter.java
                        Namespaces.java Types.java todo.txt
  Removed:     java/src/org/apache/axis/wsdlgen Emitter.java Java2Wsdl.java
                        Namespaces.java Types.java todo.txt
  Log:
  Repackaged Java2WSDL
  
  Revision  Changes    Path
  1.1                  xml-axis/java/src/org/apache/axis/wsdl/Java2WSDL.java
  
  Index: Java2WSDL.java
  ===================================================================
  /*
   * The Apache Software License, Version 1.1
   *
   *
   * Copyright (c) 2001 The Apache Software Foundation.  All rights
   * reserved.
   *
   * Redistribution and use in source and binary forms, with or without
   * modification, are permitted provided that the following conditions
   * are met:
   *
   * 1. Redistributions of source code must retain the above copyright
   *    notice, this list of conditions and the following disclaimer.
   *
   * 2. Redistributions in binary form must reproduce the above copyright
   *    notice, this list of conditions and the following disclaimer in
   *    the documentation and/or other materials provided with the
   *    distribution.
   *
   * 3. The end-user documentation included with the redistribution,
   *    if any, must include the following acknowledgment:
   *       "This product includes software developed by the
   *        Apache Software Foundation (http://www.apache.org/)."
   *    Alternately, this acknowledgment may appear in the software itself,
   *    if and wherever such third-party acknowledgments normally appear.
   *
   * 4. The names "Axis" and "Apache Software Foundation" must
   *    not be used to endorse or promote products derived from this
   *    software without prior written permission. For written
   *    permission, please contact apache@apache.org.
   *
   * 5. Products derived from this software may not be called "Apache",
   *    nor may "Apache" appear in their name, without prior written
   *    permission of the Apache Software Foundation.
   *
   * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
   * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
   * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
   * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
   * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
   * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
   * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
   * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
   * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
   * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   * SUCH DAMAGE.
   * ====================================================================
   *
   * This software consists of voluntary contributions made by many
   * individuals on behalf of the Apache Software Foundation.  For more
   * information on the Apache Software Foundation, please see
   * <http://www.apache.org/>.
   */
  package org.apache.axis.wsdl;
  
  import org.apache.avalon.excalibur.cli.CLArgsParser;
  import org.apache.avalon.excalibur.cli.CLOption;
  import org.apache.avalon.excalibur.cli.CLOptionDescriptor;
  import org.apache.avalon.excalibur.cli.CLUtil;
  
  import org.apache.axis.wsdl.fromJava.Emitter;
  
  import java.util.HashMap;
  import java.util.List;
  
  /**
   * Command line interface to the java2wsdl utility
   *
   * @author Ravi Kumar (rkumar@borland.com)
   */
  
  public class Java2WSDL {
      // Define our short one-letter option identifiers.
      protected static final int HELP_OPT = 'h';
      protected static final int OUTPUT_WSDL_MODE_OPT = 'w';
      protected static final int OUTPUT_OPT = 'o';
      protected static final int OUTPUT_IMPL_OPT = 'O';
      protected static final int PACKAGE_OPT = 'p';
      protected static final int NAMESPACE_OPT = 'n';
      protected static final int NAMESPACE_IMPL_OPT = 'N';
      protected static final int SERVICE_NAME_OPT = 's';
      protected static final int LOCATION_OPT = 'l';
      protected static final int LOCATION_IMPORT_OPT = 'L';
  //    protected static final int CLASSDIR_OPT = 'c';
      protected static final int METHODS_ALLOWED_OPT = 'm';
      protected static final int INHERITED_CLASS_OPT = 'a';
  
      /**
       *  Define the understood options. Each CLOptionDescriptor contains:
       * - The "long" version of the option. Eg, "help" means that "--help" will
       * be recognised.
       * - The option flags, governing the option's argument(s).
       * - The "short" version of the option. Eg, 'h' means that "-h" will be
       * recognised.
       * - A description of the option for the usage message
       */
      protected static final CLOptionDescriptor[] options = new CLOptionDescriptor[]{
          new CLOptionDescriptor("help",
                  CLOptionDescriptor.ARGUMENT_DISALLOWED,
                  HELP_OPT,
                  "print this message and exit"),
          new CLOptionDescriptor("output",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  OUTPUT_OPT,
                  "output Wsdl filename"),
          new CLOptionDescriptor("location",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  LOCATION_OPT,
                  "service location url"),
          new CLOptionDescriptor("service",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  SERVICE_NAME_OPT,
                  "service name (obtained from --location if not specified)"),
          new CLOptionDescriptor("namespace",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  NAMESPACE_OPT,
                  "target namespace"),
          new CLOptionDescriptor("PkgtoNS",
                  CLOptionDescriptor.DUPLICATES_ALLOWED + CLOptionDescriptor.ARGUMENTS_REQUIRED_2,
                  PACKAGE_OPT,
                  "package=namespace, name value pairs"),
          new CLOptionDescriptor("methods",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  METHODS_ALLOWED_OPT,
                  "space separated list of methods to export"),
          new CLOptionDescriptor("all",
                  CLOptionDescriptor.ARGUMENT_DISALLOWED,
                  INHERITED_CLASS_OPT,
                  "look for allowed methods in inherited class"),
  //        there is no implementation for a class loader
  //        look at todo in Emitter
  //        new CLOptionDescriptor("classDir",
  //                CLOptionDescriptor.ARGUMENT_REQUIRED,
  //                CLASSDIR_OPT,
  //                "classes directory"),
          new CLOptionDescriptor("outputWsdlMode",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  OUTPUT_WSDL_MODE_OPT,
                  "output WSDL mode: All, Interface, Implementation"),
          new CLOptionDescriptor("locationImport",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  LOCATION_IMPORT_OPT,
                  "location of interface wsdl"),
          new CLOptionDescriptor("namespaceImpl",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  NAMESPACE_IMPL_OPT,
                  "target namespace for implementation wsdl"),
          new CLOptionDescriptor("outputImpl",
                  CLOptionDescriptor.ARGUMENT_REQUIRED,
                  OUTPUT_IMPL_OPT,
                  "output Implementation Wsdl filename, setting this causes --outputWsdlMode to be ignored"),
      };
  
      
      /**
       * Main
       */
      public static void main(String args[]) {
  
          String className = null;
          String classDir = null;
          String wsdlFilename = null;
          String wsdlImplFilename = null;
          HashMap namespaceMap = new HashMap();
          int mode = Emitter.MODE_ALL;
  
          // Parse the arguments
          CLArgsParser parser = new CLArgsParser(args, options);
  
          // Print parser errors, if any
          if (null != parser.getErrorString()) {
              System.err.println("Error: " + parser.getErrorString());
              printUsage();
          }
  
          // Get a list of parsed options
          List clOptions = parser.getArguments();
          int size = clOptions.size();
  
          try {
  
              // Instantiate the emitter
              Emitter emitter = new Emitter();
  
              // Parse the options and configure the emitter as appropriate.
              for (int i = 0; i < size; i++) {
                  CLOption option = (CLOption)clOptions.get(i);
  
                  switch (option.getId()) {
                      case CLOption.TEXT_ARGUMENT:
                          if (className != null) {
                              printUsage();
                          }
                          className = option.getArgument();
                          break;
  
                      case METHODS_ALLOWED_OPT:
                          emitter.setAllowedMethods(option.getArgument());
                          break;
  
                      case INHERITED_CLASS_OPT:
                          emitter.setUseInheritedMethods(true);
                          break;
  
                      case HELP_OPT:
                          printUsage();
                          break;
  
  //                    case CLASSDIR_OPT:
  //                        classDir = option.getArgument();
  //                        break;
  //
                      case OUTPUT_WSDL_MODE_OPT:
                          String modeArg = option.getArgument();
                          if ("All".equalsIgnoreCase(modeArg))
                              mode = Emitter.MODE_ALL;
                          else if ("Interface".equalsIgnoreCase(modeArg))
                              mode = Emitter.MODE_INTERFACE;
                          else if ("Implementation".equalsIgnoreCase(modeArg))
                              mode = Emitter.MODE_IMPLEMENTATION;
                          else {
                              mode = Emitter.MODE_ALL; 
                              System.err.println("unrecognized mode : " + modeArg);
                              System.err.println("use All, Interface and Implementation");
                              System.err.println("using default: All");
                          }
                          break;
  
                      case OUTPUT_OPT:
                          wsdlFilename = option.getArgument();
                          break;
  
                      case OUTPUT_IMPL_OPT:
                          wsdlImplFilename = option.getArgument();
                          break;
  
                      case PACKAGE_OPT:
                          String packageName = option.getArgument(0);
                          String namespace = option.getArgument(1);
                          namespaceMap.put(packageName, namespace);
                          break;
  
                      case NAMESPACE_OPT:
                          emitter.setIntfNamespace(option.getArgument());
                          break;
  
                      case NAMESPACE_IMPL_OPT:
                          emitter.setImplNamespace(option.getArgument());
                          break;
  
                      case SERVICE_NAME_OPT:
                          emitter.setServiceName(option.getArgument());
                          break;
  
                      case LOCATION_OPT:
                          emitter.setLocationUrl(option.getArgument());
                          break;
  
                      case LOCATION_IMPORT_OPT:
                          emitter.setImportUrl(option.getArgument());
                          break;
                  }
              }
  
              // Can't proceed without a class name
              if ((className == null)) {
                  printUsage();
              }
  
              if (!namespaceMap.isEmpty()) {
                  emitter.setNamespaceMap(namespaceMap);
              }
  
              // Find the class using the name and optionally the classDir
              emitter.setCls(className, classDir);
  
              // Generate a full wsdl, or interface & implementation wsdls
              if (wsdlImplFilename == null) {
                  emitter.emit(wsdlFilename, mode);
              } else {
                  emitter.emit(wsdlFilename, wsdlImplFilename);
              }
          }
          catch (Throwable t) {
              t.printStackTrace();
          }
  
      }
  
      /**
       * Print usage message and exit
       */
      private static void printUsage() {
          String lSep = System.getProperty("line.separator");
          StringBuffer msg = new StringBuffer();
          msg.append("Java2WSDL generator").append(lSep);
          msg.append("Usage: java " + Java2WSDL.class.getName() + " [options] class-of-portType").append(lSep);
          msg.append("Options: ").append(lSep);
          msg.append(CLUtil.describeOptions(Java2WSDL.options).toString());
          msg.append("Details: ").append(lSep);
          msg.append("\tportType    name= <class-of-portType name>").append(lSep);
          msg.append("\tbinding     name= <--service value>SoapBinding").append(lSep);
          msg.append("\tservice     name= <--service value>Service").append(lSep);
          msg.append("\tport        name= <--service value>").append(lSep);
          msg.append("\taddress location= <--location value>").append(lSep);
          System.out.println(msg.toString());
          System.exit(0);
      }
  
  }
  
  
  
  1.1                  xml-axis/java/src/org/apache/axis/wsdl/fromJava/Emitter.java
  
  Index: Emitter.java
  ===================================================================
  
  /*
   * The Apache Software License, Version 1.1
   *
   *
   * Copyright (c) 2001 The Apache Software Foundation.  All rights
   * reserved.
   *
   * Redistribution and use in source and binary forms, with or without
   * modification, are permitted provided that the following conditions
   * are met:
   *
   * 1. Redistributions of source code must retain the above copyright
   *    notice, this list of conditions and the following disclaimer.
   *
   * 2. Redistributions in binary form must reproduce the above copyright
   *    notice, this list of conditions and the following disclaimer in
   *    the documentation and/or other materials provided with the
   *    distribution.
   *
   * 3. The end-user documentation included with the redistribution,
   *    if any, must include the following acknowledgment:
   *       "This product includes software developed by the
   *        Apache Software Foundation (http://www.apache.org/)."
   *    Alternately, this acknowledgment may appear in the software itself,
   *    if and wherever such third-party acknowledgments normally appear.
   *
   * 4. The names "Axis" and "Apache Software Foundation" must
   *    not be used to endorse or promote products derived from this
   *    software without prior written permission. For written
   *    permission, please contact apache@apache.org.
   *
   * 5. Products derived from this software may not be called "Apache",
   *    nor may "Apache" appear in their name, without prior written
   *    permission of the Apache Software Foundation.
   *
   * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
   * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
   * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
   * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
   * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
   * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
   * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
   * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
   * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
   * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   * SUCH DAMAGE.
   * ====================================================================
   *
   * This software consists of voluntary contributions made by many
   * individuals on behalf of the Apache Software Foundation.  For more
   * information on the Apache Software Foundation, please see
   * <http://www.apache.org/>.
   */
  
  package org.apache.axis.wsdl.fromJava;
  
  import javax.wsdl.extensions.soap.SOAPAddress;
  import javax.wsdl.extensions.soap.SOAPBinding;
  import javax.wsdl.extensions.soap.SOAPBody;
  import javax.wsdl.extensions.soap.SOAPOperation;
  
  import com.ibm.wsdl.extensions.soap.SOAPAddressImpl;
  import com.ibm.wsdl.extensions.soap.SOAPBindingImpl;
  import com.ibm.wsdl.extensions.soap.SOAPBodyImpl;
  import com.ibm.wsdl.extensions.soap.SOAPOperationImpl;
  
  import org.apache.axis.Constants;
  import org.apache.axis.MessageContext;
  import org.apache.axis.encoding.SOAPTypeMappingRegistry;
  import org.apache.axis.encoding.TypeMappingRegistry;
  import org.apache.axis.utils.XMLUtils;
  import org.w3c.dom.Document;
  
  
  import javax.wsdl.Binding;
  import javax.wsdl.BindingInput;
  import javax.wsdl.BindingOperation;
  import javax.wsdl.BindingOutput;
  import javax.wsdl.Definition;
  import javax.wsdl.Input;
  import javax.wsdl.Import;
  import javax.wsdl.Message;
  import javax.wsdl.Operation;
  import javax.wsdl.Output;
  import javax.wsdl.Part;
  import javax.wsdl.Port;
  import javax.wsdl.PortType;
  import javax.wsdl.Service;
  import javax.wsdl.factory.WSDLFactory;
  import javax.xml.rpc.namespace.QName;
  
  import java.io.File;
  import java.io.FileOutputStream;
  import java.lang.reflect.Method;
  import java.lang.reflect.Modifier;
  import java.util.ArrayList;
  import java.util.Map;
  import java.util.StringTokenizer;
  
  /**
   * WSDL utility class, 1st cut.  Right now all the WSDL functionality for
   * dynamic Java->WSDL is in here - it probably wants to move elsewhere when
   * a more solid design stabilizes.
   *
   * @author Glen Daniels (gdaniels@macromedia.com)
   */
  public class Emitter {
  
      public static final int MODE_ALL = 0;
      public static final int MODE_INTERFACE = 1;
      public static final int MODE_IMPLEMENTATION = 2;
  
      private Class cls;
      private String allowedMethods;
      private boolean useInheritedMethods = false;
      private String intfNS;          
      private String implNS;
      private String locationUrl;
      private String importUrl;
      private String serviceName;
      private String targetService = null;
      private String description;
      private TypeMappingRegistry reg;
      private Namespaces namespaces;
  
      private ArrayList encodingList;
      private Types types;
      private String clsName;
  
      /**
       * Construct Emitter.                                            
       * Set the contextual information using set* methods at the end of the class.
       * Invoke emit to emit the code
       */
      public Emitter () {
        namespaces = new Namespaces();
      }
  
      /**
       * Generates WSDL documents for a given <code>Class</code> 
       *
       * @param filename1  interface WSDL                    
       * @param filename2  implementation WSDL                                
       * @throws Exception
       */
      public void emit(String filename1, String filename2) throws Exception {
          // Get interface and implementation defs
          Definition intf = getIntfWSDL();
          Definition impl = getImplWSDL();
  
          // Supply reasonable file names if not supplied
          if (filename1 == null) {
              filename1 = getServiceName() + "_interface.wsdl";
          }
          if (filename2 == null) {
              filename2 = getServiceName() + "_implementation.wsdl";
          }
  
          // Write out the interface def      
          Document doc = WSDLFactory.newInstance().newWSDLWriter().getDocument(intf);
          types.insertTypesFragment(doc);
          XMLUtils.PrettyDocumentToStream(doc, new FileOutputStream(new File(filename1)));
  
          // Write out the implementation def 
          doc = WSDLFactory.newInstance().newWSDLWriter().getDocument(impl);
          XMLUtils.PrettyDocumentToStream(doc, new FileOutputStream(new File(filename2)));
      }
  
      /**
       * Generates a complete WSDL document for a given <code>Class</code>
       *
       * @param filename  WSDL                    
       * @throws Exception
       */
      public void emit(String filename) throws Exception {
          emit(filename, MODE_ALL);
      }
  
      /**
       * Generates a WSDL document for a given <code>Class</code>. The sections of
       * the WSDL generated are controlled by the mode parameter 
       * mode 0: All
       * mode 1: Interface
       * mode 2: Implementation
       * 
       * @param filename  WSDL
       * @param mode generation mode - all, interface, implementation                     
       * @throws Exception
       */
      public void emit(String filename, int mode) throws Exception {
          Document doc = null;
          Definition def = null;
          switch (mode) {
              case MODE_ALL:
                  def = getWSDL();
                  doc = WSDLFactory.newInstance().newWSDLWriter().getDocument(def);
                  types.insertTypesFragment(doc);
                  break;
              case MODE_INTERFACE:
                  def = getIntfWSDL();
                  doc = WSDLFactory.newInstance().newWSDLWriter().getDocument(def);
                  types.insertTypesFragment(doc);
                  break;
              case MODE_IMPLEMENTATION:
                  def = getImplWSDL();
                  doc = WSDLFactory.newInstance().newWSDLWriter().getDocument(def);
                  break;
              default:
                  throw new Exception ("unrecognized output WSDL mode"); 
          }
  
          // Supply a reasonable file name if not supplied
          if (filename == null) {
              filename = getServiceName();
              switch (mode) {
              case MODE_ALL:
                  filename +=".wsdl";
                  break;
              case MODE_INTERFACE:
                  filename +="_interface.wsdl";
                  break;
              case MODE_IMPLEMENTATION:
                  filename +="_implementation.wsdl";
                  break;
              }
          }
              
          XMLUtils.PrettyDocumentToStream(doc, new FileOutputStream(new File(filename)));
      }
  
      /**
       * Get a Full WSDL <code>Definition</code> for the current configuration parameters
       *
       * @return WSDL <code>Definition</code>
       * @throws Exception
       */
      public Definition getWSDL() throws Exception {
          // Invoke the init() method to ensure configuration is setup
          init();
          
          // Create a definition
          Definition def = WSDLFactory.newInstance().newDefinition();
  
          // Write interface header
          writeDefinitions(def, intfNS);
          types = new Types(def, reg, namespaces, intfNS);
          Binding binding = writeBinding(def, true);
          writePortType(def, binding);
          writeService(def, binding);
          return def;
      }
  
     /**
       * Get a interface WSDL <code>Definition</code> for the current configuration parameters
       *
       * @return WSDL <code>Definition</code>
       * @throws Exception
       */
      public Definition getIntfWSDL() throws Exception {
          // Invoke the init() method to ensure configuration is setup
          init();
  
          // Create a definition
          Definition def = WSDLFactory.newInstance().newDefinition();
  
          // Write interface header
          writeDefinitions(def, intfNS);
          types = new Types(def, reg, namespaces, intfNS);
          Binding binding = writeBinding(def, true);
          writePortType(def, binding);
          return def;
      }
  
     /**
       * Get implementation WSDL <code>Definition</code> for the current configuration parameters
       *
       * @return WSDL <code>Definition</code>
       * @throws Exception
       */
      public Definition getImplWSDL() throws Exception {
          // Invoke the init() method to ensure configuration is setup
          init();
  
          // Create a definition
          Definition def = WSDLFactory.newInstance().newDefinition();
  
          // Write interface header
          writeDefinitions(def, implNS);
          writeImport(def, intfNS, importUrl);
          Binding binding = writeBinding(def, false); // Don't write binding to def
          writeService(def, binding);
          return def;
      }
      /**
       * Invoked prior to building a definition to ensure parms and data are set up.      
       * @throws Exception
       */
      private void init() throws Exception {
          if (encodingList == null) {
              clsName = cls.getName();
              clsName = clsName.substring(clsName.lastIndexOf('.') + 1);
  
              // If service name is null, construct it from location or className
              if (getServiceName() == null) {
                  String name = getLocationUrl();
                  if (name != null) {
                      if (name.lastIndexOf('/') > 0) {
                          name = name.substring(name.lastIndexOf('/') + 1);
                      } else if (name.lastIndexOf('\\') > 0) {
                          name = name.substring(name.lastIndexOf('\\') + 1);
                      } else { 
                          name = null;
                      }
                  }
                  if (name == null) {
                      name = clsName;
                  }
                  setServiceName(name);
              }
              
              encodingList = new ArrayList();
              encodingList.add(Constants.URI_SOAP_ENC);
              
              if (reg == null) {
                  reg = new SOAPTypeMappingRegistry();
              }
  
              if (intfNS == null) 
                  intfNS = Namespaces.makeNamespace(cls.getName());
              if (implNS == null)
                  implNS = intfNS + "-impl";
  
              namespaces.put(cls.getName(), intfNS, "intf");
              namespaces.putPrefix(implNS, "impl");
          }
      }
  
      /**
       * Create the definition header information.                                        
       *
       * @param def  <code>Definition</code>
       * @param tns  target namespace
       * @throws Exception
       */
      private void writeDefinitions(Definition def, String tns) throws Exception {
          def.setTargetNamespace(tns);
  
          def.addNamespace("intf", intfNS);
          def.addNamespace("impl", implNS);
  
          def.addNamespace("soap", "http://schemas.xmlsoap.org/wsdl/soap/");
          namespaces.putPrefix("http://schemas.xmlsoap.org/wsdl/soap/", "soap");
  
          def.addNamespace("wsdl", "http://schemas.xmlsoap.org/wsdl/");
          namespaces.putPrefix("wsdl", "http://schemas.xmlsoap.org/wsdl/");
  
          def.addNamespace("soapenc", Constants.URI_SOAP_ENC);
          namespaces.putPrefix(Constants.URI_SOAP_ENC, "soapenc");
  
          def.addNamespace("xsd", Constants.URI_CURRENT_SCHEMA_XSD);
          namespaces.putPrefix(Constants.URI_CURRENT_SCHEMA_XSD, "xsd");
      }
  
     /**
       * Create and add an import                                        
       *
       * @param def  <code>Definition</code>
       * @param tns  target namespace
       * @param loc  target location 
       * @throws Exception
       */
      private void writeImport(Definition def, String tns, String loc) throws Exception {
          Import imp = def.createImport();
  
          imp.setNamespaceURI(tns);
          if (loc != null && !loc.equals(""))
              imp.setLocationURI(loc);
          def.addImport(imp);
      }
  
      /**
       * Create the binding.                                        
       *
       * @param def  <code>Definition</code>
       * @param add  true if binding should be added to the def
       * @throws Exception
       */
      private Binding writeBinding(Definition def, boolean add) throws Exception {
          Binding binding = def.createBinding();
          binding.setUndefined(false);
          binding.setQName(new javax.wsdl.QName(intfNS, getServiceName() + "SoapBinding"));
  
          SOAPBinding soapBinding = new SOAPBindingImpl();
          soapBinding.setStyle("rpc");
          soapBinding.setTransportURI("http://schemas.xmlsoap.org/soap/http");
  
          binding.addExtensibilityElement(soapBinding);
  
          if (add) {
              def.addBinding(binding);
          }
          return binding;
      }
  
      /**
       * Create the service.                                        
       *
       * @param def  
       * @param binding                        
       * @throws Exception
       */
      private void writeService(Definition def, Binding binding) {
  
          Service service = def.createService();
  
          service.setQName(new javax.wsdl.QName(implNS, getServiceName()+"Service"));
          def.addService(service);
  
          Port port = def.createPort();
  
          port.setBinding(binding);
  
          // Probably should use the end of the location Url
          port.setName(getServiceName());
  
          SOAPAddress addr = new SOAPAddressImpl();
          addr.setLocationURI(locationUrl);
  
          port.addExtensibilityElement(addr);
  
          service.addPort(port);
      }
  
      /** Create a PortType                                        
       *
       * @param def  
       * @param binding                        
       * @throws Exception
       */
      private void writePortType(Definition def, Binding binding) throws Exception{
  
          PortType portType = def.createPortType();
          portType.setUndefined(false);
  
          // PortType name is the name of the class being processed
          portType.setQName(new javax.wsdl.QName(intfNS, clsName));
  
          /** @todo should introduce allowInterfaces, to publish all methods from a interface */
          /** @todo if allowedMethods is specified always look for inherited methods as well?? */
          Method[] methods;
          if (useInheritedMethods & (allowedMethods != null) && (allowedMethods.trim().length() > 0))
            methods = cls.getMethods();
          else
            methods = cls.getDeclaredMethods();
  
          for(int i = 0, j = methods.length; i < j; i++) {
              if (allowedMethods != null) {
                  if (allowedMethods.indexOf(methods[i].getName()) == -1)
                      continue;
              }
              if (!Modifier.isPublic(methods[i].getModifiers()))
                  continue;
              Operation oper = writeOperation(def, binding, methods[i].getName());
              writeMessages(def, oper, methods[i]);
              portType.addOperation(oper);
          }
  
          def.addPortType(portType);
  
          binding.setPortType(portType);
      }
  
      /** Create a Message                                        
       *
       * @param def  
       * @param oper                        
       * @param method                        
       * @throws Exception
       */
      private void writeMessages(Definition def, Operation oper, Method method) throws Exception{
          Input input = def.createInput();
  
          Message msg = writeRequestMessage(def, method);
          input.setMessage(msg);
          oper.setInput(input);
  
          def.addMessage(msg);
  
          msg = writeResponseMessage(def, method);
          Output output = def.createOutput();
          output.setMessage(msg);
          oper.setOutput(output);
  
          def.addMessage(msg);
      }
  
      /** Create a Operation
       *
       * @param def  
       * @param binding                        
       * @param operName                        
       * @throws Exception
       */
      private Operation writeOperation(Definition def, Binding binding, String operName) {
          Operation oper = def.createOperation();
          oper.setName(operName);
          oper.setUndefined(false);
          writeBindingOperation(def, binding, oper);
          return oper;
      }
  
      /** Create a Binding Operation
       *
       * @param def  
       * @param binding                        
       * @param oper                        
       * @throws Exception
       */
      private void writeBindingOperation (Definition def, Binding binding, Operation oper) {
          BindingOperation bindingOper = def.createBindingOperation();
          BindingInput bindingInput = def.createBindingInput();
          BindingOutput bindingOutput = def.createBindingOutput();
  
          bindingOper.setName(oper.getName());
  
          SOAPOperation soapOper = new SOAPOperationImpl();
          soapOper.setSoapActionURI("");
          soapOper.setStyle("rpc");
          bindingOper.addExtensibilityElement(soapOper);
  
          SOAPBody soapBody = new SOAPBodyImpl();
          soapBody.setUse("encoded");
          if (targetService == null)
              soapBody.setNamespaceURI(intfNS);
          else
              soapBody.setNamespaceURI(targetService);
          soapBody.setEncodingStyles(encodingList);
  
          bindingInput.addExtensibilityElement(soapBody);
          bindingOutput.addExtensibilityElement(soapBody);
  
          bindingOper.setBindingInput(bindingInput);
          bindingOper.setBindingOutput(bindingOutput);
  
          binding.addBindingOperation(bindingOper);
      }
  
      /** Create a Request Message
       *
       * @param def  
       * @param method             
       * @throws Exception
       */
      private Message writeRequestMessage(Definition def, Method method) throws Exception
      {
          Message msg = def.createMessage();
  
          javax.wsdl.QName qName
                  = createMessageName(def, method.getName(), "Request");
  
          msg.setQName(qName);
          msg.setUndefined(false);
  
          Class[] parameters = method.getParameterTypes();
          int offset = 0;
          for(int i = 0, j = parameters.length; i < j; i++) {
              // If the first param is a MessageContext, Axis will
              // generate it for us - it shouldn't be in the WSDL.
              if ((i == 0) && MessageContext.class.equals(parameters[i])) {
                  offset = 1;
                  continue;
              }
              writePartToMessage(def, msg, true, (i-offset), parameters[i], null); 
          }
  
          return msg;
      }
  
      /** Create a Response Message
       *
       * @param def  
       * @param method             
       * @throws Exception
       */
      private Message writeResponseMessage(Definition def, Method method) throws Exception
      {
          Message msg = def.createMessage();
  
          javax.wsdl.QName qName
                  = createMessageName(def, method.getName(), "Response");
  
          msg.setQName(qName);
          msg.setUndefined(false);
  
          Class type = method.getReturnType();
          writePartToMessage(def, msg, false, -1, type, method.getName().concat("Result"));
  
          Class[] parameters = method.getParameterTypes();
          int offset = 0;
          for(int i = 0, j = parameters.length; i < j; i++) {
              // If the first param is a MessageContext, Axis will
              // generate it for us - it shouldn't be in the WSDL.
              if ((i == 0) && MessageContext.class.equals(parameters[i])) {
                  offset = 1;
                  continue;
              }
              writePartToMessage(def, msg, false, (i-offset), parameters[i], null); 
          }
  
          return msg;
      }
  
      /** Create a Part
       *
       * @param def  
       * @param msg             
       * @param request     message is for a request
       * @param num         parm number (-1 if return value)     
       * @param param       Class type of parameter             
       * @param paramName   optional name of parameter  
       * @throws Exception
       */
      public void writePartToMessage(Definition def, Message msg, boolean request, int num, Class param, String paramName) throws Exception
      {
          // Return if this is a void type
          if (param == null ||
              param == java.lang.Void.TYPE)
              return;
  
          // Determine if this is a Holder class.  
          boolean holder = false;
          if (num >= 0 &&
              param.getName() != null &&
              param.getName().endsWith("Holder")) {
              // Holder is supposed to have a public value field.
              // (It appears the Wsdl2Java emits a _value field ??)
              java.lang.reflect.Field field;
              try {
                  field = param.getField("value");
              } catch (Exception e) {
                  field = null;
              }
              if (field == null) {
                  try {
                      field = param.getField("_value");
                  } catch (Exception e) {
                      field = null;
                  }
              }
              // If this is a holder, set the flag and change param to the held type.
              if (field != null) {
                  holder = true;
                  param = field.getType();
              }
          }
  
          // If Response message, only continue if holder or return
          if (!request && num >= 0 && !holder)
              return;
  
          // Create a paramName
          if (paramName == null) {
              if (num == -1)
                  paramName = "return";
              else if (holder)
                  paramName = "inOut" + num;
              else
                  paramName = "in" + num;
          }
  
          // Create the Part
          Part part = def.createPart();
  
          // Write the type representing the parameter type
          javax.wsdl.QName typeQName = types.writePartType(param);
          if (typeQName != null) {
              part.setTypeName(typeQName);
              part.setName(paramName);
          }
          msg.addPart(part);
      }
  
      /*
       * Return a message QName which has not already been defined in the WSDL
       */
      private javax.wsdl.QName createMessageName(Definition def,
                                                 String methodName,
                                                 String suffix) {
  
          javax.wsdl.QName qName = new javax.wsdl.QName(intfNS,
                                          methodName.concat(suffix));
  
          // Check the make sure there isn't a message with this name already
          int messageNumber = 1;
          while (def.getMessage(qName) != null) {
              StringBuffer namebuf = new StringBuffer(methodName.concat(suffix));
              namebuf.append(messageNumber);
              qName = new javax.wsdl.QName(intfNS, namebuf.toString());
              messageNumber++;
          }
          return qName;
      }
  
      // -------------------- Parameter Query Methods ----------------------------//
      
      /**
       * Returns the <code>Class</code> to export
       * @return the <code>Class</code> to export
       */
      public Class getCls() {
          return cls;
      }
  
      /**
       * Sets the <code>Class</code> to export
       * @param cls the <code>Class</code> to export
       */
      public void setCls(Class cls) {
          this.cls = cls;
      }
  
     /**
       * Returns the interface namespace
       * @return interface target namespace
       */
      public String getIntfNamespace() {
          return intfNS;     
      }
  
      /**
       * Set the interface namespace
       * @param ns interface target namespace            
       */
      public void setIntfNamespace(String ns) {
          this.intfNS = ns;                 
      }
  
     /**
       * Returns the implementation namespace
       * @return implementation target namespace
       */
      public String getImplNamespace() {
          return implNS;     
      }
  
      /**
       * Set the implementation namespace
       * @param ns implementation target namespace            
       */
      public void setImplNamespace(String ns) {
          this.implNS = ns;                 
      }
  
      /**
       * Sets the <code>Class</code> to export
       * @param className the name of the <code>Class</code> to export
       * @param classDir the directory containing the class (optional)
       */
      public void setCls(String className, String classDir) {
          try {
              cls = Class.forName(className);
          }
          catch (Exception ex) {
              /** @todo ravi: use classDir to load class directly into the class loader
               *  The case for it is that one can create a new directory, drop some source, compile and use a
               *  WSDL gen tool to generate wsdl - without editing the Wsdl gen tool's classpath
               *  Assuming all of the classes are either under classDir or otherwise in the classpath
               *
               *  Would this be useful?
               *  */
              ex.printStackTrace();
          }
      }
  
  
      /**
       * Returns a list of a space separated list of methods to export
       * @return a space separated list of methods to export
       */
      public String getAllowedMethods() {
          return allowedMethods;
      }
  
      /**
       * Set a space separated list of methods to export
       * @param allowedMethods a space separated list of methods to export
       */
      public void setAllowedMethods(String allowedMethods) {
          this.allowedMethods = allowedMethods;
      }
      
      public boolean getUseInheritedMethods() {
          return useInheritedMethods;
      }    
  
      public void setUseInheritedMethods(boolean useInheritedMethods) {
          this.useInheritedMethods = useInheritedMethods;
      }    
  
      /**
       * get the packagename to namespace map
       * @return <code>Map</code>
       */
      public Map getNamespaceMap() {
          return namespaces;
      }
  
      /**
       * Set the packagename to namespace map with the given map
       * @param map packagename/namespace <code>Map</code>
       */
      public void setNamespaceMap(Map map) {
          if (map != null)
              namespaces.putAll(map);
      }
  
      /**
       * Returns the String representation of the service endpoint URL
       * @return String representation of the service endpoint URL
       */
      public String getLocationUrl() {
          return locationUrl;
      }
  
      /**
       * Set the String representation of the service endpoint URL
       * @param locationUrl the String representation of the service endpoint URL
       */
      public void setLocationUrl(String locationUrl) {
          this.locationUrl = locationUrl;
      }
  
      /**
       * Returns the String representation of the interface import location URL
       * @return String representation of the interface import location URL
       */
      public String getImportUrl() {
          return importUrl;
      }
  
      /**
       * Set the String representation of the interface location URL for importing
       * @param locationUrl the String representation of the interface location URL for importing
       */
      public void setImportUrl(String importUrl) {
          this.importUrl = importUrl;
      }
  
      /**
       * Returns the String representation of the service URN
       * @return String representation of the service URN
       */
      public String getServiceName() {
          return serviceName;
      }
  
      /**
       * Set the String representation of the service URN
       * @param serviceUrn the String representation of the service URN
       */
      public void setServiceName(String serviceName) {
          this.serviceName = serviceName;
      }
  
      /**
       * Returns the target service name
       * @return the target service name
       */
      public String getTargetService() {
          return targetService;
      }
  
      /**
       * Set the target service name
       * @param targetService the target service name
       */
      public void setTargetService(String targetService) {
          this.targetService = targetService;
      }
  
      /**
       * Returns the service description
       * @return service description String
       */
      public String getDescription() {
          return description;
      }
  
      /**
       * Set the service description
       * @param description service description String
       */
      public void setDescription(String description) {
          this.description = description;
      }
  
      /**
       * Returns the <code>TypeMappingRegistry</code> used by the service
       * @return the <code>TypeMappingRegistry</code> used by the service
       */
      public TypeMappingRegistry getReg() {
          return reg;
      }
  
      /**
       * Sets the <code>TypeMappingRegistry</code> used by the service
       * @param reg the <code>TypeMappingRegistry</code> used by the service
       */
      public void setReg(TypeMappingRegistry reg) {
          this.reg = reg;
      }
  
  
      /**
       * @todo: this is the logic to hook into the existing WSDLUtils code.
       * WSDLUtils should be changed to invoke Emitter using the same interface
       * as Java2Wsdl.  Remove this method after WSDLUtils is changed.
       * 
       * Generates a WSDL document for a given <code>Class</code> and
       * a space separated list of methods at runtime
       *
       * @param cls <code>Class</code> object
       * @param allowedMethods space separated methods
       * @param locationUrl location of the service
       * @param serviceUrn service URN
       * @param description description of service
       * @param msgContext <code>MsgContext</code> of the service invocation
       * @return WSDL <code>Document</code>
       * @throws Exception
       */
          /** @todo ravi: fix targetNamespace for runtime generation
          // This is set to auto generated or user defined targetNamespace
          // need to figure out what it should be in the runtime situation
          // till we revisit, leave it as it was in WSDLUtils **/
  
      /*    
      public static Document writeWSDLDoc(Class cls,
                                      String allowedMethods,
                                      String locationUrl,
                                      String serviceUrn,
                                      String description,
                                      MessageContext msgContext) throws Exception
      {
          Emitter emitter = new Emitter();
          emitter.setCls(cls);
          emitter.setAllowedMethods(allowedMethods);
          emitter.setLocationUrl(locationUrl);
  
          emitter.setTargetNamespace(locationUrl);
  
          emitter.setServiceUrn(serviceUrn);
          emitter.setDescription(description);
          String targetService = msgContext.getTargetService();
          if ((targetService == null) || ("JWSProcessor".equals(targetService)))
              targetService = "";
          emitter.setTargetService(targetService);
          emitter.setReg(msgContext.getTypeMappingRegistry());
          Document doc = WSDLFactory.newInstance().newWSDLWriter().getDocument(emitter.emit());
          return doc;
      }
      */
  }
  
  
  
  1.1                  xml-axis/java/src/org/apache/axis/wsdl/fromJava/Namespaces.java
  
  Index: Namespaces.java
  ===================================================================
  /*
   * The Apache Software License, Version 1.1
   *
   *
   * Copyright (c) 2001 The Apache Software Foundation.  All rights
   * reserved.
   *
   * Redistribution and use in source and binary forms, with or without
   * modification, are permitted provided that the following conditions
   * are met:
   *
   * 1. Redistributions of source code must retain the above copyright
   *    notice, this list of conditions and the following disclaimer.
   *
   * 2. Redistributions in binary form must reproduce the above copyright
   *    notice, this list of conditions and the following disclaimer in
   *    the documentation and/or other materials provided with the
   *    distribution.
   *
   * 3. The end-user documentation included with the redistribution,
   *    if any, must include the following acknowledgment:
   *       "This product includes software developed by the
   *        Apache Software Foundation (http://www.apache.org/)."
   *    Alternately, this acknowledgment may appear in the software itself,
   *    if and wherever such third-party acknowledgments normally appear.
   *
   * 4. The names "Axis" and "Apache Software Foundation" must
   *    not be used to endorse or promote products derived from this
   *    software without prior written permission. For written
   *    permission, please contact apache@apache.org.
   *
   * 5. Products derived from this software may not be called "Apache",
   *    nor may "Apache" appear in their name, without prior written
   *    permission of the Apache Software Foundation.
   *
   * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
   * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
   * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
   * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
   * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
   * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
   * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
   * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
   * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
   * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   * SUCH DAMAGE.
   * ====================================================================
   *
   * This software consists of voluntary contributions made by many
   * individuals on behalf of the Apache Software Foundation.  For more
   * information on the Apache Software Foundation, please see
   * <http://www.apache.org/>.
   */
  package org.apache.axis.wsdl.fromJava;
  
  import java.util.HashMap;
  import java.util.Iterator;
  import java.util.Map;
  import java.util.StringTokenizer;
  
  /**
   * <p>Description: A HashMap of packageNames and namespaces with some helper methods </p>
   *
   * @author rkumar@borland.com
   */
  public class Namespaces extends HashMap {
      private int prefixCount = 1;
      private HashMap namespacePrefixMap = null;
  
      public Namespaces() {
          super();
          namespacePrefixMap  = new HashMap();
      }
  
      /**
       * Get the namespaace for the given package  If there is no entry in the HashMap for
       * this namespace, create one.
       * @param key String representing packagename
       * @return the namespace either created or existing
       */
      public String getCreate(String key) {
          Object value = super.get(key);
          if (value == null) {
              value = makeNamespaceFromPackageName((String) key);
              put(key, value, null);
          }
          return (String) value;
      }
  
      /**
       * Get the namespaace for the given package  If there is no entry in the HashMap for
       * this namespace, create one.
       * @param key String representing packagename
       * @param prefix the prefix to use for the generated namespace
       * @return the namespace either created or existing
       */
      public String getCreate(String key, String prefix) {
          Object value = super.get(key);
          if (value == null) {
              value = makeNamespaceFromPackageName((String) key);
              put(key, value, prefix);
          }
          return (String) value;
      }
  
      /**
       * adds an entry to the packagename/namespace HashMap.  In addition,
       * also makes an entry in the auxillary namespace/prefix HashMap if an
       * entry doesn't already exists
       * @param key packageName String
       * @param value namespace value
       * @param prefix the prefix to use for the given namespace
       * @return old value for the specified key
       */
      public Object put(Object key, Object value, String prefix) {
          if (prefix != null)
              namespacePrefixMap.put(value, prefix);
          else
              getCreatePrefix((String)value);
          return super.put(key, value);
      }
  
      /**
       * adds an entry to the packagename/namespace HashMap
       * for each of the entry in the map.  In addition, also add an entries in the
       * auxillary namespace/prefix HashMap
       * @param map packageName/namespace map
       */
      public void putAll(Map map) {
          Iterator i = map.keySet().iterator();
          while (i.hasNext()) {
              Object key = i.next();
              String namespace = (String) map.get(key);
              put(key, namespace, null);
          }
      }
  
      /**
       * Get the prefix for the given namespace. If one exists, create one
       * @param namespace namespace
       * @return prefix String
       */
      public String  getCreatePrefix(String namespace) {
          if (namespacePrefixMap.get(namespace) == null) {
              namespacePrefixMap.put(namespace, "tns" + prefixCount++);
          }
          return (String)namespacePrefixMap.get(namespace);
      }
  
      /**
       * put the gine namespace / prefix into the appropriate HashMap
       * @param namespace
       * @param prefix
       */
      public void putPrefix(String namespace, String prefix) {
          namespacePrefixMap.put(namespace, prefix);
      }
  
      /**
       * adds an entry to the namespace / prefix HashMap
       * for each of the entry in the map.
       *
       * @param map packageName/namespace map
       */
      public void putAllPrefix(Map map) {
          Iterator i = namespacePrefixMap.keySet().iterator();
          while (i.hasNext()) {
              Object key = i.next();
              String prefix = (String) map.get(key);
              put(key, prefix);
          }
      }
  
      /**
       * Make namespace from a fully qualified class name
       * use the default protocol for the namespace
       *
       * @param clsName fully qualified class name
       * @return namespace namespace String
       */
      public static String makeNamespace (String clsName) {
          return makeNamespace(clsName, "http");
      }
  
      /**
       * Make namespace from a fully qualified class name
       * and the given protocol
       *
       * @param clsName fully qualified class name
       * @param protocol protocol String
       * @return namespace namespace String
       */
      public static String makeNamespace (String clsName, String protocol) {
          if (clsName.lastIndexOf('.') == -1)
              return protocol + "://" + "DefaultNamespace";
          String packageName = clsName.substring(0, clsName.lastIndexOf('.'));
          return makeNamespaceFromPackageName(packageName, protocol);       
      }
  
      private static String makeNamespaceFromPackageName(String packageName) {
        return makeNamespaceFromPackageName(packageName, "http");       
      }
      
      
      private static String makeNamespaceFromPackageName(String packageName, String protocol) {
          if (packageName.equals("") ||packageName == null)
              return protocol + "://" + "DefaultNamespace";
          StringTokenizer st = new StringTokenizer( packageName, "." );
          String[] words = new String[ st.countTokens() ];
          for(int i = 0; i < words.length; ++i)
              words[i] = st.nextToken();
  
          StringBuffer sb = new StringBuffer(80);
          for(int i = words.length-1; i >= 0; --i) {
              String word = words[i];
              // seperate with dot
              if( i != words.length-1 )
                  sb.append('.');
              sb.append( word );
          }
          return protocol + "://" + sb.toString();
      }
  }
  
  
  
  1.1                  xml-axis/java/src/org/apache/axis/wsdl/fromJava/Types.java
  
  Index: Types.java
  ===================================================================
  
  /*
   * The Apache Software License, Version 1.1
   *
   *
   * Copyright (c) 2001 The Apache Software Foundation.  All rights
   * reserved.
   *
   * Redistribution and use in source and binary forms, with or without
   * modification, are permitted provided that the following conditions
   * are met:
   *
   * 1. Redistributions of source code must retain the above copyright
   *    notice, this list of conditions and the following disclaimer.
   *
   * 2. Redistributions in binary form must reproduce the above copyright
   *    notice, this list of conditions and the following disclaimer in
   *    the documentation and/or other materials provided with the
   *    distribution.
   *
   * 3. The end-user documentation included with the redistribution,
   *    if any, must include the following acknowledgment:
   *       "This product includes software developed by the
   *        Apache Software Foundation (http://www.apache.org/)."
   *    Alternately, this acknowledgment may appear in the software itself,
   *    if and wherever such third-party acknowledgments normally appear.
   *
   * 4. The names "Axis" and "Apache Software Foundation" must
   *    not be used to endorse or promote products derived from this
   *    software without prior written permission. For written
   *    permission, please contact apache@apache.org.
   *
   * 5. Products derived from this software may not be called "Apache",
   *    nor may "Apache" appear in their name, without prior written
   *    permission of the Apache Software Foundation.
   *
   * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
   * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
   * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
   * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
   * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
   * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
   * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
   * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
   * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
   * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   * SUCH DAMAGE.
   * ====================================================================
   *
   * This software consists of voluntary contributions made by many
   * individuals on behalf of the Apache Software Foundation.  For more
   * information on the Apache Software Foundation, please see
   * <http://www.apache.org/>.
   */
  
  package org.apache.axis.wsdl.fromJava;
  
  import org.apache.axis.Constants;
  import org.apache.axis.encoding.SOAPTypeMappingRegistry;
  import org.apache.axis.encoding.TypeMappingRegistry;
  import org.apache.axis.utils.XMLUtils;
  
  import org.w3c.dom.Attr;
  import org.w3c.dom.Document;
  import org.w3c.dom.DocumentFragment;
  import org.w3c.dom.Element;
  import org.w3c.dom.NamedNodeMap;
  import org.w3c.dom.Node;
  import org.w3c.dom.NodeList;
  
  
  
  import java.lang.reflect.Modifier;
  import java.lang.reflect.Method;
  import java.lang.reflect.Field;
  import java.util.ArrayList;
  import java.util.HashMap;
  import java.util.Iterator;
  import java.util.Map;
  
  import javax.wsdl.Definition;
  import javax.wsdl.factory.WSDLFactory;
  import javax.wsdl.QName;
  
  import com.ibm.wsdl.util.xml.DOMUtils;
  
  /**
   *
   * <p>Description: </p> This class is used to recursively serializes a Java Class into
   * an XML Schema representation.
   *
   * It has utility methods to create a schema node, assosiate namespaces to the various types
   *
   *
   * @author unascribed
   */
  public class Types {
  
      Definition def;
      Namespaces namespaces = null;
      TypeMappingRegistry reg;
      String targetNamespace;
      Element wsdlTypesElem = null;
      HashMap schemaTypes = null;
      HashMap schemaElementNames = null;
  
      /**
       * This class serailizes a <code>Class</code> to XML Schema. The constructor
       * provides the context for the streamed node within the WSDL document
       * @param def WSDL Definition Element to declare namespaces
       * @param doc Document element of the WSDL used to create child elements
       * @param reg TypeMappingRegistry to handle known types
       * @param namespaces user defined or autogenerated namespace and prefix maps
       * @param targetNamespace targetNamespace of the document
       */
      public Types(Definition def, TypeMappingRegistry reg, Namespaces namespaces, String targetNamespace) {
          this.def = def;
          createDocumentFragment();
          this.reg = reg;
          this.namespaces = namespaces;
          this.targetNamespace = targetNamespace;
          schemaElementNames = new HashMap();
          schemaTypes = new HashMap();
      }
  
      /**
       * Serialize the Class as XML schema to the document.
       * Create a types node for the WSDL if one doesn't exist
       * Create a schema node for the Class namespace, if one doesn't exist
       *
       * In case of a primitive type, no need to stream out anything, just return
       * the QName of the primitive type
       *
       * @param param <code>Class</code> to generate the XML Schema info for
       * @return the QName of the generated Schema type, null if void
       */
      public QName writePartType(Class type) throws Exception {
          if (type.getName().equals("void"))
            return null;
          if (isPrimitiveWsdlType(type)) {
              javax.xml.rpc.namespace.QName qName = reg.getTypeQName(type);
              return getWsdlQName(qName);
          }else {
              if (wsdlTypesElem == null)
                  writeWsdlTypesElement();
              return writeTypeAsElement(type);
          }
      }
  
      /**
       * Create a schema element for the given type
       * @param type the class type
       * @return the QName of the generated Element
       */
      private QName writeTypeAsElement(Class type) throws Exception {
          QName qName = writeTypeNamespace(type);
          String elementType = writeType(type);
          writeSchemaElement(qName, createElement(qName, elementType, isNullable(type)));
          return qName;
      }
  
      /**
       * write out the namespace declaration and return the type QName for the
       * given <code>Class</code>
       *
       * @param type input Class
       * @return QName for the schema type representing the class
       */
      private QName writeTypeNamespace(Class type) {
          javax.xml.rpc.namespace.QName qName = getTypeQName(type);
          String pref = def.getPrefix(qName.getNamespaceURI());
          if (pref == null)
            def.addNamespace(namespaces.getCreatePrefix(qName.getNamespaceURI()), qName.getNamespaceURI());
          return getWsdlQName(qName);
      }
  
      /**
       * Return the QName of the type
       * @param type input class
       * @return QName
       */
      private javax.xml.rpc.namespace.QName getTypeQName(Class type) {
          javax.xml.rpc.namespace.QName qName = null;
          String typeName = null;
          if (type.isArray()) {
              Class componentType = type.getComponentType();
  
              // Check for byte[] and Object[]
              if (componentType == java.lang.Byte.class ||
                  componentType == java.lang.Byte.TYPE) {
                  qName = new javax.xml.rpc.namespace.QName(Constants.URI_SOAP_ENC, "base64");
              } else if (componentType == java.lang.Object.class) {
                  qName = new javax.xml.rpc.namespace.QName(Constants.URI_SOAP_ENC, "Array");
              } else {
                  // Construct ArrayOf in targetNamespace
                  javax.xml.rpc.namespace.QName cqName = getTypeQName(componentType);
                  String pre = namespaces.getCreatePrefix(cqName.getNamespaceURI());
                  String localPart = "ArrayOf_" + pre + "_" + cqName.getLocalPart();
                  qName = new javax.xml.rpc.namespace.QName(targetNamespace, 
                                                            localPart);
              } 
          } else {
              // Get the QName from the registry, or create our own.
              qName = reg.getTypeQName(type);
              if (qName == null) {
                  String pkg = getPackageNameFromFullName(type.getName());
                  String lcl = getLocalNameFromFullName(type.getName());
  
                  String ns = namespaces.getCreate(pkg);
                  String pre = namespaces.getCreatePrefix(ns);
                  String localPart = lcl.replace('$', '_');
                  qName = new javax.xml.rpc.namespace.QName(ns, localPart);
              }
          }
  
          return qName;
      }
  
      /**
       * Utility method to get the package name from a fully qualified java class name
       * @param full input class name
       * @return package name
       */
      private String getPackageNameFromFullName(String full) {
          if (full.lastIndexOf('.') < 0)
              return "";
          else 
              return full.substring(0, full.lastIndexOf('.')); 
      }
  
      /**
       * Utility method to get the local class name from a fully qualified java class name
       * @param full input class name
       * @return package name
       */
      private String getLocalNameFromFullName(String full) {
          if (full.lastIndexOf('.') < 0)
              return full;
          else 
              return full.substring(full.lastIndexOf('.')+1); 
      }
  
      /**
       * Write out the given Element into the appropriate schema node.
       * If need be create the schema node as well
       *
       * @param qName qName to get the namespace of the schema node
       * @param element the Element to append to the Schema node
       */
      private void writeSchemaElement(QName qName, Element element) {
          Element schemaElem = null;
          NodeList nl = wsdlTypesElem.getChildNodes();
          for (int i = 0; i < nl.getLength(); i++ ) {
              NamedNodeMap attrs = nl.item(i).getAttributes();
              for (int n = 0; n < attrs.getLength(); n++) {
                  Attr a = (Attr)attrs.item(n);
                  if (a.getName().equals("targetNamespace") &&
                      a.getValue().equals(qName.getNamespaceURI()))
                      schemaElem = (Element)nl.item(i);
              }
          }
          if (schemaElem == null) {
            schemaElem = docHolder.createElement("schema");
            wsdlTypesElem.appendChild(schemaElem);
            schemaElem.setAttribute("xmlns", Constants.URI_CURRENT_SCHEMA_XSD);
            schemaElem.setAttribute("targetNamespace", qName.getNamespaceURI());
          }
          schemaElem.appendChild(element);
      }
  
      /**
       * Get the Types element for the WSDL document. If not present, create one
       * @throws Exception
       */
      private void writeWsdlTypesElement() throws Exception {
          NodeList nl = docFragment.getChildNodes();
          for (int n = 0; n < nl.getLength(); n++) {
              if (nl.item(n).getLocalName().equals("types")) {
                  wsdlTypesElem = (Element)nl.item(n);
                  return;
              }
          }
          wsdlTypesElem = docHolder.createElement("types");
          docFragment.appendChild(wsdlTypesElem);
      }
  
      /**
       * Write a schema representation for the given <code>Class</code>. Recurse through all the
       * Public fields as well as fields represented by java bean compliant accesor
       * methods.
       * Then return the qualified string representation of the generated type
       *
       * @param type Class for which to generate schema
       * @return a prefixed string for the schema type
       * @throws Exception
       */
      private String writeType(Class type) throws Exception {
  
          // Quick return if schema type
          if (isPrimitiveWsdlType(type))
              return "xsd:" + reg.getTypeQName(type).getLocalPart();
  
          // Write the namespace
          QName qName = writeTypeNamespace(type);
  
          // If an array the component type should be processed first
          String componentTypeName = null;
          Class componentType = null;
          if (type.isArray()) {
              componentType = type.getComponentType();
              componentTypeName = writeType(componentType);
          }
  
          String soapTypeName = qName.getLocalPart();
          String prefix = namespaces.getCreatePrefix(qName.getNamespaceURI());
          String prefixedName = prefix+":"+soapTypeName;
  
          // If processed before, or this is a known namespace, return
          if (!addToTypesList(qName, soapTypeName))
            return prefixedName;
  
          if (type.isArray()) {
              // ComplexType representation of array
              Element complexType = docHolder.createElement("complexType");
              writeSchemaElement(qName, complexType);
              complexType.setAttribute("name", soapTypeName);
  
              Element complexContent = docHolder.createElement("complexContent");
              complexType.appendChild(complexContent);
  
              Element restriction = docHolder.createElement("restriction");
              complexContent.appendChild(restriction);
              restriction.setAttribute("base", "soap:Array");
  
              Element attribute = docHolder.createElement("attribute");
              restriction.appendChild(attribute);
              attribute.setAttribute("ref", "soapenc:arrayType");
              attribute.setAttribute("wsdl:arrayType", componentTypeName + "[]" );
          } else {
              if (isEnumClass(type)) {
                  writeEnumType(qName, type);
              } else {
                  writeBeanClassType(qName, type);
              }
          }
          return prefixedName;
      }
      
      /**
       * Returns true if indicated type matches the JAX-RPC enumeration class.
       * (Only supports enumeration classes of string)
       */
      private boolean isEnumClass(Class type) {
          try {
              if (type.getDeclaredConstructor( new Class[] {String.class} ) != null &&
                  type.getMethod ("getValue", null) != null &&
                  type.getDeclaredMethod ("fromValue", new Class[] {String.class}) != null &&
                  type.getDeclaredFields() != null)
                  return true;
              else
                  return false;
                  
          } catch (Exception e) {
              return false;
          }
      }
  
      /**
       * Write Enumeration Complex Type
       * (Only supports enumeration classes of string types)
       * @param qname QName of type.
       * @param type class of type
       */
      private void writeEnumType(QName qName, Class type)  throws Exception  {
          if (!isEnumClass(type))
              return;
          Element simpleType = docHolder.createElement("simpleType");
          writeSchemaElement(qName, simpleType);
          simpleType.setAttribute("name", qName.getLocalPart());
          Element restriction = docHolder.createElement("restriction");
          simpleType.appendChild(restriction);
          String stringType = writeType(String.class);
          restriction.setAttribute("base", stringType);
          Field[] fields= type.getDeclaredFields();
          for (int i=0; i < fields.length; i++) {
              Field field = fields[i];
              int mod = field.getModifiers();
  
              // Inspect each public static final field of the same type as the class.
              if (Modifier.isPublic(mod) && 
                  Modifier.isStatic(mod) &&
                  Modifier.isFinal(mod) &&
                  field.getType() == type) {
                  Element enumeration = docHolder.createElement("enumeration");
                  enumeration.setAttribute("value", field.getName());
                  restriction.appendChild(enumeration);
                  
              }
          }
  
      }
  
      /**
       * Write Bean Class Complex Type
       * @param qname QName of type.
       * @param type class of type
       */
      private void writeBeanClassType(QName qName, Class type)  throws Exception  {
          // ComplexType representation of bean class
          Element complexType = docHolder.createElement("complexType");
          writeSchemaElement(qName, complexType);
          complexType.setAttribute("name", qName.getLocalPart());
  
          // See if there is a super class
          Element e = null;
          Class superClass = type.getSuperclass();
          if (superClass != null &&
              superClass != java.lang.Object.class) {
              // Write out the super class
              String base = writeType(superClass);
              Element complexContent = docHolder.createElement("complexContent");
              complexType.appendChild(complexContent);
              Element extension = docHolder.createElement("extension");
              complexContent.appendChild(extension);
              extension.setAttribute("base", base);
              e = extension;
          } else {
              e = complexType;
          }
  
          // Add fields under all element
          Element all = docHolder.createElement("all");
          e.appendChild(all);
          
          // Write out public fields and fields with bean accessors
          Field[] fld= type.getDeclaredFields();         
          for (int i=0;i<fld.length;i++) {
              if ((fld[i].getModifiers() == Modifier.PUBLIC) ||
                  (isJavaBean(type, fld[i]))) {
                  writeField (fld[i].getName(),fld[i].getType(),all);
              }
          }
      }
  
      /**
       * write a schema representation of the given Class field and append it to the where Node     * recurse on complex types
       * @param fieldName name of the field
       * @param fieldType type of the field
       * @param where location for the generated schema node
       * @throws Exception
       */
      private void writeField(String fieldName, Class fieldType, Element where) throws Exception {
          String elementType = writeType(fieldType);
          Element elem = createElement(fieldName, elementType, isNullable(fieldType));
          where.appendChild(elem);
      }
  
      /**
       * Create Element with a unique name generated from the namespace information
       * @param qName the namespace of the created element
       * @param elementType schema type representation of the element
       * @param nullable nillable attribute of the element
       * @return the created Element
       */
      private Element createElement(QName qName, String elementType, boolean nullable) {
          Element element = docHolder.createElement("element");
          String name = generateUniqueElementName(qName);
          element.setAttribute("name", name);
          if (nullable)
              element.setAttribute("nillable", "true");
          element.setAttribute("type", elementType);
          return element;
      }
  
      /**
       * Create Element with a given name and type
       * @param elementName the name of the created element
       * @param elementType schema type representation of the element
       * @param nullable nullable attribute of the element
       * @return the created Element
       */
      private Element createElement(String elementName, String elementType, boolean nullable) {
          Element element = docHolder.createElement("element");
          element.setAttribute("name", elementName);
          if (nullable)
              element.setAttribute("nillable", "true");
          element.setAttribute("type", elementType);
          return element;
      }
  
      /**
       * convert from JAX-RPC QName to WSDL QName
       * @param qName JAX-RPC QName
       * @return WSDL QName
       */
      private QName getWsdlQName (javax.xml.rpc.namespace.QName qName) {
          return new QName(qName.getNamespaceURI(), qName.getLocalPart());
      }
  
      /**
       * Is the given class one of the WSDL primitive types
       * @param type input Class
       * @return true if the type is primitive
       */
      boolean isPrimitiveWsdlType(Class type) {
        return (type == java.lang.Boolean.class ||
                type == java.lang.Boolean.TYPE  ||
                type == java.lang.Byte.class ||
                type == java.lang.Byte.TYPE ||
                type == java.lang.Character.class ||
                type == java.lang.Character.TYPE ||
                type == java.lang.Double.class ||
                type == java.lang.Double.TYPE ||
                type == java.lang.Float.class ||
                type == java.lang.Float.TYPE ||
                type == java.lang.Integer.class ||
                type == java.lang.Integer.TYPE ||
                type == java.lang.Long.class ||
                type == java.lang.Long.TYPE ||
                type == java.lang.Short.class ||
                type == java.lang.Short.TYPE ||
                type == java.lang.String.class);
      }
  
      /**
       * Generates a unique element name for a given namespace of the form
       * el0, el1 ....
       *
       * @param qName the namespace for the generated element
       * @return elementname
       */
      private String generateUniqueElementName(QName qName) {
        Integer count = (Integer)schemaElementNames.get(qName.getNamespaceURI());
        if (count == null)
          count = new Integer(0);
        else
          count = new Integer(count.intValue() + 1);
        schemaElementNames.put(qName.getNamespaceURI(), count);
        return "el" + count.intValue();
      }
  
      /**
       * Add the type to an ArrayList and return true if the Schema node
       * needs to be generated
       * If the type already exists, just return false to indicate that the type is already
       * generated in a previous iterration
       *
       * @param qName the name space of the type
       * @param typeName the name of the type
       * @return if the type is added returns true, else if the type is already present returns false
       */
      private boolean addToTypesList (QName qName, String typeName) {
          boolean added = false;
          ArrayList types = (ArrayList)schemaTypes.get(qName.getNamespaceURI());
          if (types == null) {
              types = new ArrayList();
              types.add(typeName);
              schemaTypes.put(qName.getNamespaceURI(), types);
              added = true;
          }
          else {
              if (!types.contains(typeName)) {
                 types.add(typeName);
                 added = true;
              }
          }
  
          // If addded, look at the namespace uri to see if the schema element should be 
          // generated.
          if (added) {
              String prefix = namespaces.getCreatePrefix(qName.getNamespaceURI());
              if (prefix.equals("soap") ||
                  prefix.equals("soapenc") ||
                  prefix.equals("wsdl") ||
                  prefix.equals("xsd")) 
                  return false;
              else
                  return true;
          }
          return false;
      }
   
      /**
       * Determines if the Field in the Class has bean compliant accessors. If so returns true,
       * else returns false
       * @param type the Class
       * @param field the Field
       * @return true if the Field has JavaBean style accessor
       */
      private boolean isJavaBean(Class type, Field field) {
          try {
              String setter = "set" + field.getName().substring(0,1).toUpperCase() + field.getName().substring(1);
              String getter = null;
              if (field.getType().getName() == "boolean")
                getter = "is" + field.getName().substring(0,1).toUpperCase() + field.getName().substring(1);
              else
                getter = "get" + field.getName().substring(0,1).toUpperCase() + field.getName().substring(1);
              type.getMethod(setter, new Class[] {field.getType()});
              type.getMethod(getter, null);
          }
          catch (NoSuchMethodException ex) {
              return false;
          }
          return true;
      }
  
      /**
       * Determines if the field is nullable. All non-primitives are Nullable
       *
       * @param type input Class
       * @return true if nullable
       */
      private boolean isNullable(Class type) {
          return !type.isPrimitive();
      }
  
  
      /** @todo ravi: Get rid of Doccument fragment and import node stuuf,
       *  once I have a handle on the wsdl4j mechanism to get at types.
       *
       *  Switch over notes: remove docHolder, docFragment in favor of wsdl4j Types
       */
      DocumentFragment docFragment;
      Document docHolder;
  
      private void createDocumentFragment () {
          this.docHolder = XMLUtils.newDocument();
          docFragment = docHolder.createDocumentFragment();
      }
      /**
       * Inserts the type fragment into the given wsdl document
       * @param doc
       */
      public void insertTypesFragment(Document doc) {
          doc.getDocumentElement().insertBefore(
                            doc.importNode(docFragment, true),
                            doc.getDocumentElement().getFirstChild());
      }
  }
  
  
  
  1.1                  xml-axis/java/src/org/apache/axis/wsdl/fromJava/todo.txt
  
  Index: todo.txt
  ===================================================================
  This is a todo list for Java2WSDL stuff
  ---------------------------------------
  Initial Version: Ravi Kumar(rkumar@borland.com) - Dec 2, 2001
  
  
  Group 1
  -------
  * Generate deployment - deploy.wsdd, undeploy.wsdd
  * Pluggable ParameterNameResolver for method parameters with complexType
  * Make PackageName=Namespace configurable using a properties file
  * Generate JAX-RPC style stub, skeleton and optionally refactor exporting 
    class as the impl class *** (see Note 1) ***
  
  Group 2
  -------
  * samples
    - Rich: I added samples/userguide/example6
  * User documentation
    - Rich: I have user-guide.html doc for example6 in my sandbox
  * Internationalization
  
  
  Group 3
  -------
  * Address roundtrip behaviour - with the exception of type promotion and param 
    naming differences
     - this has been started see test/sequence
  
  * A mechanism to register types (class:serializer:deserializer)
  
  
  Group 4
  -------
  * Support method overloading
  * support exporting by interface - in addition to allowed methods
  * Output mode currently has ALL, Interface, Implementation -- need to add Types
  * Output and OUTPUT_IMPL options are there to generate "split" files -- need to 
    add OUTPUT_TYPES as well 
  * Allow options for just for Java->XML type generation
  
  
  Group 5
  -------
  * Style/use support: rpc/encoded, document/literal, rpc/literal and document/encoded
  * Switch the runtime WSDL generation to use Java2WSDL
  
  
  
  ********************************************************************************
  NOTES:
  Use this place to clarify features if they are not immediately obvious
  
   
  Note 1: Generate JAX-RPC style classes
  --------------------------------------
  Java2WSDL needs to satisfy the following scenarios
  1. Export a class as a Web service 
          no wsdl is required, just the deploy.wsdd and undeploy.wsdd
  2. Export a class and generate WSD
          get both WSDL and deploy.wsdd, undeploy.wsdd
  3. Export a class and generate WSDL and JAX-RPC compliant stubs
          same as above plus client stub code --- Most typical need
  4. Export a class and generate WSDL and JAX-RPC compliant stubs and skeletons
          same as above plus skeleton and impl classes, optionally refactoring 
          the exporting class to be an impl class
  Basically IN ONE STEP, ALL code, wsdl and deployment generation for any of the 
  above scenarios. 
  Note, the functionality will be achieved y calling into Wsdl2Java as appropriate
  
  
  

Mime
View raw message