/*******************************************************************************
 * Copyright (c) 2001, 2004 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *******************************************************************************/
package org.eclipse.wst.wsdl.tests.util;

import java.io.FileOutputStream;
import java.util.Iterator;

import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Source;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;

import junit.framework.Test;
import junit.framework.TestSuite;

import org.eclipse.emf.ecore.resource.Resource;
import org.eclipse.wst.wsdl.Binding;
import org.eclipse.wst.wsdl.BindingFault;
import org.eclipse.wst.wsdl.BindingInput;
import org.eclipse.wst.wsdl.BindingOperation;
import org.eclipse.wst.wsdl.BindingOutput;
import org.eclipse.wst.wsdl.Definition;
import org.eclipse.wst.wsdl.ExtensibilityElement;
import org.eclipse.wst.wsdl.ExtensibleElement;
import org.eclipse.wst.wsdl.Fault;
import org.eclipse.wst.wsdl.Import;
import org.eclipse.wst.wsdl.Input;
import org.eclipse.wst.wsdl.MessageReference;
import org.eclipse.wst.wsdl.Operation;
import org.eclipse.wst.wsdl.Output;
import org.eclipse.wst.wsdl.Part;
import org.eclipse.wst.wsdl.Port;
import org.eclipse.wst.wsdl.PortType;
import org.eclipse.wst.wsdl.Service;
import org.eclipse.wst.wsdl.Types;
import org.eclipse.wst.wsdl.WSDLPackage;
import org.eclipse.wst.wsdl.internal.util.WSDLResourceFactoryImpl;
import org.eclipse.xsd.XSDPackage;
import org.eclipse.xsd.XSDSchema;
import org.eclipse.xsd.util.XSDResourceFactoryImpl;
import org.w3c.dom.Document;
import org.w3c.dom.Element;

import javax.wsdl.OperationType;

/**
 * @author Kihup Boo
 */
public class WSDLConverter extends DefinitionVisitor
{
  private Document doc;
  private Element description;
  private Element currentTypes;
  private Element currentService;
  private Element currentEndpoint;
  private Element currentInterface;
  private Element currentOperation;
  
  private Element currentBinding;
  private Element currentBindingOperation;
  private Element currentBindingInput;
  private Element currentBindingOutput;
  private Element currentBindingFault;
  
  private String wsdlNamespacePrefix;
  private String xsdNamespacePrefix;
  
  {
    // This is needed because we don't have the following in the plugin.xml
    //
    //   <extension point = "org.eclipse.emf.extension_parser">
    //     <parser type="wsdl" class="com.ibm.etools.wsdl.util.WSDLResourceFactoryImpl"/>
    //   </extension>
    //
    Resource.Factory.Registry.INSTANCE.getExtensionToFactoryMap().put("wsdl", new WSDLResourceFactoryImpl());
    WSDLPackage pkg = WSDLPackage.eINSTANCE;
  
    // We need this for XSD <import>.
    Resource.Factory.Registry.INSTANCE.getExtensionToFactoryMap().put("xsd", new XSDResourceFactoryImpl());
    XSDPackage xsdpkg = XSDPackage.eINSTANCE;
  }
  
  // Added for JUnit
  public WSDLConverter(String name) 
  {
    super(name);
  }
  
  /**
   * @param definition
   */
  public WSDLConverter(Definition definition)
  {
    super(definition);
    // TODO Auto-generated constructor stub
  }

  public void generate20(String filename) throws Exception
  {
    createDocument();
    visit();
    serialize(filename);
  }
  
  private void serialize(String filename) throws Exception
  {
    Source domSource = new DOMSource(doc);
    Transformer transformer = TransformerFactory.newInstance().newTransformer();
    transformer.setOutputProperty(OutputKeys.INDENT,"yes");
    transformer.setOutputProperty(OutputKeys.ENCODING,"UTF-8");
    transformer.setOutputProperty("{http://xml.apache.org/xslt}indent-amount","4");
    transformer.transform(domSource,new StreamResult(new FileOutputStream(filename)));
  }
  
  private void createDocument() throws ParserConfigurationException
  {
    doc = DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument();
  }
  
  private Element createWSDLElement(String name)
  {
    Element element = doc.createElementNS("http://www.w3.org/2004/08/wsdl",name);
    if (wsdlNamespacePrefix != null)
      element.setPrefix(wsdlNamespacePrefix);
    
    return element;
  }
  
