diff --git a/daraja/build.gradle.kts b/daraja/build.gradle.kts index c3e46478..40ff732f 100644 --- a/daraja/build.gradle.kts +++ b/daraja/build.gradle.kts @@ -85,6 +85,7 @@ kotlin { implementation(libs.kotlinX.coroutines.test) implementation(libs.mockative) implementation(libs.ktor.mock) + implementation(libs.assertK) } androidMain.dependencies { diff --git a/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/network/DarajaApiServiceTest.kt b/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/network/DarajaApiServiceTest.kt index 9fa9277b..5ca15c51 100644 --- a/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/network/DarajaApiServiceTest.kt +++ b/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/network/DarajaApiServiceTest.kt @@ -16,6 +16,8 @@ package com.vickbt.darajakmp.network +import assertk.assertThat +import assertk.assertions.isEqualTo import com.vickbt.darajakmp.network.models.DarajaToken import com.vickbt.darajakmp.network.models.DarajaTransactionRequest import com.vickbt.darajakmp.network.models.DarajaTransactionResponse @@ -29,8 +31,6 @@ import kotlinx.coroutines.test.runTest import kotlin.test.AfterTest import kotlin.test.BeforeTest import kotlin.test.Test -import kotlin.test.assertEquals -import kotlin.test.assertNotNull import kotlin.test.assertNull class DarajaApiServiceTest { @@ -99,10 +99,7 @@ class DarajaApiServiceTest { val actualResult = darajaApiService.fetchAccessToken() // then - assertEquals( - expected = DarajaResult.Success(darajaToken), - actual = actualResult, - ) + assertThat(actualResult).isEqualTo(DarajaResult.Success(darajaToken)) } @Test @@ -116,8 +113,7 @@ class DarajaApiServiceTest { // then val cachedToken = mockInMemoryCache.get(1) - assertNotNull(cachedToken) - assertEquals(expected = darajaToken, actual = cachedToken) + assertThat(darajaToken).isEqualTo(cachedToken) } @Test @@ -140,8 +136,8 @@ class DarajaApiServiceTest { ) // then - assertEquals(expected = expectedResult, actual = actualResult) - assertNotNull(mockInMemoryCache.get(1)) + assertThat(expectedResult).isEqualTo(actualResult) + assertThat(mockInMemoryCache.get(1)).isEqualTo(darajaToken) } @Test @@ -162,6 +158,6 @@ class DarajaApiServiceTest { ), ) - assertEquals(expected = expectedResult, actual = actualResult) + assertThat(expectedResult).isEqualTo(actualResult) } } diff --git a/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/utils/DarajaResultTest.kt b/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/utils/DarajaResultTest.kt index 38c07801..7d968421 100644 --- a/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/utils/DarajaResultTest.kt +++ b/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/utils/DarajaResultTest.kt @@ -16,10 +16,18 @@ package com.vickbt.darajakmp.utils +import assertk.all +import assertk.assertThat +import assertk.assertions.hasMessage +import assertk.assertions.isEqualTo +import assertk.assertions.isNotNull +import assertk.assertions.isNull +import assertk.assertions.isSameInstanceAs +import assertk.assertions.prop import com.vickbt.darajakmp.network.models.DarajaException +import com.vickbt.darajakmp.utils.DarajaResult.Success +import kotlinx.coroutines.test.runTest import kotlin.test.Test -import kotlin.test.assertEquals -import kotlin.test.assertNotNull import kotlin.test.assertNull class DarajaResultTest { @@ -31,94 +39,110 @@ class DarajaResultTest { ) @Test - fun darajaResult_getOrNull_returns_data_on_success() { - val result = DarajaResult.Success(data = "Success").getOrNull() + fun `darajaResult getOrNull returns data on success`() = + runTest { + val result = Success(data = "Success").getOrNull() - assertNotNull(result) - assertEquals(expected = "Success", actual = result) - } + assertThat(result).isEqualTo("Success") + } @Test - fun darajaResult_getOrNull_returns_null_on_error() { - val result = DarajaResult.Failure(exception = darajaException).getOrNull() + fun `darajaResult getOrNull returns null on error`() = + runTest { + val result = DarajaResult.Failure(exception = darajaException).getOrNull() - assertNull(result) - assertEquals(expected = null, actual = result) - } + assertThat(result).isEqualTo(null) + } @Test - fun darajaResult_throwOnFailure_returns_exception_on_error() { - val result = DarajaResult.Failure(exception = darajaException).throwOnFailure() - - assertNotNull(result) - assertEquals(expected = darajaException, actual = result) - } + fun `darajaResult throwOnFailure returns exception on error`() = + runTest { + val result = DarajaResult.Failure(exception = darajaException).throwOnFailure() + + assertThat(result).all { + hasMessage(darajaException.errorMessage) + isSameInstanceAs(darajaException) + } + } @Test - fun darajaResult_getOrThrow_returns_data_on_success() { - val result = DarajaResult.Success("Success").getOrThrow() + fun `darajaResult getOrThrow returns data on success`() = + runTest { + val result = Success("Success").getOrThrow() - assertNotNull(result) - assertEquals(expected = "Success", actual = result) - } + assertThat(result).isEqualTo("Success") + } @Test - fun darajaResult_onSuccess_returns_data_on_success() { - val result = DarajaResult.Success(data = "Success") - - result.onSuccess { - assertNotNull(it) - assertEquals(expected = it, actual = "Success") + fun `darajaResult onSuccess returns data on success`() = + runTest { + val result = Success(data = "Success") + + result.onSuccess { + assertThat(it).isEqualTo("Success") + }.onFailure { + assertThat(it).all { + prop(DarajaException::errorMessage).isNotNull() + isSameInstanceAs(DarajaException::errorMessage) + } + } } - } @Test - fun darajaResult_onSuccess_returns_null_on_error() { - val result = DarajaResult.Failure(darajaException) - - result.onSuccess { - assertNull(it) + fun `darajaResult onSuccess returns null on error`() = + runTest { + val result = DarajaResult.Failure(darajaException) + + result.onSuccess { + assertNull(it) + }.onFailure { + assertThat(it.errorMessage).isEqualTo("Invalid Authentication passed") + } } - } @Test - fun darajaResult_onFailure_returns_null_on_success() { - val result = DarajaResult.Success(data = "Success") + fun `darajaResult onFailure returns null on success`() = + runTest { + val result = Success(data = "Success") - result.onFailure { - assertNull(it) + result.onFailure { + assertThat(it.errorMessage).isEqualTo("Invalid Authentication passed") + } } - } @Test - fun darajaResult_onFailure_returns_exception_on_error() { - val result = DarajaResult.Failure(darajaException) - - result.onFailure { - assertNotNull(it) - assertEquals(expected = it, actual = darajaException) + fun `darajaResult onFailure returns exception on error`() = + runTest { + val result = DarajaResult.Failure(darajaException) + + result.onFailure { + assertThat(it).all { + prop(DarajaException::errorMessage).isEqualTo("Invalid Authentication passed") + } + } } - } @Test - fun darajaResult_onSuccess_onFailure_on_success() { - val result = DarajaResult.Success(data = "Success") - - result.onSuccess { - assertNotNull(it) - assertEquals(expected = it, actual = "Success") - }.onFailure { - assertNull(it) + fun `darajaResult onSuccess does not trigger onFailure on success`() = + runTest { + val result = Success(data = "Success") + + result.onSuccess { + assertThat(it).isEqualTo("Success") + }.onFailure { + assertThat(it).isNull() + } } - } @Test - fun darajaResult_onSuccess_onFailure_on_error() { - val result = DarajaResult.Failure(darajaException) - - result.onFailure { - assertNotNull(it) - assertEquals(expected = it, actual = darajaException) + fun `darajaResult onSuccess returns onFailure on error`() = + runTest { + val result = DarajaResult.Failure(darajaException) + + result.onFailure { + assertThat(it).all { + prop(DarajaException::errorMessage).isEqualTo("Invalid Authentication passed") + } + } } - } } diff --git a/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/utils/UtilsTest.kt b/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/utils/UtilsTest.kt index 0735ed49..5122dc61 100644 --- a/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/utils/UtilsTest.kt +++ b/daraja/src/commonTest/kotlin/com/vickbt/darajakmp/utils/UtilsTest.kt @@ -16,106 +16,133 @@ package com.vickbt.darajakmp.utils +import assertk.all +import assertk.assertFailure +import assertk.assertThat +import assertk.assertions.isEqualTo import com.vickbt.darajakmp.network.models.DarajaException +import io.ktor.util.decodeBase64String +import io.ktor.util.reflect.instanceOf +import kotlinx.coroutines.test.runTest +import kotlinx.datetime.LocalDateTime import kotlinx.datetime.TimeZone import kotlinx.datetime.toInstant -import kotlinx.datetime.toLocalDateTime import kotlin.test.Test -import kotlin.test.assertEquals -import kotlin.test.assertFailsWith class UtilsTest { @Test - fun getDarajaTimeStamp_returns_correct_timestamp_on_single_digit_values() { - val currentDateTime = - "2022-01-01T01:01:01.694394300".toLocalDateTime() - .toInstant(TimeZone.currentSystemDefault()) - val expectedResult = "20220101010101" + fun `getDarajaTimeStamp returns correct timestamp on single digit values`() = + runTest { + val currentDateTime = + LocalDateTime.parse("2022-01-01T01:01:01.694394300") + .toInstant(TimeZone.currentSystemDefault()) + val expectedResult = "20220101010101" + + assertThat(currentDateTime.getDarajaTimestamp()).isEqualTo(expectedResult) + } - assertEquals(expected = expectedResult, actual = currentDateTime.getDarajaTimestamp()) - } + @Test + fun `getDarajaTimeStamp returns correct timestamp on double digit values`() = + runTest { + val currentDateTime = + LocalDateTime.parse("2022-12-12T12:12:12.694394300") + .toInstant(TimeZone.currentSystemDefault()) + val expectedResult = "20221212121212" + + assertThat(currentDateTime.getDarajaTimestamp()).isEqualTo(expectedResult) + } @Test - fun getDarajaTimeStamp_returns_correct_timestamp_on_double_digit_values() { - val currentDateTime = - "2022-12-12T12:12:12.694394300".toLocalDateTime() - .toInstant(TimeZone.currentSystemDefault()) - val expectedResult = "20221212121212" + fun `getDarajaPassword returns correct password`() = + runTest { + val darajaPassword = getDarajaPassword("abc", "123", "xyz") + val result = "abc" + "123" + "xyz" - assertEquals(expected = expectedResult, actual = currentDateTime.getDarajaTimestamp()) - } + assertThat(darajaPassword.decodeBase64String()).isEqualTo(result) + } @Test - fun phone_number_starting_with_07_is_formatted_correctly() { - val phoneNumber = "0714021306" - val expectedResult = "254714021306" + fun `phone number starting with 07 is formatted correctly`() = + runTest { + val phoneNumber = "0714021306" + val expectedResult = "254714021306" - assertEquals(expected = expectedResult, actual = phoneNumber.getDarajaPhoneNumber()) - } + assertThat(phoneNumber.getDarajaPhoneNumber()).isEqualTo(expectedResult) + } @Test - fun phone_number_starting_with_01_is_formatted_correctly() { - val phoneNumber = "0114624401" - val expectedResult = "254114624401" + fun `phone number starting with 01 is formatted correctly`() = + runTest { + val phoneNumber = "0114624401" + val expectedResult = "254114624401" - assertEquals(expected = expectedResult, actual = phoneNumber.getDarajaPhoneNumber()) - } + assertThat(phoneNumber.getDarajaPhoneNumber()).isEqualTo(expectedResult) + } @Test - fun phone_number_starting_with_254_is_formatted_correctly() { - val phoneNumber = "254714091301" - val expectedResult = "254714091301" + fun `phone number starting with 254 is formatted correctly`() = + runTest { + val phoneNumber = "254714091301" + val expectedResult = "254714091301" - assertEquals(expected = expectedResult, actual = phoneNumber.getDarajaPhoneNumber()) - } + assertThat(phoneNumber.getDarajaPhoneNumber()).isEqualTo(expectedResult) + } @Test - fun phone_number_starting_with_plus_254_is_formatted_correctly() { - val phoneNumber = "+254714091301" - val expectedResult = "254714091301" + fun `phone number starting with plus 254 is formatted correctly`() = + runTest { + val phoneNumber = "+254714091301" + val expectedResult = "254714091301" - assertEquals(expected = expectedResult, actual = phoneNumber.getDarajaPhoneNumber()) - } + assertThat(phoneNumber.getDarajaPhoneNumber()).isEqualTo(expectedResult) + } @Test - fun phone_number_less_than_10_characters_throws_errors() { - val phoneNumbers = listOf("071409130", "+25471409130", "25471409130") + fun `phone number less than 10 characters throws errors`() = + runTest { + val phoneNumbers = listOf("071409130", "+25471409130", "25471409130") - assertFailsWith { - phoneNumbers.forEach { phoneNumber -> phoneNumber.getDarajaPhoneNumber() } + assertFailure { + phoneNumbers.forEach { phoneNumber -> phoneNumber.getDarajaPhoneNumber() } + } } - } @Test - fun phone_number_more_than_10_characters_throws_errors() { - val phoneNumbers = listOf("07140913023", "+2547140913023", "2547140913023") - - assertFailsWith { - phoneNumbers.forEach { phoneNumber -> phoneNumber.getDarajaPhoneNumber() } + fun `phone number more than 10 characters throws errors`() = + runTest { + val phoneNumbers = listOf("07140913023", "+2547140913023", "2547140913023") + + assertFailure { + phoneNumbers.forEach { phoneNumber -> phoneNumber.getDarajaPhoneNumber() } + }.all { + instanceOf(DarajaException::class) + } } - } @Test - fun phone_number_with_spaces_are_formatted_correctly() { - val phoneNumbers = listOf("0 714091 30 3", " + 2 547 140 913 03", "2 5 4714 091 30 3 ") - val expectedPhoneNumbers = listOf("254714091303", "254714091303", "254714091303") + fun `phone number with spaces are formatted correctly`() = + runTest { + val phoneNumbers = listOf("0 714091 30 3", " + 2 547 140 913 03", "2 5 4714 091 30 3 ") + val expectedPhoneNumbers = listOf("254714091303", "254714091303", "254714091303") - assertEquals(expectedPhoneNumbers, phoneNumbers.map { it.getDarajaPhoneNumber() }) - } + assertThat(phoneNumbers.map { it.getDarajaPhoneNumber() }).isEqualTo(expectedPhoneNumbers) + } @Test - fun time_units_with_value_less_than_ten_are_formatted_correctly() { - val timeUnit = 1 - val expectedTimeUnit = "01" + fun `time units with value less than ten are formatted correctly`() = + runTest { + val timeUnit = 1 + val expectedTimeUnit = "01" - assertEquals(expected = expectedTimeUnit, actual = timeUnit.asFormattedWithZero()) - } + assertThat(timeUnit.asFormattedWithZero()).isEqualTo(expectedTimeUnit) + } @Test - fun time_units_with_value_more_than_ten_retain_their_formatting() { - val timeUnit = 11 - val expectedTimeUnit = 11 + fun `time units with value more than ten retain their formatting`() = + runTest { + val timeUnit = 11 + val expectedTimeUnit = 11 - assertEquals(expected = expectedTimeUnit, actual = timeUnit.asFormattedWithZero()) - } + assertThat(timeUnit.asFormattedWithZero()).isEqualTo(expectedTimeUnit) + } } diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index d5797097..dfa1a965 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -18,6 +18,7 @@ ktor = "2.3.12" composeMultiplatform = "1.6.11" cache4k = "0.13.0" mockative = "2.2.2" +assertK = "0.28.1" [plugins] ktLint = { id = "org.jlleitschuh.gradle.ktlint", version.ref = "ktLint" } @@ -57,4 +58,5 @@ cache4k = { module = "io.github.reactivecircus.cache4k:cache4k", version.ref = " #Tests Lib Dependencies kotlinX-coroutines-test = { module = "org.jetbrains.kotlinx:kotlinx-coroutines-test", version.ref = "kotlinxCoroutines" } -mockative = { module = "io.mockative:mockative", version.ref = "mockative" } \ No newline at end of file +mockative = { module = "io.mockative:mockative", version.ref = "mockative" } +assertK = { module = "com.willowtreeapps.assertk:assertk", version.ref = "assertK" } \ No newline at end of file