Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
36 changes: 36 additions & 0 deletions finch-java-core/src/main/kotlin/com/tryfinch/api/core/Utils.kt
Original file line number Diff line number Diff line change
Expand Up @@ -25,4 +25,40 @@ internal fun <K : Comparable<K>, V> SortedMap<K, V>.toImmutable(): SortedMap<K,
if (isEmpty()) Collections.emptySortedMap()
else Collections.unmodifiableSortedMap(toSortedMap(comparator()))

/**
* Returns whether [this] is equal to [other].
*
* This differs from [Object.equals] because it also deeply equates arrays based on their contents,
* even when there are arrays directly nested within other arrays.
*/
@JvmSynthetic
internal infix fun Any?.contentEquals(other: Any?): Boolean =
arrayOf(this).contentDeepEquals(arrayOf(other))

/**
* Returns a hash of the given sequence of [values].
*
* This differs from [java.util.Objects.hash] because it also deeply hashes arrays based on their
* contents, even when there are arrays directly nested within other arrays.
*/
@JvmSynthetic internal fun contentHash(vararg values: Any?): Int = values.contentDeepHashCode()

/**
* Returns a [String] representation of [this].
*
* This differs from [Object.toString] because it also deeply stringifies arrays based on their
* contents, even when there are arrays directly nested within other arrays.
*/
@JvmSynthetic
internal fun Any?.contentToString(): String {
var string = arrayOf(this).contentDeepToString()
if (string.startsWith('[')) {
string = string.substring(1)
}
if (string.endsWith(']')) {
string = string.substring(0, string.length - 1)
}
return string
}

internal interface Enum
43 changes: 11 additions & 32 deletions finch-java-core/src/main/kotlin/com/tryfinch/api/core/Values.kt
Original file line number Diff line number Diff line change
Expand Up @@ -470,41 +470,20 @@ internal constructor(
val filename: String? = null,
) {

private var hashCode: Int = 0

override fun hashCode(): Int {
if (hashCode == 0) {
hashCode =
Objects.hash(
name,
contentType,
filename,
when (value) {
is ByteArray -> value.contentHashCode()
is String -> value
is Boolean -> value
is Long -> value
is Double -> value
else -> value?.hashCode()
},
)
}
return hashCode
}

override fun equals(other: Any?): Boolean {
if (this === other) return true
if (other == null || this.javaClass != other.javaClass) return false
private val hashCode: Int by lazy { contentHash(name, value, contentType, filename) }

other as MultipartFormValue<*>
override fun hashCode(): Int = hashCode

if (name != other.name || contentType != other.contentType || filename != other.filename)
return false

return when {
value is ByteArray && other.value is ByteArray -> value contentEquals other.value
else -> value?.equals(other.value) ?: (other.value == null)
override fun equals(other: Any?): Boolean {
if (this === other) {
return true
}

return other is MultipartFormValue<*> &&
name == other.name &&
value contentEquals other.value &&
contentType == other.contentType &&
filename == other.filename
}

override fun toString(): String =
Expand Down
33 changes: 33 additions & 0 deletions finch-java-core/src/test/kotlin/com/tryfinch/api/core/UtilsTest.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
package com.tryfinch.api.core

import org.assertj.core.api.Assertions.assertThat
import org.junit.jupiter.api.Test

internal class UtilsTest {
@Test
fun contentDeepEquals() {
assertThat(42 contentEquals 42).isTrue()
assertThat(42 contentEquals "Hello World!").isFalse()
assertThat(byteArrayOf(1, 2, 3) contentEquals byteArrayOf(1, 2, 3)).isTrue()
assertThat(byteArrayOf(1, 2, 3) contentEquals byteArrayOf(1, 2, 4)).isFalse()
assertThat(
arrayOf(byteArrayOf(1, 2), byteArrayOf(3)) contentEquals
arrayOf(byteArrayOf(1, 2), byteArrayOf(3))
)
.isTrue()
assertThat(
arrayOf(byteArrayOf(1, 2), byteArrayOf(3)) contentEquals
arrayOf(byteArrayOf(1), byteArrayOf(2, 3))
)
.isFalse()
}

@Test
fun contentToString() {
assertThat((42).contentToString()).isEqualTo("42")
assertThat("Hello World!".contentToString()).isEqualTo("Hello World!")
assertThat(byteArrayOf(1, 2, 3).contentToString()).isEqualTo("[1, 2, 3]")
assertThat(arrayOf(byteArrayOf(1, 2), byteArrayOf(3)).contentToString())
.isEqualTo("[[1, 2], [3]]")
}
}