  private void processDocumentation(Element docElement, Element parent)
  {
    if (docElement == null)
      return;

    Element adoptedDocElement = (Element)doc.importNode(docElement,true);
    parent.appendChild(adoptedDocElement);
  }
  
  protected void visitDefinition(Definition def)
  {
    description = createWSDLElement("description");
    processDocumentation(def.getDocumentationElement(),description);
    
    // TBD - Determine later if we want to convert the document to use SOAP 1.2.
    // However adding these two namespaces may not be harmful.
    description.setAttribute("xmlns:soapenv","http://www.w3.org/2003/05/soap-envelop");
    description.setAttribute("xmlns:wsoap","http://www.w3.org/2004/08/soap12");

    String targetNamespace = def.getTargetNamespace();
    if (targetNamespace != null)
      description.setAttribute("targetNamespace",targetNamespace);
    
    Iterator iterator = def.getNamespaces().keySet().iterator();
    String prefix = null;
    String namespace = null;
    /*
	xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
		xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"*/
    while (iterator.hasNext())
    {
      prefix = (String)iterator.next();
      namespace = def.getNamespace(prefix);
      
      if ("http://schemas.xmlsoap.org/wsdl/".equals(namespace))
      {
      	if (prefix.length() == 0) // meant to be default namespace
      	  description.setAttribute("xmlns","http://www.w3.org/2004/08/wsdl");
      	else
      	{
          description.setAttribute("xmlns:" + prefix,"http://www.w3.org/2004/08/wsdl");
          wsdlNamespacePrefix = prefix;
          description.setPrefix(wsdlNamespacePrefix);
      	}
      	continue;
      }
      
      // SOAP 1.2
      if ("http://schemas.xmlsoap.org/wsdl/soap/".equals(namespace))
      {
      	// SOAP 1.2
        description.setAttribute("xmlns:" + prefix,"http://www.w3.org/2003/05/soap-envelop");
        
        // WSDL 2.0 binding for SOAP 1.2
        description.setAttribute("xmlns:wsoap","http://www.w3.org/2004/08/soap12");
      	continue;
      }
      
      //if ("http://schemas.xmlsoap.org/soap/encoding/".equals(namespace))
      //  continue;
      
      if ("http://www.w3.org/2001/XMLSchema".equals(namespace))
        xsdNamespacePrefix = prefix; // We will use this in visitImport().
      
      if (prefix.length() == 0) // meant to be default namespace
        description.setAttribute("xmlns" + prefix,namespace);
      else
        description.setAttribute("xmlns:" + prefix,namespace);
    }
    
    doc.appendChild(description);
    super.visitDefinition(def);
    
  }
  
  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitImport(org.eclipse.wst.wsdl.Import)
   */
  protected void visitImport(Import wsdlImport)
  {
    // Determine if we <import> a schema.
    if (importingSchema(wsdlImport))
    {
      currentTypes = createWSDLElement("types");
      description.appendChild(currentTypes);
      
      //  <xs:import namespace="http://foo.com" schemaLocation= "bar.xsd"/>
      Element schemaImport = doc.createElementNS("http://www.w3.org/2001/XMLSchema","import");
      if (xsdNamespacePrefix == null) // need to add one
      {
        description.setAttribute("xmlns:xs","http://www.w3.org/2001/XMLSchema");
        xsdNamespacePrefix = "xs";
        schemaImport.setPrefix(xsdNamespacePrefix);
      }
      else if (!"".equals(xsdNamespacePrefix)) // it is not default namespace
      	schemaImport.setPrefix(xsdNamespacePrefix);
      
      schemaImport.setAttribute("namespace",wsdlImport.getNamespaceURI());
      schemaImport.setAttribute("schemaLocation",wsdlImport.getLocationURI());
      processDocumentation(wsdlImport.getDocumentationElement(),schemaImport);
      currentTypes.appendChild(schemaImport);
    }
  	else
    {
      Element importElement = wsdlImport.getElement();
      Element adoptedImportElement = (Element)doc.importNode(importElement,true);
      processDocumentation(wsdlImport.getDocumentationElement(),adoptedImportElement);
      description.appendChild(adoptedImportElement);
    }
  }
  
