/*******************************************************************************
 * Copyright (c) 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.ui.internal.dialogs.types;

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

import org.eclipse.core.resources.IFile;
import org.eclipse.jface.viewers.ILabelProvider;
import org.eclipse.swt.graphics.Image;
import org.eclipse.wst.common.core.search.pattern.QualifiedName;
import org.eclipse.wst.wsdl.Definition;
import org.eclipse.wst.wsdl.Import;
import org.eclipse.wst.wsdl.WSDLElement;
import org.eclipse.wst.wsdl.XSDSchemaExtensibilityElement;
import org.eclipse.wst.wsdl.internal.impl.ImportImpl;
import org.eclipse.wst.wsdl.ui.internal.WSDLEditorPlugin;
import org.eclipse.wst.wsdl.util.WSDLConstants;
import org.eclipse.wst.xsd.ui.internal.XSDEditorPlugin;
import org.eclipse.wst.xsd.ui.internal.dialogs.types.common.IComponentList;
import org.eclipse.wst.xsd.ui.internal.dialogs.types.xml.XMLComponentFinder;
import org.eclipse.wst.xsd.ui.internal.dialogs.types.xml.XMLComponentSelectionDialog;
import org.eclipse.wst.xsd.ui.internal.dialogs.types.xml.XMLComponentSelectionProvider;
import org.eclipse.wst.xsd.ui.internal.dialogs.types.xml.XMLComponentSpecification;
import org.eclipse.wst.xsd.ui.internal.search.IXSDSearchConstants;
import org.eclipse.wst.xsd.ui.internal.util.XSDDOMHelper;
import org.eclipse.wst.wsdl.ui.internal.search.IWSDLSearchConstants;
import org.eclipse.wst.wsdl.ui.internal.util.WSDLEditorUtil;
import org.eclipse.xsd.XSDComplexTypeDefinition;
import org.eclipse.xsd.XSDElementDeclaration;
import org.eclipse.xsd.XSDImport;
import org.eclipse.xsd.XSDNamedComponent;
import org.eclipse.xsd.XSDSchema;
import org.eclipse.xsd.XSDSchemaContent;
import org.eclipse.xsd.XSDSimpleTypeDefinition;
import org.eclipse.xsd.impl.XSDImportImpl;
import org.eclipse.xsd.util.XSDConstants;

public class WSDLComponentSelectionProvider extends XMLComponentSelectionProvider {
    public static final String BUILT_IN_TYPE = "BUILT_IN_TYPE";
    
    private WSDLComponentFinder wsdlComponentFinder;
    private WSDLComponentSelectionDialog dialog;
    private WSDLComponentLabelProvider labelProvider;
    private Definition definition;
    private QualifiedName metaName;
    private int kind;
    
    /*
     * Takes in the IFile we are currently editing.
     */
    public WSDLComponentSelectionProvider(IFile file, Definition definition, int kind) {
    	this.kind = kind;
        List validExt = new ArrayList(1);
        validExt.add("wsdl");
        this.metaName = getQualifiedName(kind);
        wsdlComponentFinder = new WSDLComponentFinder(metaName);
        wsdlComponentFinder.setFile(file);
        //wsdlComponentFinder.setValidExtensions(validExt);
        this.definition = definition;
        labelProvider = new WSDLComponentLabelProvider();
    }
    
    protected QualifiedName getQualifiedName(int kind)
    {    	 
    	switch (kind)
		{
		case WSDLConstants.BINDING :
		{
			return IWSDLSearchConstants.BINDING_META_NAME;
		}
		case WSDLConstants.PORT_TYPE :
		{
			return IWSDLSearchConstants.PORT_TYPE_META_NAME;
		}	
		case WSDLConstants.MESSAGE :
		{
			return IWSDLSearchConstants.MESSAGE_META_NAME;
		}   
		case WSDLEditorUtil.TYPE :
		{
			// TODO... need to combine complex and simple into a single meta name
			return IXSDSearchConstants.COMPLEX_TYPE_META_NAME;
		}
		case WSDLEditorUtil.ELEMENT :
		{
			return IXSDSearchConstants.ELEMENT_META_NAME;
		}
		}    	
    	return null;
    }

    public WSDLComponentSelectionProvider(IFile file, Definition definition, int kind, List validExt) {
        this(file, definition, kind);
        //wsdlComponentFinder.setValidExtensions(validExt);
    }
    
    public void setDialog(WSDLComponentSelectionDialog dialog) {
        this.dialog = dialog;
    }
    
    public String getType(Object element) {
        return null;
    }
    
    private void createWSDLComponentObjects(IComponentList list, List inputComponents, QualifiedName metaName) {
        Iterator it = inputComponents.iterator();
        while (it.hasNext()) {
            WSDLElement wsdlElement = (WSDLElement) it.next();
            XMLComponentSpecification spec = new XMLComponentSpecification(metaName); 
            spec.addAttributeInfo("name", wsdlElement.getElement().getAttribute("name"));
            spec.setTargetNamespace(wsdlElement.getEnclosingDefinition().getTargetNamespace());
            
            String normalizedFile = getNormalizedLocation(wsdlElement.getEnclosingDefinition().getLocation());
            spec.setFileLocation(normalizedFile);
            
            addDataItemToTreeNode(list, spec);
        }
    }
    
    private void createXSDComponentObjects(IComponentList list, List inputComponents, QualifiedName metaName) {
        Iterator it = inputComponents.iterator();
        while (it.hasNext()) {
            XSDNamedComponent xsdElement = (XSDNamedComponent) it.next();
            XMLComponentSpecification spec = new XMLComponentSpecification(metaName); 
            spec.addAttributeInfo("name", xsdElement.getName());
            spec.setTargetNamespace(xsdElement.getTargetNamespace());
            
            String normalizedFile = getNormalizedLocation(xsdElement.getSchema().getSchemaLocation());
            spec.setFileLocation(normalizedFile);
            
            addDataItemToTreeNode(list, spec);
        }
    }
        
    public void getComponents(IComponentList list, boolean quick) {
        if (quick) {
            //Iterator tags = lookupTagPaths.iterator();
            //while (tags.hasNext()) {
                getComponentsQuick(list, metaName);
            //}
        }
        else {
            // Grab components from workspace locations
            String scope = "";
            if (dialog != null) {
                scope = dialog.getSearchScope();
            }
            
            List comps = new ArrayList();
            if (scope.equals(XMLComponentSelectionDialog.SCOPE_ENCLOSING_PROJECT)) {
                comps = wsdlComponentFinder.getWorkbenchResourceComponents(XMLComponentFinder.ENCLOSING_PROJECT_SCOPE);
            }
            else if (scope.equals(XMLComponentSelectionDialog.SCOPE_WORKSPACE)) {
                comps = wsdlComponentFinder.getWorkbenchResourceComponents(XMLComponentFinder.ENTIRE_WORKSPACE_SCOPE);            
            }

            Iterator compsIt = comps.iterator();
            while (compsIt.hasNext()) {
                XMLComponentSpecification item = (XMLComponentSpecification) compsIt.next();
                addDataItemToTreeNode(list, item);
            }
        }
    }
    
    private void getComponentsQuick(IComponentList list, QualifiedName metaName) {
        // Grab components within the file
        if (metaName == IWSDLSearchConstants.BINDING_META_NAME) {
            // Grab explictly defined components
            createWSDLComponentObjects(list, definition.getEBindings(), metaName);
            
            // Grab directly imported components
            Iterator importsIt = getWSDLFileImports(definition.getEImports()).iterator();
            while (importsIt.hasNext()) {
                Import importItem = (Import) importsIt.next();
                Definition importDefinition = importItem.getEDefinition();
                List importedComponents = importDefinition.getEBindings();
                
                createWSDLComponentObjects(list, importedComponents, metaName);
            }
        }
        else if (metaName == IWSDLSearchConstants.PORT_TYPE_META_NAME) {
            // Grab explictly defined components
            createWSDLComponentObjects(list, definition.getEPortTypes(), metaName);
            
            // Grab directly imported components
            Iterator importsIt = getWSDLFileImports(definition.getEImports()).iterator();
            while (importsIt.hasNext()) {
                Import importItem = (Import) importsIt.next();
                Definition importDefinition = importItem.getEDefinition();
                List importedComponents = importDefinition.getEPortTypes();
                
                createWSDLComponentObjects(list, importedComponents, metaName);
            }
        }
        else if (metaName == IWSDLSearchConstants.MESSAGE_META_NAME) {
            // Grab explictly defined components
            createWSDLComponentObjects(list, definition.getEMessages(), metaName);
            
            // Grab directly imported components
            Iterator importsIt = getWSDLFileImports(definition.getEImports()).iterator();
            while (importsIt.hasNext()) {
                Import importItem = (Import) importsIt.next();
                Definition importDefinition = importItem.getEDefinition();
                List importedComponents = importDefinition.getEMessages();
                
                createWSDLComponentObjects(list, importedComponents, metaName);
            }
        }
        /*TODO... fix these cases
        else if (metaName == IXSDSearchConstants.COMPLEX_TYPE_META_NAME) {
            createXSDInlineTypesObjects(list, metaName);
        }
        else if (metaName.equals("/definitions/types/schema/simpleType")) {
            createXSDInlineTypesObjects(list, metaName);
        }*/
        else if (metaName == IXSDSearchConstants.ELEMENT_META_NAME) {
            createXSDElementObjects(list, metaName);
            createRegularImportXSDElementObjects(list);
        }
        else if (metaName == IXSDSearchConstants.COMPLEX_TYPE_META_NAME){
            createXSDInlineWrapperTypeObjects(list, metaName);
            
            createXSDBuiltInTypeObjects(list);
            createRegularImportXSDTypeObjects(list);
        }
        else if (metaName == IXSDSearchConstants.SIMPLE_TYPE_META_NAME) {
            createXSDInlineWrapperTypeObjects(list, metaName);
        }
        //else if (metaName.equals("/schema/element")) {
        //    createXSDInlineWrapperElementObjects(list, metaName);
        //}
    }
    
    private List getWSDLFileImports(List wsdlImports) {
        List list = new ArrayList();
        Iterator it = wsdlImports.iterator();
        while (it.hasNext()) {
            ImportImpl importItem = (ImportImpl) it.next();
            importItem.importDefinitionOrSchema();          // Load if necessary
            if (importItem.getESchema() == null) {
                list.add(importItem);
            }
        }
        
        return list;
    }
    
    private void createXSDBuiltInTypeObjects(IComponentList list) { 
        for (int i = 0; i < XSDDOMHelper.dataType.length; i++) {
            String builtIn = XSDDOMHelper.dataType[i][0];
            XMLComponentSpecification spec = new XMLComponentSpecification(null);//BUILT_IN_TYPE); 
            spec.addAttributeInfo("name", builtIn);
            spec.setTargetNamespace(XSDConstants.SCHEMA_FOR_SCHEMA_URI_2001);

//            String normalizedFile = getNormalizedLocation(definition.getLocation());
//            spec.setFileLocation(normalizedFile);
            spec.setFileLocation("Built-in");    
            
            addDataItemToTreeNode(list, spec);
        }
    }
    
    private void createRegularImportXSDTypeObjects(IComponentList list) {
        // Handle regular imports(xsd and wsdl).
        Iterator imports = definition.getEImports().iterator();
        while (imports.hasNext()) {
            Import importItem = (Import) imports.next();
            ((ImportImpl) importItem).importDefinitionOrSchema();
            List schemas = new ArrayList();
            String complexPath = "";
            String simplePath = "";
            
            if (importItem.getESchema() != null) {
                // Import is a xsd file
                schemas.add(importItem.getESchema());
                complexPath = "/schema/complexType";
                simplePath = "/schema/simpleType";
            }
            else if (importItem.getEDefinition() != null) {
                // Import is a wsdl file
                Definition definition = importItem.getEDefinition();
                if (definition.getETypes() != null) {
	                Iterator schemaIt = definition.getETypes().getEExtensibilityElements().iterator();
	                while (schemaIt.hasNext()) {
	                    XSDSchemaExtensibilityElement eeElement = (XSDSchemaExtensibilityElement) schemaIt.next();
	                    schemas.add(eeElement.getSchema());
	                    complexPath = "/definitions/types/schema/complexType";
	                    simplePath = "/definitions/types/schema/simpleType";
	                }
                }
            }
            
            if (schemas.size() > 0) {
                Iterator schemaIt = schemas.iterator();
                while (schemaIt.hasNext()) {
                    Iterator typesIt = ((XSDSchema) schemaIt.next()).getTypeDefinitions().iterator();
                    List complexList = new ArrayList();
                    List simpleList = new ArrayList();
                    while (typesIt.hasNext()) {
                        Object component = typesIt.next();
                        if (component instanceof XSDComplexTypeDefinition) {
                            complexList.add(component);
                        }
                        else if (component instanceof XSDSimpleTypeDefinition) {
                            simpleList.add(component);
                        }
                    }
                    
                    createXSDComponentObjects(list, complexList, IXSDSearchConstants.COMPLEX_TYPE_META_NAME);
                    createXSDComponentObjects(list, simpleList, IXSDSearchConstants.SIMPLE_TYPE_META_NAME);
                }
            }
        }
    }
    
    private void createRegularImportXSDElementObjects(IComponentList list) {
        // Handle regular imports(xsd and wsdl).
        Iterator imports = definition.getEImports().iterator();
        while (imports.hasNext()) {
            Import importItem = (Import) imports.next();
            ((ImportImpl) importItem).importDefinitionOrSchema();
            List schemas = new ArrayList();
            String path = "";
            
            if (importItem.getESchema() != null) {
                // Import is a xsd file
                schemas.add(importItem.getESchema());
                path = "/schema/element";
            }
            else if (importItem.getEDefinition() != null) {
                // Import is a wsdl file
                Definition definition = importItem.getEDefinition();
                if (definition.getETypes() != null) {
	                Iterator schemaIt = definition.getETypes().getEExtensibilityElements().iterator();
	                while (schemaIt.hasNext()) {
	                    XSDSchemaExtensibilityElement eeElement = (XSDSchemaExtensibilityElement) schemaIt.next();
	                    schemas.add(eeElement.getSchema());
	                    path = "/definitions/types/schema/element";
	                }
                }
            }
            
            if (schemas.size() > 0) {
                Iterator schemaIt = schemas.iterator();
                while (schemaIt.hasNext()) {
                    List elementList = ((XSDSchema) schemaIt.next()).getElementDeclarations();
                    createXSDComponentObjects(list, elementList, IXSDSearchConstants.ELEMENT_META_NAME);
                }
            }
        }
    }
    
    private void createXSDInlineTypesObjects(IComponentList list, QualifiedName tagPath) {
        // Handle inline schemas
    	if (definition.getETypes() == null) {
    		return;
    	}
    	
        Iterator inlineSchemasIt = definition.getETypes().getSchemas().iterator();
        while (inlineSchemasIt.hasNext()) {
            XSDSchema schema = (XSDSchema) inlineSchemasIt.next();
            
            if (schema.getTargetNamespace() != null && !schema.getTargetNamespace().equals("")) {
                    List keepTypes = new ArrayList();
                    Iterator typeIterator = schema.getTypeDefinitions().iterator();
                    // Filter out unwanted Types
                    if (tagPath.equals("/definitions/types/schema/complexType")) {
                        while (typeIterator.hasNext()) {
                            Object type = typeIterator.next();
                            if (type instanceof XSDComplexTypeDefinition &&
                                    ((XSDComplexTypeDefinition) type).getSchema().equals(schema)) {
                                keepTypes.add(type);
                            }
                        }
                    }
                    else if (tagPath.equals("/definitions/types/schema/simpleType")) {
                        while (typeIterator.hasNext()) {
                            Object type = typeIterator.next();
                            if (type instanceof XSDSimpleTypeDefinition &&
                                    ((XSDSimpleTypeDefinition) type).getSchema().equals(schema)) {
                                keepTypes.add(type);
                            }
                        }
                    }
                    
                    createXSDComponentObjects(list, keepTypes, tagPath);
            }
        }
    }

    private void createXSDElementObjects(IComponentList list, QualifiedName tagPath) {
    	if (definition.getETypes() == null) {
    		return;
    	}
    	
        Iterator inlineSchemasIt = definition.getETypes().getSchemas().iterator();
        while (inlineSchemasIt.hasNext()) {
            XSDSchema schema = (XSDSchema) inlineSchemasIt.next();
            
            List keepElements = new ArrayList();
            if (schema.getTargetNamespace() != null && !schema.getTargetNamespace().equals("")) {
                Iterator elementIt = schema.getElementDeclarations().iterator();
                while (elementIt.hasNext()) {
                    // Only look for elements explicitly defined in the Schema (not through imports).
                    XSDElementDeclaration xsdElement = (XSDElementDeclaration) elementIt.next();
                    if (xsdElement.getSchema().equals(schema)) {
                        keepElements.add(xsdElement);
                    }
                }
                
                createXSDComponentObjects(list, keepElements, tagPath);
            }
        }
    }
    
    private void createXSDInlineWrapperTypeObjects(IComponentList list, QualifiedName tagPath) {
        // Handle inline schemas
    	if (definition.getETypes() == null) {
    		return;
    	}
    	
        Iterator inlineSchemasIt = definition.getETypes().getSchemas().iterator();
        while (inlineSchemasIt.hasNext()) {
            XSDSchema schema = (XSDSchema) inlineSchemasIt.next();
            
            if (schema.getTargetNamespace() == null || schema.getTargetNamespace().equals("")) {
                List keepTypes = new ArrayList();
                
                List imports = new ArrayList();
                Iterator contents = schema.getContents().iterator();
                while (contents.hasNext()) {
                    XSDSchemaContent content = (XSDSchemaContent) contents.next();
                    if (content instanceof XSDImport) {
                        imports.add(content);             
                    }
                }
                
                Iterator importIterator = imports.iterator();
                while (importIterator.hasNext()) {
                    XSDImport importObject = (XSDImport) importIterator.next();
                    XSDSchema importSchema = ((XSDImportImpl) importObject).importSchema();
                    Iterator typesIt = importSchema.getTypeDefinitions().iterator();
                    while (typesIt.hasNext()) {
                        Object typeObject = typesIt.next();
                        if (tagPath.equals("/schema/complexType") &&
                            typeObject instanceof XSDComplexTypeDefinition) {
                            keepTypes.add(typeObject);
                        }
                        else if (tagPath.equals("/schema/simpleType") &&
                                 typeObject instanceof XSDSimpleTypeDefinition) {
                            keepTypes.add(typeObject);
                        }
                    }
                    
                }

                createXSDComponentObjects(list, keepTypes, tagPath);
            }
        }
    }
    
    private void createXSDInlineWrapperElementObjects(IComponentList list, QualifiedName tagPath) {
    	if (definition.getETypes() == null) {
    		return;
    	}
    	
        Iterator inlineSchemasIt = definition.getETypes().getSchemas().iterator();
        while (inlineSchemasIt.hasNext()) {
            XSDSchema schema = (XSDSchema) inlineSchemasIt.next();
            
            if (schema.getTargetNamespace() == null || schema.getTargetNamespace().equals("")) {
                Iterator contents = schema.getContents().iterator();
                List imports = new ArrayList();
                while (contents.hasNext()) {
                    XSDSchemaContent content = (XSDSchemaContent) contents.next();
                    if (content instanceof XSDImport) {
                        imports.add(content);             
                    }
                }
                
                Iterator importIterator = imports.iterator();
                while (importIterator.hasNext()) {
                    XSDImport importObject = (XSDImport) importIterator.next();
                    XSDSchema importSchema = ((XSDImportImpl) importObject).importSchema();

                    createXSDComponentObjects(list, importSchema.getElementDeclarations(), tagPath);    
                }                
            }
        }
    }

