001package co.codewizards.cloudstore.core.io; 002 003import java.io.IOException; 004import java.io.InputStream; 005import java.lang.reflect.Proxy; 006 007/** 008 * {@link InputStream}-representing interface to be used in API contracts. 009 * <p> 010 * Interfaces modelling API should always use {@link IInputStream} instead 011 * of {@link InputStream}, because this facilitates the usage of 012 * {@linkplain Proxy proxies}. Proxies are needed to use APIs accross 013 * local-server/-client boundaries. 014 * <p> 015 * To convert between {@link InputStream} and {@link IInputStream}, use 016 * {@link StreamUtil#castStream(IInputStream)} or {@link StreamUtil#castStream(InputStream)}. 017 * <p> 018 * It is recommended that you statically import {@code StreamUtil.*} whenever 019 * you need a {@code castStream(...)}. Also, you should register this in your IDE 020 * as a favorite for static method imports. 021 * <p> 022 * <b>Important note about the naming:</b> We usually <i>never</i> use the "I-for-interface" 023 * naming scheme! It sucks! But due to the fact that we already have "InputStream" rather than 024 * "InputStreamImpl", we exceptionally use the "I"-prefix here. 025 * 026 * @author Marco หงุ่ยตระกูล-Schulze - marco at codewizards dot co 027 */ 028public interface IInputStream extends AutoCloseable { 029 030 /** 031 * Reads the next byte of data from the input stream. The value byte is 032 * returned as an <code>int</code> in the range <code>0</code> to 033 * <code>255</code>. If no byte is available because the end of the stream 034 * has been reached, the value <code>-1</code> is returned. This method 035 * blocks until input data is available, the end of the stream is detected, 036 * or an exception is thrown. 037 * 038 * <p> A subclass must provide an implementation of this method. 039 * 040 * @return the next byte of data, or <code>-1</code> if the end of the 041 * stream is reached. 042 * @exception IOException if an I/O error occurs. 043 */ 044 int read() throws IOException; 045 046 /** 047 * Reads some number of bytes from the input stream and stores them into 048 * the buffer array <code>b</code>. The number of bytes actually read is 049 * returned as an integer. This method blocks until input data is 050 * available, end of file is detected, or an exception is thrown. 051 * 052 * <p> If the length of <code>b</code> is zero, then no bytes are read and 053 * <code>0</code> is returned; otherwise, there is an attempt to read at 054 * least one byte. If no byte is available because the stream is at the 055 * end of the file, the value <code>-1</code> is returned; otherwise, at 056 * least one byte is read and stored into <code>b</code>. 057 * 058 * <p> The first byte read is stored into element <code>b[0]</code>, the 059 * next one into <code>b[1]</code>, and so on. The number of bytes read is, 060 * at most, equal to the length of <code>b</code>. Let <i>k</i> be the 061 * number of bytes actually read; these bytes will be stored in elements 062 * <code>b[0]</code> through <code>b[</code><i>k</i><code>-1]</code>, 063 * leaving elements <code>b[</code><i>k</i><code>]</code> through 064 * <code>b[b.length-1]</code> unaffected. 065 * 066 * <p> The <code>read(b)</code> method for class <code>IInputStream</code> 067 * has the same effect as: <pre><code> read(b, 0, b.length) </code></pre> 068 * 069 * @param b the buffer into which the data is read. 070 * @return the total number of bytes read into the buffer, or 071 * <code>-1</code> if there is no more data because the end of 072 * the stream has been reached. 073 * @exception IOException If the first byte cannot be read for any reason 074 * other than the end of the file, if the input stream has been closed, or 075 * if some other I/O error occurs. 076 * @exception NullPointerException if <code>b</code> is <code>null</code>. 077 * @see java.io.InputStream#read(byte[], int, int) 078 */ 079 int read(byte b[]) throws IOException; 080 081 /** 082 * Reads up to <code>len</code> bytes of data from the input stream into 083 * an array of bytes. An attempt is made to read as many as 084 * <code>len</code> bytes, but a smaller number may be read. 085 * The number of bytes actually read is returned as an integer. 086 * 087 * <p> This method blocks until input data is available, end of file is 088 * detected, or an exception is thrown. 089 * 090 * <p> If <code>len</code> is zero, then no bytes are read and 091 * <code>0</code> is returned; otherwise, there is an attempt to read at 092 * least one byte. If no byte is available because the stream is at end of 093 * file, the value <code>-1</code> is returned; otherwise, at least one 094 * byte is read and stored into <code>b</code>. 095 * 096 * <p> The first byte read is stored into element <code>b[off]</code>, the 097 * next one into <code>b[off+1]</code>, and so on. The number of bytes read 098 * is, at most, equal to <code>len</code>. Let <i>k</i> be the number of 099 * bytes actually read; these bytes will be stored in elements 100 * <code>b[off]</code> through <code>b[off+</code><i>k</i><code>-1]</code>, 101 * leaving elements <code>b[off+</code><i>k</i><code>]</code> through 102 * <code>b[off+len-1]</code> unaffected. 103 * 104 * <p> In every case, elements <code>b[0]</code> through 105 * <code>b[off]</code> and elements <code>b[off+len]</code> through 106 * <code>b[b.length-1]</code> are unaffected. 107 * 108 * <p> The <code>read(b,</code> <code>off,</code> <code>len)</code> method 109 * for class <code>IInputStream</code> simply calls the method 110 * <code>read()</code> repeatedly. If the first such call results in an 111 * <code>IOException</code>, that exception is returned from the call to 112 * the <code>read(b,</code> <code>off,</code> <code>len)</code> method. If 113 * any subsequent call to <code>read()</code> results in a 114 * <code>IOException</code>, the exception is caught and treated as if it 115 * were end of file; the bytes read up to that point are stored into 116 * <code>b</code> and the number of bytes read before the exception 117 * occurred is returned. The default implementation of this method blocks 118 * until the requested amount of input data <code>len</code> has been read, 119 * end of file is detected, or an exception is thrown. Subclasses are encouraged 120 * to provide a more efficient implementation of this method. 121 * 122 * @param b the buffer into which the data is read. 123 * @param off the start offset in array <code>b</code> 124 * at which the data is written. 125 * @param len the maximum number of bytes to read. 126 * @return the total number of bytes read into the buffer, or 127 * <code>-1</code> if there is no more data because the end of 128 * the stream has been reached. 129 * @exception IOException If the first byte cannot be read for any reason 130 * other than end of file, or if the input stream has been closed, or if 131 * some other I/O error occurs. 132 * @exception NullPointerException If <code>b</code> is <code>null</code>. 133 * @exception IndexOutOfBoundsException If <code>off</code> is negative, 134 * <code>len</code> is negative, or <code>len</code> is greater than 135 * <code>b.length - off</code> 136 * @see java.io.InputStream#read() 137 */ 138 int read(byte b[], int off, int len) throws IOException; 139 140 /** 141 * Skips over and discards <code>n</code> bytes of data from this input 142 * stream. The <code>skip</code> method may, for a variety of reasons, end 143 * up skipping over some smaller number of bytes, possibly <code>0</code>. 144 * This may result from any of a number of conditions; reaching end of file 145 * before <code>n</code> bytes have been skipped is only one possibility. 146 * The actual number of bytes skipped is returned. If {@code n} is 147 * negative, the {@code skip} method for class {@code IInputStream} always 148 * returns 0, and no bytes are skipped. Subclasses may handle the negative 149 * value differently. 150 * 151 * <p> The <code>skip</code> method of this class creates a 152 * byte array and then repeatedly reads into it until <code>n</code> bytes 153 * have been read or the end of the stream has been reached. Subclasses are 154 * encouraged to provide a more efficient implementation of this method. 155 * For instance, the implementation may depend on the ability to seek. 156 * 157 * @param n the number of bytes to be skipped. 158 * @return the actual number of bytes skipped. 159 * @exception IOException if the stream does not support seek, 160 * or if some other I/O error occurs. 161 */ 162 long skip(long n) throws IOException; 163 164 /** 165 * Returns an estimate of the number of bytes that can be read (or 166 * skipped over) from this input stream without blocking by the next 167 * invocation of a method for this input stream. The next invocation 168 * might be the same thread or another thread. A single read or skip of this 169 * many bytes will not block, but may read or skip fewer bytes. 170 * 171 * <p> Note that while some implementations of {@code IInputStream} will return 172 * the total number of bytes in the stream, many will not. It is 173 * never correct to use the return value of this method to allocate 174 * a buffer intended to hold all data in this stream. 175 * 176 * <p> A subclass' implementation of this method may choose to throw an 177 * {@link IOException} if this input stream has been closed by 178 * invoking the {@link #close()} method. 179 * 180 * <p> The {@code available} method for class {@code IInputStream} always 181 * returns {@code 0}. 182 * 183 * <p> This method should be overridden by subclasses. 184 * 185 * @return an estimate of the number of bytes that can be read (or skipped 186 * over) from this input stream without blocking or {@code 0} when 187 * it reaches the end of the input stream. 188 * @exception IOException if an I/O error occurs. 189 */ 190 int available() throws IOException; 191 192 /** 193 * Closes this input stream and releases any system resources associated 194 * with the stream. 195 * 196 * <p> The <code>close</code> method of <code>IInputStream</code> does 197 * nothing. 198 * 199 * @exception IOException if an I/O error occurs. 200 */ 201 @Override 202 void close() throws IOException; 203 204 /** 205 * Marks the current position in this input stream. A subsequent call to 206 * the <code>reset</code> method repositions this stream at the last marked 207 * position so that subsequent reads re-read the same bytes. 208 * 209 * <p> The <code>readlimit</code> arguments tells this input stream to 210 * allow that many bytes to be read before the mark position gets 211 * invalidated. 212 * 213 * <p> The general contract of <code>mark</code> is that, if the method 214 * <code>markSupported</code> returns <code>true</code>, the stream somehow 215 * remembers all the bytes read after the call to <code>mark</code> and 216 * stands ready to supply those same bytes again if and whenever the method 217 * <code>reset</code> is called. However, the stream is not required to 218 * remember any data at all if more than <code>readlimit</code> bytes are 219 * read from the stream before <code>reset</code> is called. 220 * 221 * <p> Marking a closed stream should not have any effect on the stream. 222 * 223 * <p> The <code>mark</code> method of <code>IInputStream</code> does 224 * nothing. 225 * 226 * @param readlimit the maximum limit of bytes that can be read before 227 * the mark position becomes invalid. 228 * @see java.io.InputStream#reset() 229 */ 230 void mark(int readlimit); 231 232 /** 233 * Repositions this stream to the position at the time the 234 * <code>mark</code> method was last called on this input stream. 235 * 236 * <p> The general contract of <code>reset</code> is: 237 * 238 * <ul> 239 * <li> If the method <code>markSupported</code> returns 240 * <code>true</code>, then: 241 * 242 * <ul><li> If the method <code>mark</code> has not been called since 243 * the stream was created, or the number of bytes read from the stream 244 * since <code>mark</code> was last called is larger than the argument 245 * to <code>mark</code> at that last call, then an 246 * <code>IOException</code> might be thrown. 247 * 248 * <li> If such an <code>IOException</code> is not thrown, then the 249 * stream is reset to a state such that all the bytes read since the 250 * most recent call to <code>mark</code> (or since the start of the 251 * file, if <code>mark</code> has not been called) will be resupplied 252 * to subsequent callers of the <code>read</code> method, followed by 253 * any bytes that otherwise would have been the next input data as of 254 * the time of the call to <code>reset</code>. </ul> 255 * 256 * <li> If the method <code>markSupported</code> returns 257 * <code>false</code>, then: 258 * 259 * <ul><li> The call to <code>reset</code> may throw an 260 * <code>IOException</code>. 261 * 262 * <li> If an <code>IOException</code> is not thrown, then the stream 263 * is reset to a fixed state that depends on the particular type of the 264 * input stream and how it was created. The bytes that will be supplied 265 * to subsequent callers of the <code>read</code> method depend on the 266 * particular type of the input stream. </ul></ul> 267 * 268 * <p>The method <code>reset</code> for class <code>IInputStream</code> 269 * does nothing except throw an <code>IOException</code>. 270 * 271 * @exception IOException if this stream has not been marked or if the 272 * mark has been invalidated. 273 * @see java.io.InputStream#mark(int) 274 * @see java.io.IOException 275 */ 276 void reset() throws IOException; 277 278 /** 279 * Tests if this input stream supports the <code>mark</code> and 280 * <code>reset</code> methods. Whether or not <code>mark</code> and 281 * <code>reset</code> are supported is an invariant property of a 282 * particular input stream instance. The <code>markSupported</code> method 283 * of <code>IInputStream</code> returns <code>false</code>. 284 * 285 * @return <code>true</code> if this stream instance supports the mark 286 * and reset methods; <code>false</code> otherwise. 287 * @see java.io.InputStream#mark(int) 288 * @see java.io.InputStream#reset() 289 */ 290 boolean markSupported(); 291}