Skip to content

Commit

Permalink
Updated the getInputStream method on EmbeddedJars to just use the Jar…
Browse files Browse the repository at this point in the history
…File.getInputStream for a entry by name, rather than parsing thru them.

This Is fixing a problem where sometimes a JAR file in constructed in such a way that JarInputStream can't seem to process it correctly, possibly due to the order of the entries inside.  (Possibly related to this: https://bugs.openjdk.org/browse/JDK-8031748 )
  • Loading branch information
jbedell-newrelic committed Jul 28, 2023
1 parent 06f080e commit a568356
Showing 1 changed file with 9 additions and 28 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -7,17 +7,18 @@

package com.newrelic.agent.service.module;

import com.google.common.collect.ImmutableMap;
import com.google.common.collect.ImmutableMap.Builder;

import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.util.Map;
import java.util.Map.Entry;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
import java.util.jar.JarInputStream;

import com.google.common.collect.ImmutableMap;
import com.google.common.collect.ImmutableMap.Builder;

public class EmbeddedJars {
private static final Map<String,String> EMBEDDED_FORMAT_TO_EXTENSION = getEmbeddedFormatToExtension("ear","war","jar");

Expand Down Expand Up @@ -46,36 +47,16 @@ public static InputStream getInputStream(URL url) throws IOException {
String path = url.toExternalForm().substring(index + entry.getKey().length());
// add 1 to skip past the `.` and the value length, which is the length of the file extension
url = new URL(url.toExternalForm().substring(0, index + 1 + entry.getValue().length()));
InputStream inputStream = url.openStream();
JarInputStream jarStream = new JarInputStream(inputStream);

if (!readToEntry(jarStream, path)) {
inputStream.close();
throw new IOException("Unable to open stream for " + path + " in " + url.toExternalForm());
}
return jarStream;
// For some reason, some JAR files cannot be read properly by JarInputStream, at least the getNextJatEntry methodI
// perhaps related to entry order (https://bugs.openjdk.org/browse/JDK-8031748)
JarFile jarFile = new JarFile(url.getFile());
JarEntry innerEntry = jarFile.getJarEntry(path);
return jarFile.getInputStream(innerEntry);
}
}

return url.openStream();
}

/**
* Read a jar input stream until a given path is found.
*
* @param jarStream
* @param path
* @return true if the path was found
* @throws IOException
*/
private static boolean readToEntry(JarInputStream jarStream, String path) throws IOException {
for (JarEntry jarEntry = null; (jarEntry = jarStream.getNextJarEntry()) != null;) {
if (path.equals(jarEntry.getName())) {
return true;
}
}
return false;
}

static JarInputStream getJarInputStream(URL url) throws IOException {
boolean isEmbedded = isEmbedded(url);
Expand Down

0 comments on commit a568356

Please sign in to comment.