Package org.apache.muse.tools.generator.synthesizer

Source Code of org.apache.muse.tools.generator.synthesizer.ServerSynthesizer

/*=============================================================================*
*  Copyright 2006 The Apache Software Foundation
*
*  Licensed under the Apache License, Version 2.0 (the "License");
*  you may not use this file except in compliance with the License.
*  You may obtain a copy of the License at
*
*      http://www.apache.org/licenses/LICENSE-2.0
*
*  Unless required by applicable law or agreed to in writing, software
*  distributed under the License is distributed on an "AS IS" BASIS,
*  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*  See the License for the specific language governing permissions and
*  limitations under the License.
*=============================================================================*/

package org.apache.muse.tools.generator.synthesizer;

import java.io.File;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;

import javax.xml.namespace.QName;

import org.apache.muse.core.AbstractCapability;
import org.apache.muse.tools.generator.util.Capability;
import org.apache.muse.tools.generator.util.ConfigurationData;
import org.apache.muse.tools.generator.util.ConfigurationDataDescriptor;
import org.apache.muse.tools.inspector.JavaMethod;
import org.apache.muse.tools.inspector.JavaProperty;
import org.apache.muse.util.ReflectUtils;
import org.apache.muse.ws.resource.impl.AbstractWsResourceCapability;

/**
* A <code>Synthesizer</code> implementation that creates
* the server-side stubs for a set of capabilities. This involves creating
* accessors and constants for any properties and creating the operation
* templates that are to be filled-in by implementors. Unlike
* <code>ProxyGenerator</code> the code that comes out of this
* phase will throw Exceptions when any method is invoked because by
* default the methods have no implementation and simply throw
*
* <code>new RuntimeException("Unimplemented Method");");</code>
*
* @author Andrew Eberbach (aeberbac)
*
* @see org.apache.muse.tools.generator.synthesizer.Synthesizer
*/
public class ServerSynthesizer implements Synthesizer {

  private static final String INDENT = "    ";

  private static final String REQUEST_SUFFIX = "Request";

  private static final String IMPL_SUFFIX = "Impl";
   
  static final String INTERFACE_PREFIX = "I";
 
 
  protected Map[] _filesMaps = null;
 
  static ConfigurationDataDescriptor[] REQUIRED_PARAMETERS =
    new ConfigurationDataDescriptor[] {
      ConfigurationData.CAPABILITIES_MAP_LIST_CONFIGURATION,
    };

  public ConfigurationData synthesize(ConfigurationData configuration) throws Exception {
    ConfigurationData.checkConfiguration(this, configuration);
   
    Map[] capabilityMaps = (Map[])configuration.getParameter(ConfigurationData.CAPABILITIES_MAP_LIST);
    _filesMaps = new HashMap[capabilityMaps.length];       
   
    for(int i = 0; i < capabilityMaps.length; i++) {
     
      Map capabilities = capabilityMaps[i];
      _filesMaps[i] = new HashMap();
     
      for (Iterator j = capabilities.values().iterator(); j.hasNext();) {
        Capability capability = (Capability)j.next();
        if(!capability.isBuiltIn()) {
          generateCapability(capability, _filesMaps[i]);
        }
      }
    }
   
    ConfigurationData resultData = (ConfigurationData) configuration.clone();
    resultData.addParameter(ConfigurationData.FILES_MAP_LIST, _filesMaps);
   
    return resultData;
  }
 
  protected void generateCapability(Capability capability, Map files) {
    ClassInfo classInfo = new ClassInfo(capability);
         
    makeInterface(classInfo, files);
    makeAbstractClass(classInfo, files);
  }

  protected void makeInterface(ClassInfo classInfo, Map files) {
    StringBuffer code = new StringBuffer();
   
    generatePackageHeader(classInfo, code);
    generateImports(classInfo, false, code);
    generateInterfaceDeclaration(classInfo, code);

    generateOpenBlock(code);
    newLine(code);

    generateNSDeclarations(classInfo, code);
    generatePropertyOperations(classInfo, code, false);
    generateOperations(classInfo, code, false);
   
    generateCloseBlock(code);
   
    String className = makeFileName(classInfo, true);
   
    files.put(className, code.toString());
  }
 
  private void makeAbstractClass(ClassInfo classInfo, Map files) {   
    StringBuffer code = new StringBuffer();
   
    generatePackageHeader(classInfo, code);
    generateImports(classInfo, true, code);
    generateClassDeclaration(classInfo, code);

    generateOpenBlock(code);
    newLine(code);

    generatePropertiesDeclarations(classInfo, code);
    generatePropertyOperations(classInfo, code, true);
    generateOperations(classInfo, code, true);
   
    generateCloseBlock(code);
   
    String className = makeFileName(classInfo, false);
   
    files.put(className, code.toString());
  }

