Skip to content

Instantly share code, notes, and snippets.

@tim-hm
Created September 14, 2021 14:16
Show Gist options
  • Save tim-hm/c703716126f998f8247514f9c8503c6a to your computer and use it in GitHub Desktop.
Save tim-hm/c703716126f998f8247514f9c8503c6a to your computer and use it in GitHub Desktop.
package glimpse.commons.testing.kotest
import glimpse.commons.kernel.app.App
import glimpse.commons.kernel.json.jackson.glimpseObjectMapper
import glimpse.commons.kernel.runtime.Gcr
import glimpse.commons.testing.infra.buildKafkaContainer
import glimpse.commons.testing.infra.buildMongoContainer
import glimpse.commons.testing.util.delayUntil
import io.kotest.core.spec.DslDrivenSpec
import io.kotest.core.spec.resolvedDefaultConfig
import io.kotest.core.spec.style.scopes.FreeSpecRootContext
import io.kotest.core.spec.style.scopes.RootTestRegistration
import io.kotest.core.test.TestCaseConfig
import io.ktor.client.HttpClient
import io.ktor.client.engine.cio.CIO
import io.ktor.client.features.json.JacksonSerializer
import io.ktor.client.features.json.JsonFeature
import io.ktor.client.features.logging.DEFAULT
import io.ktor.client.features.logging.LogLevel
import io.ktor.client.features.logging.Logger
import io.ktor.client.features.logging.Logging
import mu.KotlinLogging
import org.testcontainers.containers.output.Slf4jLogConsumer
private val mongoLogger = KotlinLogging.logger("glimpse.it.mongo")
private val kafkaLogger = KotlinLogging.logger("glimpse.it.kafka")
private val mongoLogConsumer = Slf4jLogConsumer(mongoLogger).withSeparateOutputStreams()
private val kafkaLogConsumer = Slf4jLogConsumer(kafkaLogger).withSeparateOutputStreams()
abstract class IntegrationSpec(
app: App,
body: IntegrationSpec.() -> Unit = {},
) : DslDrivenSpec(), FreeSpecRootContext {
override fun defaultConfig(): TestCaseConfig = resolvedDefaultConfig()
override fun registration(): RootTestRegistration = RootTestRegistration.from(this)
// override fun isolationMode() = IsolationMode.InstancePerTest
val client = HttpClient(CIO) {
developmentMode = true
expectSuccess = false
install(JsonFeature) {
serializer = JacksonSerializer(glimpseObjectMapper())
}
install(Logging) {
logger = Logger.DEFAULT
level = LogLevel.INFO
}
}
var before: IntegrationSpec.() -> Unit = {}
fun before(block: IntegrationSpec.() -> Unit) {
before = block
}
var after: IntegrationSpec.() -> Unit = {}
fun after(block: IntegrationSpec.() -> Unit) {
after = block
}
init {
tags(Tag.Integration)
val kafka = buildKafkaContainer()
val mongo = buildMongoContainer()
beforeSpec {
kafka.start()
mongo.start()
if (Gcr.Env.IntegrationTestContainerLogging) {
kafka.followOutput(kafkaLogConsumer)
mongo.followOutput(mongoLogConsumer)
}
delayUntil {
kafka.isRunning && mongo.isRunning
}
before()
Gcr.Env.print()
app.start()
}
afterSpec {
app.stop()
after()
client.close()
mongo.stop()
kafka.stop()
}
body()
}
}
package glimpse.ads.advertiser.integration
import glimpse.ads.advertiser.app
import glimpse.ads.advertiser.helpers.AccountTester
import glimpse.ads.advertiser.helpers.CompanyTester
import glimpse.commons.testing.fp.shouldBeRight
import glimpse.commons.testing.kotest.IntegrationSpec
import io.kotest.assertions.arrow.either.shouldBeLeft
import io.kotest.matchers.booleans.shouldBeTrue
import io.kotest.matchers.shouldBe
class LogoutIntegrationTest : IntegrationSpec(app(), {
lateinit var tester: AccountTester
before {
tester = AccountTester
.Builder()
.init()
}
"register" {
tester
.register()
.shouldBeRight {
val expected = tester.registrationInput!!
it.email.shouldBe(expected.email)
}
}
"logout" {
tester
.logout()
.shouldBeTrue()
}
"create company should fail" {
val companyTester = CompanyTester
.Builder()
.init()
companyTester
.createCompany()
.shouldBeLeft()
}
})
package glimpse.ads.advertiser.integration
import glimpse.ads.advertiser.app
import glimpse.ads.advertiser.helpers.AccountTester
import glimpse.commons.testing.fp.shouldBeRight
import glimpse.commons.testing.kotest.IntegrationSpec
import io.kotest.matchers.shouldBe
class RegisterIntegrationTest : IntegrationSpec(app(), {
lateinit var tester: AccountTester
before {
tester = AccountTester
.Builder()
.init()
}
"register" {
tester
.register()
.shouldBeRight {
val expected = tester.registrationInput!!
it.email.shouldBe(expected.email)
}
}
"login" {
tester
.login()
.shouldBeRight {
val expected = tester.loginInput!!
it.email.shouldBe(expected.email)
}
}
})
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment