Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPascal Rapicault2015-10-04 21:17:00 -0400
committerPascal Rapicault2015-10-04 21:51:35 -0400
commit6542434b77b0b5f915d469e1c234c50a438ced0b (patch)
tree4d23baac8b0465dea7c265dbf5d6b18844b6f968
parente3e578c98878b6e5bc8b9140389ffe36c5651b56 (diff)
downloadrt.equinox.p2-6542434b77b0b5f915d469e1c234c50a438ced0b.tar.gz
rt.equinox.p2-6542434b77b0b5f915d469e1c234c50a438ced0b.tar.xz
rt.equinox.p2-6542434b77b0b5f915d469e1c234c50a438ced0b.zip
Helper library to compress to XZ an existing p2 repoI20151006-0800
-rw-r--r--bundles/org.eclipse.equinox.p2.repository.tools/META-INF/MANIFEST.MF6
-rw-r--r--bundles/org.eclipse.equinox.p2.repository.tools/pom.xml2
-rw-r--r--bundles/org.eclipse.equinox.p2.repository.tools/src/org/eclipse/equinox/p2/internal/repository/tools/XZCompressor.java187
3 files changed, 192 insertions, 3 deletions
diff --git a/bundles/org.eclipse.equinox.p2.repository.tools/META-INF/MANIFEST.MF b/bundles/org.eclipse.equinox.p2.repository.tools/META-INF/MANIFEST.MF
index 019814bf8..fd84cd814 100644
--- a/bundles/org.eclipse.equinox.p2.repository.tools/META-INF/MANIFEST.MF
+++ b/bundles/org.eclipse.equinox.p2.repository.tools/META-INF/MANIFEST.MF
@@ -2,7 +2,7 @@ Manifest-Version: 1.0
Bundle-ManifestVersion: 2
Bundle-Name: %bundleName
Bundle-SymbolicName: org.eclipse.equinox.p2.repository.tools;singleton:=true
-Bundle-Version: 2.1.100.qualifier
+Bundle-Version: 2.1.300.qualifier
Bundle-Activator: org.eclipse.equinox.p2.internal.repository.tools.Activator
Bundle-Vendor: %providerName
Bundle-Localization: plugin
@@ -12,7 +12,9 @@ Export-Package: org.eclipse.equinox.p2.internal.repository.comparator;x-internal
org.eclipse.equinox.p2.internal.repository.tools.analyzer;x-internal:=true,
org.eclipse.equinox.p2.repository.tools.analyzer;version="2.0.0",
org.eclipse.equinox.p2.repository.tools.comparator;version="2.0.0"
-Require-Bundle: org.eclipse.equinox.common;bundle-version="3.3.0", org.eclipse.equinox.registry
+Require-Bundle: org.eclipse.equinox.common;bundle-version="3.3.0",
+ org.eclipse.equinox.registry,
+ org.tukaani.xz;bundle-version="1.3.0"
Bundle-RequiredExecutionEnvironment: J2SE-1.5
Bundle-ActivationPolicy: lazy
Import-Package: org.eclipse.equinox.app;version="1.0.0",
diff --git a/bundles/org.eclipse.equinox.p2.repository.tools/pom.xml b/bundles/org.eclipse.equinox.p2.repository.tools/pom.xml
index 38fd306ad..cff3ff163 100644
--- a/bundles/org.eclipse.equinox.p2.repository.tools/pom.xml
+++ b/bundles/org.eclipse.equinox.p2.repository.tools/pom.xml
@@ -9,6 +9,6 @@
</parent>
<groupId>org.eclipse.equinox</groupId>
<artifactId>org.eclipse.equinox.p2.repository.tools</artifactId>
- <version>2.1.100-SNAPSHOT</version>
+ <version>2.1.300-SNAPSHOT</version>
<packaging>eclipse-plugin</packaging>
</project>
diff --git a/bundles/org.eclipse.equinox.p2.repository.tools/src/org/eclipse/equinox/p2/internal/repository/tools/XZCompressor.java b/bundles/org.eclipse.equinox.p2.repository.tools/src/org/eclipse/equinox/p2/internal/repository/tools/XZCompressor.java
new file mode 100644
index 000000000..429b145f9
--- /dev/null
+++ b/bundles/org.eclipse.equinox.p2.repository.tools/src/org/eclipse/equinox/p2/internal/repository/tools/XZCompressor.java
@@ -0,0 +1,187 @@
+/*******************************************************************************
+ * Copyright (c) 2015 Rapicorp, Inc 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:
+ * Rapicorp, Inc - initial API and implementation
+ *******************************************************************************/
+package org.eclipse.equinox.p2.internal.repository.tools;
+
+import java.io.*;
+import java.util.*;
+import java.util.jar.JarEntry;
+import java.util.jar.JarInputStream;
+import org.eclipse.equinox.internal.p2.metadata.repository.Messages;
+import org.eclipse.osgi.util.NLS;
+import org.tukaani.xz.*;
+
+/**
+ * A class taking care of creating the XZ'ed version of a repository.
+ * It takes as input the folder where a p2 repository is stored and produces the new files in this folder.
+ *
+ * The files expected in to be found as input are content.xml or content.jar, or artifacts.xml or artifacts.jar.
+ * Note that the tool does not require both the a metadata repository and an artifact repository.
+ * The output will be <fileName>.xml.xz, and a p2.index
+ *
+ */
+
+public class XZCompressor {
+ private static final String CONTENT_XML_XZ = "content.xml.xz"; //$NON-NLS-1$
+ private static final String ARTIFACTS_XML_XZ = "artifacts.xml.xz"; //$NON-NLS-1$
+ private static final String ARTIFACTS2 = "artifacts"; //$NON-NLS-1$
+ private static final String CONTENT = "content"; //$NON-NLS-1$
+ private static final String JAR = ".jar"; //$NON-NLS-1$
+ private static final String XML = ".xml"; //$NON-NLS-1$
+
+ private String repoFolder;
+ private boolean preserveOriginalFile = true;
+ private ArrayList<File> filesToDelete = new ArrayList<File>();
+
+ public String getRepoFolder() {
+ return repoFolder;
+ }
+
+ public void setRepoFolder(String repoFolder) {
+ this.repoFolder = repoFolder;
+ }
+
+ public boolean isPreserveOriginalFile() {
+ return preserveOriginalFile;
+ }
+
+ public void setPreserveOriginalFile(boolean preserveOriginalFile) {
+ this.preserveOriginalFile = preserveOriginalFile;
+ }
+
+ private File uncompressJar(File jarFile, String fileToExtract) throws IOException {
+ JarInputStream jarStream = new JarInputStream(new FileInputStream(jarFile));
+ JarEntry jarEntry = jarStream.getNextJarEntry();
+ while (jarEntry != null && (!fileToExtract.equals(jarEntry.getName()))) {
+ jarEntry = jarStream.getNextJarEntry();
+ }
+ //if there is a jar but the entry is missing or invalid, treat this as an invalid repository
+ if (jarEntry == null) {
+ jarStream.close();
+ throw new IOException(NLS.bind(Messages.repoMan_invalidLocation, jarFile.getAbsolutePath()));
+ }
+
+ BufferedInputStream input = null;
+ OutputStream output = null;
+ File extractedFile = new File(jarFile.getAbsoluteFile().getParent(), fileToExtract);
+ try {
+ input = new BufferedInputStream(jarStream);
+ output = new BufferedOutputStream(new FileOutputStream(extractedFile));
+
+ byte[] buffer = new byte[8192];
+ int bytesRead = 0;
+ while ((bytesRead = input.read(buffer)) != -1)
+ output.write(buffer, 0, bytesRead);
+ } finally {
+ if (input != null) {
+ input.close();
+ }
+ if (output != null) {
+ output.close();
+ }
+ }
+ filesToDelete.add(extractedFile);
+ return extractedFile;
+ }
+
+ private File getMetadataFile(String prefix) throws IOException {
+ File candidate = new File(repoFolder, prefix + XML);
+ if (candidate.exists()) {
+ if (!preserveOriginalFile) {
+ filesToDelete.add(candidate);
+ }
+ return candidate;
+ }
+
+ candidate = new File(repoFolder, prefix + JAR);
+ if (candidate.exists()) {
+ if (!preserveOriginalFile) {
+ filesToDelete.add(candidate);
+ }
+ return uncompressJar(candidate, prefix + XML);
+ }
+ return null;
+ }
+
+ public void compressRepo() throws IOException {
+ File metadata = getMetadataFile(CONTENT);
+ if (metadata != null)
+ compressFile(metadata, new File(repoFolder, CONTENT_XML_XZ));
+
+ File artifacts = getMetadataFile(ARTIFACTS2);
+ if (artifacts != null)
+ compressFile(artifacts, new File(repoFolder, ARTIFACTS_XML_XZ));
+
+ createP2Index(metadata != null, artifacts != null);
+ deleteFiles();
+ }
+
+ private void deleteFiles() {
+ for (Iterator<File> iterator = filesToDelete.iterator(); iterator.hasNext();) {
+ iterator.next().delete();
+ }
+ }
+
+ private void compressFile(File input, File output) throws IOException {
+ LZMA2Options options = new LZMA2Options();
+ try {
+ options.setDictSize(LZMA2Options.DICT_SIZE_DEFAULT);
+ options.setLcLp(3, 0);
+ options.setPb(LZMA2Options.PB_MAX);
+ options.setMode(LZMA2Options.MODE_NORMAL);
+ options.setNiceLen(LZMA2Options.NICE_LEN_MAX);
+ options.setMatchFinder(LZMA2Options.MF_BT4);
+ options.setDepthLimit(512);
+ } catch (UnsupportedOptionsException e) {
+ //Can't happen
+ }
+ XZOutputStream out = null;
+ java.io.FileInputStream is = null;
+ try {
+ out = new XZOutputStream(new FileOutputStream(output), options);
+ is = new FileInputStream(input);
+ byte[] buf = new byte[8192];
+ int size;
+ while ((size = is.read(buf)) != -1)
+ out.write(buf, 0, size);
+ } finally {
+ if (out != null)
+ out.close();
+ if (is != null)
+ is.close();
+ }
+
+ }
+
+ private void createP2Index(boolean metadata, boolean artifacts) throws IOException {
+ Properties p2Index = new Properties();
+ if (metadata) {
+ if (preserveOriginalFile)
+ p2Index.setProperty("metadata.repository.factory.order", "content.xml.xz,content.xml,!"); //$NON-NLS-1$//$NON-NLS-2$
+ else
+ p2Index.setProperty("metadata.repository.factory.order", "content.xml.xz,!"); //$NON-NLS-1$//$NON-NLS-2$
+ }
+ if (artifacts) {
+ if (preserveOriginalFile)
+ p2Index.setProperty("artifact.repository.factory.order", "artifacts.xml.xz,artifacts.xml,!"); //$NON-NLS-1$//$NON-NLS-2$
+ else
+ p2Index.setProperty("artifact.repository.factory.order", "artifacts.xml.xz,!"); //$NON-NLS-1$//$NON-NLS-2$
+ }
+ p2Index.setProperty("version", "1"); //$NON-NLS-1$//$NON-NLS-2$
+ OutputStream output = null;
+ try {
+ output = new FileOutputStream(new File(repoFolder, "p2.index")); //$NON-NLS-1$
+ p2Index.store(output, null);
+ } finally {
+ if (output != null)
+ output.close();
+ }
+ }
+}

Back to the top