//      private ITypeSystemProvider getTypeSystemProvider() {
//            ITypeSystemProvider provider = WSDLEditorUtil.getInstance().getTypeSystemProvider(definition);
//            if (provider instanceof ExtensibleTypeSystemProvider) {
//                provider = (ExtensibleTypeSystemProvider) provider; 
//            }
//            else {
//                return null;
//            }
//            
//            return provider;
//      }

    
  
    public ILabelProvider getLabelProvider() {
        return labelProvider;
    }    
    
	public String getListTitle() {

		switch (kind)
		{
		case WSDLConstants.BINDING :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_MATCHING_BINDINGS");
		}
		case WSDLConstants.PORT_TYPE :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_MATCHING_PORTTYPES");
		}	
		case WSDLConstants.MESSAGE :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_MATCHING_MESSAGES");
		}   
		case WSDLEditorUtil.TYPE :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_MATCHING_TYPES");
		}
		case WSDLEditorUtil.ELEMENT :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_MATCHING_ELEMENTS");
		}
		}    	
		return null;	   
	}

	public String getNameFieldTitle() {
		switch (kind)
		{
		case WSDLConstants.BINDING :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_BINDING_NAME");
		}
		case WSDLConstants.PORT_TYPE :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_PORTTYPE_NAME");
		}	
		case WSDLConstants.MESSAGE :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_MESSAGE_NAME");
		}   
		case WSDLEditorUtil.TYPE :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_TYPE_NAME");
		}
		case WSDLEditorUtil.ELEMENT :
		{
			return WSDLEditorPlugin.getWSDLString("_UI_LABEL_ELEMENT_NAME");
		}
		}    	
		return null;	   
	}
    public class WSDLComponentLabelProvider extends XMLComponentSelectionLabelProvider {
        public Image getImage(Object element) {
            XMLComponentTreeObject specification = (XMLComponentTreeObject) element;
            XMLComponentSpecification spec = (XMLComponentSpecification) specification.getXMLComponentSpecification().get(0);
            if (spec.getMetaName() == IWSDLSearchConstants.BINDING_META_NAME) {
                return WSDLEditorPlugin.getInstance().getImage("icons/binding_obj.gif");
            }
            else if (spec.getMetaName() == IWSDLSearchConstants.PORT_TYPE_META_NAME) {
                return WSDLEditorPlugin.getInstance().getImage("icons/portType_obj.gif");
            }
            else if (spec.getMetaName() == IWSDLSearchConstants.MESSAGE_META_NAME) {
                return WSDLEditorPlugin.getInstance().getImage("icons/message_obj.gif");
            }
            else if (spec.getMetaName() == IXSDSearchConstants.COMPLEX_TYPE_META_NAME){
            	//|| spec.getMetaName() == ("/schema/complexType"))             	
                return XSDEditorPlugin.getXSDImage("icons/XSDComplexType.gif");
            }
            else if (spec.getMetaName() == IXSDSearchConstants.SIMPLE_TYPE_META_NAME ||
                     //spec.getMetaName() == ("/schema/simpleType") ||
                     spec.getMetaName() == null /*BUILT_IN_TYPE*/){ 
                return XSDEditorPlugin.getXSDImage("icons/XSDSimpleType.gif");
            }
            else if (spec.getMetaName() == IXSDSearchConstants.ELEMENT_META_NAME){
            		// ||spec.getMetaName() == ("/schema/element"))
                return XSDEditorPlugin.getXSDImage("icons/XSDElement.gif");
            }
    
            return null;
        }
    }
}
