blob: 141ecf63f1af1884f097356b560753c0df110b50 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2000, 2011 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
* Manuel Doninger - fixes for bug 376271
*******************************************************************************/
package org.eclipse.mylyn.versions.core;
import java.io.BufferedWriter;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.io.UnsupportedEncodingException;
import java.lang.reflect.InvocationTargetException;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.TreeSet;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import org.eclipse.core.resources.IProject;
import org.eclipse.core.runtime.CoreException;
import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Status;
import org.eclipse.mylyn.commons.core.XmlMemento;
import org.eclipse.mylyn.internal.versions.core.ScmInternal;
import org.eclipse.team.core.ProjectSetCapability;
import org.eclipse.team.core.RepositoryProvider;
import org.eclipse.team.core.RepositoryProviderType;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
/**
* Provides support for importing and exporting team project sets.
*
* @author Manuel Doninger
*/
public class ProjectSetConverter {
/**
* Returns a team project set for <code>projects</code>.
*
* @param projects
* the projects to include
* @return an XML document
* @throws CoreException
* indicates that the team project set could not be created
*/
public static ByteArrayOutputStream exportProjectSet(List<IProject> projects) throws CoreException {
Map<String, Set<IProject>> map = new HashMap<String, Set<IProject>>();
for (IProject project : projects) {
RepositoryProvider provider = RepositoryProvider.getProvider(project);
if (provider != null) {
String id = provider.getID();
Set<IProject> list = map.get(id);
if (list == null) {
list = new TreeSet<IProject>(new Comparator<IProject>() {
public int compare(IProject o1, IProject o2) {
return o1.getName().toLowerCase().compareTo(o2.getName().toLowerCase());
}
});
map.put(id, list);
}
list.add(project);
}
}
BufferedWriter writer = null;
ByteArrayOutputStream output = new ByteArrayOutputStream();
try {
writer = new BufferedWriter(new OutputStreamWriter(output, "UTF-8")); //$NON-NLS-1$
XmlMemento xmlMemento = getXMLMementoRoot();
Iterator<String> it = map.keySet().iterator();
while (it.hasNext()) {
String id = it.next();
XmlMemento memento = xmlMemento.createChild("provider"); //$NON-NLS-1$
memento.putString("id", id); //$NON-NLS-1$
Set<IProject> list = map.get(id);
IProject[] projectArray = list.toArray(new IProject[list.size()]);
RepositoryProviderType providerType = RepositoryProviderType.getProviderType(id);
ProjectSetCapability serializer = providerType.getProjectSetCapability();
ProjectSetCapability.ensureBackwardsCompatible(providerType, serializer);
if (serializer != null) {
String[] references = serializer.asReference(projectArray, null, null);
for (String reference : references) {
XmlMemento proj = memento.createChild("project"); //$NON-NLS-1$
proj.putString("reference", reference); //$NON-NLS-1$
}
}
}
xmlMemento.save(writer);
return output;
} catch (Exception e) {
throw new CoreException(new Status(IStatus.ERROR, ScmInternal.ID_PLUGIN,
"Unexpected error exporting project sets.", e)); //$NON-NLS-1$
} finally {
if (writer != null) {
try {
writer.close();
} catch (IOException e) {
// ignore
}
}
}
}
/**
* Returns a list of project names referenced in the team project set <code>input</code> for the provider
* <code>prooviderType</code>.
*
* @throws CoreException
*/
public static List<String> readProjectReferences(InputStream input, RepositoryProviderType providerType)
throws CoreException {
try {
List<String> referenceStrings = new ArrayList<String>();
XmlMemento[] providers = importProjectSet(input);
for (XmlMemento provider : providers) {
if (provider.getString("id").equals(providerType.getID())) { //$NON-NLS-1$
XmlMemento[] projects = provider.getChildren("project"); //$NON-NLS-1$
for (XmlMemento project : projects) {
referenceStrings.add(project.getString("reference")); //$NON-NLS-1$
}
}
}
return referenceStrings;
} catch (Exception e) {
throw new CoreException(new Status(IStatus.ERROR, ScmInternal.ID_PLUGIN,
"Unexpected error reading project sets.", e)); //$NON-NLS-1$
}
}
private static XmlMemento getXMLMementoRoot() throws ParserConfigurationException {
Document document = DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument();
Element element = document.createElement("psf"); //$NON-NLS-1$
element.setAttribute("version", "2.0"); //$NON-NLS-1$ //$NON-NLS-2$
document.appendChild(element);
return new XmlMemento(document, element);
}
private static XmlMemento[] importProjectSet(InputStream input) throws UnsupportedEncodingException,
InvocationTargetException {
XmlMemento xmlMemento = parseStream(input);
return xmlMemento.getChildren("provider"); //$NON-NLS-1$
}
private static XmlMemento parseStream(InputStream input) throws InvocationTargetException,
UnsupportedEncodingException {
InputStreamReader reader = new InputStreamReader(input, "UTF-8"); //$NON-NLS-1$
try {
return XmlMemento.createReadRoot(reader);
} finally {
try {
reader.close();
} catch (IOException e) {
// ignore
}
}
}
}