Skip to content

Commit 113f28a

Browse files
authored
[DPMBE-63] 이미지 관련 테스트 코드를 작성한다 (#78)
* chore: spring security test 의존성 추가 * test: S3Properties Test * test: S3UploadPresignedUrl Service Test * test: GetPresignedUrl UseCase Test * test: Image Controller Test * fix: WAIT, LATE일때 throw 키워드 추가, PictureAdapter로 파일이름 수정 * test: PictureDomain Servicer Test * test: PictureUploadSuccess UseCase Test * test: Picture Adapter Test * style: spotless * test: S3UploadPresignedUrl Service Test resultUrl 수정 * fix: GetPresignedUrl UseCase Test에 ImageUrlDto 필요없는 부분 제거 * test: Picture Controller Test * fix: AutoConfigureMockMvc에 addFilters = false 설정으로 filter 안불러오도록 변경 * style: spotless
1 parent d6b9fae commit 113f28a

File tree

12 files changed

+390
-6
lines changed

12 files changed

+390
-6
lines changed

Whatnow-Api/build.gradle.kts

+1
Original file line numberDiff line numberDiff line change
@@ -9,4 +9,5 @@ dependencies {
99

1010
implementation("org.springdoc:springdoc-openapi-ui:1.6.12")
1111
implementation("org.springframework.boot:spring-boot-starter-security")
12+
testImplementation("org.springframework.security:spring-security-test")
1213
}

Whatnow-Api/src/main/kotlin/com/depromeet/whatnow/api/image/controller/ImageController.kt

-1
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@ import org.springframework.web.bind.annotation.PathVariable
1111
import org.springframework.web.bind.annotation.RequestMapping
1212
import org.springframework.web.bind.annotation.RequestParam
1313
import org.springframework.web.bind.annotation.RestController
14-
import java.util.*
1514

1615
@RestController
1716
@Tag(name = "6. [이미지]")
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
package com.depromeet.whatnow.api.image.controller
2+
3+
import com.depromeet.whatnow.api.image.usecase.GetPresignedUrlUseCase
4+
import com.depromeet.whatnow.config.s3.ImageFileExtension
5+
import org.junit.jupiter.api.Test
6+
import org.springframework.beans.factory.annotation.Autowired
7+
import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc
8+
import org.springframework.boot.test.autoconfigure.web.servlet.WebMvcTest
9+
import org.springframework.boot.test.mock.mockito.MockBean
10+
import org.springframework.test.context.ContextConfiguration
11+
import org.springframework.test.web.servlet.MockMvc
12+
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get
13+
import org.springframework.test.web.servlet.result.MockMvcResultMatchers.status
14+
15+
@WebMvcTest(ImageController::class)
16+
@ContextConfiguration(classes = [ImageController::class])
17+
@AutoConfigureMockMvc(addFilters = false)
18+
class ImageControllerTest {
19+
@MockBean
20+
lateinit var getPresignedUrlUseCase: GetPresignedUrlUseCase
21+
22+
@Autowired
23+
lateinit var mockMvc: MockMvc
24+
25+
@Test
26+
fun `presignedUrl 요청에 성공하면 200을 응답한다`() {
27+
// given
28+
val promiseId = 1L
29+
val fileExtension = ImageFileExtension.JPEG.name
30+
31+
// when, then
32+
mockMvc.perform(
33+
get("/v1/promises/{promiseId}/images", promiseId)
34+
.param("fileExtension", fileExtension),
35+
)
36+
.andExpect(status().isOk)
37+
.andDo { print(it) }
38+
}
39+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
package com.depromeet.whatnow.api.image.usecase
2+
3+
import com.depromeet.whatnow.config.s3.ImageFileExtension
4+
import com.depromeet.whatnow.config.s3.ImageUrlDto
5+
import com.depromeet.whatnow.config.s3.S3UploadPresignedUrlService
6+
import org.junit.jupiter.api.Assertions.assertEquals
7+
import org.junit.jupiter.api.Test
8+
import org.junit.jupiter.api.extension.ExtendWith
9+
import org.mockito.InjectMocks
10+
import org.mockito.Mock
11+
import org.mockito.junit.jupiter.MockitoExtension
12+
import org.mockito.kotlin.given
13+
14+
@ExtendWith(MockitoExtension::class)
15+
class GetPresignedUrlUseCaseTest {
16+
@Mock
17+
lateinit var presignedUrlService: S3UploadPresignedUrlService
18+
19+
@InjectMocks
20+
lateinit var getPresignedUrlUseCase: GetPresignedUrlUseCase
21+
22+
@Test
23+
fun `PresignUrl 을 요청하면 url 을 반환한다`() {
24+
// given
25+
given(presignedUrlService.forPromise(1, ImageFileExtension.JPEG)).willReturn(
26+
ImageUrlDto(
27+
url = "https://whatnow.kr/1.jpg",
28+
key = "1.jpg",
29+
),
30+
)
31+
// when
32+
val imageUrlResponse = getPresignedUrlUseCase.forPromise(1, ImageFileExtension.JPEG)
33+
34+
// then
35+
assertEquals("https://whatnow.kr/1.jpg", imageUrlResponse.presignedUrl)
36+
assertEquals("1.jpg", imageUrlResponse.key)
37+
}
38+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
package com.depromeet.whatnow.api.picture.controller
2+
3+
import com.depromeet.whatnow.api.picture.usecase.PictureUploadSuccessUseCase
4+
import com.depromeet.whatnow.domains.picture.domain.PictureCommentType
5+
import org.junit.jupiter.api.Test
6+
import org.springframework.beans.factory.annotation.Autowired
7+
import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc
8+
import org.springframework.boot.test.autoconfigure.web.servlet.WebMvcTest
9+
import org.springframework.boot.test.mock.mockito.MockBean
10+
import org.springframework.test.context.ContextConfiguration
11+
import org.springframework.test.web.servlet.MockMvc
12+
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post
13+
import org.springframework.test.web.servlet.result.MockMvcResultMatchers.status
14+
15+
@WebMvcTest(PictureController::class)
16+
@ContextConfiguration(classes = [PictureController::class])
17+
@AutoConfigureMockMvc(addFilters = false)
18+
class PictureControllerTest {
19+
@MockBean
20+
lateinit var successUseCase: PictureUploadSuccessUseCase
21+
22+
@Autowired
23+
lateinit var mockMvc: MockMvc
24+
25+
@Test
26+
fun `이미지 업로드 성공 요청에 정상적으로 200을 반환한다`() {
27+
// given
28+
val promiseId = 1
29+
val imageKey = "imageKey"
30+
val pictureCommentType = PictureCommentType.SORRY_LATE
31+
32+
// when, then
33+
mockMvc.perform(
34+
post("/v1/promises/{promiseId}/images/success/{imageKey}", promiseId, imageKey)
35+
.param("pictureCommentType", pictureCommentType.name),
36+
)
37+
.andExpect(status().isOk)
38+
.andDo { print(it) }
39+
}
40+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
package com.depromeet.whatnow.api.picture.usecase
2+
3+
import com.depromeet.whatnow.domains.picture.domain.PictureCommentType
4+
import com.depromeet.whatnow.domains.picture.service.PictureDomainService
5+
import org.assertj.core.api.Assertions.assertThatCode
6+
import org.junit.jupiter.api.BeforeEach
7+
import org.junit.jupiter.api.Test
8+
import org.junit.jupiter.api.extension.ExtendWith
9+
import org.mockito.InjectMocks
10+
import org.mockito.Mock
11+
import org.mockito.junit.jupiter.MockitoExtension
12+
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken
13+
import org.springframework.security.core.authority.SimpleGrantedAuthority
14+
import org.springframework.security.core.context.SecurityContextHolder
15+
16+
@ExtendWith(MockitoExtension::class)
17+
class PictureUploadSuccessUseCaseTest {
18+
@Mock
19+
lateinit var pictureDomainService: PictureDomainService
20+
21+
@InjectMocks
22+
lateinit var pictureUploadSuccessUseCase: PictureUploadSuccessUseCase
23+
24+
@BeforeEach
25+
fun setup() {
26+
val securityContext = SecurityContextHolder.createEmptyContext()
27+
val authentication = UsernamePasswordAuthenticationToken("1", null, setOf(SimpleGrantedAuthority("ROLE_USER")))
28+
securityContext.authentication = authentication
29+
SecurityContextHolder.setContext(securityContext)
30+
}
31+
32+
@Test
33+
fun `이미지 업로드 성공 요청시 정상적이라면 에러가 발생하지 않는다`() {
34+
// given
35+
36+
// when
37+
38+
// then
39+
assertThatCode {
40+
pictureUploadSuccessUseCase.successUploadImage(1, "1", PictureCommentType.SORRY_LATE)
41+
}.doesNotThrowAnyException()
42+
}
43+
}

Whatnow-Domain/src/main/kotlin/com/depromeet/whatnow/domains/picture/adapter/PromiseAdapter.kt renamed to Whatnow-Domain/src/main/kotlin/com/depromeet/whatnow/domains/picture/adapter/PictureAdapter.kt

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ import com.depromeet.whatnow.domains.picture.domain.PictureCommentType
66
import com.depromeet.whatnow.domains.picture.repository.PictureRepository
77

88
@Adapter
9-
class PromiseAdapter(
9+
class PictureAdapter(
1010
val pictureRepository: PictureRepository,
1111
) {
1212
fun save(userId: Long, promiseId: Long, imageUrl: String, imageKey: String, pictureCommentType: PictureCommentType) {

Whatnow-Domain/src/main/kotlin/com/depromeet/whatnow/domains/picture/service/PictureDomainService.kt

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
package com.depromeet.whatnow.domains.picture.service
22

33
import com.depromeet.whatnow.consts.IMAGE_DOMAIN
4-
import com.depromeet.whatnow.domains.picture.adapter.PromiseAdapter
4+
import com.depromeet.whatnow.domains.picture.adapter.PictureAdapter
55
import com.depromeet.whatnow.domains.picture.domain.PictureCommentType
66
import com.depromeet.whatnow.domains.picture.exception.CancelledUserUploadException
77
import com.depromeet.whatnow.domains.picture.exception.InvalidCommentTypeException
@@ -13,7 +13,7 @@ import org.springframework.transaction.annotation.Transactional
1313

1414
@Service
1515
class PictureDomainService(
16-
val pictureAdapter: PromiseAdapter,
16+
val pictureAdapter: PictureAdapter,
1717
val promiseUserAdapter: PromiseUserAdaptor,
1818
) {
1919
@Transactional
@@ -29,9 +29,9 @@ class PictureDomainService(
2929
when (promiseUserType) {
3030
PromiseUserType.READY -> throw UploadBeforeTrackingException.EXCEPTION
3131
PromiseUserType.CANCEL -> throw CancelledUserUploadException.EXCEPTION
32-
else -> {
32+
PromiseUserType.WAIT, PromiseUserType.LATE -> {
3333
if (pictureCommentType.promiseUserType != promiseUserType) {
34-
InvalidCommentTypeException.EXCEPTION
34+
throw InvalidCommentTypeException.EXCEPTION
3535
}
3636
}
3737
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
package com.depromeet.whatnow.domains.picture.adapter
2+
3+
import com.depromeet.whatnow.domains.picture.domain.Picture
4+
import com.depromeet.whatnow.domains.picture.domain.PictureCommentType
5+
import com.depromeet.whatnow.domains.picture.repository.PictureRepository
6+
import org.junit.jupiter.api.Test
7+
import org.junit.jupiter.api.extension.ExtendWith
8+
import org.mockito.ArgumentCaptor
9+
import org.mockito.InjectMocks
10+
import org.mockito.Mock
11+
import org.mockito.Mockito
12+
import org.mockito.junit.jupiter.MockitoExtension
13+
import org.mockito.kotlin.then
14+
15+
@ExtendWith(MockitoExtension::class)
16+
class PictureAdapterTest {
17+
@Mock
18+
lateinit var pictureRepository: PictureRepository
19+
20+
@InjectMocks
21+
lateinit var pictureAdapter: PictureAdapter
22+
23+
@Test
24+
fun `Picture 저장 시 정상적으로 저장된다`() {
25+
val captor: ArgumentCaptor<Picture> = ArgumentCaptor.forClass(Picture::class.java)
26+
27+
// when
28+
pictureAdapter.save(1, 1, "imageUrl", "imageKey", PictureCommentType.RUNNING)
29+
30+
// then
31+
then(pictureRepository).should(Mockito.times(1)).save(captor.capture())
32+
}
33+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,121 @@
1+
package com.depromeet.whatnow.domains.picture.service
2+
3+
import com.depromeet.whatnow.common.vo.CoordinateVo
4+
import com.depromeet.whatnow.domains.picture.adapter.PictureAdapter
5+
import com.depromeet.whatnow.domains.picture.domain.PictureCommentType
6+
import com.depromeet.whatnow.domains.picture.exception.CancelledUserUploadException
7+
import com.depromeet.whatnow.domains.picture.exception.InvalidCommentTypeException
8+
import com.depromeet.whatnow.domains.picture.exception.UploadBeforeTrackingException
9+
import com.depromeet.whatnow.domains.promiseuser.adaptor.PromiseUserAdaptor
10+
import com.depromeet.whatnow.domains.promiseuser.domain.PromiseUser
11+
import com.depromeet.whatnow.domains.promiseuser.domain.PromiseUserType
12+
import org.assertj.core.api.Assertions
13+
import org.junit.jupiter.api.Test
14+
import org.junit.jupiter.api.extension.ExtendWith
15+
import org.mockito.ArgumentMatchers.anyLong
16+
import org.mockito.InjectMocks
17+
import org.mockito.Mock
18+
import org.mockito.junit.jupiter.MockitoExtension
19+
import org.mockito.kotlin.given
20+
21+
@ExtendWith(MockitoExtension::class)
22+
class PictureDomainServiceTest {
23+
@Mock
24+
lateinit var pictureAdapter: PictureAdapter
25+
26+
@Mock
27+
lateinit var promiseUserAdapter: PromiseUserAdaptor
28+
29+
@InjectMocks
30+
lateinit var pictureDomainService: PictureDomainService
31+
32+
@Test
33+
fun `사진 업로드 성공 요청시 정상적이라면 에러를 반환하지 않는다`() {
34+
// given
35+
val promiseUser = PromiseUser(
36+
promiseId = 1,
37+
userId = 1,
38+
userLocation = CoordinateVo(1.0, 1.0),
39+
promiseUserType = PromiseUserType.LATE,
40+
)
41+
given(promiseUserAdapter.findByPromiseIdAndUserId(anyLong(), anyLong()))
42+
.willReturn(promiseUser)
43+
44+
// when, then
45+
Assertions.assertThatCode {
46+
pictureDomainService.successUploadImage(1, 1, "imageKey", PictureCommentType.RUNNING)
47+
}.doesNotThrowAnyException()
48+
}
49+
50+
@Test
51+
fun `유저가 READY 상태라면 예외가 발생한다`() {
52+
// given
53+
val promiseUser = PromiseUser(
54+
promiseId = 1,
55+
userId = 1,
56+
userLocation = CoordinateVo(1.0, 1.0),
57+
promiseUserType = PromiseUserType.READY,
58+
)
59+
given(promiseUserAdapter.findByPromiseIdAndUserId(anyLong(), anyLong()))
60+
.willReturn(promiseUser)
61+
62+
// when, then
63+
Assertions.assertThatThrownBy {
64+
pictureDomainService.successUploadImage(1, 1, "imageKey", PictureCommentType.RUNNING)
65+
}.isInstanceOf(UploadBeforeTrackingException::class.java)
66+
}
67+
68+
@Test
69+
fun `유저가 CANCEL 상태라면 예외가 발생한다`() {
70+
// given
71+
val promiseUser = PromiseUser(
72+
promiseId = 1,
73+
userId = 1,
74+
userLocation = CoordinateVo(1.0, 1.0),
75+
promiseUserType = PromiseUserType.CANCEL,
76+
)
77+
given(promiseUserAdapter.findByPromiseIdAndUserId(anyLong(), anyLong()))
78+
.willReturn(promiseUser)
79+
80+
// when, then
81+
Assertions.assertThatThrownBy {
82+
pictureDomainService.successUploadImage(1, 1, "imageKey", PictureCommentType.RUNNING)
83+
}.isInstanceOf(CancelledUserUploadException::class.java)
84+
}
85+
86+
@Test
87+
fun `LATE 유저가 WAIT 타입의 코멘트를 입력 할 경우 예외가 발생한다`() {
88+
// given
89+
val promiseUser = PromiseUser(
90+
promiseId = 1,
91+
userId = 1,
92+
userLocation = CoordinateVo(1.0, 1.0),
93+
promiseUserType = PromiseUserType.LATE,
94+
)
95+
given(promiseUserAdapter.findByPromiseIdAndUserId(anyLong(), anyLong()))
96+
.willReturn(promiseUser)
97+
98+
// when, then
99+
Assertions.assertThatThrownBy {
100+
pictureDomainService.successUploadImage(1, 1, "imageKey", PictureCommentType.DID_YOU_COME)
101+
}.isInstanceOf(InvalidCommentTypeException::class.java)
102+
}
103+
104+
@Test
105+
fun `WAIT 유저가 LATE 타입의 코멘트를 입력 할 경우 예외가 발생한다`() {
106+
// given
107+
val promiseUser = PromiseUser(
108+
promiseId = 1,
109+
userId = 1,
110+
userLocation = CoordinateVo(1.0, 1.0),
111+
promiseUserType = PromiseUserType.WAIT,
112+
)
113+
given(promiseUserAdapter.findByPromiseIdAndUserId(anyLong(), anyLong()))
114+
.willReturn(promiseUser)
115+
116+
// when, then
117+
Assertions.assertThatThrownBy {
118+
pictureDomainService.successUploadImage(1, 1, "imageKey", PictureCommentType.WAIT_A_BIT)
119+
}.isInstanceOf(InvalidCommentTypeException::class.java)
120+
}
121+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
package com.depromeet.whatnow.config.s3
2+
3+
import com.depromeet.whatnow.config.InfraIntegrateSpringBootTest
4+
import org.junit.jupiter.api.Assertions.assertEquals
5+
import org.junit.jupiter.api.Test
6+
import org.springframework.beans.factory.annotation.Autowired
7+
8+
@InfraIntegrateSpringBootTest
9+
class S3PropertiesTest {
10+
@Autowired
11+
lateinit var s3Properties: S3Properties
12+
13+
@Test
14+
fun `s3 프로퍼티가 제대로 init 되어야한다`() {
15+
assertEquals(s3Properties.s3.endpoint, "https://kr.object.ncloudstorage.com")
16+
}
17+
}

0 commit comments

Comments
 (0)