-
Notifications
You must be signed in to change notification settings - Fork 22
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add tests for compat functions, ensuring parity with the methods they…
… replace.
- Loading branch information
1 parent
fb51550
commit 11a33cb
Showing
2 changed files
with
247 additions
and
0 deletions.
There are no files selected for viewing
93 changes: 93 additions & 0 deletions
93
src/test/java/in/dragonbra/javasteam/util/compat/ByteArrayOutputStreamCompatTest.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,93 @@ | ||
package in.dragonbra.javasteam.util.compat; | ||
|
||
import org.junit.jupiter.api.Assertions; | ||
import org.junit.jupiter.api.Test; | ||
|
||
import java.io.ByteArrayOutputStream; | ||
import java.nio.charset.StandardCharsets; | ||
|
||
public class ByteArrayOutputStreamCompatTest { | ||
|
||
@Test | ||
public void testEmptyStream() { | ||
var baos = new ByteArrayOutputStream(); | ||
|
||
var compatResult = ByteArrayOutputStreamCompat.toString(baos); | ||
var standardResult = baos.toString(); | ||
|
||
Assertions.assertEquals("", compatResult); | ||
Assertions.assertEquals("", standardResult); | ||
Assertions.assertEquals(standardResult, compatResult); | ||
} | ||
|
||
@Test | ||
public void testAsciiContent() { | ||
var baos = new ByteArrayOutputStream(); | ||
var testString = "Hello, World!"; | ||
|
||
baos.write(testString.getBytes(StandardCharsets.UTF_8), 0, testString.length()); | ||
|
||
var compatResult = ByteArrayOutputStreamCompat.toString(baos); | ||
var standardResult = baos.toString(); | ||
|
||
Assertions.assertEquals(testString, compatResult); | ||
Assertions.assertEquals(testString, standardResult); | ||
Assertions.assertEquals(standardResult, compatResult); | ||
} | ||
|
||
@Test | ||
public void testUnicodeContent() { | ||
var baos = new ByteArrayOutputStream(); | ||
var testString = "Hello, 世界! 👋"; | ||
var bytes = testString.getBytes(StandardCharsets.UTF_8); | ||
|
||
baos.write(bytes, 0, bytes.length); | ||
|
||
var compatResult = ByteArrayOutputStreamCompat.toString(baos); | ||
var standardResult = baos.toString(); | ||
|
||
Assertions.assertEquals(testString, compatResult); | ||
Assertions.assertEquals(testString, standardResult); | ||
Assertions.assertEquals(standardResult, compatResult); | ||
} | ||
|
||
@Test | ||
public void testLargeContent() { | ||
var baos = new ByteArrayOutputStream(); | ||
var largeString = new StringBuilder(); | ||
for (int i = 0; i < 1000; i++) { | ||
largeString.append("Line ").append(i).append("\n"); | ||
} | ||
var testString = largeString.toString(); | ||
var bytes = testString.getBytes(StandardCharsets.UTF_8); | ||
baos.write(bytes, 0, bytes.length); | ||
|
||
var compatResult = ByteArrayOutputStreamCompat.toString(baos); | ||
var standardResult = baos.toString(); | ||
|
||
Assertions.assertEquals(testString, compatResult); | ||
Assertions.assertEquals(testString, standardResult); | ||
Assertions.assertEquals(standardResult, compatResult); | ||
} | ||
|
||
@Test | ||
public void testPartialWrites() { | ||
var baos = new ByteArrayOutputStream(); | ||
var part1 = "Hello"; | ||
var part2 = ", "; | ||
var part3 = "World!"; | ||
|
||
baos.write(part1.getBytes(StandardCharsets.UTF_8), 0, part1.length()); | ||
baos.write(part2.getBytes(StandardCharsets.UTF_8), 0, part2.length()); | ||
baos.write(part3.getBytes(StandardCharsets.UTF_8), 0, part3.length()); | ||
|
||
var expected = part1 + part2 + part3; | ||
var compatResult = ByteArrayOutputStreamCompat.toString(baos); | ||
var standardResult = baos.toString(); | ||
|
||
Assertions.assertEquals(expected, compatResult); | ||
Assertions.assertEquals(expected, standardResult); | ||
Assertions.assertEquals(standardResult, compatResult); | ||
} | ||
|
||
} |
154 changes: 154 additions & 0 deletions
154
src/test/java/in/dragonbra/javasteam/util/compat/InputStreamCompatTest.kt
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,154 @@ | ||
package `in`.dragonbra.javasteam.util.compat | ||
|
||
import org.junit.jupiter.api.Assertions | ||
import org.junit.jupiter.api.BeforeEach | ||
import org.junit.jupiter.api.Nested | ||
import org.junit.jupiter.api.Test | ||
import org.junit.jupiter.params.ParameterizedTest | ||
import org.junit.jupiter.params.provider.ValueSource | ||
import java.io.ByteArrayInputStream | ||
import java.io.IOException | ||
import java.io.InputStream | ||
import kotlin.random.Random | ||
|
||
/** | ||
* [readNBytesCompat] methods are kotlin only extension functions for [InputStream]. | ||
* This test is in Kotlin to ensure functionality for the extension functions | ||
*/ | ||
class InputStreamCompatTest { | ||
|
||
private lateinit var testData: ByteArray | ||
private lateinit var emptyStream: InputStream | ||
private lateinit var normalStream: InputStream | ||
private lateinit var largeStream: InputStream | ||
|
||
@BeforeEach | ||
fun setup() { | ||
testData = Random.nextBytes(16384) | ||
emptyStream = ByteArrayInputStream(ByteArray(0)) | ||
normalStream = ByteArrayInputStream(testData) | ||
largeStream = ByteArrayInputStream(Random.nextBytes(1024 * 1024)) | ||
} | ||
|
||
@Nested | ||
inner class ReadNBytesCompatArrayTest { | ||
|
||
@Test | ||
fun `empty stream returns zero bytes`() { | ||
val buffer = ByteArray(100) | ||
val bytesRead = emptyStream.readNBytesCompat(buffer, 0, buffer.size) | ||
Assertions.assertEquals(0, bytesRead) | ||
} | ||
|
||
@Test | ||
fun `reading zero bytes returns zero`() { | ||
val buffer = ByteArray(100) | ||
val bytesRead = normalStream.readNBytesCompat(buffer, 0, 0) | ||
Assertions.assertEquals(0, bytesRead) | ||
} | ||
|
||
@ParameterizedTest | ||
@ValueSource(ints = [1, 100, 1000, 8192]) | ||
fun `reading n bytes matches JDK implementation`(n: Int) { | ||
val compatBuffer = ByteArray(n) | ||
val jdkBuffer = ByteArray(n) | ||
|
||
val stream1 = ByteArrayInputStream(testData) | ||
val stream2 = ByteArrayInputStream(testData) | ||
|
||
val compatBytesRead = stream1.readNBytesCompat(compatBuffer, 0, n) | ||
val jdkBytesRead = stream2.readNBytes(jdkBuffer, 0, n) | ||
|
||
Assertions.assertArrayEquals(jdkBuffer, compatBuffer) | ||
Assertions.assertEquals(jdkBytesRead, compatBytesRead) | ||
} | ||
|
||
@Test | ||
fun `throws exception on negative length`() { | ||
val buffer = ByteArray(100) | ||
Assertions.assertThrows(IndexOutOfBoundsException::class.java) { | ||
normalStream.readNBytesCompat(buffer, 0, -1) | ||
} | ||
} | ||
|
||
@Test | ||
fun `throws exception on invalid offset`() { | ||
val buffer = ByteArray(100) | ||
Assertions.assertThrows(IndexOutOfBoundsException::class.java) { | ||
normalStream.readNBytesCompat(buffer, -1, 50) | ||
} | ||
Assertions.assertThrows(IndexOutOfBoundsException::class.java) { | ||
normalStream.readNBytesCompat(buffer, 101, 50) | ||
} | ||
} | ||
} | ||
|
||
@Nested | ||
inner class ReadNBytesCompatLengthTest { | ||
|
||
@Test | ||
fun `empty stream returns empty array`() { | ||
val result = emptyStream.readNBytesCompat(100) | ||
Assertions.assertEquals(0, result.size) | ||
} | ||
|
||
@Test | ||
fun `reading zero bytes returns empty array`() { | ||
val result = normalStream.readNBytesCompat(0) | ||
Assertions.assertEquals(0, result.size) | ||
} | ||
|
||
@ParameterizedTest | ||
@ValueSource(ints = [1, 100, 1000, 8192, 16384]) | ||
fun `reading n bytes matches JDK implementation`(n: Int) { | ||
val stream1 = ByteArrayInputStream(testData) | ||
val stream2 = ByteArrayInputStream(testData) | ||
|
||
val compatResult = stream1.readNBytesCompat(n) | ||
val jdkResult = stream2.readNBytes(n) | ||
|
||
Assertions.assertArrayEquals(jdkResult, compatResult) | ||
} | ||
|
||
@Test | ||
fun `throws exception on negative length`() { | ||
Assertions.assertThrows(IllegalArgumentException::class.java) { | ||
normalStream.readNBytesCompat(-1) | ||
} | ||
} | ||
|
||
@Test | ||
fun `handles large reads correctly`() { | ||
val lengthToRead = 1024 * 1024 | ||
val result = largeStream.readNBytesCompat(lengthToRead) | ||
Assertions.assertEquals(lengthToRead, result.size) | ||
} | ||
|
||
@Test | ||
fun `partial read when EOF reached`() { | ||
val result = normalStream.readNBytesCompat(testData.size * 2) | ||
Assertions.assertEquals(testData.size, result.size) | ||
Assertions.assertArrayEquals(testData, result) | ||
} | ||
} | ||
|
||
@Nested | ||
inner class ErrorConditionsTest { | ||
|
||
@Test | ||
fun `handles IOException from underlying stream`() { | ||
val failingStream = object : InputStream() { | ||
override fun read(): Int = throw IOException("Simulated failure") | ||
override fun read(b: ByteArray, off: Int, len: Int): Int = throw IOException("Simulated failure") | ||
} | ||
|
||
Assertions.assertThrows(IOException::class.java) { | ||
failingStream.readNBytesCompat(100) | ||
} | ||
|
||
Assertions.assertThrows(IOException::class.java) { | ||
failingStream.readNBytesCompat(ByteArray(100), 0, 100) | ||
} | ||
} | ||
} | ||
} |