1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.apache.commons.io.input;
18
19 import static org.junit.jupiter.api.Assertions.assertEquals;
20 import static org.junit.jupiter.api.Assertions.assertNotEquals;
21 import static org.junit.jupiter.api.Assertions.assertTrue;
22
23 import java.io.IOException;
24 import java.io.InputStream;
25 import java.nio.file.Files;
26 import java.nio.file.Path;
27 import java.util.concurrent.atomic.AtomicInteger;
28 import java.util.function.Supplier;
29
30 import org.apache.commons.io.IOUtils;
31 import org.apache.commons.lang3.RandomUtils;
32 import org.junit.jupiter.api.AfterEach;
33 import org.junit.jupiter.api.BeforeAll;
34 import org.junit.jupiter.api.Test;
35 import org.junit.jupiter.api.io.TempDir;
36 import org.junit.jupiter.params.ParameterizedTest;
37 import org.junit.jupiter.params.provider.MethodSource;
38
39
40
41
42
43
44
45
46 public abstract class AbstractInputStreamTest {
47
48 static final String ARRAY_LENGTHS_NAME = "org.apache.commons.io.input.AbstractInputStreamTest#getArrayLengths";
49
50 static final int[] ARRAY_LENGTHS = { 0, 1, 2, 4, 8, 16, 32, 64, 128 };
51
52 protected static byte[] ActualBytes;
53
54 protected static byte[] ExpectedBytes;
55 protected static Path InputPath;
56
57 @TempDir
58 static Path tempDir;
59
60 static int[] getArrayLengths() {
61 return ARRAY_LENGTHS;
62 }
63
64 @BeforeAll
65 public static void setUp() throws IOException {
66
67 ActualBytes = RandomUtils.insecure().randomBytes(2 * 1024 * 1024);
68 ExpectedBytes = ActualBytes.clone();
69 InputPath = tempDir.resolve(AbstractInputStreamTest.class.getSimpleName() + ".tmp");
70 Files.write(InputPath, ActualBytes);
71 }
72
73
74
75
76 protected InputStream[] inputStreams;
77
78 @AfterEach
79 public void tearDown() throws IOException {
80 IOUtils.close(inputStreams);
81 }
82
83 @Test
84 void testAvailableAfterClose() throws Exception {
85 for (final InputStream inputStream : inputStreams) {
86 inputStream.close();
87 assertEquals(0, inputStream.available());
88 }
89 }
90
91 @Test
92 void testAvailableAfterOpen() throws Exception {
93 for (final InputStream inputStream : inputStreams) {
94 assertTrue(inputStream.available() >= 0);
95 }
96 }
97
98 @Test
99 void testAvailableAfterRead() throws Exception {
100 for (final InputStream inputStream : inputStreams) {
101 assertNotEquals(IOUtils.EOF, inputStream.read());
102 assertTrue(inputStream.available() > 0);
103 }
104 }
105
106 @Test
107 void testAvailableAtEnd() throws Exception {
108 for (final InputStream inputStream : inputStreams) {
109 IOUtils.consume(inputStream);
110 assertEquals(0, inputStream.available());
111 }
112 }
113
114 @Test
115 void testBytesSkipped() throws IOException {
116 for (final InputStream inputStream : inputStreams) {
117 assertEquals(1024, inputStream.skip(1024));
118 for (int i = 1024; i < ExpectedBytes.length; i++) {
119 assertEquals(ExpectedBytes[i], (byte) inputStream.read());
120 }
121 }
122 }
123
124 @Test
125 void testBytesSkippedAfterEOF() throws IOException {
126 for (final InputStream inputStream : inputStreams) {
127 assertEquals(ExpectedBytes.length, inputStream.skip(ActualBytes.length + 1));
128 assertEquals(-1, inputStream.read());
129 }
130 }
131
132 @Test
133 void testBytesSkippedAfterRead() throws IOException {
134 for (final InputStream inputStream : inputStreams) {
135 for (int i = 0; i < 1024; i++) {
136 assertEquals(ExpectedBytes[i], (byte) inputStream.read());
137 }
138 assertEquals(1024, inputStream.skip(1024));
139 for (int i = 2048; i < ExpectedBytes.length; i++) {
140 assertEquals(ExpectedBytes[i], (byte) inputStream.read());
141 }
142 }
143 }
144
145 @Test
146 void testNegativeBytesSkippedAfterRead() throws IOException {
147 for (final InputStream inputStream : inputStreams) {
148 for (int i = 0; i < 1024; i++) {
149 assertEquals(ExpectedBytes[i], (byte) inputStream.read());
150 }
151
152 assertEquals(0, inputStream.skip(-1));
153 assertEquals(0, inputStream.skip(-1024));
154 assertEquals(0, inputStream.skip(Long.MIN_VALUE));
155 assertEquals(1024, inputStream.skip(1024));
156 for (int i = 2048; i < ExpectedBytes.length; i++) {
157 assertEquals(ExpectedBytes[i], (byte) inputStream.read());
158 }
159 }
160 }
161
162 @ParameterizedTest
163 @MethodSource("org.apache.commons.io.input.ReversedLinesFileReaderParamBlockSizeTest#blockSizes")
164 void testReadMultipleBytes(final int bufferSize) throws IOException {
165 for (final InputStream inputStream : inputStreams) {
166 final byte[] readBytes = new byte[bufferSize];
167 int i = 0;
168 while (i < ExpectedBytes.length) {
169 final int read = inputStream.read(readBytes, 0, readBytes.length);
170 for (int j = 0; j < read; j++) {
171 assertEquals(ExpectedBytes[i], readBytes[j]);
172 i++;
173 }
174 }
175 }
176 }
177
178 @Test
179 void testReadOneByOne() throws IOException {
180 for (final InputStream inputStream : inputStreams) {
181 for (final byte randomByte : ExpectedBytes) {
182 assertEquals(randomByte, (byte) inputStream.read());
183 }
184 }
185 }
186
187 @Test
188 void testReadOneByOneCheckAvailable() throws IOException {
189 final AtomicInteger refII = new AtomicInteger();
190 for (int idxInputs = 0; idxInputs < inputStreams.length; idxInputs++) {
191 refII.set(idxInputs);
192 final AtomicInteger refIB = new AtomicInteger();
193 @SuppressWarnings("resource")
194 final InputStream inputStream = inputStreams[idxInputs];
195 for (int idxBytes = 0; idxBytes < ExpectedBytes.length; idxBytes++) {
196 refIB.set(idxBytes);
197 final byte randomByte = ExpectedBytes[idxBytes];
198
199 final int available = inputStream.available();
200 final Supplier<String> messageSupplier = () -> String.format("idxInputs = %,d, idxBytes = %,d, available = %,d", refII.get(), refIB.get(),
201 available);
202 assertTrue(available >= 0, messageSupplier);
203 assertEquals(randomByte, (byte) inputStream.read());
204 }
205 }
206 }
207
208 @Test
209 void testReadPastEof() throws IOException {
210 final InputStream is = inputStreams[0];
211 final byte[] buf = new byte[1024];
212 while (is.read(buf, 0, buf.length) != -1) {
213
214 }
215 final int readAfterEOF = is.read(buf, 0, buf.length);
216 assertEquals(-1, readAfterEOF);
217 }
218
219 @Test
220 void testSkipFromFileChannel() throws IOException {
221 for (final InputStream inputStream : inputStreams) {
222
223
224 assertEquals(1024, inputStream.skip(1024));
225 for (int i = 1024; i < 2048; i++) {
226 assertEquals(ExpectedBytes[i], (byte) inputStream.read());
227 }
228 assertEquals(256, inputStream.skip(256));
229 assertEquals(256, inputStream.skip(256));
230 assertEquals(512, inputStream.skip(512));
231 for (int i = 3072; i < ExpectedBytes.length; i++) {
232 assertEquals(ExpectedBytes[i], (byte) inputStream.read());
233 }
234 }
235 }
236 }