package com.bumptech.glide.util;
import static com.google.common.truth.Truth.assertThat;
import static org.junit.Assert.fail;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.anyInt;
import static org.mockito.Mockito.when;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
import org.robolectric.RobolectricTestRunner;
import org.robolectric.annotation.Config;
@RunWith(RobolectricTestRunner.class)
@Config(manifest = Config.NONE, sdk = 18)
public class ContentLengthInputStreamTest {
@Mock InputStream wrapped;
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
}
@Test
public void testAvailable_withZeroReadsAndValidContentLength_returnsContentLength()
throws IOException {
int value = 123356;
InputStream is = ContentLengthInputStream.obtain(wrapped, String.valueOf(value));
assertThat(is.available()).isEqualTo(value);
}
@Test
public void testAvailable_withNullContentLength_returnsWrappedAvailable()
throws IOException {
InputStream is = ContentLengthInputStream.obtain(wrapped, null /*contentLengthHeader*/);
int expected = 1234;
when(wrapped.available()).thenReturn(expected);
assertThat(is.available()).isEqualTo(expected);
}
@Test
public void testAvailable_withInvalidContentLength_returnsWrappedAvailable() throws IOException {
InputStream is = ContentLengthInputStream.obtain(wrapped, "invalid_length");
int expected = 567;
when(wrapped.available()).thenReturn(expected);
assertThat(is.available()).isEqualTo(expected);
}
@Test
public void testAvailable_withRead_returnsContentLengthOffsetByRead() throws IOException {
int contentLength = 999;
InputStream is = ContentLengthInputStream.obtain(wrapped, String.valueOf(contentLength));
when(wrapped.read()).thenReturn(1);
assertThat(is.read()).isEqualTo(1);
assertThat(is.available()).isEqualTo(contentLength - 1);
}
@Test
public void testAvailable_handlesReadValueOfZero() throws IOException {
int contentLength = 999;
InputStream is = ContentLengthInputStream.obtain(wrapped, String.valueOf(contentLength));
when(wrapped.read()).thenReturn(0);
assertThat(is.read()).isEqualTo(0);
assertThat(is.available()).isEqualTo(contentLength - 1);
}
@Test
public void testAvailable_withReadBytes_returnsContentLengthOffsetByNumberOfBytes()
throws IOException {
int contentLength = 678;
InputStream is = ContentLengthInputStream.obtain(wrapped, String.valueOf(contentLength));
int read = 100;
when(wrapped.read(any(byte[].class), anyInt(), anyInt())).thenReturn(read);
assertThat(is.read(new byte[500], 0, 0)).isEqualTo(read);
assertThat(is.available()).isEqualTo(contentLength - read);
}
@Test
public void testRead_whenReturnsLessThanZeroWithoutReadingAllContent_throwsIOException()
throws IOException {
int contentLength = 1;
InputStream is = ContentLengthInputStream.obtain(wrapped, String.valueOf(contentLength));
when(wrapped.read()).thenReturn(-1);
try {
is.read();
fail("Failed to throw expected exception");
} catch (IOException e) {
// Expected.
}
}
@Test
public void testReadBytes_whenReturnsLessThanZeroWithoutReadingAllContent_throwsIOException()
throws IOException {
int contentLength = 2;
InputStream is = ContentLengthInputStream.obtain(wrapped, String.valueOf(contentLength));
when(wrapped.read(any(byte[].class), anyInt(), anyInt())).thenReturn(-1);
try {
is.read(new byte[10], 0, 0);
fail("Failed to throw expected exception");
} catch (IOException e) {
// Expected.
}
}
@Test
public void testRead_whenReturnsLessThanZeroWithInvalidLength_doesNotThrow() throws IOException {
InputStream is = ContentLengthInputStream.obtain(wrapped, "invalid_length");
when(wrapped.read()).thenReturn(-1);
is.read();
}
@Test
public void testReadBytes_whenReturnsLessThanZeroWithInvalidLength_doesNotThrow()
throws IOException {
InputStream is = ContentLengthInputStream.obtain(wrapped, "invalid_length");
when(wrapped.read(any(byte[].class), anyInt(), anyInt())).thenReturn(-1);
is.read(new byte[10], 0, 0);
}
@Test
public void testRead_readWithZeroes_doesNotThrow() throws IOException {
ByteArrayInputStream inner = new ByteArrayInputStream(new byte[] {0, 0, 0});
InputStream is = ContentLengthInputStream.obtain(inner, 3);
assertThat(is.read()).isEqualTo(0);
assertThat(is.read()).isEqualTo(0);
assertThat(is.read()).isEqualTo(0);
assertThat(is.read()).isEqualTo(-1);
}
@Test
public void testRead_readWithHighValues_doesNotThrow() throws IOException {
ByteArrayInputStream inner =
new ByteArrayInputStream(new byte[] {(byte) 0xF0, (byte) 0xA0, (byte) 0xFF});
InputStream is = ContentLengthInputStream.obtain(inner, 3);
assertThat(is.read()).isEqualTo(0xF0);
assertThat(is.read()).isEqualTo(0xA0);
assertThat(is.read()).isEqualTo(0xFF);
assertThat(is.read()).isEqualTo(-1);
}
}