package be.simplenotes.persistance.users import be.simplenotes.domain.model.User import be.simplenotes.domain.usecases.repositories.UserRepository import be.simplenotes.persistance.DbMigrations import be.simplenotes.persistance.persistanceModule import be.simplenotes.shared.config.DataSourceConfig import me.liuwj.ktorm.database.* import me.liuwj.ktorm.dsl.* import me.liuwj.ktorm.entity.* import org.assertj.core.api.Assertions.assertThat import org.flywaydb.core.Flyway import org.junit.jupiter.api.AfterAll import org.junit.jupiter.api.BeforeEach import org.junit.jupiter.api.Nested import org.junit.jupiter.api.Test import org.junit.jupiter.api.parallel.ResourceLock import org.koin.dsl.koinApplication import org.koin.dsl.module import javax.sql.DataSource @ResourceLock("h2") internal class UserRepositoryImplTest { // region setup private val testModule = module { single { dataSourceConfig() } } private val koinApp = koinApplication { modules(persistanceModule, testModule) } private fun dataSourceConfig() = DataSourceConfig( jdbcUrl = "jdbc:h2:mem:regular;DB_CLOSE_DELAY=-1;", driverClassName = "org.h2.Driver", username = "h2", password = "", maximumPoolSize = 2, connectionTimeout = 3000 ) private val koin = koinApp.koin @AfterAll fun afterAll() = koinApp.close() private val migration = koin.get() private val dataSource = koin.get() private val userRepo = koin.get() private val db = koin.get() @BeforeEach fun beforeEach() { Flyway.configure() .dataSource(dataSource) .load() .clean() migration.migrate() } // endregion setup @Test fun `insert user`() { val user = User("username", "test") assertThat(userRepo.create(user)) .isNotNull .hasFieldOrPropertyWithValue("username", user.username) .hasFieldOrPropertyWithValue("password", user.password) assertThat(db.users.find { it.username eq user.username }).isNotNull assertThat(db.users.toList()).hasSize(1) assertThat(userRepo.create(user)).isNull() } @Nested inner class Query { @Test fun `query existing user`() { val user = User("username", "test") userRepo.create(user) val foundUserMaybe = userRepo.find(user.username) assertThat(foundUserMaybe).isNotNull val foundUser = foundUserMaybe!! assertThat(foundUser).isEqualToIgnoringGivenFields(user, "id") assertThat(userRepo.exists(user.username)).isTrue assertThat(userRepo.find(foundUser.id)).isEqualTo(foundUser) assertThat(userRepo.exists(foundUser.id)).isTrue } @Test fun `query non existing user`() { assertThat(userRepo.find("I don't exist")).isNull() assertThat(userRepo.find(1)).isNull() assertThat(userRepo.exists(1)).isFalse assertThat(userRepo.exists("I don't exist")).isFalse } } @Nested inner class Delete { @Test fun `delete existing user`() { val user = User("username", "test") userRepo.create(user) val foundUser = userRepo.find(user.username)!! assertThat(userRepo.delete(foundUser.id)).isTrue assertThat(db.users.toList()).isEmpty() } @Test fun `delete non existing user`() { assertThat(userRepo.delete(1)).isFalse } } }