Package com.subhajit.eclipse.util

Source Code of com.subhajit.eclipse.util.ProjectUtils

package com.subhajit.eclipse.util;

import java.io.File;
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;

import org.eclipse.core.resources.IMarker;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.IResource;
import org.eclipse.core.resources.IWorkspace;
import org.eclipse.core.resources.IWorkspaceRoot;
import org.eclipse.core.resources.IncrementalProjectBuilder;
import org.eclipse.core.resources.ResourcesPlugin;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.jdt.core.IJavaModelMarker;
import org.eclipse.jdt.core.IJavaProject;
import org.eclipse.jdt.core.IMethod;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.core.Signature;
import org.eclipse.jface.operation.IRunnableWithProgress;
import org.eclipse.ui.IWorkbench;
import org.eclipse.ui.PlatformUI;
import org.eclipse.ui.progress.IProgressService;
import org.jdom.JDOMException;

import com.subhajit.common.classloaders.URLClassLoaderX;
import com.subhajit.common.javacompiler.Compiler.CodeLevel;
import com.subhajit.common.util.CommonUtils;
import com.subhajit.common.util.IConstants;
import com.subhajit.common.util.IProgress;
import com.subhajit.eclipse.entities.CompiledJar;
import com.subhajit.eclipse.entities.EclipseClasspath;
import com.subhajit.eclipse.entities.EclipseMetafile;
import com.subhajit.eclipse.entities.EclipseProject;
import com.subhajit.eclipse.swt.SwtDialog;
import com.subhajit.eclipse.swt.SwtProgressImpl;
import com.sun.idm.svc.common.xmlutil.XmlUtils;

public class ProjectUtils {
  private static final URL[] ZERO_LENGTH_URL_ARRAY = new URL[0];

  private ProjectUtils() {
    super();
  }

  /**
   * Convenient organization of build related methods.
   *
   * @author sdasgupta
   *
   */
  public static class BuildUtils {
    /**
     * Builds the given java project and all its dependencies in the correct
     * order using the {@link IncrementalProjectBuilder}.
     *
     * @param javaProject
     * @throws Exception
     */
    public static Map<IJavaProject, IMarker[]> buildProjectInteractively0(
        final IJavaProject javaProject, final int buildKind)
        throws Exception {
      final Map<IJavaProject, IMarker[]> problems = new HashMap<IJavaProject, IMarker[]>();
      final List<Exception> exceptionHolder = new ArrayList<Exception>();
      IWorkbench wb = PlatformUI.getWorkbench();
      IProgressService ps = wb.getProgressService();
      ps.busyCursorWhile(new IRunnableWithProgress() {
        public void run(IProgressMonitor progressMonitor) {
          try {
            IProgress progress = new SwtProgressImpl(
                progressMonitor);
            ProjectUtils.updateProjectLocations(progress);
            List<IJavaProject> dependentProjects = BuildUtils
                .getDependentProjects(javaProject, progress);
            progress.setRange(0, dependentProjects.size());
            int index = 0;
            for (IJavaProject project : dependentProjects) {
              progress.increment(1, "Building "
                  + project.getProject().getName());
              BuildUtils.buildJavaProjectInteractively0(project,
                  progress, buildKind, problems);
              progress.setRange(0, dependentProjects.size());
              for (int i = 0; i < index; i++) {
                progress.increment(1, "");
              }
              index++;
            }
            BuildUtils.buildJavaProjectInteractively0(javaProject,
                progress, buildKind, problems);
          } catch (Exception exc) {
            exceptionHolder.add(exc);
          }
        }
      });

      if (!exceptionHolder.isEmpty()) {
        SwtDialog.show(exceptionHolder.get(0));
      }
      return problems;
    }

