From e73f725850b6f1b34553dafb6f4ac3845cb7ff72 Mon Sep 17 00:00:00 2001 From: Eva Tatarka Date: Tue, 28 Nov 2023 23:04:54 -0800 Subject: [PATCH 1/2] Add assume function to abort tests instead of failing them jvm only, uses open4j's TestAbortedException under the hood so works on junit5 or other compatible testing framework (does not work on junit4) Fixes #432 --- CHANGELOG.md | 8 ++++++ assertk/build.gradle.kts | 4 +++ assertk/src/jvmMain/kotlin/assertk/assume.kt | 15 ++++++++++ assertk/src/jvmMain/kotlin/assertk/failure.kt | 21 ++++++++++++++ .../kotlin/test/assertk/JVMAssertAllTest.kt | 2 +- .../test/assertk/assertions/AssumeTest.kt | 28 +++++++++++++++++++ .../test/assertk/assertions/JVMResultTest.kt | 2 +- .../test/assertk/assertions/OptionalTest.kt | 2 +- .../assertions/support/JavaNumberTest.kt | 2 +- 9 files changed, 80 insertions(+), 4 deletions(-) create mode 100644 assertk/src/jvmMain/kotlin/assertk/assume.kt create mode 100644 assertk/src/jvmTest/kotlin/test/assertk/assertions/AssumeTest.kt diff --git a/CHANGELOG.md b/CHANGELOG.md index 132b71c4..68c91993 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -23,6 +23,14 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0. ### Added - Added `doesNotContainKey` assertion for `Map` +- Added `assume` to support test assumptions. To use, wrap your assertions + ```kotlin + assume { + assertThat(System.getProperty("os.name")).startsWith("Windows") + } + ``` + this will cause the test to be skipped instead of failing. + Note: This feature only works with opentest4j-compatible testing frameworks like junit5. ### Fixed - Fixed incorrect usage of contains in some kdoc examples diff --git a/assertk/build.gradle.kts b/assertk/build.gradle.kts index c3ae5f6e..ea0eb906 100644 --- a/assertk/build.gradle.kts +++ b/assertk/build.gradle.kts @@ -64,3 +64,7 @@ kotlin { } } } + +tasks.withType().configureEach { + useJUnitPlatform() +} \ No newline at end of file diff --git a/assertk/src/jvmMain/kotlin/assertk/assume.kt b/assertk/src/jvmMain/kotlin/assertk/assume.kt new file mode 100644 index 00000000..6f2ef94b --- /dev/null +++ b/assertk/src/jvmMain/kotlin/assertk/assume.kt @@ -0,0 +1,15 @@ +package assertk + +/** + * Aborts the test instead of failing it, this gives you a way to skip tests based on a dynamic assertion. + * + * ``` + * // only run test on windows + * assume { + * assertThat(System.getProperty("os.name")).startsWith("Windows") + * } + * ``` + */ +fun assume(f: () -> Unit) { + AssumptionFailure.run { f() } +} \ No newline at end of file diff --git a/assertk/src/jvmMain/kotlin/assertk/failure.kt b/assertk/src/jvmMain/kotlin/assertk/failure.kt index a782578f..a55b42ab 100644 --- a/assertk/src/jvmMain/kotlin/assertk/failure.kt +++ b/assertk/src/jvmMain/kotlin/assertk/failure.kt @@ -3,6 +3,9 @@ package assertk +import com.willowtreeapps.opentest4k.AssertionFailedError +import com.willowtreeapps.opentest4k.TestAbortedException + internal actual inline fun failWithNotInStacktrace(error: Throwable): Nothing { val filtered = error.stackTrace .dropWhile { it.className.startsWith("assertk") } @@ -16,3 +19,21 @@ internal actual inline fun failWithNotInStacktrace(error: Throwable): Nothing { internal actual inline fun Throwable.isFatal(): Boolean = // https://github.com/ReactiveX/RxJava/blob/6a44e5d0543a48f1c378dc833a155f3f71333bc2/src/main/java/io/reactivex/exceptions/Exceptions.java#L66 this is VirtualMachineError || this is ThreadDeath || this is LinkageError + +internal object AssumptionFailure : Failure { + override fun fail(error: Throwable) { + failWithNotInStacktrace( + TestAbortedException( + buildString { + append("Assumption failed") + error.message?.let { message -> + append(": ") + append(message) + } + }, + // unwrap assertion errors + if (error is AssertionFailedError) error.cause else error + ) + ) + } +} \ No newline at end of file diff --git a/assertk/src/jvmTest/kotlin/test/assertk/JVMAssertAllTest.kt b/assertk/src/jvmTest/kotlin/test/assertk/JVMAssertAllTest.kt index fabfb159..5327bbe5 100644 --- a/assertk/src/jvmTest/kotlin/test/assertk/JVMAssertAllTest.kt +++ b/assertk/src/jvmTest/kotlin/test/assertk/JVMAssertAllTest.kt @@ -4,9 +4,9 @@ import assertk.all import assertk.assertAll import assertk.assertThat import assertk.assertions.* -import org.junit.Test import java.util.concurrent.Executors import java.util.concurrent.TimeUnit +import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertFailsWith import kotlin.test.assertFalse diff --git a/assertk/src/jvmTest/kotlin/test/assertk/assertions/AssumeTest.kt b/assertk/src/jvmTest/kotlin/test/assertk/assertions/AssumeTest.kt new file mode 100644 index 00000000..4468c5cd --- /dev/null +++ b/assertk/src/jvmTest/kotlin/test/assertk/assertions/AssumeTest.kt @@ -0,0 +1,28 @@ +package test.assertk.assertions + +import assertk.assertThat +import assertk.assertions.isFalse +import assertk.assume +import com.willowtreeapps.opentest4k.TestAbortedException +import kotlin.test.Test +import kotlin.test.assertEquals +import kotlin.test.assertFailsWith + +class AssumeTest { + @Test + fun assume_throws_TestAbortedException() { + val error = assertFailsWith { + assume { + assertThat(true).isFalse() + } + } + + assertEquals("Assumption failed: expected to be false", error.message) + } + + @Test + fun assume_aborts_instead_of_fails_test() { + // this test should be skipped instead of failing + assume { assertThat(true).isFalse() } + } +} \ No newline at end of file diff --git a/assertk/src/jvmTest/kotlin/test/assertk/assertions/JVMResultTest.kt b/assertk/src/jvmTest/kotlin/test/assertk/assertions/JVMResultTest.kt index 06ccbb1d..90df55a6 100644 --- a/assertk/src/jvmTest/kotlin/test/assertk/assertions/JVMResultTest.kt +++ b/assertk/src/jvmTest/kotlin/test/assertk/assertions/JVMResultTest.kt @@ -2,8 +2,8 @@ package test.assertk.assertions import assertk.assertThat import assertk.assertions.isSuccess -import org.junit.Test import test.assertk.exceptionPackageName +import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertFailsWith import kotlin.test.assertNotNull diff --git a/assertk/src/jvmTest/kotlin/test/assertk/assertions/OptionalTest.kt b/assertk/src/jvmTest/kotlin/test/assertk/assertions/OptionalTest.kt index 0596a1a3..f1d40acd 100644 --- a/assertk/src/jvmTest/kotlin/test/assertk/assertions/OptionalTest.kt +++ b/assertk/src/jvmTest/kotlin/test/assertk/assertions/OptionalTest.kt @@ -4,10 +4,10 @@ import assertk.all import assertk.assertAll import assertk.assertThat import assertk.assertions.* -import org.junit.Test import java.time.LocalDate import java.time.Month import java.util.* +import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertFailsWith diff --git a/assertk/src/jvmTest/kotlin/test/assertk/assertions/support/JavaNumberTest.kt b/assertk/src/jvmTest/kotlin/test/assertk/assertions/support/JavaNumberTest.kt index 20e95af2..a2d9a9dc 100644 --- a/assertk/src/jvmTest/kotlin/test/assertk/assertions/support/JavaNumberTest.kt +++ b/assertk/src/jvmTest/kotlin/test/assertk/assertions/support/JavaNumberTest.kt @@ -4,9 +4,9 @@ import assertk.assertThat import assertk.assertions.isNegative import assertk.assertions.isPositive import assertk.assertions.isZero -import org.junit.Test import java.math.BigDecimal import java.math.BigInteger +import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertFailsWith From 270449dbf4cd2167fe08e766aab68501c9ad7a85 Mon Sep 17 00:00:00 2001 From: Eva Tatarka Date: Tue, 5 Dec 2023 13:12:22 -0800 Subject: [PATCH 2/2] make assume inline, add additional tests --- assertk/src/jvmMain/kotlin/assertk/assume.kt | 2 +- .../kotlin/test/assertk/assertions/AssumeTest.kt | 15 +++++++++++++++ 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/assertk/src/jvmMain/kotlin/assertk/assume.kt b/assertk/src/jvmMain/kotlin/assertk/assume.kt index 6f2ef94b..9cfd52cb 100644 --- a/assertk/src/jvmMain/kotlin/assertk/assume.kt +++ b/assertk/src/jvmMain/kotlin/assertk/assume.kt @@ -10,6 +10,6 @@ package assertk * } * ``` */ -fun assume(f: () -> Unit) { +inline fun assume(f: () -> Unit) { AssumptionFailure.run { f() } } \ No newline at end of file diff --git a/assertk/src/jvmTest/kotlin/test/assertk/assertions/AssumeTest.kt b/assertk/src/jvmTest/kotlin/test/assertk/assertions/AssumeTest.kt index 4468c5cd..2acf64c7 100644 --- a/assertk/src/jvmTest/kotlin/test/assertk/assertions/AssumeTest.kt +++ b/assertk/src/jvmTest/kotlin/test/assertk/assertions/AssumeTest.kt @@ -1,9 +1,12 @@ package test.assertk.assertions import assertk.assertThat +import assertk.assertions.isEqualTo import assertk.assertions.isFalse +import assertk.assertions.isTrue import assertk.assume import com.willowtreeapps.opentest4k.TestAbortedException +import test.assertk.runTest import kotlin.test.Test import kotlin.test.assertEquals import kotlin.test.assertFailsWith @@ -25,4 +28,16 @@ class AssumeTest { // this test should be skipped instead of failing assume { assertThat(true).isFalse() } } + + @Test + fun assume_does_not_capture_unexpected_exceptions() { + assertFailsWith { + assume { throw NullPointerException() } + } + } + + @Test + fun assume_aborts_when_suspend() = runTest { + assume { assertThat(suspend { true }()).isFalse() } + } } \ No newline at end of file