  private void generateInterfaceDeclaration(ClassInfo classInfo, StringBuffer code) {
    code.append("public interface "
      + getInterfaceName(classInfo.getClassShortName()));
    newLine(code);
  }

  private String getInterfaceName(String classShortName) {
    int indexOfImpl = classShortName.indexOf(IMPL_SUFFIX);
    if(indexOfImpl > 0) {
      classShortName = classShortName.substring(0, indexOfImpl);
    }
    return INTERFACE_PREFIX + classShortName;
  }

  protected void generateClassDeclaration(ClassInfo classInfo, StringBuffer code) {
    Capability capability = classInfo.getCapability();
    code.append("public class "
      + ReflectUtils.getShortName(capability.getImplementingClass())
      + " extends "
      + convertType(getBaseClass(capability),classInfo));
    code.append(" implements " + getInterfaceName(classInfo.getClassShortName()));
    newLine(code);
  }

  private void generatePropertiesDeclarations(ClassInfo classInfo, StringBuffer code) {
    Capability capability = classInfo.getCapability();
   
    if(capability.getProperties().size() == 0) {
      return;
    }
   
    indent(code);
    code.append("private static final "
      + convertType(QName.class, classInfo)
      + "[] _PROPERTIES = new "
      + convertType(QName.class, classInfo)
      + "[]");
    newLine(code);
   
    indent(code);
    generateOpenBlock(code);
    newLine(code);
   
    for(Iterator i=capability.getProperties().iterator(); i.hasNext();) {
      JavaProperty property = (JavaProperty)i.next();
      indent(2,code);
      code.append("new "
        + convertType(QName.class, classInfo)
        + "(NAMESPACE_URI, \""
        + getPropertyName(property, false)
        + "\", PREFIX)");
      if(i.hasNext()) {
        code.append(",");
      }
      newLine(code);
    }
   
    indent(code);
    generateCloseBlock(code);
    statement(";",code);
    newLine(2,code);
   
    indent(code);
    code.append("public "
      + convertType(QName.class, classInfo)
      + "[] getPropertyNames()");
    newLine(code);
   
    indent(code);
    generateOpenBlock(code);
    newLine(code);
   
    indent(2,code);
    code.append("return _PROPERTIES;");
   
    newLine(code);
    indent(code);
    generateCloseBlock(code);
    newLine(2,code);
   
    for(Iterator i=capability.getProperties().iterator(); i.hasNext();) {
      JavaProperty property = (JavaProperty)i.next();
      indent(code);
      code.append("private "
        + convertType(property.getJavaType(), classInfo)
        + " _"
        + getPropertyName(property, false)
        + ";");
      newLine(2, code);
    }
  }

  private String getPropertyName(JavaProperty property, boolean forSetter)  {   
    String name = property.getName().getLocalPart();
    if(!forSetter) {
      return name;
    }
    name = name.substring(0,1).toUpperCase() + name.substring(1);
    return name;
  }

  protected void generateOperations(ClassInfo classInfo, StringBuffer code, boolean generateBody) {
    Capability capability = classInfo.getCapability();
   
    for(Iterator i=capability.getOperations().iterator(); i.hasNext();) {
      JavaMethod method = (JavaMethod)i.next();   
     
      indent(code);
      code.append("public "
        + convertType(method.getReturnType(), classInfo)
        + " " + getMethodName(method));
     
      Class[] params = method.getParameterTypes();
      code.append("(");
     
      if (params.length > 0) {
        int j;
        for (j = 0; j < params.length - 1; j++) {
          code.append(convertType(params[j], classInfo)
            + " "
            + "param"
            + j
            + ", ");
        }
        code.append(convertType(params[j], classInfo)
          + " "
          + "param" + j);
      }
     
      code.append(") throws Exception")
     
      if(generateBody) {
        indent(code);
        generateOpenBlock(code);
        newLine(code);
       
        indent(2,code);
        code.append("//TODO implement " + getMethodName(method));
        newLine(code);
       
        indent(2,code);
        code.append("throw new RuntimeException(\"Unimplemented Method: " + getMethodName(method) + "\");");
        newLine(code);
       
        indent(code);
        generateCloseBlock(code);
      } else {
        code.append(";");
      }
      newLine(2,code);
    }
  }

