blob: a8bf55b941969043752333a71aac58d9b8518587 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 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
******************************************************************************/
package org.eclipse.indigo.tests.jars;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Properties;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
import java.util.zip.ZipFile;
import org.apache.tools.ant.BuildException;
import org.eclipse.indigo.tests.utils.FullJarNameParser;
import org.eclipse.indigo.tests.utils.JARFileNameFilter;
import org.eclipse.indigo.tests.utils.ReportWriter;
import org.eclipse.osgi.util.ManifestElement;
import org.osgi.framework.BundleException;
/**
* Test to check MANIFEST.MF files in jars in a repository for presence of
* Eclipse-SourceReferences.
*
* @since 3.7
*/
public class ESTest extends TestJars {
private static final Object PROPERTY_ECLIPSE_SOURCEREFERENCES = "Eclipse-SourceReferences";
private static final FullJarNameParser nameParser = new FullJarNameParser();
private static final String outputFilename = "esdata.txt";
private String bundleDirectory = null;
public static void main(String[] args) {
ESTest testlayout = new ESTest();
testlayout.setDirectoryToCheck("/home/files/buildzips/indigoRC2/eclipseJEE/");
try {
testlayout.testESSettingRule();
}
catch (IOException e) {
e.printStackTrace();
}
}
public boolean testESSettingRule() throws IOException {
File inputdir = new File(getBundleDirectory());
if (!(inputdir.exists() && inputdir.isDirectory())) {
throw new BuildException("bundle direcotry (" + getBundleDirectory() + ") must be an existing directory.");
}
boolean failuresOccured;
failuresOccured = checkBundleES(inputdir);
return failuresOccured;
}
private boolean checkBundleES(File inputdir) throws IOException {
// reset/initialize errors
InputStream propertyStream = this.getClass().getResourceAsStream("exceptions.properties");
Properties esExceptionProperties = new Properties();
String esExceptions = "";
try {
esExceptionProperties.load(propertyStream);
esExceptions = esExceptionProperties.getProperty("esExceptions");
if (esExceptions == null) {
esExceptions = "";
}
}
catch (IOException e) {
e.printStackTrace();
}
finally {
if (propertyStream != null) {
try {
propertyStream.close();
}
catch (IOException e) {
// would be unusual to get here?
e.printStackTrace();
}
}
}
Map withEs = new HashMap();
List withoutEs = new ArrayList();
boolean failuresOccured = false;
File[] children = inputdir.listFiles(new JARFileNameFilter());
int totalsize = children.length;
int checked = 0;
int nProjectTags = 0;
for (int i = 0; i < totalsize; i++) {
File child = children[i];
String name = child.getName();
String bundleName = getBundleName(name);
if ((bundleName != null) && !esExceptions.contains(bundleName)) {
checked++;
String es = getESFromJAR(child);
if ((es != null) && es.contains("project=")) {
nProjectTags++;
}
if ((es != null) && (es.length() > 0)) {
// has ES
incrementCounts(withEs, es);
}
else {
// no ES
trackOmissions(withoutEs, child);
}
}
}
printreport(withEs, withoutEs, totalsize, checked, nProjectTags);
return failuresOccured;
}
private void printreport(Map withEs, List withoutESs, int totalsize, int checked, int nProjectTags) throws IOException {
ReportWriter reportWriter = new ReportWriter(getOutputDirectory(), outputFilename);
try {
reportWriter.writeln();
reportWriter.writeln(" Directory checked: " + getBundleDirectory());
reportWriter.writeln(" Checked " + checked + " of " + totalsize + " jars.");
reportWriter.writeln();
reportWriter.writeln();
reportWriter.writeln(" Number of bundles with an Eclipse-SourceReferences: " + totalCount(withEs));
reportWriter.writeln(" Number of those with 'project=': " + nProjectTags + " attribute.");
reportWriter.writeln(" Number of bundles without an Eclipse-SourceReferences: " + withoutESs.size());
reportWriter.writeln();
reportWriter.writeln();
reportWriter.writeln(" Bundles with Eclipse-SourceReferences (total: " + totalCount(withEs) + ")");
reportWriter.writeln();
Collection allESs = withEs.keySet();
List allESList = new ArrayList(allESs);
Collections.sort(allESList);
for (Object object : allESList) {
//Integer count = (Integer) withEs.get(object);
//reportWriter.writeln(" " + count.intValue() + " " + object);
reportWriter.writeln(" " + object);
}
reportWriter.writeln();
reportWriter.writeln();
reportWriter.writeln(" Bundles without an Eclipse-SourceReferences (total: " + withoutESs.size() + ")");
Collections.sort(withoutESs);
for (Object object : withoutESs) {
reportWriter.writeln(" " + object);
}
reportWriter.writeln();
}
finally {
reportWriter.close();
}
}
private int totalCount(Map bundlesWithEs) {
Collection allCounts = bundlesWithEs.values();
int total = 0;
for (Iterator iterator = allCounts.iterator(); iterator.hasNext();) {
Integer count = (Integer) iterator.next();
total = total + count.intValue();
}
return total;
}
private void trackOmissions(List bundlesWithoutEs, File child) {
bundlesWithoutEs.add(child.getName());
}
private void incrementCounts(Map esMap, String es) {
Integer count = (Integer) esMap.get(es);
if (count == null) {
esMap.put(es, new Integer(1));
}
else {
esMap.put(es, increment(count));
}
}
private Integer increment(Integer count) {
return new Integer(count.intValue() + 1);
}
private String getBundleName(String fullname) {
String result = null;
boolean parsable = nameParser.parse(fullname);
if (parsable) {
result = nameParser.getProjectString();
}
return result;
}
/*
* Return the bundle id from the manifest pointed to by the given input
* stream.
*/
private String getESFromManifest(InputStream input, String path) {
String es = null;
try {
Map attributes = ManifestElement.parseBundleManifest(input, null);
es = (String) attributes.get(PROPERTY_ECLIPSE_SOURCEREFERENCES);
}
catch (BundleException e) {
e.printStackTrace();
}
catch (IOException e) {
e.printStackTrace();
}
finally {
if (input != null) {
try {
input.close();
}
catch (IOException e) {
// ignore
}
}
}
return es;
}
/*
* The given file points to a bundle contained in an archive. Look into
* the bundle manifest file to find the bundle identifier.
*/
private String getESFromJAR(File file) {
InputStream input = null;
JarFile jar = null;
try {
jar = new JarFile(file, false, ZipFile.OPEN_READ);
JarEntry entry = jar.getJarEntry(JarFile.MANIFEST_NAME);
if (entry == null) {
// addError("Bundle does not contain a MANIFEST.MF file: " +
// file.getAbsolutePath());
return null;
}
input = jar.getInputStream(entry);
return getESFromManifest(input, file.getAbsolutePath());
}
catch (IOException e) {
System.out.println(e.getMessage());
// addError(e.getMessage());
return null;
}
finally {
if (input != null) {
try {
input.close();
}
catch (IOException e) {
// ignore
}
}
if (jar != null) {
try {
jar.close();
}
catch (IOException e) {
// ignore
}
}
}
}
private String getBundleDirectory() {
if (bundleDirectory == null) {
String property = getDirectoryToCheck();
if (property == null) {
throw new BuildException("Need to set input directory to check against.");
}
if (property.endsWith("/")) {
bundleDirectory = property + "aggregate/plugins";
}
else {
bundleDirectory = property + "/aggregate/plugins";
}
}
return bundleDirectory;
}
}