    private static void buildJavaProjectInteractively0(
        final IJavaProject javaProject, IProgress progress,
        int buildKind, Map<IJavaProject, IMarker[]> markers)
        throws InvocationTargetException, InterruptedException {
      try {
        IProgressMonitor progressMonitor = ((SwtProgressImpl) progress)
            .getProgressMonitor();
        javaProject.getProject().clearHistory(progressMonitor);
        javaProject.getProject().refreshLocal(IResource.DEPTH_INFINITE,
            null);
        if (progressMonitor != null) {
          progressMonitor.subTask("Building "
              + javaProject.getProject().getName());
        }
        javaProject.getProject().build(buildKind, progressMonitor);
        IMarker[] problemMarkers = javaProject.getUnderlyingResource()
            .findMarkers(
                IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER,
                true, IResource.DEPTH_INFINITE);
        if (problemMarkers.length != 0) {
          markers.put(javaProject, problemMarkers);
        }
      } catch (CoreException exc) {
        exc.printStackTrace();
      }
    }

    private static List<IJavaProject> getDependentProjects(
        final IJavaProject javaProject, IProgress progress)
        throws IOException, JDOMException, InterruptedException {
      int[] initialProgressRange = null;
      if (progress != null) {
        initialProgressRange = progress.getRange();
      }
      try {
        if (progress != null) {
          progress.setRange(0, 2);
          progress.increment(1, "Computing project dependencies");
        }
        final File projectFile = ProjectUtils
            .getProjectFile(javaProject);
        EclipseProject eclipseProject = new EclipseProject(projectFile);
        EclipseMetafile[] metafiles = eclipseProject.getAllDependants();
        List<IJavaProject> projects = new ArrayList<IJavaProject>();
        if (progress != null) {
          progress.setRange(0, metafiles.length);
        }
        for (EclipseMetafile metafile : metafiles) {
          if (progress != null) {
            progress.increment(1, "Inspecting "
                + metafile.getFile().getAbsolutePath());
          }
          if (metafile instanceof EclipseProject) {
            projects.add(ProjectUtils
                .getJavaProject(((EclipseProject) metafile)
                    .getFile()));
          }
        }
        return projects;
      } finally {
        if (progress != null) {
          progress.setRange(initialProgressRange[0],
              initialProgressRange[1]);
        }
      }
    }
  }

  public static File getProjectFile(final IJavaProject javaProject) {
    return new File(javaProject.getProject().getLocation().toFile(),
        ".project");
  }

  public static IJavaProject getJavaProject(final File projectFile)
      throws IOException {
    try {
      IWorkspace workspace = ResourcesPlugin.getWorkspace();
      IWorkspaceRoot root = workspace.getRoot();
      final String projectName = XmlUtils.loadElement(projectFile)
          .getChild("name").getText().trim();
      IProject project = root.getProject(projectName);
      IJavaProject ret = JavaCore.create(project);
      try {
        project.create(null);
      } catch (CoreException exc) {
      }
      try {
        project.open(null);
      } catch (CoreException exc) {
      }
      return ret;
    } catch (JDOMException exc) {
      throw new RuntimeException(exc);
    }
  }

  /**
   * Returns a Set containing the project locations of all projects loaded in
   * this workspace.
   *
   * @param javaProject
   * @return
   * @throws IOException
   */
  // protected static Set<String> getProjectLocations() throws IOException {
  // // Get the base directories of all projects in the workspace.
  // IWorkspace workspace = ResourcesPlugin.getWorkspace();
  // IProject[] projects = workspace.getRoot().getProjects();
  // Set<String> projectLocations = new HashSet<String>();
  // for (IProject project : projects) {
  // File projectLocation = project.getProject().getLocation().toFile();
  // projectLocations.add(projectLocation.getParentFile()
  // .getCanonicalPath());
  // }
  // return projectLocations;
  // }
  protected static Set<File> getDirectoriesContainingProjects()
      throws IOException {
    // Get the base directories of all projects in the workspace.
    IWorkspace workspace = ResourcesPlugin.getWorkspace();
    IProject[] projects = workspace.getRoot().getProjects();
    Set<File> projectLocations = new HashSet<File>();
    for (IProject project : projects) {
      File projectLocation = project.getProject().getLocation().toFile();
      projectLocations.add(projectLocation.getParentFile()
          .getCanonicalFile());
    }
    return projectLocations;
  }