  private void generatePropertyOperations(ClassInfo classInfo, StringBuffer code, boolean generateBody) {
    Capability capability = classInfo.getCapability();
   
    if(capability.getProperties().size() == 0) {
      return;
    }
   
    for(Iterator i=capability.getProperties().iterator(); i.hasNext();) {
      JavaProperty property = (JavaProperty)i.next();
      indent(code);
      code.append("public "
        + convertType(property.getJavaType(), classInfo)
        + " get"
        + getPropertyName(property, true)
        + "()");
     
      if(generateBody) {
        newLine(code);
        indent(code);
        generateOpenBlock(code);
        newLine(code);
       
        indent(2,code);
        statement("return _"
          + getPropertyName(property, false)
          ";",code);
        newLine(code);
       
        indent(code);
        generateCloseBlock(code);
      } else {
        code.append(";");
      }
      newLine(2,code);
     
      indent(code);
      code.append("public void");
      code.append(" set"
        + getPropertyName(property, true)
        + "("
        + convertType(property.getJavaType(), classInfo)
        + " param0)");
     
      if(generateBody) {
        newLine(code);
        indent(code);
        generateOpenBlock(code);
        newLine(code);
       
        indent(2,code);
        statement("_"
          + getPropertyName(property, false)
          + " = param0;",code);       
        newLine(code);
       
        indent(code);
        generateCloseBlock(code);       
      } else {
        code.append(";");
      }
      newLine(2,code);
    }
  }

  private void generateNSDeclarations(ClassInfo classInfo, StringBuffer code) {
    Capability capability = classInfo.getCapability();
    indent(code);
    statement("String PREFIX = \"tns\";", code);
    newLine(2,code);
   
    indent(code);
    statement("String NAMESPACE_URI = \""+ capability.getURI() +"\";", code);
    newLine(2,code);
  }

  protected void generateImports(ClassInfo classInfo, boolean isImpl, StringBuffer code) {
    Set imports = classInfo.getImports();
   
    Class baseClass = getBaseClass(classInfo.getCapability());
     
    if(isImpl && !imports.contains(baseClass)) {
      generateImport(baseClass, code);
    }
   
    if(classInfo.getCapability().getProperties().size() > 0) {   
      if(!imports.contains(QName.class)) {
        generateImport(QName.class, code);
      }
    }

    for (Iterator i = imports.iterator(); i.hasNext(); ) {
      generateImport((Class)i.next(),code);
    }
   
    newLine(code);
  }

  private void generateImport(Class theClass, StringBuffer code) {
    String className = needsImport(theClass);
    if (className != null) {
      code.append("import " + className + ";");
      code.append("\n");
    }
  }


  protected void generatePackageHeader(ClassInfo classInfo, StringBuffer code) {
    statement("package " + classInfo.getPackageName() + ";",code);
    newLine(2, code);
  }
 
  protected String getMethodName(JavaMethod method) {
    String name = method.getName().getLocalPart();
    name = name.substring(0,1).toLowerCase() + name.substring(1);
    if(name.endsWith(REQUEST_SUFFIX)) {
      name = name.substring(0, name.indexOf(REQUEST_SUFFIX));
    }
    return name;
  }

  protected String needsImport(Class className) {
    if(className.isPrimitive()) {
      return null;
    }
    if(className.isArray()) {
      className = ReflectUtils.getClassFromArrayClass(className);
    }   
    if(className.getName().startsWith("java.lang.")) {
      return null;
    }
    return className.getName();
    }
 
  protected String convertType(Class returnType, ClassInfo classInfo) {
    boolean isArray = returnType.isArray();
    returnType = isArray?ReflectUtils.getClassFromArrayClass(returnType):returnType;
   
    //Use fully-qualified name if conflict exists
    if(classInfo.hasConflict(returnType)) {     
      return returnType.getName()
    }
        return ReflectUtils.getShortName(returnType);   
  }

  protected Class getBaseClass(Capability capability) {
    if(capability.getProperties().size() > 0) {
      return AbstractWsResourceCapability.class;
    }
        return AbstractCapability.class;
  }   
 
  protected String makeFileName(ClassInfo classInfo, boolean isInterface) {
    String name = name = classInfo.getPackageName() + ".";
    if(isInterface) {
      name += getInterfaceName(classInfo.getClassShortName());
    } else {
      name += classInfo.getClassShortName()
    }   
    return name.replaceAll("\\.", "\\" + File.separator) + ".java";
  }

  protected void statement(String statement, StringBuffer code) {
    code.append(statement);
  }

  protected void newLine(StringBuffer code) {
    newLine(1,code);
  }
 
  protected void newLine(int n, StringBuffer code) {
    for(int i=0; i < n; i++) {
      code.append("\n");
    }
  }

  protected void generateCloseBlock(StringBuffer code) {
    code.append("}");
  }

  protected void generateOpenBlock(StringBuffer code) {
    code.append("{");
  }

  protected void indent(StringBuffer code) {
    indent(1,code);
  }
 
  protected void indent(int indent, StringBuffer code) {
    for(int i=0; i < indent; i++) {
      code.append(INDENT);
    }
  }

  public ConfigurationDataDescriptor[] getConfigurationDataDescriptions() {
    return REQUIRED_PARAMETERS;
  }
}
TOP

Related Classes of org.apache.muse.tools.generator.synthesizer.ServerSynthesizer

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.