unit-tests: Add gtest-like output
This commit is contained in:
@@ -8,15 +8,15 @@ class SimpleTestListener: TestListener {
|
||||
private set
|
||||
|
||||
override fun startTesting(runner: TestRunner) = println("Starting testing")
|
||||
override fun endTesting(runner: TestRunner) = println("Testing finished")
|
||||
override fun endTesting(runner: TestRunner, timeMillis: Long) = println("Testing finished")
|
||||
|
||||
override fun startSuite(suite: TestSuite) = println("Starting test suite: $suite")
|
||||
override fun endSuite(suite: TestSuite) = println("Test suite finished: $suite")
|
||||
override fun endSuite(suite: TestSuite, timeMillis: Long) = println("Test suite finished: $suite")
|
||||
override fun ignoreSuite(suite: TestSuite) = println("Test suite ignored: $suite")
|
||||
|
||||
override fun start(testCase: TestCase) = println("Starting test case: $testCase")
|
||||
override fun pass(testCase: TestCase) = println("Passed: $testCase")
|
||||
override fun fail(testCase: TestCase, e: Throwable) {
|
||||
override fun pass(testCase: TestCase, timeMillis: Long) = println("Passed: $testCase")
|
||||
override fun fail(testCase: TestCase, e: Throwable, timeMillis: Long) {
|
||||
println("Failed: $testCase. Exception:")
|
||||
e.printStackTrace()
|
||||
hasFails = true
|
||||
@@ -25,7 +25,7 @@ class SimpleTestListener: TestListener {
|
||||
}
|
||||
|
||||
fun main(args:Array<String>) {
|
||||
val listener = SimpleTestListener()
|
||||
val listener = GTestListener()
|
||||
TestRunner.run(listener)
|
||||
exitProcess( if (listener.hasFails) -1 else 0 )
|
||||
exitProcess( if (listener.hasFailedTests) -1 else 0 )
|
||||
}
|
||||
|
||||
@@ -0,0 +1,67 @@
|
||||
package konan.test
|
||||
|
||||
val TestRunner.totalTests
|
||||
get() = suites.map { it.size }.reduce { sum, size -> sum + size }
|
||||
|
||||
val TestRunner.totalSuites
|
||||
get() = suites.size
|
||||
|
||||
class GTestListener: TestListener, AbstractTestStatistics() {
|
||||
|
||||
private val TestCase.prettyName get() = "${suite.name}.$name"
|
||||
private val failedTests_ = mutableListOf<TestCase>()
|
||||
|
||||
private var totalSuites = 0
|
||||
|
||||
override fun startTesting(runner: TestRunner) {
|
||||
println("[==========] Running ${runner.totalTests} tests from ${runner.totalSuites} test case.")
|
||||
println("[----------] Global test environment set-up.") // TODO: just emulation
|
||||
}
|
||||
|
||||
private fun printResults(timeMillis: Long) {
|
||||
println("[----------] Global test environment tear-down")
|
||||
println("[==========] $total tests from $totalSuites test cases ran. ($timeMillis ms total)")
|
||||
println("[ PASSED ] $passed tests.")
|
||||
if (hasFailedTests) {
|
||||
println("[ FAILED ] $failed tests, listed below:")
|
||||
failedTests.forEach {
|
||||
println("[ FAILED ] ${it.prettyName}")
|
||||
}
|
||||
println("\n$failed FAILED TESTS")
|
||||
}
|
||||
if (ignored != 0) {
|
||||
println("YOU HAVE $ignored DISABLED TEST(S)")
|
||||
}
|
||||
}
|
||||
|
||||
override fun endTesting(runner: TestRunner, timeMillis: Long) = printResults(timeMillis)
|
||||
|
||||
override fun startSuite(suite: TestSuite) = println("[----------] ${suite.size} tests from ${suite.name}")
|
||||
override fun endSuite(suite: TestSuite, timeMillis: Long) {
|
||||
totalSuites++
|
||||
println("[----------] ${suite.size} tests from ${suite.name} ($timeMillis ms total)\n")
|
||||
}
|
||||
|
||||
override fun ignoreSuite(suite: TestSuite) {}
|
||||
|
||||
override fun start(testCase: TestCase) = println("[ RUN ] ${testCase.prettyName}")
|
||||
|
||||
override fun pass(testCase: TestCase, timeMillis: Long) {
|
||||
registerPass()
|
||||
println("[ OK ] ${testCase.prettyName} ($timeMillis ms)")
|
||||
}
|
||||
|
||||
override fun fail(testCase: TestCase, e: Throwable, timeMillis: Long) {
|
||||
registerFail()
|
||||
failedTests_.add(testCase)
|
||||
e.printStackTrace()
|
||||
println("[ FAILED ] ${testCase.prettyName} ($timeMillis ms)")
|
||||
}
|
||||
|
||||
override fun ignore(testCase: TestCase) = registerIgnore()
|
||||
|
||||
override val failedTests: Collection<TestCase>
|
||||
get() = failedTests_
|
||||
override val hasFailedTests: Boolean
|
||||
get() = failed != 0
|
||||
}
|
||||
@@ -1,17 +1,37 @@
|
||||
package konan.test
|
||||
|
||||
import kotlin.AssertionError
|
||||
|
||||
interface TestListener {
|
||||
fun startTesting(runner: TestRunner)
|
||||
fun endTesting(runner: TestRunner)
|
||||
fun endTesting(runner: TestRunner, timeMillis: Long)
|
||||
|
||||
fun startSuite(suite: TestSuite)
|
||||
fun endSuite(suite: TestSuite)
|
||||
fun endSuite(suite: TestSuite, timeMillis: Long)
|
||||
fun ignoreSuite(suite: TestSuite)
|
||||
|
||||
fun start(testCase: TestCase)
|
||||
fun pass(testCase: TestCase)
|
||||
fun fail(testCase: TestCase, e: Throwable)
|
||||
fun pass(testCase: TestCase, timeMillis: Long)
|
||||
fun fail(testCase: TestCase, e: Throwable, timeMillis: Long)
|
||||
fun ignore(testCase: TestCase)
|
||||
}
|
||||
|
||||
interface TestStatistics {
|
||||
val total: Int
|
||||
val passed: Int
|
||||
val failed: Int
|
||||
val ignored: Int
|
||||
|
||||
// TODO: Do we need such properties for other cases?
|
||||
val failedTests: Collection<TestCase>
|
||||
val hasFailedTests: Boolean
|
||||
}
|
||||
|
||||
abstract class AbstractTestStatistics: TestStatistics {
|
||||
override var total: Int = 0; protected set
|
||||
override var passed: Int = 0; protected set
|
||||
override var failed: Int = 0; protected set
|
||||
override var ignored: Int = 0; protected set
|
||||
|
||||
protected fun registerPass() { total++; passed++ }
|
||||
protected fun registerFail() { total++; failed++ }
|
||||
protected fun registerIgnore() { total++; ignored++ }
|
||||
}
|
||||
@@ -1,5 +1,7 @@
|
||||
package konan.test
|
||||
|
||||
import kotlin.system.measureTimeMillis
|
||||
|
||||
object TestRunner {
|
||||
|
||||
private val _suites = mutableListOf<TestSuite>()
|
||||
@@ -11,15 +13,17 @@ object TestRunner {
|
||||
|
||||
fun run(listener: TestListener) = with(listener) {
|
||||
startTesting(this@TestRunner)
|
||||
suites.forEach {
|
||||
if (it.ignored) {
|
||||
ignoreSuite(it)
|
||||
} else {
|
||||
startSuite(it)
|
||||
it.run(listener)
|
||||
endSuite(it)
|
||||
val totalTime = measureTimeMillis {
|
||||
suites.forEach {
|
||||
if (it.ignored) {
|
||||
ignoreSuite(it)
|
||||
} else {
|
||||
startSuite(it)
|
||||
val time = measureTimeMillis { it.run(listener) }
|
||||
endSuite(it, time)
|
||||
}
|
||||
}
|
||||
}
|
||||
endTesting(this@TestRunner)
|
||||
endTesting(this@TestRunner, totalTime)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
package konan.test
|
||||
|
||||
import kotlin.IllegalArgumentException
|
||||
import kotlin.system.getTimeMillis
|
||||
import kotlin.system.measureTimeMillis
|
||||
|
||||
interface TestCase {
|
||||
val name: String
|
||||
@@ -12,6 +14,7 @@ interface TestSuite {
|
||||
val name: String
|
||||
val ignored: Boolean
|
||||
val testCases: Map<String, TestCase>
|
||||
val size : Int
|
||||
fun run(listener: TestListener)
|
||||
}
|
||||
|
||||
@@ -57,21 +60,24 @@ abstract class AbstractTestSuite<F: Function<Unit>>(override val name: String, o
|
||||
TestRunner.register(this)
|
||||
}
|
||||
|
||||
override val size: Int
|
||||
get() = testCases.size
|
||||
|
||||
override fun run(listener: TestListener) {
|
||||
doBeforeClass()
|
||||
testCases.values.forEach {
|
||||
if (it.ignored) {
|
||||
listener.ignore(it)
|
||||
} else {
|
||||
val startTime = getTimeMillis()
|
||||
try {
|
||||
listener.start(it)
|
||||
doTest(it)
|
||||
listener.pass(it)
|
||||
listener.pass(it, getTimeMillis() - startTime)
|
||||
} catch (e: Throwable) {
|
||||
listener.fail(it, e)
|
||||
listener.fail(it, e, getTimeMillis() - startTime)
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
doAfterClass()
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user