blob: 444c20bcb0bc27344efbd2a9d9937c13d0c3def8 [file] [log] [blame]
package org.eclipse.jem.internal.beaninfo.adapters;
/*******************************************************************************
* Copyright (c) 2001, 2003 IBM Corporation and others.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Common Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/cpl-v10.html
*
* Contributors:
* IBM Corporation - initial API and implementation
*******************************************************************************/
/*
* $RCSfile: BeaninfoEntry.java,v $
* $Revision: 1.1 $ $Date: 2003/10/27 17:17:59 $
*/
import java.util.ArrayList;
import org.eclipse.jem.internal.proxy.core.ProxyPlugin;
import org.eclipse.core.resources.*;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.resources.IWorkspaceRoot;
import org.eclipse.core.runtime.*;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.Path;
import org.eclipse.jdt.core.*;
import org.eclipse.jdt.core.IClasspathEntry;
import org.eclipse.jdt.core.JavaCore;
import org.eclipse.jdt.core.JavaModelException;
import org.w3c.dom.*;
/**
* Beaninfo entry. Location of the beaninfos. Much like a standard classpath entry.
*
* @version 1.0
* @author
*/
public class BeaninfoEntry implements IBeaninfosDocEntry {
final static String sBeaninfo = "beaninfo"; // Beaninfo entry, shared with BeaninfosDoc. //$NON-NLS-1$
public static final int BIE_PLUGIN = 100; // Beaninfo jar can be found in a plugin.
static int kindFromString(String kindStr) {
if (kindStr.equalsIgnoreCase("var")) //$NON-NLS-1$
return IClasspathEntry.CPE_VARIABLE;
if (kindStr.equalsIgnoreCase("src")) //$NON-NLS-1$
return IClasspathEntry.CPE_SOURCE;
if (kindStr.equalsIgnoreCase("lib")) //$NON-NLS-1$
return IClasspathEntry.CPE_LIBRARY;
if (kindStr.equalsIgnoreCase("plugin")) //$NON-NLS-1$
return BIE_PLUGIN;
return -1;
}
static String kindToString(int kind) {
switch (kind) {
case IClasspathEntry.CPE_PROJECT :
return "src"; // backward compatibility //$NON-NLS-1$
case IClasspathEntry.CPE_SOURCE :
return "src"; //$NON-NLS-1$
case IClasspathEntry.CPE_LIBRARY :
return "lib"; //$NON-NLS-1$
case IClasspathEntry.CPE_VARIABLE :
return "var"; //$NON-NLS-1$
case BIE_PLUGIN:
return "plugin"; //$NON-NLS-1$
default :
return "unknown"; //$NON-NLS-1$
}
}
/**
* Return the appropriate kind of entry when we know it is a classpath entry.
*/
public static IClasspathEntry createEntry(int kind, IPath path, IProject project, boolean isExported) {
switch (kind) {
case IClasspathEntry.CPE_LIBRARY :
if (path.isAbsolute())
return JavaCore.newLibraryEntry(path, null, null, isExported);
break;
case IClasspathEntry.CPE_SOURCE :
if (path.isAbsolute()) {
// must be an entry in this project or specify another project
String projSegment = path.segment(0);
if (project != null && projSegment != null && projSegment.equals(project.getName())) {
// this project
return JavaCore.newSourceEntry(path);
} else {
// another project
return JavaCore.newProjectEntry(path, isExported);
}
}
break;
case IClasspathEntry.CPE_VARIABLE :
return JavaCore.newVariableEntry(path, null, null, isExported);
}
return null;
}
/**
* Read the entry in from the element.
*/
public static BeaninfoEntry readEntry(IReader reader, Object element, IProject project) {
String elementKind = reader.getAttribute(element, BeaninfosDoc.sKind);
String pathStr = reader.getAttribute(element, BeaninfosDoc.sPath);
// ensure path is absolute
IPath path = new Path(pathStr);
int kind = kindFromString(elementKind);
if (kind != IClasspathEntry.CPE_VARIABLE && kind != BIE_PLUGIN && !path.isAbsolute()) {
path = project != null ? project.getFullPath().append(path) : path.makeAbsolute(); // Some folder/jar within this project
}
// exported flag
String exportedString = reader.getAttribute(element, BeaninfosDoc.sExported);
boolean isExported = "true".equalsIgnoreCase(exportedString); //$NON-NLS-1$
//$NON-NLS-1$
// recreate the entry
IClasspathEntry cpEntry = null;
IPath pluginPath = null;
if (kind != BIE_PLUGIN) {
cpEntry = createEntry(kind, path, project, isExported);
} else {
if (path.isAbsolute())
pluginPath = path;
}
ArrayList searchpaths = new ArrayList();
Object children = reader.getChildren(element);
int childrenLength = reader.getLength(children);
for (int i = 0; i < childrenLength; i++) {
Object child = reader.getItem(children, i);
if (reader.isNodeTypeElement(child)) {
Object entry = null;
if (reader.getNodeName(child).equalsIgnoreCase(SearchpathEntry.sSearchpath)) {
entry = SearchpathEntry.readEntry(reader, child, project, true);
}
if (entry != null)
searchpaths.add(entry);
}
}
if (cpEntry != null)
return new BeaninfoEntry(
cpEntry,
(SearchpathEntry[]) searchpaths.toArray(new SearchpathEntry[searchpaths.size()]),
isExported);
else if (pluginPath != null)
return new BeaninfoEntry(
pluginPath,
(SearchpathEntry[]) searchpaths.toArray(new SearchpathEntry[searchpaths.size()]),
isExported);
else
return null;
}
protected IClasspathEntry entry; // Store it as a classpath entry for convienence. It is the RAW classpath entry. This is only used when pointing to something other than a plugin.
protected IPath pluginPath; // When stored in a plugin, this will be set instead.
protected boolean isExported;
protected SearchpathEntry[] searchpaths;
/**
* Used when the beaninfo jar is within a plugin. In that case, the first segment
* of the path is the plugin descriptor, and the rest is the path from the plugin
* directory to the jar.
*/
public BeaninfoEntry(IPath pluginPath, SearchpathEntry[] searchpaths, boolean isExported) {
this(searchpaths, isExported);
this.pluginPath = pluginPath;
}
/**
* Used when the beaninfo jar/folder is either an external jar/folder or is somewhere else
* in the workspace. In that case the entry is the RAW classpath entry to that code.
*/
public BeaninfoEntry(IClasspathEntry entry, SearchpathEntry[] searchpaths, boolean isExported) {
this(searchpaths, isExported);
this.entry = entry;
}
protected BeaninfoEntry(SearchpathEntry[] searchpaths, boolean isExported) {
this.isExported = isExported;
this.searchpaths = searchpaths != null ? searchpaths : new SearchpathEntry[0];
}
public SearchpathEntry[] getSearchPaths() {
return searchpaths;
}
public void setSearchPaths(SearchpathEntry[] searchpaths) {
this.searchpaths = searchpaths;
}
public boolean isExported() {
return isExported;
}
public void setIsExported(boolean isExported) {
this.isExported = isExported;
}
public Node writeEntry(Document doc, IProject project) {
Element element = doc.createElement(sBeaninfo);
IPath path = null;
if (entry != null) {
element.setAttribute(BeaninfosDoc.sKind, kindToString(entry.getEntryKind()));
path = entry.getPath();
if (entry.getEntryKind() != IClasspathEntry.CPE_VARIABLE) {
// translate to project relative from absolute (unless a device path)
if (path.isAbsolute()) {
if (path.segment(0).equals(project.getFullPath().segment(0))) {
path = path.removeFirstSegments(1);
path = path.makeRelative();
} else {
path = path.makeAbsolute();
}
}
}
} else {
element.setAttribute(BeaninfosDoc.sKind, kindToString(BIE_PLUGIN));
path = pluginPath;
}
element.setAttribute(BeaninfosDoc.sPath, path.toString()); //$NON-NLS-1$
if (isExported()) {
element.setAttribute(BeaninfosDoc.sExported, "true"); //$NON-NLS-1$
}
for (int i = 0; i < searchpaths.length; i++) {
SearchpathEntry spe = searchpaths[i];
element.appendChild(spe.writeEntry(doc, project));
}
return element;
}
/**
* If this is not a plugin info, then return the classpath entry.
*/
public IClasspathEntry getClasspathEntry() {
return entry;
}
/**
* Return the resolved classpath for this entry. This is the path to the
* beaninfo jar.
* Returns either:
* 1) a string if a single jar,
* 2) an IProject if it is a project,
* 3) a String[] if it is a jar (including from any fragments) in a plugin. The [0] entry should be the one directly from the plugin, the rest will be from fragments.
* It can return null if the path could not be computed.
*/
public Object getClasspath() {
if (entry != null) {
// It is a standard CPE Entry.
IWorkspaceRoot root = ResourcesPlugin.getWorkspace().getRoot();
IClasspathEntry resolvedEntry = JavaCore.getResolvedClasspathEntry(entry);
switch (resolvedEntry.getEntryKind()) {
case IClasspathEntry.CPE_PROJECT :
IProject reqProject = (IProject) root.findMember(resolvedEntry.getPath().lastSegment());
// Project entries only have one segment.
if (reqProject != null && reqProject.isOpen())
return reqProject;
else
return null;
case IClasspathEntry.CPE_SOURCE :
reqProject = (IProject) root.findMember(resolvedEntry.getPath().segment(0));
// Find project from the first segment.
IJavaProject javaProject = JavaCore.create(reqProject);
if (javaProject != null) {
try {
IPath outputLocation = javaProject.getOutputLocation();
IResource resource = root.findMember(outputLocation);
if (resource != null) {
return resource.getLocation().toString();
}
} catch(JavaModelException e) {
}
}
break;
case IClasspathEntry.CPE_LIBRARY :
IResource library = root.findMember(resolvedEntry.getPath());
// can be external or in workspace
return (library != null) ? library.getLocation().toString() : resolvedEntry.getPath().toString();
}
} else {
IPluginDescriptor descr = Platform.getPluginRegistry().getPluginDescriptor(pluginPath.segment(0));
if (descr != null)
return ProxyPlugin.getPlugin().localizeFromPluginDescriptorAndFragments(
descr,
pluginPath.removeFirstSegments(1).toString());
}
return null;
}
public int getKind() {
return entry != null ? entry.getEntryKind() : BIE_PLUGIN;
}
public IPath getPath() {
return entry != null ? entry.getPath() : pluginPath;
}
public boolean equals(Object other) {
if (this == other)
return true;
if (!(other instanceof BeaninfoEntry))
return false;
// Return equal if the classpath entry is the same classpath entry or plugin path entry.
// The search path doesn't have any affect on the semantic equality.
BeaninfoEntry otherEntry = (BeaninfoEntry) other;
if (isExported != otherEntry.isExported)
return false;
if (entry != null)
return entry.equals(otherEntry.entry);
return pluginPath.equals(otherEntry.pluginPath);
}
public int hashCode() {
if (entry != null)
return entry.hashCode() ^ (isExported ? Boolean.TRUE : Boolean.FALSE).hashCode();
else
return pluginPath.hashCode() ^ (isExported ? Boolean.TRUE : Boolean.FALSE).hashCode();
}
}