  private boolean importingSchema(Import myImport)
  {
    if (myImport.getDefinition() != null) // it is WSDL import
      return false;
    else
      return true;
  }

  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitTypes(org.eclipse.wst.wsdl.Types)
   */
  protected void visitTypes(Types types)
  {
  	// currentTypes may have been created in visitImport().
    if (currentTypes == null)
    {
      currentTypes = createWSDLElement("types");
      processDocumentation(types.getDocumentationElement(),currentTypes);
      description.appendChild(currentTypes);
    }
    
    Iterator iterator = types.getSchemas().iterator();
    XSDSchema schema = null;
    Element schemaElement = null;
    Element adoptedSchemaElement = null;
    while (iterator.hasNext())
    {
      schema = (XSDSchema)iterator.next();
      schema.updateElement();
      schemaElement = schema.getElement();
      adoptedSchemaElement = (Element)doc.importNode(schemaElement,true);
      currentTypes.appendChild(adoptedSchemaElement);
    }    
  }

  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitPart(org.eclipse.wst.wsdl.Part)
   */
  protected void visitPart(Part part)
  {
    // TODO Auto-generated method stub
  }

  protected void visitPortType(PortType portType)
  {
    currentInterface = createWSDLElement("interface");
  	processDocumentation(portType.getDocumentationElement(),currentInterface);
  	
    Element portTypeElement = portType.getElement();
    if (portTypeElement.hasAttribute("name"))
      currentInterface.setAttribute("name",portTypeElement.getAttribute("name"));
    
    description.appendChild(currentInterface);
    super.visitPortType(portType);
  }
  
  protected void visitOperation(Operation operation)
  {
    currentOperation = createWSDLElement("operation");
    processDocumentation(operation.getDocumentationElement(),currentOperation);
	
    Element operationElement = operation.getElement();
    if (operationElement.hasAttribute("name"))
      currentOperation.setAttribute("name",operationElement.getAttribute("name"));

    OperationType opType = operation.getStyle();
    if (OperationType.REQUEST_RESPONSE == opType)
      currentOperation.setAttribute("pattern","http://www.w3.org/2004/03/wsdl/in-out");
    else if (OperationType.SOLICIT_RESPONSE == opType)
        currentOperation.setAttribute("pattern","http://www.w3.org/2004/03/wsdl/out-in");
    else if (OperationType.NOTIFICATION == opType)
        currentOperation.setAttribute("pattern","http://www.w3.org/2004/03/wsdl/out-only");
    else if (OperationType.ONE_WAY == opType)
        currentOperation.setAttribute("pattern","http://www.w3.org/2004/03/wsdl/in-only");
    
    currentInterface.appendChild(currentOperation);
    super.visitOperation(operation);
  }
  
  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitInput(org.eclipse.wst.wsdl.Input)
   */
  protected void visitInput(Input input)
  {
    Element currentInput = createWSDLElement("input");
    processDocumentation(input.getDocumentationElement(),currentInput);
    
    Element inputElement = input.getElement();
    
    if (inputElement.hasAttribute("name"))
      currentInput.setAttribute("messageLabel",inputElement.getAttribute("name"));
    
    Element partElement = getPartElement(input);
    if (partElement.hasAttribute("element"))
      currentInput.setAttribute("element",partElement.getAttribute("element"));
    // TBD - what if the part uses "type"?
    
    currentOperation.appendChild(currentInput);
  }
  
