1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.commons.compress;
20
21 import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
22 import static org.junit.jupiter.api.Assertions.assertEquals;
23 import static org.junit.jupiter.api.Assertions.assertFalse;
24 import static org.junit.jupiter.api.Assertions.assertInstanceOf;
25 import static org.junit.jupiter.api.Assertions.assertNotNull;
26 import static org.junit.jupiter.api.Assertions.assertNull;
27 import static org.junit.jupiter.api.Assertions.assertThrows;
28 import static org.junit.jupiter.api.Assertions.assertTrue;
29
30 import java.io.BufferedInputStream;
31 import java.io.IOException;
32 import java.io.InputStream;
33 import java.nio.file.Files;
34 import java.nio.file.Path;
35 import java.nio.file.attribute.FileTime;
36 import java.time.Instant;
37 import java.util.Collections;
38
39 import org.apache.commons.compress.archivers.ArchiveEntry;
40 import org.apache.commons.compress.archivers.ArchiveException;
41 import org.apache.commons.compress.archivers.ArchiveInputStream;
42 import org.apache.commons.compress.archivers.ArchiveStreamFactory;
43 import org.apache.commons.compress.archivers.ar.ArArchiveInputStream;
44 import org.apache.commons.compress.archivers.arj.ArjArchiveInputStream;
45 import org.apache.commons.compress.archivers.cpio.CpioArchiveInputStream;
46 import org.apache.commons.compress.archivers.tar.TarArchiveEntry;
47 import org.apache.commons.compress.archivers.tar.TarArchiveInputStream;
48 import org.apache.commons.compress.archivers.zip.ZipArchiveInputStream;
49 import org.junit.jupiter.api.Test;
50
51 public final class DetectArchiverTest extends AbstractTest {
52
53 final ClassLoader classLoader = getClass().getClassLoader();
54
55 private void checkDetectedType(final String type, final Path path) throws ArchiveException, IOException {
56 try (BufferedInputStream inputStream = new BufferedInputStream(Files.newInputStream(path))) {
57
58
59 assertEquals(ArchiveStreamFactory.JAR.equals(type) ? ArchiveStreamFactory.ZIP : type, ArchiveStreamFactory.detect(inputStream));
60 }
61 }
62
63 private void checkEmptyArchive(final String type) throws Exception {
64 final Path path = createEmptyArchive(type);
65 assertDoesNotThrow(() -> {
66 try (BufferedInputStream inputStream = new BufferedInputStream(Files.newInputStream(path));
67 ArchiveInputStream<?> ais = factory.createArchiveInputStream(inputStream)) {
68
69 }
70 }, "Should have recognized empty archive for " + type);
71 checkDetectedType(type, path);
72 }
73
74 @SuppressWarnings("resource")
75 private <T extends ArchiveInputStream<? extends E>, E extends ArchiveEntry> T createArchiveInputStream(final String resource)
76 throws ArchiveException, IOException {
77 return factory.createArchiveInputStream(createBufferedInputStream(resource));
78 }
79
80 private BufferedInputStream createBufferedInputStream(final String resource) throws IOException {
81 return new BufferedInputStream(newInputStream(resource));
82 }
83
84 private boolean isValidName(final String value) {
85 return value.isEmpty() || value.chars().allMatch(ch -> ch > 31 && ch < 128);
86 }
87
88 @Test
89 void testCOMPRESS_117() throws Exception {
90 try (ArchiveInputStream<?> tar = createArchiveInputStream("COMPRESS-117.tar")) {
91 assertNotNull(tar);
92 assertInstanceOf(TarArchiveInputStream.class, tar);
93 }
94 }
95
96 @Test
97 void testCOMPRESS_335() throws Exception {
98 try (ArchiveInputStream<?> tar = createArchiveInputStream("COMPRESS-335.tar")) {
99 assertNotNull(tar);
100 assertInstanceOf(TarArchiveInputStream.class, tar);
101 }
102 }
103
104 @Test
105 void testDetection() throws Exception {
106
107 try (ArchiveInputStream<?> ar = createArchiveInputStream("bla.ar")) {
108 assertNotNull(ar);
109 assertInstanceOf(ArArchiveInputStream.class, ar);
110 }
111
112 try (ArchiveInputStream<?> tar = createArchiveInputStream("bla.tar")) {
113 assertNotNull(tar);
114 assertInstanceOf(TarArchiveInputStream.class, tar);
115 }
116
117 try (ArchiveInputStream<?> zip = createArchiveInputStream("bla.zip")) {
118 assertNotNull(zip);
119 assertInstanceOf(ZipArchiveInputStream.class, zip);
120 }
121
122 try (ArchiveInputStream<?> jar = createArchiveInputStream("bla.jar")) {
123 assertNotNull(jar);
124 assertInstanceOf(ZipArchiveInputStream.class, jar);
125 }
126
127 try (ArchiveInputStream<?> cpio = createArchiveInputStream("bla.cpio")) {
128 assertNotNull(cpio);
129 assertInstanceOf(CpioArchiveInputStream.class, cpio);
130 }
131
132 try (ArchiveInputStream<?> arj = createArchiveInputStream("bla.arj")) {
133 assertNotNull(arj);
134 assertInstanceOf(ArjArchiveInputStream.class, arj);
135 }
136
137
138
139
140
141
142 }
143
144
145
146
147
148
149
150
151 @Test
152 void testDetectionNotArchive() {
153 assertThrows(ArchiveException.class, () -> createArchiveInputStream("test.txt"));
154 }
155
156 @Test
157 void testDetectOldTarFormatArchive() throws Exception {
158 try (ArchiveInputStream<?> tar = createArchiveInputStream("COMPRESS-612/test-times-star-folder.tar")) {
159 assertNotNull(tar);
160 assertInstanceOf(TarArchiveInputStream.class, tar);
161 }
162 }
163
164 @Test
165 void testEmptyCpioArchive() throws Exception {
166 checkEmptyArchive("cpio");
167 }
168
169 @Test
170 void testEmptyJarArchive() throws Exception {
171 checkEmptyArchive("jar");
172 }
173
174 @Test
175 void testEmptyTarArchive() throws Exception {
176
177 final Path path = createEmptyArchive("tar");
178 assertThrows(ArchiveException.class, () -> checkDetectedType("tar", path));
179 }
180
181 @Test
182 void testEmptyZipArchive() throws Exception {
183 checkEmptyArchive("zip");
184 }
185
186
187
188
189 @Test
190 void testIcoFile() {
191 assertThrows(ArchiveException.class, () -> {
192 try (InputStream in = createBufferedInputStream("org/apache/commons/compress/COMPRESS-644/ARW05UP.ICO")) {
193 assertNull(ArchiveStreamFactory.detect(in));
194 }
195 });
196 }
197
198 @Test
199 void testIcoFileFirstTarArchiveEntry() throws Exception {
200 try (TarArchiveInputStream inputStream = new TarArchiveInputStream(createBufferedInputStream("org/apache/commons/compress/COMPRESS-644/ARW05UP.ICO"))) {
201 final TarArchiveEntry entry = inputStream.getNextEntry();
202
203 assertNull(entry.getCreationTime());
204 assertEquals(-1, entry.getDataOffset());
205 assertEquals(0, entry.getDevMajor());
206 assertEquals(0, entry.getDevMinor());
207 assertEquals(Collections.emptyMap(), entry.getExtraPaxHeaders());
208 assertEquals(0, entry.getGroupId());
209 assertFalse(isValidName(entry.getGroupName()), entry::getGroupName);
210 assertNull(entry.getLastAccessTime());
211 assertEquals(0, entry.getLastModifiedDate().getTime());
212 assertEquals(FileTime.from(Instant.EPOCH), entry.getLastModifiedTime());
213 assertEquals(0, entry.getLinkFlag());
214 assertEquals("", entry.getLinkName());
215 assertEquals(0, entry.getLongGroupId());
216 assertEquals(16777215, entry.getLongUserId());
217 assertEquals(0, entry.getMode());
218 assertEquals(0, entry.getModTime().getTime());
219 assertFalse(isValidName(entry.getName()), entry::getName);
220 assertNull(entry.getPath());
221 assertEquals(0, entry.getRealSize());
222 assertEquals(0, entry.getSize());
223 assertNull(entry.getStatusChangeTime());
224 assertEquals(16777215, entry.getUserId());
225 assertFalse(isValidName(entry.getUserName()), entry::getUserName);
226 assertTrue(entry.isFile());
227 assertFalse(entry.isBlockDevice());
228 assertFalse(entry.isCharacterDevice());
229 assertTrue(entry.isCheckSumOK());
230 assertFalse(entry.isDirectory());
231 assertFalse(entry.isExtended());
232 assertFalse(entry.isFIFO());
233 assertFalse(entry.isGlobalPaxHeader());
234 assertFalse(entry.isGNULongLinkEntry());
235 assertFalse(entry.isGNULongNameEntry());
236 assertFalse(entry.isGNUSparse());
237 assertFalse(entry.isLink());
238 assertFalse(entry.isOldGNUSparse());
239 assertFalse(entry.isPaxGNU1XSparse());
240 assertFalse(entry.isPaxGNUSparse());
241 assertFalse(entry.isPaxHeader());
242 assertFalse(entry.isSparse());
243 assertFalse(entry.isStarSparse());
244 assertTrue(entry.isStreamContiguous());
245 assertFalse(entry.isSymbolicLink());
246 }
247 }
248 }