package roomescape.member.business import io.github.oshai.kotlinlogging.KotlinLogging import org.springframework.data.repository.findByIdOrNull import org.springframework.stereotype.Service import org.springframework.transaction.annotation.Transactional import roomescape.member.exception.MemberErrorCode import roomescape.member.exception.MemberException import roomescape.member.infrastructure.persistence.MemberEntity import roomescape.member.infrastructure.persistence.MemberRepository import roomescape.member.infrastructure.persistence.Role import roomescape.member.web.* private val log = KotlinLogging.logger {} @Service @Transactional(readOnly = true) class MemberService( private val memberRepository: MemberRepository, ) { fun findMembers(): MemberRetrieveListResponse { log.debug { "[MemberService.findMembers] 회원 조회 시작" } return memberRepository.findAll() .also { log.info { "[MemberService.findMembers] 회원 ${it.size}명 조회 완료" } } .toRetrieveListResponse() } fun findById(memberId: Long): MemberEntity { return fetchOrThrow("findById", "memberId=$memberId") { memberRepository.findByIdOrNull(memberId) } } fun findByEmailAndPassword(email: String, password: String): MemberEntity { return fetchOrThrow("findByEmailAndPassword", "email=$email, password=$password") { memberRepository.findByEmailAndPassword(email, password) } } @Transactional fun createMember(request: SignupRequest): SignupResponse { memberRepository.findByEmail(request.email)?.let { log.info { "[MemberService.createMember] 회원가입 실패(이메일 중복): email=${request.email}" } throw MemberException(MemberErrorCode.DUPLICATE_EMAIL) } val member = MemberEntity( name = request.name, email = request.email, password = request.password, role = Role.MEMBER ) return memberRepository.save(member).toSignupResponse() .also { log.info { "[MemberService.create] 회원가입 완료: email=${request.email} memberId=${it.id}" } } } private fun fetchOrThrow(calledBy: String, params: String, block: () -> MemberEntity?): MemberEntity { log.debug { "[MemberService.$calledBy] 회원 조회 시작: $params" } return block() ?.also { log.info { "[MemberService.$calledBy] 회원 조회 완료: memberId=${it.id}" } } ?: run { log.info { "[MemberService.$calledBy] 회원 조회 실패: $params" } throw MemberException(MemberErrorCode.MEMBER_NOT_FOUND) } } }