  public static Set<File> getProjectLocations() throws IOException {
    // Get the base directories of all projects in the workspace.
    IWorkspace workspace = ResourcesPlugin.getWorkspace();
    IProject[] projects = workspace.getRoot().getProjects();
    Set<File> projectLocations = new HashSet<File>();
    for (IProject project : projects) {
      File projectLocation = project.getProject().getLocation().toFile();
      projectLocations.add(projectLocation.getCanonicalFile());
    }
    return projectLocations;
  }

  public static void updateProjectLocations(IProgress... progresses)
      throws IOException {
    Set<File> projectLocations = getDirectoriesContainingProjects();
    for (IProgress progress : progresses) {
      progress.setRange(0, projectLocations.size());
    }
    StringBuilder str = new StringBuilder();
    int index = 0;
    for (File projectLocation : projectLocations) {
      for (IProgress progress : progresses) {
        progress.increment(1, "Updating project info - "
            + projectLocation.getAbsolutePath());
      }
      str.append(projectLocation.getCanonicalPath());
      index++;
      if (index < projectLocations.size()) {
        str.append(IConstants.COMMA);
      }
    }
    for (IProgress progress : progresses) {
      progress.increment(1, "Updated project info.");
    }
    System.setProperty(EclipseProject.PROJECT_LOCATIONS_SYSTEM_PROPERTIES,
        str.toString());
  }

  public static final URLClassLoader getClassLoader(
      final IJavaProject javaProject, boolean rebuildProject)
      throws Exception {
    final File projectFile = getProjectFile(javaProject);
    if (rebuildProject) {
      BuildUtils.buildProjectInteractively0(javaProject,
          IncrementalProjectBuilder.FULL_BUILD);
    } else {
      BuildUtils.buildProjectInteractively0(javaProject,
          IncrementalProjectBuilder.INCREMENTAL_BUILD);
    }
    // return new URLClassLoaderX(EclipseProjectBuilder
    // .computeProjectOutputURLs(projectFile).toArray(
    // ZERO_LENGTH_URL_ARRAY), ProjectUtils.class
    // .getClassLoader());
    List<URL> urls = new ArrayList<URL>();
    EclipseProject project = new EclipseProject(projectFile);
    urls.add(project.getOutputDirectory().toURI().toURL());
    for (EclipseMetafile dependent : project.getAllDependants()) {
      if (dependent instanceof CompiledJar) {
        urls.add(((CompiledJar) dependent).getFile().toURI().toURL());
      } else if (dependent instanceof EclipseProject) {
        EclipseProject dependentProject = (EclipseProject) dependent;
        urls.add(dependentProject.getOutputDirectory().toURI().toURL());
      } else if (dependent instanceof EclipseClasspath) {
        // EclipseClasspath classpath = ( EclipseClasspath )dependent;
      }
    }
    return new URLClassLoaderX(urls.toArray(ZERO_LENGTH_URL_ARRAY));
  }

  // public static URLClassLoader getClassLoader(final File projectFile,
  // boolean rebuildProject) throws Exception, IOException,
  // JDOMException, InterruptedException {
  // if (rebuildProject) {
  // buildProjectInteractively(projectFile);
  // }
  // return new URLClassLoader(EclipseProjectBuilder
  // .computeProjectOutputURLs(projectFile).toArray(
  // ZERO_LENGTH_URL_ARRAY), ProjectUtils.class
  // .getClassLoader());
  // }

  public static CodeLevel getTargetCompilerVersion(IJavaProject javaProject) {
    String value = (String) javaProject.getOptions(true).get(
        "org.eclipse.jdt.core.compiler.codegen.targetPlatform");
    if (value == null) {
      value = "1.6";
    }

    if (value.equals("1.5")) {
      return CodeLevel.ONE_FIVE;
    } else if (value.equals("1.6")) {
      return CodeLevel.ONE_SIX;
    } else {
      throw new UnsupportedOperationException(
          "Class version not supported - " + value);
    }
  }

