fix: MattermostRestClient 생성자 모호성으로 인한 Spring 빈 생성 실패 수정
생성자가 2개(공개 1-인자, 패키지 전용 2-인자)로 늘어나며 Spring의 단일 생성자 자동 선택 규칙이 더 이상 적용되지 않아, 기본 생성자를 찾지 못해 컨텍스트 리프레시 단계에서 BeanCreationException으로 애플리케이션 기동이 실패하고 있었다. 공개 1-인자 생성자에 @Autowired를 명시해 Spring이 이를 명확히 선택하도록 고쳤다. Spring 컨텍스트를 실제로 로딩해 MattermostClient 빈을 검증하는 테스트가 없어 이 회귀를 잡지 못했으므로, AbstractDbTest(신규 공통 베이스)와 이를 상속하는 MattermostRestClientSpringWiringTest를 추가해 재발을 방지한다.
@6f984d4895958b243c14e199d2b6346822eb28a8
--- src/main/java/kr/itn/itnhub/mattermost/MattermostRestClient.java
+++ src/main/java/kr/itn/itnhub/mattermost/MattermostRestClient.java
... | ... | @@ -2,6 +2,7 @@ |
| 2 | 2 |
|
| 3 | 3 |
import com.fasterxml.jackson.databind.JsonNode; |
| 4 | 4 |
import kr.itn.itnhub.config.MattermostProperties; |
| 5 |
+import org.springframework.beans.factory.annotation.Autowired; |
|
| 5 | 6 |
import org.springframework.http.MediaType; |
| 6 | 7 |
import org.springframework.stereotype.Component; |
| 7 | 8 |
import org.springframework.web.client.RestClient; |
... | ... | @@ -17,6 +18,7 @@ |
| 17 | 18 |
private final RestClient rest; |
| 18 | 19 |
private final String teamId; |
| 19 | 20 |
|
| 21 |
+ @Autowired |
|
| 20 | 22 |
public MattermostRestClient(MattermostProperties props) {
|
| 21 | 23 |
this(props, RestClient.builder()); |
| 22 | 24 |
} |
+++ src/test/java/kr/itn/itnhub/AbstractDbTest.java
... | ... | @@ -0,0 +1,34 @@ |
| 1 | +package kr.itn.itnhub; | |
| 2 | + | |
| 3 | +import org.springframework.boot.test.context.SpringBootTest; | |
| 4 | +import org.springframework.boot.testcontainers.service.connection.ServiceConnection; | |
| 5 | +import org.springframework.test.context.DynamicPropertyRegistry; | |
| 6 | +import org.springframework.test.context.DynamicPropertySource; | |
| 7 | +import org.testcontainers.containers.PostgreSQLContainer; | |
| 8 | +import org.testcontainers.junit.jupiter.Container; | |
| 9 | +import org.testcontainers.junit.jupiter.Testcontainers; | |
| 10 | + | |
| 11 | +/** | |
| 12 | + * Spring 컨텍스트를 실제로 로딩해야 하는 테스트의 공통 베이스. | |
| 13 | + * | |
| 14 | + * <p>Testcontainers PostgreSQL 컨테이너를 띄우고, 애플리케이션 구동에 필요한 | |
| 15 | + * {@code mattermost.*} / {@code app.admin.*} 필수 프로퍼티를 더미 값으로 채워 | |
| 16 | + * 컨텍스트 리프레시가 실제 외부 시스템 없이도 성공하도록 한다.</p> | |
| 17 | + */ | |
| 18 | +@SpringBootTest | |
| 19 | +@Testcontainers | |
| 20 | +public abstract class AbstractDbTest { | |
| 21 | + | |
| 22 | + @Container | |
| 23 | + @ServiceConnection | |
| 24 | + static PostgreSQLContainer<?> postgres = new PostgreSQLContainer<>("postgres:16"); | |
| 25 | + | |
| 26 | + @DynamicPropertySource | |
| 27 | + static void secrets(DynamicPropertyRegistry registry) { | |
| 28 | + registry.add("app.admin.username", () -> "admin"); | |
| 29 | + registry.add("app.admin.password", () -> "test-password"); | |
| 30 | + registry.add("mattermost.base-url", () -> "http://localhost:1"); | |
| 31 | + registry.add("mattermost.token", () -> "test-token"); | |
| 32 | + registry.add("mattermost.team-id", () -> "test-team"); | |
| 33 | + } | |
| 34 | +} |
+++ src/test/java/kr/itn/itnhub/mattermost/MattermostRestClientSpringWiringTest.java
... | ... | @@ -0,0 +1,28 @@ |
| 1 | +package kr.itn.itnhub.mattermost; | |
| 2 | + | |
| 3 | +import kr.itn.itnhub.AbstractDbTest; | |
| 4 | +import org.junit.jupiter.api.Test; | |
| 5 | +import org.springframework.beans.factory.annotation.Autowired; | |
| 6 | + | |
| 7 | +import static org.assertj.core.api.Assertions.assertThat; | |
| 8 | + | |
| 9 | +/** | |
| 10 | + * {@link MattermostRestClient}가 Spring 컨테이너에 의해 실제로 생성될 수 있는지 검증한다. | |
| 11 | + * | |
| 12 | + * <p>{@link MattermostRestClientTest}는 {@code new}로 직접 생성하기 때문에 생성자가 | |
| 13 | + * 여러 개일 때 Spring이 어떤 생성자를 선택할지(혹은 선택하지 못해 컨텍스트 로딩에 | |
| 14 | + * 실패하는지)를 전혀 검증하지 못한다. 이 테스트는 실제 ApplicationContext를 띄워 | |
| 15 | + * 빈 생성 단계에서 생성자 모호성으로 인한 회귀를 잡아낸다.</p> | |
| 16 | + */ | |
| 17 | +class MattermostRestClientSpringWiringTest extends AbstractDbTest { | |
| 18 | + | |
| 19 | + @Autowired | |
| 20 | + private MattermostClient mattermostClient; | |
| 21 | + | |
| 22 | + @Test | |
| 23 | + void MattermostClient_빈이_Spring에_의해_정상_생성된다() { | |
| 24 | + assertThat(mattermostClient) | |
| 25 | + .isNotNull() | |
| 26 | + .isInstanceOf(MattermostRestClient.class); | |
| 27 | + } | |
| 28 | +} |
Add a comment
Delete comment
Once you delete this comment, you won't be able to recover it. Are you sure you want to delete this comment?