  private Element getPartElement(MessageReference messageRef)
  {
    Iterator iterator = messageRef.getEMessage().getEParts().iterator();
    // TBD - for now, take the first part.
    Part part = (Part)iterator.next();
    Element partElement = part.getElement();
    return partElement;
  }

  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitOutput(org.eclipse.wst.wsdl.Output)
   */
  protected void visitOutput(Output output)
  {
    Element currentOutput = createWSDLElement("output");
    processDocumentation(output.getDocumentationElement(),currentOutput);
    
    Element outputElement = output.getElement();
    
    if (outputElement.hasAttribute("name"))
      currentOutput.setAttribute("messageLabel",outputElement.getAttribute("name"));
    
    Element partElement = getPartElement(output);
    if (partElement.hasAttribute("element"))
      currentOutput.setAttribute("element",partElement.getAttribute("element"));
    // TBD - what if the part uses "type"?
    
    currentOperation.appendChild(currentOutput);
  }

  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitFault(org.eclipse.wst.wsdl.Fault)
   */
  protected void visitFault(Fault fault)
  {
    // TODO Auto-generated method stub

  }

  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitBinding(org.eclipse.wst.wsdl.Binding)
   */
  protected void visitBinding(Binding binding)
  {
    currentBinding = createWSDLElement("binding");
    processDocumentation(binding.getDocumentationElement(),currentBinding);
    
    Element bindingElement = binding.getElement();
    if (bindingElement.hasAttribute("name"))
      currentBinding.setAttribute("name",bindingElement.getAttribute("name"));
    if (bindingElement.hasAttribute("type"))
      currentBinding.setAttribute("interface",bindingElement.getAttribute("type"));
    
    // TBD - is the next line fixed for SOAP?
    currentBinding.setAttribute("type","http://www.w3.org/2004/08/wsdl/soap12");
    currentBinding.setAttribute("wsoap:protocol","http://www.w3.org/2003/05/soap/bindings/HTTP");
    currentBinding.setAttribute("wsoap:mepDefault","http://www.w3.org.2003/05/soap/mep/request-response");

    description.appendChild(currentBinding);
    super.visitBinding(binding);
  }
  
  protected void visitBindingOperation(BindingOperation operation)
  {
    currentBindingOperation = createWSDLElement("operation");
    processDocumentation(operation.getDocumentationElement(),currentBindingOperation);
    
    Element operationElement = operation.getElement();
    String operationName = operation.getEOperation().getName();
 
    // Determine prefix
    String prefix = null;
    String targetNamespace = null;
    Definition def = operation.getEnclosingDefinition();
    if (def != null)
      targetNamespace = def.getTargetNamespace();
    if (targetNamespace != null)
      prefix = def.getPrefix(targetNamespace);
    
    if (prefix == null)
      prefix = "";
    else
      prefix += ":";
      
    currentBindingOperation.setAttribute("ref",prefix + operationName);
    
    currentBinding.appendChild(currentBindingOperation);
    super.visitBindingOperation(operation);
  }
 
  protected void visitBindingInput(BindingInput input)
  {
    currentBindingInput = createWSDLElement("input");
    processDocumentation(input.getDocumentationElement(),currentBindingInput);
    
    Element inputElement = input.getElement();
    String inputName = input.getName();
    if (inputName != null)
      inputElement.setAttribute("name",inputName);
    
    currentBindingOperation.appendChild(currentBindingInput);
    super.visitBindingInput(input);
  }
  
  protected void visitBindingOutput(BindingOutput output)
  {
    currentBindingOutput = createWSDLElement("output");
    processDocumentation(output.getDocumentationElement(),currentBindingOutput);
    
    Element outputElement = output.getElement();
    String outputName = output.getName();
    if (outputName != null)
      outputElement.setAttribute("name",outputName);
    
    currentBindingOperation.appendChild(currentBindingOutput);
    super.visitBindingOutput(output);
  }
  
  protected void visitBindingFault(BindingFault fault)
  {
    currentBindingFault = createWSDLElement("fault");
    processDocumentation(fault.getDocumentationElement(),currentBindingFault);
    
    Element faultElement = fault.getElement();
    String faultName = fault.getName();
    if (faultName != null)
      faultElement.setAttribute("name",faultName);
    
    currentBindingOperation.appendChild(currentBindingFault);
    super.visitBindingFault(fault); 
  }
 
  protected void visitService(Service service)
  {
    currentService = createWSDLElement("service");
    processDocumentation(service.getDocumentationElement(),currentService);
    
    Element serviceElement = service.getElement();
    if (serviceElement.hasAttribute("name"))
      currentService.setAttribute("name",serviceElement.getAttribute("name"));
    
    description.appendChild(currentService);
    super.visitService(service);
  }
  
  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitPort(org.eclipse.wst.wsdl.Port)
   */
  protected void visitPort(Port port)
  {
    currentEndpoint = createWSDLElement("endpoint");
    processDocumentation(port.getDocumentationElement(),currentEndpoint);
    
    Element portElement = port.getElement();
    if (portElement.hasAttribute("name"))
      currentEndpoint.setAttribute("name",portElement.getAttribute("name"));
    if (portElement.hasAttribute("binding"))
      currentEndpoint.setAttribute("binding",portElement.getAttribute("binding"));
    
    // Add interface to current service
    Binding binding = port.getEBinding();
    if (binding != null) // binding could not be resolved
    {
      Element bindingElement = binding.getElement();
      if (bindingElement.hasAttribute("type"))
        currentService.setAttribute("interface",bindingElement.getAttribute("type"));
    }
   
    currentService.appendChild(currentEndpoint);
    super.visitPort(port);
  }

