Java tutorial
/******************************************************************************* * Copyright (c) 2007, 2012 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 * yyyymmdd bug Email and other contact information * -------- -------- ----------------------------------------------------------- * IBM Corporation. - initial API and implementation * 20070523 158230 kathy@ca.ibm.com - Kathy Chan * 20071219 213356 kathy@ca.ibm.com - Kathy Chan * 20080325 222473 makandre@ca.ibm.com - Andrew Mak, Create EAR version based on the version of modules to be added * 20080429 213730 trungha@ca.ibm.com - Trung Ha * 20080507 229532 kathy@ca.ibm.com - Kathy Chan * 20090303 242635 mahutch@ca.ibm.com - Mark Hutchinson, Remove unnecessary UI dependencies from org.eclipse.jst.ws.consumption * 20100203 kchong@ca.ibm.com - Keith Chong, Java Facet change * 20120127 369959 kchong@ca.ibm.com - Yen Lu, Keith Chong - JavaFacetUtil needs to be updated to include Java 7 *******************************************************************************/ package org.eclipse.jst.ws.internal.consumption.common; import java.util.ArrayList; import java.util.Collections; import java.util.HashSet; import java.util.Iterator; import java.util.List; import java.util.Set; import org.eclipse.core.resources.IProject; import org.eclipse.core.resources.ResourcesPlugin; import org.eclipse.core.runtime.CoreException; import org.eclipse.core.runtime.IConfigurationElement; import org.eclipse.core.runtime.IExtension; import org.eclipse.core.runtime.IExtensionPoint; import org.eclipse.core.runtime.IExtensionRegistry; import org.eclipse.core.runtime.IProgressMonitor; import org.eclipse.core.runtime.IStatus; import org.eclipse.core.runtime.Platform; import org.eclipse.core.runtime.Status; import org.eclipse.jdt.core.IJavaProject; import org.eclipse.jdt.core.JavaCore; import org.eclipse.jem.util.emf.workbench.ProjectUtilities; import org.eclipse.jst.common.project.facet.core.JavaFacet; import org.eclipse.jst.j2ee.internal.common.J2EEVersionUtil; import org.eclipse.jst.j2ee.internal.ejb.project.operations.EjbFacetInstallDataModelProvider; import org.eclipse.jst.j2ee.internal.ejb.project.operations.IEjbFacetInstallDataModelProperties; import org.eclipse.jst.j2ee.internal.plugin.IJ2EEModuleConstants; import org.eclipse.jst.j2ee.internal.project.J2EEProjectUtilities; import org.eclipse.jst.j2ee.project.JavaEEProjectUtilities; import org.eclipse.jst.j2ee.project.facet.AppClientFacetInstallDataModelProvider; import org.eclipse.jst.j2ee.project.facet.IAppClientFacetInstallDataModelProperties; import org.eclipse.jst.j2ee.project.facet.IUtilityFacetInstallDataModelProperties; import org.eclipse.jst.j2ee.project.facet.UtilityFacetInstallDataModelProvider; import org.eclipse.jst.j2ee.web.project.facet.IWebFacetInstallDataModelProperties; import org.eclipse.jst.j2ee.web.project.facet.WebFacetInstallDataModelProvider; import org.eclipse.jst.ws.internal.common.J2EEUtils; import org.eclipse.jst.ws.internal.common.ResourceUtils; import org.eclipse.jst.ws.internal.consumption.ConsumptionMessages; import org.eclipse.osgi.util.NLS; import org.eclipse.wst.command.internal.env.core.common.StatusUtils; import org.eclipse.wst.common.componentcore.internal.util.IModuleConstants; import org.eclipse.wst.common.frameworks.datamodel.DataModelFactory; import org.eclipse.wst.common.frameworks.datamodel.IDataModel; import org.eclipse.wst.common.project.facet.core.IFacetedProject; import org.eclipse.wst.common.project.facet.core.IFacetedProjectTemplate; 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.ProjectFacetsManager; import org.eclipse.wst.common.project.facet.core.VersionFormatException; import org.eclipse.wst.common.project.facet.core.IFacetedProject.Action; import org.eclipse.wst.common.project.facet.core.IFacetedProject.Action.Type; import org.eclipse.wst.common.project.facet.core.runtime.IRuntime; import org.eclipse.wst.common.project.facet.core.runtime.RuntimeManager; import com.ibm.icu.util.StringTokenizer; /** * FacetUtils contains utility methods related to facets and templates. * <br/><br/> * Terminology used in the Javadoc in this class * <ul> * <li><b>facet</b>: An {@link IProjectFacet}</li> * <li><b>facet version</b>: An {@link IProjectFacetVersion} </li> * <li><b>facet runtime</b>: An {@link IRuntime}</li> * <li><b>faceted project</b>: An {@link IFacetedProject}. A faceted project may be obtained * from an IProject (@see ProjectFacetsManager#create)</li> * <li><b>template</b>: An {@link IFacetedProjectTemplate}. Conceptually this is similar to a project type.</li> * <li><b>required facet version</b>: A {@link RequiredFacetVersion}. Used by serviceRuntimes and clientRuntimes * to identify what they require in terms of facet versions.</li> * </ul> */ public class FacetUtils { private static IFacetOperationDelegate delegate; //if a delegate is plugged in, delegate some operations to it private static boolean failedToLoadDelegate = false; /** * Returns an array of valid projects. Valid projects include projects with the facets nature or * projects with the Java nature. * @return IProject[] an array of valid projects */ public static IProject[] getAllProjects() { //Return all projects in the workspace that have the project facet nature or that do not have the project //facet nature but have the Java nature. IProject[] projects = ResourcesPlugin.getWorkspace().getRoot().getProjects(); ArrayList validProjects = new ArrayList(); for (int i = 0; i < projects.length; i++) { try { IFacetedProject facProject = ProjectFacetsManager.create(projects[i]); if (facProject != null) { //Add it to the list validProjects.add(projects[i]); } else { if (ResourceUtils.isJavaProject(projects[i])) { validProjects.add(projects[i]); } } } catch (CoreException ce) { } } return (IProject[]) validProjects.toArray(new IProject[] {}); } /** * Returns the facet versions on the given project. * @param projectName name of an existing project. * @returns Set containing elements of type {@link IProjectFacetVersion}. * These are the facet versions currently installed on this project. If the project * is a Java project, facets are inferred from the Java project. Returns null * <ul> * <li>if the project is not a faceted project or a Java project or</li> * <li>if the project does not exist or</li> * <li>if the project is null</li> * </ul> */ public static Set getFacetsForProject(String projectName) { Set facetVersions = null; IProject project = ProjectUtilities.getProject(projectName); if (project != null && project.exists()) { try { IFacetedProject fproject = ProjectFacetsManager.create(project); if (fproject != null) { facetVersions = fproject.getProjectFacets(); } else { //If this is not a faceted project, it may still be okay if it is a Java project //and the client runtime supports a Java project. IJavaProject javaProject = null; if (ResourceUtils.isJavaProject(project)) { javaProject = JavaCore.create(project); facetVersions = FacetUtils.getFacetsForJavaProject(javaProject); } } } catch (CoreException ce) { //Leaving the catch block empty. This method will return null if there //were any blow-ups in the facet API being called. } } return facetVersions; } /** * Returns the facet runtime the given project is bound to. * @param projectName name of an existing project * @return {@link IRuntime} the project is bound to. Returns null * <ul> * <li>if the project is not bound to a facet runtime</li> * <li>if the project does not exist</li> * <li>if the project is null</li> * </ul> */ public static IRuntime getFacetRuntimeForProject(String projectName) { IProject project = ProjectUtilities.getProject(projectName); if (project != null && project.exists()) { try { IFacetedProject fproject = ProjectFacetsManager.create(project); if (fproject != null) { return fproject.getPrimaryRuntime(); } } catch (CoreException ce) { //Leaving the catch block empty. This method will return null if there //were any blow-ups in the facet API being called. } } return null; } /** * Returns a set of combinations of facet versions derived from the facet versions * in the provided arrayOfProjectFacetVersionArrays. For example, if * arrayOfProjectFacetVersionArrays is a two dimenstional array of facet versions that has * a structure like this:<br/> * {{FacetA_version1, FacetA_version2},<br/> * {FacetB_version1},<br/> * {FacetC_version1, FacetC_version2}}<br/> * the following array of Sets will be returned:<br/> * {Set1, Set2, Set3, Set4}, where<br/> * Set1 = [FacetA_version1, FacetB_version1, FacetC_version1]<br/> * Set2 = [FacetA_version2, FacetB_version1, FacetC_version1]<br/> * Set3 = [FacetA_version1, FacetB_version1, FacetC_version2]<br/> * Set4 = [FacetA_version2, FacetB_version1, FacetC_version2]<br/> * <br/> * @param arrayOfProjectFacetVersionArrays a two dimensional array containing elements * of type {@link IProjectFacetVersion} * @param returnValidOnly false if all combinations of facet versions are to be returned. * true if only valid combinations of facet versions are to be returned. * @return Set[] an array of Sets, where each Set contains elements of type {@link IProjectFacetVersion}. */ public static Set[] getFacetCombinations(IProjectFacetVersion[][] arrayOfProjectFacetVersionArrays, boolean returnValidOnly) { ArrayList allCombinations = new ArrayList(); //maxCount contains the number of versions in each array of IProjectFacetVersions. //initialize counter, which will be used to navigate arrayOfProjectFacetVersionArrays. int n = arrayOfProjectFacetVersionArrays.length; int[] maxCount = new int[n]; int[] counter = new int[n]; for (int i = 0; i < n; i++) { maxCount[i] = arrayOfProjectFacetVersionArrays[i].length - 1; counter[i] = 0; } //Navigate arrayOfProjectFacetVersionArrays to create all possible combinations. boolean done = false; while (!done) { //Create a combination of size n using current values in counter. //Add it to the list of all combinations, checking first for validity if returnValidOnly is true. Set combination = new HashSet(); for (int j = 0; j < n; j++) { IProjectFacetVersion pfv = arrayOfProjectFacetVersionArrays[j][counter[j]]; combination.add(pfv); } //Check if valid. if (returnValidOnly) { Set actions = getInstallActions(combination); try { if (ProjectFacetsManager.check(new HashSet(), actions).getSeverity() == IStatus.OK) { allCombinations.add((combination)); } } catch (Throwable e) { // Do nothing if ProjectFacetsManager.check() throws exception. // TODO This try/catch will be unneccesary once WTP bug 137551 is fixed so that an OK Status // would not be returned when an exception is thrown. } } else { allCombinations.add((combination)); } //Update the counters. for (int p = 0; p < n; p++) { if ((counter[p] + 1) <= maxCount[p]) { (counter[p])++; break; } else { counter[p] = 0; if (p == n - 1) { done = true; } } } } Set[] allCombinationsArray = (Set[]) allCombinations.toArray(new Set[0]); return allCombinationsArray; } /** * Returns a set of facet versions given a template. The highest facet version of every fixed * facet in the template is returned, with the exception of the jst.java facet, where the 1.4 * facet version is returned. * * @param templateId id of a {@link IFacetedProjectTemplate} * @return Set containing elements of type {@link IProjectFacetVersion} */ public static Set getInitialFacetVersionsFromTemplate(String templateId) { IFacetedProjectTemplate template = ProjectFacetsManager.getTemplate(templateId); Set fixedFacets = template.getFixedProjectFacets(); HashSet initial = new HashSet(); for (Iterator itr2 = fixedFacets.iterator(); itr2.hasNext();) { IProjectFacet facet = (IProjectFacet) itr2.next(); IProjectFacetVersion highestFacetVersion = null; try { if (isJavaFacet(facet)) //special case the java facet because 1.4 is a better default than 5.0 for now. { highestFacetVersion = facet.getVersion("1.4"); } else { highestFacetVersion = facet.getLatestVersion(); } } catch (VersionFormatException e) { } catch (CoreException e) { } initial.add(highestFacetVersion); } return initial; } /** * Returns a set of facet versions given a template. The default facet version of every fixed * facet in the template is returned. If unable to get default versions, an empty set will be returned. * * @param templateId id of a {@link IFacetedProjectTemplate} * @return Set containing elements of type {@link IProjectFacetVersion} */ public static Set getDefaultFacetVersionsFromTemplate(String templateId) { HashSet defaultSet = new HashSet(); try { IFacetedProjectTemplate template = ProjectFacetsManager.getTemplate(templateId); Set fixedFacets = template.getFixedProjectFacets(); for (Iterator itr2 = fixedFacets.iterator(); itr2.hasNext();) { IProjectFacet facet = (IProjectFacet) itr2.next(); IProjectFacetVersion defaultFacetVersion = null; defaultFacetVersion = facet.getDefaultVersion(); defaultSet.add(defaultFacetVersion); } return defaultSet; } catch (IllegalArgumentException e) { return defaultSet; } catch (VersionFormatException e) { return defaultSet; } } /** * Returns the template lables corresponding to the provided templateIds. * @param templateIds array of valid template ids. Each id must correspond to a {@link IFacetedProjectTemplate}. * @return String[] array of template labels. */ public static String[] getTemplateLabels(String[] templateIds) { String[] labels = new String[templateIds.length]; for (int i = 0; i < templateIds.length; i++) { IFacetedProjectTemplate template = ProjectFacetsManager.getTemplate(templateIds[i]); labels[i] = template.getLabel(); } return labels; } /** * Returns the id of a template given its label. * * @param templateLabel label of a template * @return template id or empty String if no {@link IFacetedProjectTemplate} with the * given templateLabel could be found. */ public static String getTemplateIdByLabel(String templateLabel) { for (Iterator itr = ProjectFacetsManager.getTemplates().iterator(); itr.hasNext();) { final IFacetedProjectTemplate template = (IFacetedProjectTemplate) itr.next(); if (template.getLabel().equals(templateLabel)) { return template.getId(); } } return ""; } /** * Returns the label of a template given its id * * @param templateId id of a {@link IFacetedProjectTemplate} * @return template label */ public static String getTemplateLabelById(String templateId) { IFacetedProjectTemplate template = ProjectFacetsManager.getTemplate(templateId); return template.getLabel(); } /** * Returns a set of install actions for the provided facet version * * @param projectFacetVersions Set containing elements of type {@link IProjectFacetVersion} * @return Set containing elements of type {@link Action} with the type attribute set to Type.INSTALL * The set contains one Action for each {@link IProjectFacetVersion} in projectFacetVersions. */ public static Set getInstallActions(Set projectFacetVersions) { HashSet actions = new HashSet(); Iterator facets = projectFacetVersions.iterator(); while (facets.hasNext()) { IProjectFacetVersion fv = (IProjectFacetVersion) facets.next(); if (fv != null) { IProjectFacet pf = fv.getProjectFacet(); Action action = new Action(Type.INSTALL, fv, getConfigObject(pf)); actions.add(action); } } return actions; } /** * Returns the data model config object for the given project facet * For J2EE facets, set Add_TO_EAR properties of the data model to false, * for other facets, just return null * @param facetID * @return data model config object */ public static Object getConfigObject(IProjectFacet projectFacet) { IDataModel dm = null; if (projectFacet != null) { String facetId = projectFacet.getId(); if (facetId != null) { // set Add to EAR to false if (facetId.equals(IModuleConstants.JST_WEB_MODULE)) { dm = DataModelFactory.createDataModel(new WebFacetInstallDataModelProvider()); dm.setBooleanProperty(IWebFacetInstallDataModelProperties.ADD_TO_EAR, false); } else if (facetId.equals(IModuleConstants.JST_EJB_MODULE)) { dm = DataModelFactory.createDataModel(new EjbFacetInstallDataModelProvider()); dm.setBooleanProperty(IEjbFacetInstallDataModelProperties.ADD_TO_EAR, false); } else if (facetId.equals(IModuleConstants.JST_APPCLIENT_MODULE)) { dm = DataModelFactory.createDataModel(new AppClientFacetInstallDataModelProvider()); dm.setBooleanProperty(IAppClientFacetInstallDataModelProperties.ADD_TO_EAR, false); } else if (facetId.equals(IModuleConstants.JST_UTILITY_MODULE)) { dm = DataModelFactory.createDataModel(new UtilityFacetInstallDataModelProvider()); dm.setBooleanProperty(IUtilityFacetInstallDataModelProperties.ADD_TO_EAR, false); } } } return dm; } /** * Returns the {@link FacetMatcher} calculated when checking the required facet versions * against the facet versions. * * @param requiredFacetVersions array of required facet versions * @param projectFacetVersions facet versions to check against. Set containing elements of type * {@link IProjectFacetVersion} * @return FacetMatcher with the following characteristics: * <ul> * <li><b>isMatch</b>: returns true if the required facet versions already exist in the facet versions * or can be added to the facet versions. isMatch will return false otherwise.</li> * <li><b>getFacetsTested</b>: returns the same set of facet versions as the input parameter, projectFacetVersions</li> * <li><b>getFacetsThatMatched</b>: if isMatch returns false, getFacetsThatMatched returns null. If isMatch returns true, * getFacetsThatMatched returns the subset of facet versions in the input parameter, projectFacetVersions, * that matched one of the required facet versions. This may be an empty set.</li> * <li><b>getFacetsToAdd</b>: if isMatch returns false, getFacetsToAdd returns null. If isMatch returns true, * getFacetsToAdd returns the subset of facet versions that would need to be added to the facet versions in * projectFacetVersions in order to satisfy the requirements of the required facet versions. This may be * an empty set.</li> * </ul> */ public static FacetMatcher match(RequiredFacetVersion[] requiredFacetVersions, Set projectFacetVersions) { FacetMatcher fm = new FacetMatcher(); fm.setFacetsTested(projectFacetVersions); HashSet facetsToAdd = new HashSet(); HashSet requiredFacetVersionsToAdd = new HashSet(); HashSet facetsThatMatched = new HashSet(); for (int i = 0; i < requiredFacetVersions.length; i++) { RequiredFacetVersion rfv = requiredFacetVersions[i]; IProjectFacetVersion rpfv = rfv.getProjectFacetVersion(); String rid = rpfv.getProjectFacet().getId(); String rv = rpfv.getVersionString(); boolean facetPresent = false; //Is the project facet present? or a later version of applicable. Iterator itr = projectFacetVersions.iterator(); while (itr.hasNext()) { IProjectFacetVersion pfv = (IProjectFacetVersion) itr.next(); String id = pfv.getProjectFacet().getId(); String version = pfv.getVersionString(); if (rid.equals(id)) { if (rv.equals(version)) { //found an exact match facetPresent = true; facetsThatMatched.add(pfv); } else { if (rfv.getAllowNewer()) { if (greaterThan(version, rv)) { //found a match facetPresent = true; facetsThatMatched.add(pfv); } } } //No need to keep iterating since we hit a facet with the same id; break; } } //if not present, put it in the list to check if it can be added. if (!facetPresent) { facetsToAdd.add(rpfv); requiredFacetVersionsToAdd.add(rfv); } } //Check if the facetsToAdd can be added if (requiredFacetVersionsToAdd.size() > 0) { //Test all possible combinations of the facets that need to be added //Create an array of arrays. Each element of the array will contain the array //of the permitted IProjectFacetVersions for each required facet. boolean facetsCanBeAdded = false; Iterator itr = requiredFacetVersionsToAdd.iterator(); ArrayList projectFacetVersionArrays = new ArrayList(); while (itr.hasNext()) { RequiredFacetVersion reqFacetVersion = (RequiredFacetVersion) itr.next(); IProjectFacetVersion[] versions = reqFacetVersion.getAllowedProjectFacetVersions(); if (versions != null && versions.length > 0) { //Add the array of versions to the list of arrays. projectFacetVersionArrays.add(versions); } } IProjectFacetVersion[][] arrayOfProjectFacetVersionArrays = (IProjectFacetVersion[][]) projectFacetVersionArrays .toArray(new IProjectFacetVersion[0][0]); Set[] combinations = getFacetCombinations(arrayOfProjectFacetVersionArrays, false); for (int i = 0; i < combinations.length; i++) { //Check if the set can be added. If so, this is a match. Update the facet matcher and break. Set actions = getInstallActions(combinations[i]); try { if (ProjectFacetsManager.check(projectFacetVersions, actions).getSeverity() == IStatus.OK) { //Facets can be added so there is a match facetsCanBeAdded = true; fm.setMatch(true); fm.setFacetsThatMatched(facetsThatMatched); fm.setFacetsToAdd(combinations[i]); break; } } catch (Throwable e) { // Do nothing if ProjectFacetsManager.check() throws exception. // TODO This try/catch will be unneccesary once WTP bug 137551 is fixed so that an OK Status // would not be returned when an exception is thrown. } } if (!facetsCanBeAdded) { fm.setMatch(false); } } else { //There are no facets to add. fm.setMatch(true); fm.setFacetsThatMatched(facetsThatMatched); fm.setFacetsToAdd(facetsToAdd); } return fm; } /** * Adds facet versions to the provided project if required based on checking provided * required facet versions against the facet versions already installed on project. * * @param project IProject which exists in the workspace * @param rfvs array of required facet versions. * @param monitor progress monitor * @return IStatus with severity IStatus.ERROR * <ul> * <li>if the project does not exist or</li> * <li>if the project is not open or</li> * <li>an attempt to add facet versions to the project resulted in an error.</li> * </ul> * Otherwise, returns an IStatus with severity IStatus.OK */ public static IStatus addRequiredFacetsToProject(IProject project, RequiredFacetVersion[] rfvs, IProgressMonitor monitor) { IStatus status = Status.OK_STATUS; Set missingFacets = null; Set facetsToAdd = new HashSet(); try { IFacetedProject fProject = ProjectFacetsManager.create(project); if (fProject != null) { Set projectFacetVersions = fProject.getProjectFacets(); FacetMatcher projectFacetMatcher = FacetUtils.match(rfvs, projectFacetVersions); if (projectFacetMatcher.isMatch()) { missingFacets = projectFacetMatcher.getFacetsToAdd(); if (missingFacets.size() > 0) { IRuntime fRuntime = null; fRuntime = FacetUtils.getFacetRuntimeForProject(project.getName()); if (fRuntime != null) { //Add the highest version supported by the runtime the project is bound to. Iterator missingFacetsItr = missingFacets.iterator(); while (missingFacetsItr.hasNext()) { IProjectFacet facet = ((IProjectFacetVersion) missingFacetsItr.next()) .getProjectFacet(); //Get the highest level of this facet supported by the runtime. List versions = null; try { versions = facet.getSortedVersions(false); } catch (VersionFormatException e) { Set versionSet = facet.getVersions(); Iterator itr = versionSet.iterator(); versions = new ArrayList(); while (itr.hasNext()) { versions.add(itr.next()); } } catch (CoreException e) { Set versionSet = facet.getVersions(); Iterator itr = versionSet.iterator(); versions = new ArrayList(); while (itr.hasNext()) { versions.add(itr.next()); } } //Iterate over the versions in descending order and pick the //first one that fRuntime supports. Iterator versionsItr = versions.iterator(); while (versionsItr.hasNext()) { boolean match = false; IProjectFacetVersion pfv = (IProjectFacetVersion) versionsItr.next(); Set pfvs = new HashSet(); pfvs.add(pfv); //Check the required facets to see if this version of this facet is supported. for (int j = 0; j < rfvs.length; j++) { RequiredFacetVersion rfv = rfvs[j]; IProjectFacetVersion rpfv = rfv.getProjectFacetVersion(); if (rpfv.getProjectFacet().getId().equals(pfv.getProjectFacet().getId())) { if (rpfv.getVersionString().equals(pfv.getVersionString())) { match = true; } else { if (rfv.getAllowNewer()) { if (greaterThan(pfv.getVersionString(), rpfv.getVersionString())) { match = true; } } } } } if (match) { //Check against Runtime if (FacetUtils.doesRuntimeSupportFacets(fRuntime, pfvs)) { //We have a match. Add this one to the master set. facetsToAdd.add(pfv); break; } } } } } else { facetsToAdd = missingFacets; } status = addFacetsToProject(fProject, facetsToAdd); } } } } catch (CoreException ce) { //Display an appropriate error message to the user. //A CoreException could have been thrown for any of the following three reasons //1. The project does not exist //2. The project is not open //3. There was a problem adding the facets to the project. if (!project.exists()) { status = StatusUtils.errorStatus(NLS.bind(ConsumptionMessages.MSG_ERROR_PROJECT_DOES_NOT_EXIST, new String[] { project.getName() })); } else if (!project.isOpen()) { status = StatusUtils.errorStatus(NLS.bind(ConsumptionMessages.MSG_ERROR_PROJECT_IS_NOT_OPEN, new String[] { project.getName() })); } else { status = getErrorStatusForAddingFacets(project.getName(), facetsToAdd, ce); } } return status; } /** * Adds the provided set of facet versions to the provided faceted project * * @param fproject A faceted project which exists in the workspace * @param projectFacetVersions A set containing elements of type {@link IProjectFacetVersion} * @return An IStatus with a severity of IStatus.OK if the facet * versions were added successfully. Otherwise, an IStatus with a severity of * IStatus.ERROR. */ public static IStatus addFacetsToProject(final IFacetedProject fproject, final Set projectFacetVersions) { final IStatus[] status = new IStatus[1]; status[0] = Status.OK_STATUS; final Set actions = getInstallActions(projectFacetVersions); if (isExtensionPresent()) { status[0] = delegate.addFacetsToProject(fproject, projectFacetVersions); } else { try { fproject.modify(actions, null); } catch (CoreException e) { status[0] = getErrorStatusForAddingFacets(fproject.getProject().getName(), projectFacetVersions, e); } } return status[0]; } /** * Returns an error status indicating that the facet versions could not be * added to the faceted project * * @param projectName a project name to insert in the error message in the IStatus * @param projectFacetVersions a set containing elements of type {@link IProjectFacetVersion}. * The facets in this set will be listed in the error message in the IStatus. * @param t a Throwable which will be inserted in the IStatus * @return an IStatus with severity IStatus.ERROR */ private static IStatus getErrorStatusForAddingFacets(String projectName, Set projectFacetVersions, Throwable t) { IStatus status = Status.OK_STATUS; int size = projectFacetVersions.size(); if (size > 0) { Set facets = new HashSet(); //Iterate over projectFacetVersions to form a set of IProjectFacets Iterator itr = projectFacetVersions.iterator(); while (itr.hasNext()) { IProjectFacetVersion projectFacet = (IProjectFacetVersion) itr.next(); IProjectFacet facet = projectFacet.getProjectFacet(); facets.add(facet); } String facetList = getFacetListMessageString(facets); status = StatusUtils.errorStatus(NLS.bind(ConsumptionMessages.MSG_ERROR_ADDING_FACETS_TO_PROJECT, new String[] { projectName, facetList }), t); } return status; } /** * Creates a new faceted project with the provided name * * @param projectName A String containing the name of the project to be created * @return An IStatus with a severity of IStatus.OK if the faceted project * was created successfully or if a project of the provided name already * exists in the workspace. Otherwise, an IStatus with severity of * IStatus.ERROR. */ public static IStatus createNewFacetedProject(final String projectName) { final IStatus[] status = new IStatus[1]; status[0] = Status.OK_STATUS; IProject project = ProjectUtilities.getProject(projectName); if (!project.exists()) { if (isExtensionPresent()) { status[0] = delegate.createNewFacetedProject(projectName); } else { try { IFacetedProject fProject = ProjectFacetsManager.create(projectName, null, null); if (fProject == null) { status[0] = StatusUtils.errorStatus(NLS.bind(ConsumptionMessages.MSG_ERROR_PROJECT_CREATION, new String[] { projectName })); } } catch (CoreException e) { status[0] = StatusUtils.errorStatus( NLS.bind(ConsumptionMessages.MSG_ERROR_PROJECT_CREATION, new String[] { projectName }), e); } } } return status[0]; } /** * Sets the provided set of facets as fixed on the faceted project * * @param fProject A faceted project which exists in the workspace * @param fixedFacets A set containing elements of type {@link IProjectFacet} * @return An IStatus with a severity of IStatus.OK if the facets * were successfully set as fixed facets on the faceted project. * Otherwise, an IStatus with a severity of IStatus.ERROR. * * @see IFacetedProject#setFixedProjectFacets */ public static IStatus setFixedFacetsOnProject(final IFacetedProject fProject, final Set fixedFacets) { final IStatus[] status = new IStatus[1]; status[0] = Status.OK_STATUS; if (isExtensionPresent()) { status[0] = delegate.setFixedFacetsOnProject(fProject, fixedFacets); } else { try { fProject.setFixedProjectFacets(fixedFacets); } catch (CoreException e) { status[0] = getErrorStatusForSettingFixedFacets(fProject.getProject().getName(), fixedFacets, e); } } return status[0]; } /** * Returns an error status indicating that the facets could not be * set as fixed facets on the faceted project * * @param projectName a project name to insert in the error message in the IStatus * @param facets a set containing elements of type {@link IProjectFacet}. * The facets in this set will be listed in the error message in the IStatus. * @param t a Throwable which will be inserted in the IStatus * @return an IStatus with severity IStatus.ERROR */ private static IStatus getErrorStatusForSettingFixedFacets(String projectName, Set facets, Throwable t) { IStatus status = Status.OK_STATUS; int size = facets.size(); if (size > 0) { String facetList = getFacetListMessageString(facets); status = StatusUtils.errorStatus( NLS.bind(ConsumptionMessages.MSG_ERROR_FIXED_FACETS, new String[] { projectName, facetList }), t); } return status; } /** * Binds the faceted project to the facet runtime * * @param fProject A faceted project which exists in the workspace * @param fRuntime A facet runtime * @return An IStatus with a severity of IStatus.OK if the faceted project * was bound to the facet runtime successfully. Otherwise, an IStatus with severity of * IStatus.ERROR. */ public static IStatus setFacetRuntimeOnProject(final IFacetedProject fProject, final IRuntime fRuntime) { final IStatus[] status = new IStatus[1]; status[0] = Status.OK_STATUS; if (isExtensionPresent()) { status[0] = delegate.setFacetRuntimeOnProject(fProject, fRuntime); } else { try { fProject.setTargetedRuntimes(Collections.singleton(fRuntime), null); //jvh - happens here... } catch (CoreException e) { status[0] = StatusUtils.errorStatus(NLS.bind(ConsumptionMessages.MSG_ERROR_SETTING_RUNTIME, new String[] { fProject.getProject().getName(), fRuntime.getName() }), e); } } return status[0]; } /** * Returns a translatable delimited list of facet labels derived from the provided * set of facets * * @param facets a set containing elements of type {@link IProjectFacet} * @return String a delimited list of facet labels */ private static String getFacetListMessageString(Set facets) { String facetListMessage = ""; int size = facets.size(); if (size > 0) { Iterator itr = facets.iterator(); IProjectFacet firstProjectFacet = (IProjectFacet) itr.next(); facetListMessage = firstProjectFacet.getLabel(); //Continue appending to facetListMessage until all the facet labels //are in the list. while (itr.hasNext()) { IProjectFacet projectFacet = (IProjectFacet) itr.next(); String pfLabel = projectFacet.getLabel(); facetListMessage = NLS.bind(ConsumptionMessages.MSG_FACETS, new String[] { facetListMessage, pfLabel }); } } return facetListMessage; } /** * Returns the set of facet versions which can be inferred from the provided Java project * * @param javaProject a Java project that exists in the workspace. Must not be null. * @return Set containing elements of type {@link IProjectFacetVersion} */ public static Set getFacetsForJavaProject(IJavaProject javaProject) { Set facets = new HashSet(); String jdkComplianceLevel = null; if (javaProject != null) { jdkComplianceLevel = javaProject.getOption("org.eclipse.jdt.core.compiler.compliance", false); if (jdkComplianceLevel == null) { jdkComplianceLevel = JavaCore.getOption(JavaCore.COMPILER_COMPLIANCE); if (jdkComplianceLevel == null) { jdkComplianceLevel = "1.4"; } } } IProjectFacet javaFacet = ProjectFacetsManager.getProjectFacet(JavaFacet.ID); IProjectFacetVersion javaFacetVersion = null; if (jdkComplianceLevel.equals("1.3")) { javaFacetVersion = javaFacet.getVersion("1.3"); } else if (jdkComplianceLevel.equals("1.4")) { javaFacetVersion = javaFacet.getVersion("1.4"); } else if (jdkComplianceLevel.equals("1.5")) { javaFacetVersion = JavaFacet.JAVA_50; } else if (jdkComplianceLevel.equals("1.6")) { javaFacetVersion = JavaFacet.JAVA_60; } else if (jdkComplianceLevel.equals("1.7")) { javaFacetVersion = JavaFacet.VERSION_1_7; } else { javaFacetVersion = javaFacet.getVersion("1.4"); } facets.add(javaFacetVersion); IProjectFacet utilityFacet = ProjectFacetsManager.getProjectFacet(IModuleConstants.JST_UTILITY_MODULE); IProjectFacetVersion utilityFacetVersion = null; try { utilityFacetVersion = utilityFacet.getLatestVersion(); } catch (CoreException ce) { } if (utilityFacetVersion != null) { facets.add(utilityFacetVersion); } return facets; } //Methods related to facet runtimes. /** * Returns a set of facet runtimes that support the given * required facet versions. * @param requiredFacetVersions an array containing elements of type {@link RequiredFacetVersion} * @return Set set of facet runtimes that support the given required facet versions. * (element type: {@link IRuntime}) */ public static Set getRuntimes(RequiredFacetVersion[] requiredFacetVersions) { //Form the sets of IProjectFacetVersions these RequiredFacetVersions represent. ArrayList listOfFacetSets = new ArrayList(); HashSet facets = new HashSet(); int javaFacetIndex = -1; for (int i = 0; i < requiredFacetVersions.length; i++) { IProjectFacetVersion pfv = requiredFacetVersions[i].getProjectFacetVersion(); if (FacetUtils.isJavaFacet(pfv.getProjectFacet())) { //Remember the index javaFacetIndex = i; } facets.add(requiredFacetVersions[i].getProjectFacetVersion()); } listOfFacetSets.add(facets); //If the java facet was one of the facets in the set, and new versions of java are allowed, //create sets that contain the newer permitted versions of the java facets. if (javaFacetIndex > -1) { ArrayList permittedJavaVersions = new ArrayList(); RequiredFacetVersion rfv = requiredFacetVersions[javaFacetIndex]; if (rfv.getAllowNewer()) { String version = rfv.getProjectFacetVersion().getVersionString(); Set allVersions = rfv.getProjectFacetVersion().getProjectFacet().getVersions(); Iterator itr = allVersions.iterator(); while (itr.hasNext()) { IProjectFacetVersion thisPfv = (IProjectFacetVersion) itr.next(); String thisVersion = thisPfv.getVersionString(); if (greaterThan(thisVersion, version)) { permittedJavaVersions.add(thisVersion); } } String[] javaVersions = (String[]) permittedJavaVersions.toArray(new String[0]); for (int j = 0; j < javaVersions.length; j++) { HashSet thisFacetSet = new HashSet(); for (int k = 0; k < requiredFacetVersions.length; k++) { if (k == javaFacetIndex) { IProjectFacetVersion pfv = requiredFacetVersions[k].getProjectFacetVersion() .getProjectFacet().getVersion(javaVersions[j]); thisFacetSet.add(pfv); } else { IProjectFacetVersion pfv = requiredFacetVersions[k].getProjectFacetVersion(); thisFacetSet.add(pfv); } } listOfFacetSets.add(thisFacetSet); } } } //Return the union of runtimes for all the facetSets. return getRuntimes((Set[]) listOfFacetSets.toArray(new Set[0])); } /** * Returns whether or not the provided facet runtime supports the provided * required facet versions. * * @param requiredFacetVersions an array containing elements of type {@link RequiredFacetVersion} * @param fRuntimeName name of a {@link IRuntime} * @return boolean <code>true</code> if the facet runtime supports the required facet versions. * Returns <code>false</code> otherwise. */ public static boolean isFacetRuntimeSupported(RequiredFacetVersion[] requiredFacetVersions, String fRuntimeName) { Set fRuntimes = getRuntimes(requiredFacetVersions); Iterator itr = fRuntimes.iterator(); while (itr.hasNext()) { IRuntime runtime = (IRuntime) itr.next(); if (runtime.getName().equals(fRuntimeName)) { return true; } } return false; } /** * Returns the union of facet runtimes that support the provided sets of facet versions. * * @param facetSets array of Sets, where each Set contains elements of type {@link IProjectFacetVersion}. * @return Set containing elements of type {@link IRuntime} */ public static Set getRuntimes(Set[] facetSets) { HashSet unionSet = new HashSet(); for (int i = 0; i < facetSets.length; i++) { Set facets = facetSets[i]; Set runtimes = RuntimeManager.getRuntimes(facets); Iterator itr = runtimes.iterator(); while (itr.hasNext()) { IRuntime runtime = (IRuntime) itr.next(); if (!unionSet.contains(runtime)) { unionSet.add(runtime); } } } return unionSet; } /** * Returns whether or not the provided facet runtime supports the provided set of facet versions. * * @param facetRuntime a facet runtime * @param projectFacetVersions set containing elements of type {@link IProjectFacetVersion} * @return boolean <code>true</code> if the facet runtime supports the provided set of facet versions. * Returns <code>false</code> otherwise. */ public static boolean doesRuntimeSupportFacets(IRuntime facetRuntime, Set projectFacetVersions) { if (facetRuntime == null || projectFacetVersions == null) return false; Set runtimes = RuntimeManager.getRuntimes(projectFacetVersions); Iterator itr = runtimes.iterator(); while (itr.hasNext()) { IRuntime runtime = (IRuntime) itr.next(); if (runtime.getName().equals(facetRuntime.getName())) { return true; } } return false; } /** * Returns whether versionA is greater than versionB * * @param versionA version number of the form 1.2.3 * @param versionA version number of the form 1.2.3 * @return boolean <code>true</code> if versionA is greater than versionB, <code>false</code> otherwise. */ public static boolean greaterThan(String versionA, String versionB) { if (versionA == null || versionB == null) return false; StringTokenizer stA = new StringTokenizer(versionA, "."); StringTokenizer stB = new StringTokenizer(versionB, "."); int sizeA = stA.countTokens(); int sizeB = stB.countTokens(); int size; if (sizeA < sizeB) { size = sizeA; } else size = sizeB; for (int i = 0; i < size; i++) { int a = Integer.parseInt(stA.nextToken()); int b = Integer.parseInt(stB.nextToken()); if (a != b) { return a > b; } } return sizeA > sizeB; } /** * Returns whether the provided facet has an id the same as that of the java facet * @param pf facet * @return <code>true</code> if facet has an id the same as that of the java facet, <code>false</code> otherwise. */ public static boolean isJavaFacet(IProjectFacet pf) { if (pf != null && pf.equals(JavaFacet.FACET)) return true; else return false; } /** * Returns whether or not the provided project is a faceted Java utility project or a non-faceted Java project. * * @param project an IProject * @return boolean <code>true</code> if the provided project is a faceted Java utility project * or a non-faceted Java project, <code>false</code> otherwise. */ public static boolean isJavaProject(IProject project) { if (project == null) return false; //Check if it's a faceted project try { IFacetedProject fProject = ProjectFacetsManager.create(project); if (fProject != null) { //Return true if it's a utility project if (J2EEUtils.isJavaComponent(project)) { return true; } else { //See if the java facet is the only one it has. Set facets = fProject.getProjectFacets(); if (facets.size() == 1) { IProjectFacetVersion pfv = (IProjectFacetVersion) facets.iterator().next(); if (isJavaFacet(pfv.getProjectFacet())) { return true; } } } } else { if (ResourceUtils.isJavaProject(project)) { return true; } } } catch (CoreException ce) { } return false; } /** * Returns whether or not the provided template id is equal to "template.jst.utility" * * @param templateId template id * @return boolean <code>true</code> if the provided template id is equal to "template.jst.utility", * <code>false</code> otherwise. */ public static boolean isUtilityTemplate(String templateId) { if (templateId != null && ProjectFacetsManager.isTemplateDefined(templateId)) { if (templateId.equals("template.jst.utility")) { return true; } } return false; } /** * Returns the required facet version of a EAR that should contain the given project. * * @param project The project * @return An array of required facet versions. If no constraints can be inferred from the * project, an empty array is returned. */ public static RequiredFacetVersion[] getRequiredEARFacetVersions(IProject project) { int version = 0; if (JavaEEProjectUtilities.isDynamicWebProject(project)) { version = J2EEVersionUtil .convertWebVersionStringToJ2EEVersionID(J2EEProjectUtilities.getJ2EEProjectVersion(project)); } else if (JavaEEProjectUtilities.isEJBProject(project)) { version = J2EEVersionUtil .convertEJBVersionStringToJ2EEVersionID(J2EEProjectUtilities.getJ2EEProjectVersion(project)); } else if (JavaEEProjectUtilities.isApplicationClientProject(project)) { version = J2EEVersionUtil.convertAppClientVersionStringToJ2EEVersionID( J2EEProjectUtilities.getJ2EEProjectVersion(project)); } else // return empty array, no constraints return new RequiredFacetVersion[0]; IProjectFacet projectFacet = ProjectFacetsManager.getProjectFacet(IJ2EEModuleConstants.JST_EAR_MODULE); IProjectFacetVersion projectFacetVersion = projectFacet .getVersion(J2EEVersionUtil.convertVersionIntToString(version)); RequiredFacetVersion[] rfv = new RequiredFacetVersion[1]; rfv[0] = new RequiredFacetVersion(); rfv[0].setAllowNewer(false); rfv[0].setProjectFacetVersion(projectFacetVersion); return rfv; } private static boolean isExtensionPresent() { if (failedToLoadDelegate) { return false; } if (delegate != null) { return true; } IExtensionRegistry registry = Platform.getExtensionRegistry(); IExtensionPoint point = registry .getExtensionPoint("org.eclipse.jst.ws.consumption.internalFacetOperationDelegate"); if (point == null) { failedToLoadDelegate = true; return false; } IExtension[] extensions = point.getExtensions(); //this extension point is internal, we know there will only be zero or one plugged in if (extensions.length > 0 && extensions[0] != null) { IConfigurationElement[] elements = extensions[0].getConfigurationElements(); if (elements.length > 0 && elements[0] != null) { try { delegate = (IFacetOperationDelegate) elements[0].createExecutableExtension("class"); return true; } catch (CoreException e) { //do nothing, just report that we failed to load the extension } } } failedToLoadDelegate = true;//set this so we don't try to load it again return false; } }