ZLibInputStream.java

 1package eu.siacs.conversations.utils.zlib;
 2
 3import java.io.IOException;
 4import java.io.InputStream;
 5import java.util.zip.Inflater;
 6import java.util.zip.InflaterInputStream;
 7
 8/**
 9 * ZLibInputStream is a zlib and input stream compatible version of an
10 * InflaterInputStream. This class solves the incompatibility between
11 * {@link InputStream#available()} and {@link InflaterInputStream#available()}.
12 */
13public class ZLibInputStream extends InflaterInputStream {
14
15	/**
16	 * Construct a ZLibInputStream, reading data from the underlying stream.
17	 * 
18	 * @param is
19	 *            The {@code InputStream} to read data from.
20	 * @throws IOException
21	 *             If an {@code IOException} occurs.
22	 */
23	public ZLibInputStream(InputStream is) throws IOException {
24		super(is, new Inflater(), 512);
25	}
26
27	/**
28	 * Provide a more InputStream compatible version of available. A return
29	 * value of 1 means that it is likly to read one byte without blocking, 0
30	 * means that the system is known to block for more input.
31	 * 
32	 * @return 0 if no data is available, 1 otherwise
33	 * @throws IOException
34	 */
35	@Override
36	public int available() throws IOException {
37		/*
38		 * This is one of the funny code blocks. InflaterInputStream.available
39		 * violates the contract of InputStream.available, which breaks kXML2.
40		 * 
41		 * I'm not sure who's to blame, oracle/sun for a broken api or the
42		 * google guys for mixing a sun bug with a xml reader that can't handle
43		 * it....
44		 * 
45		 * Anyway, this simple if breaks suns distorted reality, but helps to
46		 * use the api as intended.
47		 */
48		if (inf.needsInput()) {
49			return 0;
50		}
51		return super.available();
52	}
53
54}