getInpustream on a URL representing the whole jar file leads to java.io.IOException: no entry name specified

Daniel Fuchs daniel.fuchs at oracle.com
Tue Sep 8 13:16:44 UTC 2020


Hi Jaikiran,

I expect it's an incorrect use of the API. AFAICS JarURLConnection
has always behaved like this.

Opening an inputstream requires an entry, (see 
https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/util/jar/JarFile.html#getInputStream(java.util.zip.ZipEntry)
and as specified, the entry in that JarURLConnection is null.

You can still obtain the JarFile or read the manifest though from
the JarURLConnection though.

That said, maybe the API should be clarified to make it
explicit that an exception will be thrown if getInputStream()
is called on a connection that refers to a jar file (and whose
entry/entry name is null).

best regards,

-- daniel

On 08/09/2020 13:22, Jaikiran Pai wrote:
> Please consider the following code:
> 
> import java.net.*;
> import java.io.*;
> import java.util.jar.*;
> 
> public class SimpleTest {
>      public static void main(final String[] args) throws Exception {
>          final String jarLocation = "/tmp/some-jar.jar";
>          URI uri = new URI("jar:file", null, jarLocation + "!/", null);
>          // URL will be of the form jar:file:/tmp/some-jar.jar!/
>          URL url = uri.toURL();
>          System.out.println("URL is " + url);
>          try (final InputStream is = url.openStream()) {
>              System.out.println("Stream opened " + is.getClass().getName());
>              final JarInputStream jarIs = new JarInputStream(is);
>              System.out.println("Jar inputstream opened " + jarIs);
>          }
>      }
> }
> 
> What it does is construct a jar file URL, uses that URL to open a stream
> and then passes that stream along to java.util.jar.JarInputStream
> constructor for it to parse jar entries out of it.
> 
>  From what I can say, the URL that is formed is correct based on what's
> explained in the docs of JarURLConnection[1]. That documentation also
> explicitly states that the entry is optional and in such a case the URL
> represents the entire jar file.
> 
> When I run the above code, I end up with the following exception:
> 
> Exception in thread "main" java.io.IOException: no entry name specified
>      at
> java.base/sun.net.www.protocol.jar.JarURLConnection.getInputStream(JarURLConnection.java:160)
>      at java.base/java.net.URL.openStream(URL.java:1140)
>      at SimpleTest.main(SimpleTest.java:12)
> 
> So it fails to open a stream out of the jar URL. I haven't found any
> documentation which states what's being done here is not allowed. Is
> this an incorrect use of the API in the sample program?
> 
> Java version in use is:
> 
> openjdk version "11.0.8" 2020-07-14
> OpenJDK Runtime Environment AdoptOpenJDK (build 11.0.8+10)
> OpenJDK 64-Bit Server VM AdoptOpenJDK (build 11.0.8+10, mixed mode)
> 
> But I could even reproduce this on Java 8.
> 
> [1]
> https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/net/JarURLConnection.html
> 
> -Jaikiran
> 
> 



More information about the net-dev mailing list