From ef7a6f6bbb20d12da947e88fa052151a7f4e9de7 Mon Sep 17 00:00:00 2001 From: usbharu <64310155+usbharu@users.noreply.github.com> Date: Wed, 26 Apr 2023 17:28:59 +0900 Subject: [PATCH] =?UTF-8?q?refactor:=20UserAuth=E9=96=A2=E9=80=A3=E3=82=92?= =?UTF-8?q?=E5=89=8A=E9=99=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../kotlin/dev/usbharu/hideout/Application.kt | 3 +- .../domain/model/UserAuthentication.kt | 17 +---- .../usbharu/hideout/plugins/ActivityPub.kt | 14 ++--- .../hideout/repository/IUserAuthRepository.kt | 15 ----- .../hideout/repository/UserAuthRepository.kt | 63 ------------------- .../hideout/service/IUserAuthService.kt | 7 --- .../activitypub/ActivityPubUserServiceImpl.kt | 23 ++----- .../hideout/service/impl/UserAuthService.kt | 35 ++--------- .../HttpSignatureVerifyServiceImpl.kt | 3 +- .../hideout/plugins/ActivityPubKtTest.kt | 38 +---------- .../usbharu/hideout/plugins/KtorKeyMapTest.kt | 38 +---------- 11 files changed, 25 insertions(+), 231 deletions(-) delete mode 100644 src/main/kotlin/dev/usbharu/hideout/repository/IUserAuthRepository.kt delete mode 100644 src/main/kotlin/dev/usbharu/hideout/repository/UserAuthRepository.kt diff --git a/src/main/kotlin/dev/usbharu/hideout/Application.kt b/src/main/kotlin/dev/usbharu/hideout/Application.kt index e4bca1fe..149a839e 100644 --- a/src/main/kotlin/dev/usbharu/hideout/Application.kt +++ b/src/main/kotlin/dev/usbharu/hideout/Application.kt @@ -58,8 +58,7 @@ fun Application.parent() { } single { UserRepository(get()) } - single { UserAuthRepository(get()) } - single { UserAuthService(get(), get()) } + single { UserAuthService(get()) } single { HttpSignatureVerifyServiceImpl(get()) } single { val kJobJobQueueService = KJobJobQueueParentService(get()) diff --git a/src/main/kotlin/dev/usbharu/hideout/domain/model/UserAuthentication.kt b/src/main/kotlin/dev/usbharu/hideout/domain/model/UserAuthentication.kt index 5754021a..9dbd767f 100644 --- a/src/main/kotlin/dev/usbharu/hideout/domain/model/UserAuthentication.kt +++ b/src/main/kotlin/dev/usbharu/hideout/domain/model/UserAuthentication.kt @@ -11,22 +11,7 @@ data class UserAuthentication( val publicKey: String, val privateKey: String? ) -@Deprecated("") -data class UserAuthenticationEntity( - val id: Long, - val userId: Long, - val hash: String?, - val publicKey: String, - val privateKey: String? -) { - constructor(id: Long, userAuthentication: UserAuthentication) : this( - id, - userAuthentication.userId, - userAuthentication.hash, - userAuthentication.publicKey, - userAuthentication.privateKey - ) -} + @Deprecated("") object UsersAuthentication : LongIdTable("users_auth") { val userId = long("user_id").references(Users.id, onUpdate = ReferenceOption.CASCADE) diff --git a/src/main/kotlin/dev/usbharu/hideout/plugins/ActivityPub.kt b/src/main/kotlin/dev/usbharu/hideout/plugins/ActivityPub.kt index db0e6a1f..50d4faaa 100644 --- a/src/main/kotlin/dev/usbharu/hideout/plugins/ActivityPub.kt +++ b/src/main/kotlin/dev/usbharu/hideout/plugins/ActivityPub.kt @@ -1,8 +1,8 @@ package dev.usbharu.hideout.plugins -import dev.usbharu.hideout.domain.model.ap.JsonLd import dev.usbharu.hideout.config.Config -import dev.usbharu.hideout.service.IUserAuthService +import dev.usbharu.hideout.domain.model.ap.JsonLd +import dev.usbharu.hideout.repository.IUserRepository import dev.usbharu.hideout.service.impl.UserAuthService import dev.usbharu.hideout.util.HttpUtil.Activity import io.ktor.client.* @@ -144,14 +144,14 @@ val httpSignaturePlugin = createClientPlugin("HttpSign", ::HttpSignaturePluginCo } } -class KtorKeyMap(private val userAuthRepository: IUserAuthService) : KeyMap { +class KtorKeyMap(private val userAuthRepository: IUserRepository) : KeyMap { override fun getPublicKey(keyId: String?): PublicKey = runBlocking { val username = (keyId ?: throw IllegalArgumentException("keyId is null")).substringBeforeLast("#pubkey") .substringAfterLast("/") val publicBytes = Base64.getDecoder().decode( - userAuthRepository.findByUsername( + userAuthRepository.findByName( username - ).publicKey?.replace("-----BEGIN PUBLIC KEY-----", "-----END PUBLIC KEY-----")?.replace("", "") + )?.publicKey?.replace("-----BEGIN PUBLIC KEY-----", "-----END PUBLIC KEY-----")?.replace("", "") ?.replace("\n", "") ) val x509EncodedKeySpec = X509EncodedKeySpec(publicBytes) @@ -162,9 +162,9 @@ class KtorKeyMap(private val userAuthRepository: IUserAuthService) : KeyMap { val username = (keyId ?: throw IllegalArgumentException("keyId is null")).substringBeforeLast("#pubkey") .substringAfterLast("/") val publicBytes = Base64.getDecoder().decode( - userAuthRepository.findByUsername( + userAuthRepository.findByName( username - ).privateKey?.replace("-----BEGIN PRIVATE KEY-----", "")?.replace("-----END PRIVATE KEY-----", "") + )?.privateKey?.replace("-----BEGIN PRIVATE KEY-----", "")?.replace("-----END PRIVATE KEY-----", "") ?.replace("\n", "") ) val x509EncodedKeySpec = PKCS8EncodedKeySpec(publicBytes) diff --git a/src/main/kotlin/dev/usbharu/hideout/repository/IUserAuthRepository.kt b/src/main/kotlin/dev/usbharu/hideout/repository/IUserAuthRepository.kt deleted file mode 100644 index 2f6f46ba..00000000 --- a/src/main/kotlin/dev/usbharu/hideout/repository/IUserAuthRepository.kt +++ /dev/null @@ -1,15 +0,0 @@ -package dev.usbharu.hideout.repository - -import dev.usbharu.hideout.domain.model.UserAuthentication -import dev.usbharu.hideout.domain.model.UserAuthenticationEntity - -interface IUserAuthRepository { - suspend fun create(userAuthentication: UserAuthentication):UserAuthenticationEntity - - suspend fun findById(id:Long):UserAuthenticationEntity? - - suspend fun update(userAuthenticationEntity: UserAuthenticationEntity) - - suspend fun delete(id:Long) - suspend fun findByUserId(id: Long): UserAuthenticationEntity? -} diff --git a/src/main/kotlin/dev/usbharu/hideout/repository/UserAuthRepository.kt b/src/main/kotlin/dev/usbharu/hideout/repository/UserAuthRepository.kt deleted file mode 100644 index 0bb5543c..00000000 --- a/src/main/kotlin/dev/usbharu/hideout/repository/UserAuthRepository.kt +++ /dev/null @@ -1,63 +0,0 @@ -package dev.usbharu.hideout.repository - -import dev.usbharu.hideout.domain.model.UserAuthentication -import dev.usbharu.hideout.domain.model.UserAuthenticationEntity -import dev.usbharu.hideout.domain.model.UsersAuthentication -import kotlinx.coroutines.Dispatchers -import org.jetbrains.exposed.sql.* -import org.jetbrains.exposed.sql.transactions.experimental.newSuspendedTransaction -import org.jetbrains.exposed.sql.transactions.transaction - -class UserAuthRepository(private val database: Database) : IUserAuthRepository { - - init { - transaction(database) { - SchemaUtils.create(UsersAuthentication) - SchemaUtils.createMissingTablesAndColumns(UsersAuthentication) - } - } - - private fun ResultRow.toUserAuth():UserAuthenticationEntity{ - return UserAuthenticationEntity( - id = this[UsersAuthentication.id].value, - userId = this[UsersAuthentication.userId], - hash = this[UsersAuthentication.hash], - publicKey = this[UsersAuthentication.publicKey], - privateKey = this[UsersAuthentication.privateKey] - ) - } - - - suspend fun query(block: suspend () -> T): T = - newSuspendedTransaction(Dispatchers.IO) {block()} - override suspend fun create(userAuthentication: UserAuthentication): UserAuthenticationEntity { - return query { - UserAuthenticationEntity( - UsersAuthentication.insert { - it[userId] = userAuthentication.userId - it[hash] = userAuthentication.hash - it[publicKey] = userAuthentication.publicKey - it[privateKey] = userAuthentication.privateKey - }[UsersAuthentication.id].value,userAuthentication - ) - } - } - - override suspend fun findById(id: Long): UserAuthenticationEntity? { - TODO("Not yet implemented") - } - - override suspend fun findByUserId(id:Long):UserAuthenticationEntity? { - return query { - UsersAuthentication.select { UsersAuthentication.userId eq id }.map { it.toUserAuth() }.singleOrNull() - } - } - - override suspend fun update(userAuthenticationEntity: UserAuthenticationEntity) { - TODO("Not yet implemented") - } - - override suspend fun delete(id: Long) { - TODO("Not yet implemented") - } -} diff --git a/src/main/kotlin/dev/usbharu/hideout/service/IUserAuthService.kt b/src/main/kotlin/dev/usbharu/hideout/service/IUserAuthService.kt index d2096d37..1702c41b 100644 --- a/src/main/kotlin/dev/usbharu/hideout/service/IUserAuthService.kt +++ b/src/main/kotlin/dev/usbharu/hideout/service/IUserAuthService.kt @@ -1,8 +1,5 @@ package dev.usbharu.hideout.service -import dev.usbharu.hideout.domain.model.UserAuthentication -import dev.usbharu.hideout.domain.model.UserAuthenticationEntity - interface IUserAuthService { fun hash(password: String): String @@ -11,8 +8,4 @@ interface IUserAuthService { suspend fun verifyAccount(username: String, password: String): Boolean - suspend fun findByUserId(userId: Long): UserAuthenticationEntity - - suspend fun findByUsername(username: String): UserAuthenticationEntity - suspend fun createAccount(userEntity: UserAuthentication): UserAuthenticationEntity } diff --git a/src/main/kotlin/dev/usbharu/hideout/service/activitypub/ActivityPubUserServiceImpl.kt b/src/main/kotlin/dev/usbharu/hideout/service/activitypub/ActivityPubUserServiceImpl.kt index f4dd9fec..14d4cd11 100644 --- a/src/main/kotlin/dev/usbharu/hideout/service/activitypub/ActivityPubUserServiceImpl.kt +++ b/src/main/kotlin/dev/usbharu/hideout/service/activitypub/ActivityPubUserServiceImpl.kt @@ -1,12 +1,11 @@ package dev.usbharu.hideout.service.activitypub import com.fasterxml.jackson.module.kotlin.readValue +import dev.usbharu.hideout.config.Config +import dev.usbharu.hideout.domain.model.User import dev.usbharu.hideout.domain.model.ap.Image import dev.usbharu.hideout.domain.model.ap.Key import dev.usbharu.hideout.domain.model.ap.Person -import dev.usbharu.hideout.config.Config -import dev.usbharu.hideout.domain.model.User -import dev.usbharu.hideout.domain.model.UserAuthentication import dev.usbharu.hideout.exception.UserNotFoundException import dev.usbharu.hideout.exception.ap.IllegalActivityPubObjectException import dev.usbharu.hideout.service.IUserAuthService @@ -30,7 +29,6 @@ class ActivityPubUserServiceImpl( override suspend fun getPersonByName(name: String): Person { // TODO: JOINで書き直し val userEntity = userService.findByName(name) - val userAuthEntity = userAuthService.findByUserId(userEntity.id) val userUrl = "${Config.configData.url}/users/$name" return Person( type = emptyList(), @@ -52,7 +50,7 @@ class ActivityPubUserServiceImpl( name = "Public Key", id = "$userUrl#pubkey", owner = userUrl, - publicKeyPem = userAuthEntity.publicKey + publicKeyPem = userEntity.publicKey ) ) } @@ -60,7 +58,6 @@ class ActivityPubUserServiceImpl( override suspend fun fetchPerson(url: String): Person { return try { val userEntity = userService.findByUrl(url) - val userAuthEntity = userAuthService.findByUsername(userEntity.name) return Person( type = emptyList(), name = userEntity.name, @@ -81,7 +78,7 @@ class ActivityPubUserServiceImpl( name = "Public Key", id = "$url#pubkey", owner = url, - publicKeyPem = userAuthEntity.publicKey + publicKeyPem = userEntity.publicKey ) ) @@ -90,7 +87,7 @@ class ActivityPubUserServiceImpl( accept(ContentType.Application.Activity) } val person = Config.configData.objectMapper.readValue(httpResponse.bodyAsText()) - val userEntity = userService.create( + userService.create( User( id = 0L, name = person.preferredUsername @@ -101,18 +98,10 @@ class ActivityPubUserServiceImpl( inbox = person.inbox ?: throw IllegalActivityPubObjectException("inbox is null"), outbox = person.outbox ?: throw IllegalActivityPubObjectException("outbox is null"), url = url, - publicKey = "", + publicKey = person.publicKey?.publicKeyPem ?: throw IllegalActivityPubObjectException("publicKey is null"), createdAt = LocalDateTime.now() ) ) - userAuthService.createAccount( - UserAuthentication( - userEntity.id, - null, - person.publicKey?.publicKeyPem ?: throw IllegalActivityPubObjectException("publicKey is null"), - null - ) - ) person } diff --git a/src/main/kotlin/dev/usbharu/hideout/service/impl/UserAuthService.kt b/src/main/kotlin/dev/usbharu/hideout/service/impl/UserAuthService.kt index a0cdfabc..db6dccf7 100644 --- a/src/main/kotlin/dev/usbharu/hideout/service/impl/UserAuthService.kt +++ b/src/main/kotlin/dev/usbharu/hideout/service/impl/UserAuthService.kt @@ -2,10 +2,7 @@ package dev.usbharu.hideout.service.impl import dev.usbharu.hideout.config.Config import dev.usbharu.hideout.domain.model.User -import dev.usbharu.hideout.domain.model.UserAuthentication -import dev.usbharu.hideout.domain.model.UserAuthenticationEntity import dev.usbharu.hideout.exception.UserNotFoundException -import dev.usbharu.hideout.repository.IUserAuthRepository import dev.usbharu.hideout.repository.IUserRepository import dev.usbharu.hideout.service.IUserAuthService import io.ktor.util.* @@ -16,8 +13,7 @@ import java.time.LocalDateTime import java.util.* class UserAuthService( - val userRepository: IUserRepository, - val userAuthRepository: IUserAuthRepository + val userRepository: IUserRepository ) : IUserAuthService { @@ -31,6 +27,7 @@ class UserAuthService( return true } + @Deprecated("") override suspend fun registerAccount(username: String, hash: String) { val url = "${Config.configData.url}/users/$username" val registerUser = User( @@ -51,37 +48,13 @@ class UserAuthService( val privateKey = keyPair.private as RSAPrivateKey val publicKey = keyPair.public as RSAPublicKey - - val userAuthentication = UserAuthentication( - createdUser.id, - hash, - publicKey.toPem(), - privateKey.toPem() - ) - - userAuthRepository.create(userAuthentication) + TODO() } override suspend fun verifyAccount(username: String, password: String): Boolean { val userEntity = userRepository.findByName(username) ?: throw UserNotFoundException("$username was not found") - val userAuthEntity = userAuthRepository.findByUserId(userEntity.id) - ?: throw UserNotFoundException("$username auth data was not found") - return userAuthEntity.hash == hash(password) - } - - override suspend fun findByUserId(userId: Long): UserAuthenticationEntity { - return userAuthRepository.findByUserId(userId) ?: throw UserNotFoundException("$userId was not found") - } - - override suspend fun findByUsername(username: String): UserAuthenticationEntity { - val userEntity = userRepository.findByName(username) ?: throw UserNotFoundException("$username was not found") - return userAuthRepository.findByUserId(userEntity.id) - ?: throw UserNotFoundException("$username auth data was not found") - } - - override suspend fun createAccount(userEntity: UserAuthentication): UserAuthenticationEntity { - return userAuthRepository.create(userEntity) + return userEntity.password == hash(password) } private fun generateKeyPair(): KeyPair { diff --git a/src/main/kotlin/dev/usbharu/hideout/service/signature/HttpSignatureVerifyServiceImpl.kt b/src/main/kotlin/dev/usbharu/hideout/service/signature/HttpSignatureVerifyServiceImpl.kt index 74525981..488b82cf 100644 --- a/src/main/kotlin/dev/usbharu/hideout/service/signature/HttpSignatureVerifyServiceImpl.kt +++ b/src/main/kotlin/dev/usbharu/hideout/service/signature/HttpSignatureVerifyServiceImpl.kt @@ -1,12 +1,13 @@ package dev.usbharu.hideout.service.signature import dev.usbharu.hideout.plugins.KtorKeyMap +import dev.usbharu.hideout.repository.IUserRepository import dev.usbharu.hideout.service.IUserAuthService import io.ktor.http.* import tech.barbero.http.message.signing.HttpMessage import tech.barbero.http.message.signing.SignatureHeaderVerifier -class HttpSignatureVerifyServiceImpl(private val userAuthService: IUserAuthService) : HttpSignatureVerifyService { +class HttpSignatureVerifyServiceImpl(private val userAuthService: IUserRepository) : HttpSignatureVerifyService { override fun verify(headers: Headers): Boolean { val build = SignatureHeaderVerifier.builder().keyMap(KtorKeyMap(userAuthService)).build() return true; diff --git a/src/test/kotlin/dev/usbharu/hideout/plugins/ActivityPubKtTest.kt b/src/test/kotlin/dev/usbharu/hideout/plugins/ActivityPubKtTest.kt index 035f3143..757c6ec7 100644 --- a/src/test/kotlin/dev/usbharu/hideout/plugins/ActivityPubKtTest.kt +++ b/src/test/kotlin/dev/usbharu/hideout/plugins/ActivityPubKtTest.kt @@ -1,28 +1,20 @@ package dev.usbharu.hideout.plugins import dev.usbharu.hideout.domain.model.User -import dev.usbharu.hideout.domain.model.UserAuthentication -import dev.usbharu.hideout.domain.model.UserAuthenticationEntity import dev.usbharu.hideout.domain.model.ap.JsonLd -import dev.usbharu.hideout.repository.IUserAuthRepository import dev.usbharu.hideout.repository.IUserRepository -import dev.usbharu.hideout.service.impl.UserAuthService -import dev.usbharu.hideout.service.impl.toPem import io.ktor.client.* import io.ktor.client.engine.mock.* import io.ktor.client.plugins.logging.* import kotlinx.coroutines.runBlocking import org.junit.jupiter.api.Test -import java.security.KeyPairGenerator -import java.security.interfaces.RSAPrivateKey -import java.security.interfaces.RSAPublicKey import java.time.LocalDateTime class ActivityPubKtTest { @Test fun HttpSignTest(): Unit = runBlocking { - val ktorKeyMap = KtorKeyMap(UserAuthService(object : IUserRepository { + val ktorKeyMap = KtorKeyMap(object : IUserRepository { override suspend fun create(user: User): User { TODO("Not yet implemented") } @@ -92,33 +84,7 @@ class ActivityPubKtTest { TODO("Not yet implemented") } - }, object : IUserAuthRepository { - override suspend fun create(userAuthentication: UserAuthentication): UserAuthenticationEntity { - TODO("Not yet implemented") - } - - override suspend fun findById(id: Long): UserAuthenticationEntity? { - TODO("Not yet implemented") - } - - override suspend fun update(userAuthenticationEntity: UserAuthenticationEntity) { - TODO("Not yet implemented") - } - - override suspend fun delete(id: Long) { - TODO("Not yet implemented") - } - - override suspend fun findByUserId(id: Long): UserAuthenticationEntity? { - val keyPairGenerator = KeyPairGenerator.getInstance("RSA") - keyPairGenerator.initialize(1024) - val generateKeyPair = keyPairGenerator.generateKeyPair() - return UserAuthenticationEntity( - 1, 1, "test", (generateKeyPair.public as RSAPublicKey).toPem(), - (generateKeyPair.private as RSAPrivateKey).toPem() - ) - } - })) + }) val httpClient = HttpClient(MockEngine { httpRequestData -> respondOk() diff --git a/src/test/kotlin/dev/usbharu/hideout/plugins/KtorKeyMapTest.kt b/src/test/kotlin/dev/usbharu/hideout/plugins/KtorKeyMapTest.kt index edaeaff3..9da97821 100644 --- a/src/test/kotlin/dev/usbharu/hideout/plugins/KtorKeyMapTest.kt +++ b/src/test/kotlin/dev/usbharu/hideout/plugins/KtorKeyMapTest.kt @@ -1,23 +1,15 @@ package dev.usbharu.hideout.plugins import dev.usbharu.hideout.domain.model.User -import dev.usbharu.hideout.domain.model.UserAuthentication -import dev.usbharu.hideout.domain.model.UserAuthenticationEntity -import dev.usbharu.hideout.repository.IUserAuthRepository import dev.usbharu.hideout.repository.IUserRepository -import dev.usbharu.hideout.service.impl.UserAuthService -import dev.usbharu.hideout.service.impl.toPem import org.junit.jupiter.api.Test -import java.security.KeyPairGenerator -import java.security.interfaces.RSAPrivateKey -import java.security.interfaces.RSAPublicKey import java.time.LocalDateTime class KtorKeyMapTest { @Test fun getPrivateKey() { - val ktorKeyMap = KtorKeyMap(UserAuthService(object : IUserRepository { + val ktorKeyMap = KtorKeyMap(object : IUserRepository { override suspend fun create(user: User): User { TODO("Not yet implemented") } @@ -86,33 +78,7 @@ class KtorKeyMapTest { TODO("Not yet implemented") } - }, object : IUserAuthRepository { - override suspend fun create(userAuthentication: UserAuthentication): UserAuthenticationEntity { - TODO("Not yet implemented") - } - - override suspend fun findById(id: Long): UserAuthenticationEntity? { - TODO("Not yet implemented") - } - - override suspend fun update(userAuthenticationEntity: UserAuthenticationEntity) { - TODO("Not yet implemented") - } - - override suspend fun delete(id: Long) { - TODO("Not yet implemented") - } - - override suspend fun findByUserId(id: Long): UserAuthenticationEntity? { - val keyPairGenerator = KeyPairGenerator.getInstance("RSA") - keyPairGenerator.initialize(1024) - val generateKeyPair = keyPairGenerator.generateKeyPair() - return UserAuthenticationEntity( - 1, 1, "test", (generateKeyPair.public as RSAPublicKey).toPem(), - (generateKeyPair.private as RSAPrivateKey).toPem() - ) - } - })) + }) ktorKeyMap.getPrivateKey("test") }