feat(creator-channel): 커뮤니티 상세 조회 계약을 추가한다
This commit is contained in:
@@ -0,0 +1,135 @@
|
||||
package kr.co.vividnext.sodalive.v2.creator.channel.community
|
||||
|
||||
import com.google.gson.annotations.SerializedName
|
||||
import io.reactivex.rxjava3.core.Single
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.community.detail.data.CreatorChannelCommunityCommentResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.community.detail.data.CreatorChannelCommunityCommentsResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.community.detail.data.CreatorChannelCommunityPostDetailResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.community.detail.data.CreatorChannelCommunityRepliesResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.community.detail.data.CreatorChannelCommunityReplyResponse
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.data.CreatorChannelApi
|
||||
import kr.co.vividnext.sodalive.v2.creator.channel.data.CreatorChannelRepository
|
||||
import org.junit.Assert.assertEquals
|
||||
import org.junit.Assert.assertNotNull
|
||||
import org.junit.Assert.assertTrue
|
||||
import org.junit.Test
|
||||
import org.mockito.kotlin.mock
|
||||
import org.mockito.kotlin.verify
|
||||
import org.mockito.kotlin.whenever
|
||||
import java.io.File
|
||||
|
||||
class CreatorChannelCommunityDetailContractTest {
|
||||
|
||||
@Test
|
||||
fun `커뮤니티 상세 API source는 신규 v2 endpoint와 ApiResponse Single 계약을 제공한다`() {
|
||||
val api = projectFile(
|
||||
"app/src/main/java/kr/co/vividnext/sodalive/v2/creator/channel/data/CreatorChannelApi.kt"
|
||||
).readText()
|
||||
|
||||
assertTrue(api.contains("@GET(\"/api/v2/creator-channels/community-posts/{postId}\")"))
|
||||
assertTrue(api.contains("@GET(\"/api/v2/creator-channels/community-posts/{postId}/comments\")"))
|
||||
assertTrue(api.contains("@GET(\"/api/v2/creator-channels/community-comments/{commentId}/replies\")"))
|
||||
assertTrue(api.contains("Single<ApiResponse<CreatorChannelCommunityPostDetailResponse>>"))
|
||||
assertTrue(api.contains("Single<ApiResponse<CreatorChannelCommunityCommentsResponse>>"))
|
||||
assertTrue(api.contains("Single<ApiResponse<CreatorChannelCommunityRepliesResponse>>"))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `커뮤니티 상세 repository는 댓글과 답글 기본 page 0 size 20 계약을 제공한다`() {
|
||||
val api = mock<CreatorChannelApi>()
|
||||
val repository = CreatorChannelRepository(api, mock(), mock(), mock(), mock())
|
||||
whenever(api.getCommunityPostDetail(11L, "Bearer token")).thenReturn(Single.never())
|
||||
whenever(api.getCommunityPostComments(11L, 0, 20, "Bearer token")).thenReturn(Single.never())
|
||||
whenever(api.getCommunityCommentReplies(22L, 0, 20, "Bearer token")).thenReturn(Single.never())
|
||||
|
||||
repository.getCommunityPostDetail(11L, "Bearer token")
|
||||
repository.getCommunityPostComments(11L, token = "Bearer token")
|
||||
repository.getCommunityCommentReplies(22L, token = "Bearer token")
|
||||
|
||||
verify(api).getCommunityPostDetail(11L, "Bearer token")
|
||||
verify(api).getCommunityPostComments(11L, 0, 20, "Bearer token")
|
||||
verify(api).getCommunityCommentReplies(22L, 0, 20, "Bearer token")
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `커뮤니티 상세 응답 모델은 SerializedName과 nullable latestReply 계약을 제공한다`() {
|
||||
val reply = CreatorChannelCommunityReplyResponse(
|
||||
commentId = 44L,
|
||||
writerId = 55L,
|
||||
writerProfileImageUrl = "reply.png",
|
||||
writerNickname = "reply member",
|
||||
content = "reply",
|
||||
createdAtUtc = "2026-07-08T00:02:00Z"
|
||||
)
|
||||
val comment = CreatorChannelCommunityCommentResponse(
|
||||
commentId = 22L,
|
||||
writerId = 33L,
|
||||
writerProfileImageUrl = "member.png",
|
||||
writerNickname = "member",
|
||||
content = "comment",
|
||||
isSecret = false,
|
||||
createdAtUtc = "2026-07-08T00:01:00Z",
|
||||
latestReply = reply
|
||||
)
|
||||
val comments = CreatorChannelCommunityCommentsResponse(
|
||||
commentCount = 1,
|
||||
comments = listOf(comment),
|
||||
page = 0,
|
||||
size = 20,
|
||||
hasNext = false
|
||||
)
|
||||
val detail = CreatorChannelCommunityPostDetailResponse(
|
||||
postId = 11L,
|
||||
creatorId = 100L,
|
||||
creatorNickname = "creator",
|
||||
creatorProfileUrl = null,
|
||||
createdAtUtc = "2026-07-08T00:00:00Z",
|
||||
content = "content",
|
||||
imageUrl = null,
|
||||
audioUrl = null,
|
||||
price = 0,
|
||||
existOrdered = true,
|
||||
isCommentAvailable = true,
|
||||
likeCount = 1,
|
||||
commentCount = 2,
|
||||
isLiked = false,
|
||||
isPinned = false,
|
||||
comments = comments
|
||||
)
|
||||
|
||||
assertEquals(11L, detail.postId)
|
||||
assertEquals(comments, detail.comments)
|
||||
assertEquals(reply, comment.latestReply)
|
||||
assertEquals(44L, reply.commentId)
|
||||
assertNotNull(
|
||||
CreatorChannelCommunityPostDetailResponse::class.java.getDeclaredField("postId")
|
||||
.getAnnotation(SerializedName::class.java)
|
||||
)
|
||||
assertNotNull(
|
||||
CreatorChannelCommunityPostDetailResponse::class.java.getDeclaredField("comments")
|
||||
.getAnnotation(SerializedName::class.java)
|
||||
)
|
||||
assertNotNull(
|
||||
CreatorChannelCommunityCommentResponse::class.java.getDeclaredField("latestReply")
|
||||
.getAnnotation(SerializedName::class.java)
|
||||
)
|
||||
assertNotNull(
|
||||
CreatorChannelCommunityCommentResponse::class.java.getDeclaredField("writerId")
|
||||
.getAnnotation(SerializedName::class.java)
|
||||
)
|
||||
assertNotNull(
|
||||
CreatorChannelCommunityReplyResponse::class.java.getDeclaredField("writerId")
|
||||
.getAnnotation(SerializedName::class.java)
|
||||
)
|
||||
assertEquals(CreatorChannelCommunityCommentsResponse(1, listOf(comment), 0, 20, false).comments.first(), comment)
|
||||
assertEquals(CreatorChannelCommunityRepliesResponse(listOf(reply), 0, 20, false).replies.first(), reply)
|
||||
}
|
||||
|
||||
private fun projectFile(path: String): File {
|
||||
var current = File(checkNotNull(System.getProperty("user.dir"))).absoluteFile
|
||||
while (current.parentFile != null && !File(current, "settings.gradle").exists()) {
|
||||
current = checkNotNull(current.parentFile)
|
||||
}
|
||||
return File(current, path)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user