  /* (non-Javadoc)
   * @see org.eclipse.wst.wsdl.tests.util.DefinitionVisitor#visitExtensibilityElement(org.eclipse.wst.wsdl.ExtensibleElement, org.eclipse.wst.wsdl.ExtensibilityElement)
   */
  protected void visitExtensibilityElement(ExtensibleElement owner, ExtensibilityElement extensibilityElement)
  {
    // TBD - It is not just SOAP binding
    if (owner instanceof org.eclipse.wst.wsdl.internal.impl.PortImpl)
    {
      Element soapElement = extensibilityElement.getElement();
      if (soapElement.hasAttribute("location"))
        currentEndpoint.setAttribute("address",soapElement.getAttribute("location"));
    }
    else
    {
      Element domElement = extensibilityElement.getElement();
      Element adoptedDOMElement = (Element)doc.importNode(domElement,true);
      
      if (owner instanceof org.eclipse.wst.wsdl.internal.impl.DefinitionImpl)
        description.insertBefore(adoptedDOMElement,description.getFirstChild());
      else if (owner instanceof org.eclipse.wst.wsdl.internal.impl.ServiceImpl)
        currentService.insertBefore(adoptedDOMElement,currentService.getFirstChild());
      else if (owner instanceof org.eclipse.wst.wsdl.internal.impl.PortTypeImpl)
      	currentInterface.insertBefore(adoptedDOMElement,currentInterface.getFirstChild());
      else if (owner instanceof org.eclipse.wst.wsdl.internal.impl.OperationImpl)
      	currentOperation.insertBefore(adoptedDOMElement,currentOperation.getFirstChild());
      else if (owner instanceof org.eclipse.wst.wsdl.internal.impl.BindingImpl)
      	currentBinding.insertBefore(adoptedDOMElement,currentBinding.getFirstChild());
      else if (owner instanceof org.eclipse.wst.wsdl.internal.impl.BindingOperationImpl)
      	currentBindingOperation.insertBefore(adoptedDOMElement,currentBindingOperation.getFirstChild());
      else if (owner instanceof org.eclipse.wst.wsdl.internal.impl.BindingInputImpl)
      	currentBindingInput.insertBefore(adoptedDOMElement,currentBindingInput.getFirstChild());
      else if (owner instanceof org.eclipse.wst.wsdl.internal.impl.BindingOutputImpl)
      	currentBindingOutput.insertBefore(adoptedDOMElement,currentBindingOutput.getFirstChild());
      else if (owner instanceof org.eclipse.wst.wsdl.internal.impl.BindingFaultImpl)
      	currentBindingFault.insertBefore(adoptedDOMElement,currentBindingFault.getFirstChild());

    }

  }
  
  public static Test suite() 
  {
    TestSuite suite = new TestSuite();
    
    suite.addTest
      (new WSDLConverter("Convert") 
         {
           protected void runTest() 
           {
             testConvert();
           }
         }
       );
    return suite;
  }
  
  public void testConvert()
  {
    try
    {
      Definition def = DefinitionLoader.load("d:/eclipse301/eclipse/workspace/org.eclipse.wst.wsdl.tests/PTATimeDistribution.wsdl");
      WSDLConverter converter = new WSDLConverter(def);
      converter.generate20("d:/eclipse301/eclipse/workspace/org.eclipse.wst.wsdl.tests/PTATimeDistribution20.wsdl");
    }
    catch (Exception e)
    {
      e.printStackTrace();
    }    
  }
  
  public static void main(String[] args)
  {
    junit.textui.TestRunner.run(suite());
    /*
    try
    {
      Definition def = DefinitionLoader.load(args[0]);
      WSDLConverter converter = new WSDLConverter(def);
      converter.generate20("test20.wsdl");
    }
    catch (Exception e)
    {
      e.printStackTrace();
    }*/
  }
}
