1package org.brotli.wrapper.enc; 2 3import static org.junit.Assert.assertEquals; 4 5import org.brotli.integration.BundleHelper; 6import org.brotli.wrapper.dec.BrotliInputStream; 7import java.io.ByteArrayInputStream; 8import java.io.ByteArrayOutputStream; 9import java.io.FileInputStream; 10import java.io.IOException; 11import java.io.InputStream; 12import java.io.OutputStream; 13import java.util.List; 14import junit.framework.TestCase; 15import junit.framework.TestSuite; 16import org.junit.runner.RunWith; 17import org.junit.runners.AllTests; 18 19/** Tests for {@link org.brotli.wrapper.enc.BrotliOutputStream}. */ 20@RunWith(AllTests.class) 21public class BrotliOutputStreamTest { 22 23 private enum TestMode { 24 WRITE_ALL, 25 WRITE_CHUNKS, 26 WRITE_BYTE 27 } 28 29 // TODO: remove when Bazel get JNI support. 30 static { 31 System.load(new java.io.File(new java.io.File(System.getProperty("java.library.path")), 32 "liblibjni.so").getAbsolutePath()); 33 } 34 35 private static final int CHUNK_SIZE = 256; 36 37 static InputStream getBundle() throws IOException { 38 return new FileInputStream(System.getProperty("TEST_BUNDLE")); 39 } 40 41 /** Creates a test suite. */ 42 public static TestSuite suite() throws IOException { 43 TestSuite suite = new TestSuite(); 44 InputStream bundle = getBundle(); 45 try { 46 List<String> entries = BundleHelper.listEntries(bundle); 47 for (String entry : entries) { 48 suite.addTest(new StreamTestCase(entry, TestMode.WRITE_ALL)); 49 suite.addTest(new StreamTestCase(entry, TestMode.WRITE_CHUNKS)); 50 suite.addTest(new StreamTestCase(entry, TestMode.WRITE_BYTE)); 51 } 52 } finally { 53 bundle.close(); 54 } 55 return suite; 56 } 57 58 /** Test case with a unique name. */ 59 static class StreamTestCase extends TestCase { 60 final String entryName; 61 final TestMode mode; 62 StreamTestCase(String entryName, TestMode mode) { 63 super("BrotliOutputStreamTest." + entryName + "." + mode.name()); 64 this.entryName = entryName; 65 this.mode = mode; 66 } 67 68 @Override 69 protected void runTest() throws Throwable { 70 BrotliOutputStreamTest.run(entryName, mode); 71 } 72 } 73 74 private static void run(String entryName, TestMode mode) throws Throwable { 75 InputStream bundle = getBundle(); 76 byte[] original; 77 try { 78 original = BundleHelper.readEntry(bundle, entryName); 79 } finally { 80 bundle.close(); 81 } 82 if (original == null) { 83 throw new RuntimeException("Can't read bundle entry: " + entryName); 84 } 85 86 if ((mode == TestMode.WRITE_CHUNKS) && (original.length <= CHUNK_SIZE)) { 87 return; 88 } 89 90 ByteArrayOutputStream dst = new ByteArrayOutputStream(); 91 OutputStream encoder = new BrotliOutputStream(dst); 92 try { 93 switch (mode) { 94 case WRITE_ALL: 95 encoder.write(original); 96 break; 97 98 case WRITE_CHUNKS: 99 for (int offset = 0; offset < original.length; offset += CHUNK_SIZE) { 100 encoder.write(original, offset, Math.min(CHUNK_SIZE, original.length - offset)); 101 } 102 break; 103 104 case WRITE_BYTE: 105 for (byte singleByte : original) { 106 encoder.write(singleByte); 107 } 108 break; 109 } 110 } finally { 111 encoder.close(); 112 } 113 114 InputStream decoder = new BrotliInputStream(new ByteArrayInputStream(dst.toByteArray())); 115 try { 116 long originalCrc = BundleHelper.fingerprintStream(new ByteArrayInputStream(original)); 117 long crc = BundleHelper.fingerprintStream(decoder); 118 assertEquals(originalCrc, crc); 119 } finally { 120 decoder.close(); 121 } 122 } 123} 124