/*******************************************************************************

 * Copyright (c) 2010 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.jst.j2ee.web.project.facet;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;
import java.util.Map;

import org.eclipse.core.commands.ExecutionException;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.core.IClasspathEntry;
import org.eclipse.jdt.core.IJavaProject;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.core.JavaModelException;
import org.eclipse.jem.util.UIContextDetermination;
import org.eclipse.jem.util.emf.workbench.ProjectUtilities;
import org.eclipse.jst.common.project.facet.JavaFacetUtils;
import org.eclipse.jst.j2ee.application.internal.operations.AddWebFragmentComponentToWebApplicationDataModelProvider;
import org.eclipse.jst.j2ee.application.internal.operations.IAddWebFragmentComponentToWebApplicationDataModelProperties;
import org.eclipse.jst.j2ee.internal.plugin.J2EEPlugin;
import org.eclipse.jst.j2ee.project.facet.IJ2EEFacetConstants;
import org.eclipse.wst.common.componentcore.ComponentCore;
import org.eclipse.wst.common.componentcore.datamodel.properties.ICreateReferenceComponentsDataModelProperties;
import org.eclipse.wst.common.componentcore.resources.IVirtualComponent;
import org.eclipse.wst.common.frameworks.datamodel.DataModelFactory;
import org.eclipse.wst.common.frameworks.datamodel.IDataModel;
import org.eclipse.wst.common.internal.emf.resource.RendererFactory;
import org.eclipse.wst.common.project.facet.core.FacetedProjectFramework;
import org.eclipse.wst.common.project.facet.core.IFacetedProjectWorkingCopy;
import org.eclipse.wst.common.project.facet.core.IProjectFacet;
import org.eclipse.wst.common.project.facet.core.IProjectFacetVersion;
import org.eclipse.wst.common.project.facet.core.runtime.IRuntime;
import org.eclipse.wst.common.project.facet.core.runtime.IRuntimeComponent;
import org.eclipse.wst.web.internal.facet.RuntimePresetMappingRegistry;

public abstract class WebFacetInstallDelegateForWebFragmentProjects {

	protected static void addToClasspath(final IJavaProject jproj, final IClasspathEntry entry) throws CoreException {
		final IClasspathEntry[] existingEntries = jproj.getRawClasspath();
		for(IClasspathEntry existingEntry : existingEntries){
			if(existingEntry.equals(entry)){
				return;
			}
		}
		final IClasspathEntry[] updated = new IClasspathEntry[existingEntries.length + 1];
		System.arraycopy(existingEntries, 0, updated, 0, existingEntries.length);
		updated[existingEntries.length] = entry;
		jproj.setRawClasspath(updated, null);
	}

    protected void installWARFacet( final String j2eeVersionText, 
                                    final String warProjectName, 
                                    final IRuntime runtime, 
                                    final IProgressMonitor monitor )
    {
		IProject project = ProjectUtilities.getProject(warProjectName); 
		if( project.exists())
			return;
		
		IFacetedProjectWorkingCopy fpjwc = null;
		try
		{	
			fpjwc = FacetedProjectFramework.createNewProject();		
		
		
			fpjwc.setProjectName( warProjectName );
			
			if( runtime != null )
			{
			    fpjwc.setTargetedRuntimes( Collections.singleton( runtime ) );
			}
			ArrayList <IProjectFacet> requiredFacets = new ArrayList<IProjectFacet>();
	        requiredFacets.add(JavaFacetUtils.JAVA_FACET);
	        requiredFacets.add(IJ2EEFacetConstants.DYNAMIC_WEB_FACET);
	        final Collection<IProjectFacet> fixedFacets = requiredFacets;
	        fpjwc.setFixedProjectFacets( new HashSet<IProjectFacet>( fixedFacets ) );
			//fpjwc.setFixedProjectFacets( Collections.singleton( JavaFacetUtils.JAVA_FACET) );
			fpjwc.setSelectedPreset( FacetedProjectFramework.DEFAULT_CONFIGURATION_PRESET_ID );
			
			if( j2eeVersionText != null )
			{
			    final IProjectFacetVersion defaultWarFacetVersion
			        = fpjwc.getProjectFacetVersion( IJ2EEFacetConstants.DYNAMIC_WEB_FACET );
			    
			    if( ! defaultWarFacetVersion.getVersionString().equals( j2eeVersionText ) )
			    {
			        String presetId = null;
			        
			        if( runtime != null )
			        {
	    		        for( IRuntimeComponent rc : runtime.getRuntimeComponents() )
	    		        {
	    		            presetId = RuntimePresetMappingRegistry.INSTANCE.getPresetID
	    		            ( 
	    		                rc.getRuntimeComponentType().getId(),
	    		                rc.getRuntimeComponentVersion().getVersionString(), 
	    		                IJ2EEFacetConstants.DYNAMIC_WEB_FACET.getId(), 
	    		                j2eeVersionText 
	    		            );
	    		            
	    		            if( presetId != null )
	    		            {
	    		                break;
	    		            }
	    		        }
			        }
			        
	                final IProjectFacetVersion warFacetVersion
	                    = IJ2EEFacetConstants.DYNAMIC_WEB_FACET.getVersion( j2eeVersionText );

            
	                
	                // Note that the next call is necessary even if a preset is going to be selected 
	                // later since it allows the dynamic preset to adjust for the war facet version.
	            	ArrayList <IProjectFacetVersion> requiredFacetVersions = new ArrayList<IProjectFacetVersion>();
	            	requiredFacetVersions.add(JavaFacetUtils.JAVA_FACET.getVersion("1.5")); //$NON-NLS-1$
	            	requiredFacetVersions.add(warFacetVersion);
	    	        final Collection<IProjectFacetVersion> fixedFacetVersions = requiredFacetVersions;
	    	        fpjwc.setProjectFacets( new HashSet<IProjectFacetVersion>( fixedFacetVersions ) );
	    	        
	                //fpjwc.setProjectFacets( Collections.singleton( warFacetVersion ) );
	                
			        if( presetId != null )
			        {
			            fpjwc.setSelectedPreset( presetId );
			        }
			    }
			}
			
			try
			{
			    fpjwc.commitChanges( null );
			}
			catch( CoreException e )
			{
			    J2EEPlugin.logError( e );
			}
		}finally {
			if(fpjwc != null){
				fpjwc.dispose();
			}
		}
	}

    protected void addToWar(IVirtualComponent warComp, IVirtualComponent j2eeComp, String moduleURI ){
		final IDataModel dataModel = DataModelFactory.createDataModel(new AddWebFragmentComponentToWebApplicationDataModelProvider());
		Map map = (Map)dataModel.getProperty(IAddWebFragmentComponentToWebApplicationDataModelProperties.TARGET_COMPONENTS_TO_URI_MAP);
		map.put(j2eeComp, moduleURI);
		
		dataModel.setProperty(ICreateReferenceComponentsDataModelProperties.SOURCE_COMPONENT, warComp);
			
		List modList = (List) dataModel.getProperty(ICreateReferenceComponentsDataModelProperties.TARGET_COMPONENT_LIST);
		modList.add(j2eeComp);
		dataModel.setProperty(ICreateReferenceComponentsDataModelProperties.TARGET_COMPONENT_LIST, modList);
		dataModel.setProperty(ICreateReferenceComponentsDataModelProperties.TARGET_COMPONENTS_DEPLOY_PATH, "/WEB-INF/lib"); //$NON-NLS-1$
		try {
			dataModel.getDefaultOperation().execute(null, null);
		} catch (ExecutionException e) {
			J2EEPlugin.logError(e);
		}
    }
    
    protected void installAndAddModuletoWAR( String j2eeVersionText,
    			String				warProjectName,
    			IRuntime			runtime,
    			IProject			moduleProject,
    			String				moduleURI,
    			IProgressMonitor	monitor ){
    	
		installWARFacet(j2eeVersionText,
					warProjectName,
					runtime,
					monitor);
		
		final IVirtualComponent c = ComponentCore.createComponent( moduleProject );
		final IProject warProject = ProjectUtilities.getProject( warProjectName );
		final IVirtualComponent warComp = ComponentCore.createComponent( warProject );
		
		if( UIContextDetermination.getCurrentContext() == UIContextDetermination.HEADLESS_CONTEXT ){
			boolean isValidating = RendererFactory.getDefaultRendererFactory().isValidating();
			try{
				if( isValidating ){
					RendererFactory.getDefaultRendererFactory().setValidating(false);
				}
				addToWar( warComp, c, moduleURI );
			}finally{
				RendererFactory.getDefaultRendererFactory().setValidating(isValidating);
			}
		}
		else
		 addToWar( warComp, c, moduleURI );
    }
    
    /**
     * This method will set the output property on the model element for the given component.
     * 
     * @param model
     * @param component
     */
    protected void setOutputFolder(IDataModel model, IVirtualComponent component) {
		IJavaProject javaProject = JavaCore.create(component.getProject());
		IPath currentDefaultOutput = null;
		try {
			currentDefaultOutput = javaProject.getOutputLocation();
			component.setMetaProperty("java-output-path", currentDefaultOutput.toString() ); //$NON-NLS-1$			
		} catch (JavaModelException e) {
			org.eclipse.jst.j2ee.internal.plugin.J2EEPlugin.logError(e);
		}
	}
 
}
