Skip to content

Commit 2a0c0a8

Browse files
committed
Feat: Voucher를 헥사고날 아키텍처로 변경한다
1 parent 81c40e5 commit 2a0c0a8

File tree

39 files changed

+873
-43
lines changed

39 files changed

+873
-43
lines changed

build.gradle.kts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@ subprojects {
2929

3030

3131
dependencies {
32-
add("testRuntimeOnly", "org.junit.platform:junit-platform-launcher:1.13.3")
32+
add("testRuntimeOnly", "org.junit.platform:junit-platform-launcher")
3333
add("testImplementation", "io.mockk:mockk:1.13.13")
3434
}
3535
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
plugins {
2+
id("io.spring.dependency-management")
3+
id("org.springframework.boot")
4+
kotlin("jvm")
5+
kotlin("plugin.spring")
6+
kotlin("plugin.jpa")
7+
}
8+
9+
dependencies {
10+
implementation(project(":voucher-adapter"))
11+
12+
13+
implementation("org.springframework.boot:spring-boot-starter-web")
14+
implementation("org.springframework.boot:spring-boot-starter-data-jpa")
15+
16+
testImplementation("org.springframework.boot:spring-boot-starter-test")
17+
testImplementation("com.h2database:h2")
18+
testImplementation("io.rest-assured:rest-assured")
19+
20+
// 테스트에서 도메인 클래스 접근을 위해 필요
21+
testImplementation(project(":voucher-domain"))
22+
testImplementation(project(":voucher-application"))
23+
24+
25+
runtimeOnly("com.mysql:mysql-connector-j")
26+
27+
}
28+
29+
tasks.withType<Test> {
30+
useJUnitPlatform()
31+
}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
package app.payment
2+
3+
import org.springframework.boot.autoconfigure.SpringBootApplication
4+
import org.springframework.boot.runApplication
5+
6+
@SpringBootApplication(scanBasePackages = ["app.payment"])
7+
class PaymentApiApplication
8+
9+
fun main(args: Array<String>) {
10+
runApplication<PaymentApiApplication>(*args)
11+
}
Lines changed: 98 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,98 @@
1+
package app.payment.integration
2+
3+
import app.payment.voucher.adapter.outbound.VoucherJpaEntity
4+
import app.payment.voucher.adapter.outbound.VoucherJpaRepository
5+
import app.payment.voucher.adapter.outbound.VoucherContentJpaEntity
6+
import app.payment.voucher.adapter.outbound.VoucherContentJpaRepository
7+
import app.payment.voucher.domain.ConsumptionType
8+
import app.payment.voucher.domain.VoucherStatus
9+
import app.payment.voucher.domain.VoucherType
10+
import org.junit.jupiter.api.BeforeEach
11+
import org.junit.jupiter.api.Test
12+
import org.junit.jupiter.api.DisplayName
13+
import org.springframework.beans.factory.annotation.Autowired
14+
import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc
15+
import org.springframework.boot.test.context.SpringBootTest
16+
import org.springframework.test.context.ActiveProfiles
17+
import org.springframework.test.web.servlet.MockMvc
18+
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get
19+
import org.springframework.test.web.servlet.result.MockMvcResultMatchers.*
20+
import org.springframework.transaction.annotation.Transactional
21+
import java.time.OffsetDateTime
22+
23+
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
24+
@AutoConfigureMockMvc
25+
@ActiveProfiles("test")
26+
@Transactional
27+
class VoucherIntegrationTest {
28+
29+
@Autowired
30+
private lateinit var mockMvc: MockMvc
31+
32+
@Autowired
33+
private lateinit var voucherRepository: VoucherJpaRepository
34+
35+
@Autowired
36+
private lateinit var voucherContentRepository: VoucherContentJpaRepository
37+
38+
@BeforeEach
39+
fun setUp() {
40+
voucherContentRepository.deleteAll()
41+
voucherRepository.deleteAll()
42+
}
43+
44+
@Test
45+
@DisplayName("발행된 바우처와 컨텐츠를 함께 조회한다")
46+
fun `should get published vouchers with contents`() {
47+
// given
48+
val savedVoucher = voucherRepository.save(
49+
VoucherJpaEntity(
50+
id = null,
51+
type = VoucherType.AI_POSTER_GENERATE,
52+
consumptionType = ConsumptionType.SINGLE_USE,
53+
status = VoucherStatus.PUBLISHED
54+
// createdAt, updatedAt은 @CreatedDate, @LastModifiedDate가 자동 설정
55+
)
56+
)
57+
58+
voucherContentRepository.save(
59+
VoucherContentJpaEntity(
60+
id = null,
61+
voucherId = savedVoucher.id!!,
62+
version = 1,
63+
title = "테스트 바우처",
64+
description = "통합 테스트용 바우처입니다",
65+
activeFrom = OffsetDateTime.now().minusDays(1),
66+
activeUntil = OffsetDateTime.now().plusDays(30)
67+
// createdAt은 @CreatedDate가 자동 설정
68+
)
69+
)
70+
71+
// when & then
72+
mockMvc.perform(get("/api/v1/vouchers"))
73+
.andExpect(status().isOk)
74+
.andExpect(jsonPath("$.vouchers[0].title").value("테스트 바우처"))
75+
.andExpect(jsonPath("$.vouchers[0].description").value("통합 테스트용 바우처입니다"))
76+
.andExpect(jsonPath("$.vouchers[0].consumptionType").value("SINGLE_USE"))
77+
}
78+
79+
@Test
80+
@DisplayName("DRAFT 상태의 바우처는 조회되지 않는다")
81+
fun `should not return draft vouchers`() {
82+
// given
83+
voucherRepository.save(
84+
VoucherJpaEntity(
85+
id = null,
86+
type = VoucherType.AI_POSTER_PURCHASE,
87+
consumptionType = ConsumptionType.SUBSCRIPTION,
88+
status = VoucherStatus.DRAFT
89+
// createdAt, updatedAt은 @CreatedDate, @LastModifiedDate가 자동 설정
90+
)
91+
)
92+
93+
// when & then
94+
mockMvc.perform(get("/api/v1/vouchers"))
95+
.andExpect(status().isOk)
96+
.andExpect(jsonPath("$.vouchers").isEmpty())
97+
}
98+
}
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
spring:
2+
datasource:
3+
url: jdbc:h2:mem:testdb;MODE=MySQL
4+
driver-class-name: org.h2.Driver
5+
username: sa
6+
password:
7+
8+
jpa:
9+
hibernate:
10+
ddl-auto: create-drop
11+
properties:
12+
hibernate:
13+
format_sql: true
14+
show_sql: true
15+
dialect: org.hibernate.dialect.H2Dialect
16+
17+
h2:
18+
console:
19+
enabled: true
20+
21+
logging:
22+
level:
23+
app.payment: DEBUG
24+
org.springframework.web: DEBUG
25+
org.hibernate.SQL: DEBUG

payment/src/main/kotlin/app/payment/domain/voucher/ConsumptionType.kt

Lines changed: 0 additions & 6 deletions
This file was deleted.

payment/src/main/kotlin/app/payment/domain/voucher/Voucher.kt

Lines changed: 0 additions & 12 deletions
This file was deleted.

payment/src/main/kotlin/app/payment/domain/voucher/VoucherContent.kt

Lines changed: 0 additions & 14 deletions
This file was deleted.

payment/src/main/kotlin/app/payment/domain/voucher/VoucherStatus.kt

Lines changed: 0 additions & 8 deletions
This file was deleted.
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
plugins {
2+
kotlin("jvm")
3+
kotlin("plugin.spring")
4+
kotlin("plugin.jpa")
5+
id("io.spring.dependency-management")
6+
}
7+
8+
dependencies {
9+
implementation(project(":voucher-application"))
10+
implementation(project(":voucher-domain"))
11+
12+
13+
implementation("org.springframework.boot:spring-boot-starter-web")
14+
implementation("org.springframework.boot:spring-boot-starter-data-jpa")
15+
implementation("com.fasterxml.jackson.module:jackson-module-kotlin")
16+
implementation("org.jetbrains.kotlin:kotlin-reflect")
17+
18+
19+
// --- test ---
20+
testImplementation("org.springframework.boot:spring-boot-starter-test") {
21+
exclude(group = "org.mockito")
22+
}
23+
testImplementation("com.ninja-squad:springmockk:4.0.2")
24+
25+
}
26+
27+
tasks.withType<Test> {
28+
useJUnitPlatform()
29+
}

0 commit comments

Comments
 (0)