  public static Set<EclipseProject> getAllEclipseProjectsInWorkspace()
      throws IOException, JDOMException, InterruptedException {
    Set<File> projectLocations = getProjectLocations();
    Set<EclipseProject> allEclipseProjects = new HashSet<EclipseProject>();
    for (File projectLocation : projectLocations) {
      try {
        allEclipseProjects.add(new EclipseProject(new File(
            projectLocation.getAbsolutePath(), ".project")));
      } catch (Exception exc) {
        // This project could not be loaded correctly.
        System.out
            .println("While trying to create EclipseProject from project location "
                + projectLocation.getAbsolutePath() + ":");
        exc.printStackTrace(System.out);
      }
    }
    return allEclipseProjects;
  }

  /**
   * Returns all elements of <tt>problems</tt> that have a severity of
   * {@link IMarker#SEVERITY_ERROR}.
   *
   * @param problems
   * @return
   * @throws CoreException
   */
  public static Map<IJavaProject, List<IMarker>> getProblemMarkers(
      Map<IJavaProject, IMarker[]> problems) throws CoreException {
    Map<IJavaProject, List<IMarker>> ret = new HashMap<IJavaProject, List<IMarker>>();
    for (Map.Entry<IJavaProject, IMarker[]> entry : problems.entrySet()) {
      List<IMarker> problemMarkers = new ArrayList<IMarker>();
      for (IMarker marker : entry.getValue()) {
        @SuppressWarnings("unchecked")
        Map<String, Object> attributes = marker.getAttributes();
        if (attributes.containsKey(IMarker.SEVERITY)
            && attributes.get(IMarker.SEVERITY).equals(
                IMarker.SEVERITY_ERROR)) {
          problemMarkers.add(marker);
        }
      }
      if (!problemMarkers.isEmpty()) {
        ret.put(entry.getKey(), problemMarkers);
      }
    }
    return ret;
  }

  /**
   * Locates the {@link Method} corresponding to the given
   * <tt>sourceMethod</tt>.
   *
   * @param classLoader
   * @param className
   * @param sourceMethod
   * @return
   * @throws ClassNotFoundException
   */
  public static Method locateMethod(URLClassLoader classLoader,
      String className, IMethod sourceMethod)
      throws ClassNotFoundException {
    Class<?> klass = Class.forName(className, true, classLoader);
    Method[] declaredMethods = klass.getDeclaredMethods();
    for (Method declaredMethod : declaredMethods) {
      if (declaredMethod.getName().equals(sourceMethod.getElementName())
          && declaredMethod.getParameterTypes().length == sourceMethod
              .getParameterTypes().length) {
        int index = 0;
        boolean parameterTypesMatch = true;
        for (String sourceMethodParameterType : sourceMethod
            .getParameterTypes()) {
          String simpleTypeName = Signature
              .toString(sourceMethodParameterType);
          boolean typesAreEqual = false;
          String simpleArgumentType = null;
          if (declaredMethod.getParameterTypes()[index].isArray()) {
            int dim = 0;
            Class<?> klass0 = declaredMethod.getParameterTypes()[index];
            while (klass0.isArray()) {
              klass0 = klass0.getComponentType();
              dim++;
            }
            simpleArgumentType = klass0.getName();
            for (int i = 0; i < dim; i++) {
              simpleArgumentType += "[]";
            }
          } else {
            simpleArgumentType = declaredMethod.getParameterTypes()[index]
                .getName();
          }
          if (simpleTypeName.indexOf(".") != -1) {
            if (simpleArgumentType.equals(simpleTypeName)) {
              typesAreEqual = true;
            }
          } else {
            if (CommonUtils.getClassNameSansPackage(
                simpleArgumentType).equals(simpleTypeName)) {
              typesAreEqual = true;
            }
          }
          index++;
          if (!typesAreEqual) {
            parameterTypesMatch = false;
            break;
          }
        }
        if (parameterTypesMatch) {
          return declaredMethod;
        }
      }
    }
    return null;
  }
}
TOP

Related Classes of com.subhajit.eclipse.util.ProjectUtils

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