[Spring Boot] Kotest + Mockk
Spring BootKotest
Open source testing framework to test and validate kotlin code
It provides 10 test layouts to test various situations. (Link)
Mockk
Kotlin Mocking Framework
Write a test code based on Domain Specific Language (DSL).
- Mocking: A simulated object. A test object that virtually replaces an external service or module.
Example
Tested services using Behavior Driven Development (BDD) method, BehaviorSpec
build.gradle.kts
kotlin
testImplementation("io.kotest:kotest-runner-junit5:5.5.5")
testImplementation("io.kotest:kotest-assertions-core:5.5.5")
testImplementation("io.mockk:mockk:1.13.4")
Intellij Plugin Install
- Settings → Plugins → Search 'Kotest' → Install
service (src>main>kotlin>package-path>service>UserServiceImpl)
kotlin
@Service
class UserServiceImpl(
private val userRepository: UserRepository
) : UserService {
override fun login(email: String, password: String): String {
// Account Inquiry
val user = userRepository.findByEmail(email) ?: throw RuntimeException("email? $email")
// Confirm password
if (user.password != password) throw PasswordFailException()
return getSession(email)
}
override fun getSession(email: String): String {
return "session-key"
}
}
test (src>test>kotlin>package-path>service>UserServiceTest)
kotlin
internal class UserServiceTest : BehaviorSpec({
// UserService dependency object declaration
val userRepository = mockk<UserRepository>()
// Test Data Declaration
var email: String
var password: String
Given("Test Login") {
email = "test@gmail.com"
password = "test-password"
// Inject dependency objects into UserService
val service = withContext(Dispatchers.IO) {
UserServiceImpl(userRepository)
}
When("If you enter a valid account") {
// Set account lookup result value arbitrarily
every { userRepository.findByEmail(any()) } returns user
Then("Login Successful") {
val result = service.login(email = email, password = password)
// Verification of the result value
result shouldNotBe null
result shouldBe "session-key"
}
}
When("If you enter an invalid account") {
And("If you enter an email that does not exist") {
every { userRepository.findByEmail(any()) } returns null
Then("An exception occurs") {
val result = shouldThrow<RuntimeException> {
service.login(email = email, password = password)
}
result.message shouldBe "email? $email"
}
}
And("If you enter the wrong password") {
password = "test-password-1"
every { userRepository.findByEmail(any()) } returns user
Then("An exception occurs") {
shouldThrow<PasswordFailException> {
service.login(email = email, password = password)
}
}
}
}
}
}) {
companion object {
val user = User(
id = 1L,
email = "test@gmail.com",
password = "test-password"
)
}
}
Run the test
Press the green arrow on the left with the Kotest Plugin to run the test in each step.
If it runs normally from Given, the following results will be obtained.