리플렉션으로 개인 필드를 가져 오거나 설정하지 마십시오.
여기에 몇 가지 답변에서 반사를 사용하면 피할 수 있습니다.
여기에는 작은 단점이 있지만 여러 가지 단점이 있습니다.
- 런타임시에만 반사 문제를 감지합니다 (예 : 더 이상 존재하지 않는 필드)
- 우리는 캡슐화를 원하지만 보이지 않는 종속성을 숨기고 클래스를 더 불투명하고 테스트하기 어려운 불투명 클래스는 아닙니다.
- 나쁜 디자인을 장려합니다. 오늘은을 선언합니다
@Value String field
. 내일 당신은 그 클래스에서 5
또는 10
그것들을 선언 할 수 있으며 , 당신은 클래스의 디자인을 줄인다는 것을 정확히 알지 못할 수도 있습니다. 이러한 필드 (생성자와 같은)를 설정하는보다 가시적 인 접근 방법을 사용하면 이러한 필드를 모두 추가하기 전에 두 번 생각하고 다른 클래스로 캡슐화하여 사용할 것 @ConfigurationProperties
입니다.
수업을 단일 및 통합 테스트 가능
일반 단위 테스트 (스프링 컨테이너가 실행 중이 아님)와 Spring 컴포넌트 클래스에 대한 통합 테스트를 모두 작성하려면이 클래스를 Spring과 함께 또는없이 사용할 수 있어야합니다.
필요하지 않을 때 단위 테스트에서 컨테이너를 실행하면 로컬 빌드 속도가 느려지는 나쁜 습관이 있습니다.
나는이 대답을 추가하지 않았기 때문에이 대답을 추가했습니다. 따라서이 컨테이너는 체계적으로 실행중인 컨테이너에 의존합니다.
따라서이 속성을 클래스 내부로 정의해야한다고 생각합니다.
@Component
public class Foo{
@Value("${property.value}") private String property;
//...
}
Spring에 의해 주입 될 생성자 매개 변수에 :
@Component
public class Foo{
private String property;
public Foo(@Value("${property.value}") String property){
this.property = property;
}
//...
}
단위 테스트 예
Foo
Spring없이 인스턴스화 property
하고 생성자 덕분에 값을 삽입 할 수 있습니다 .
public class FooTest{
Foo foo = new Foo("dummyValue");
@Test
public void doThat(){
...
}
}
통합 테스트 예
다음과 같은 properties
속성 덕분에 Spring Boot를 사용하여 컨텍스트에 속성을 주입 할 수 있습니다 @SpringBootTest
.
@SpringBootTest(properties="property.value=dummyValue")
public class FooTest{
@Autowired
Foo foo;
@Test
public void doThat(){
...
}
}
대안으로 사용할 수 @TestPropertySource
있지만 추가 주석이 추가됩니다.
@SpringBootTest
@TestPropertySource("property.value=dummyValue")
public class FooTest{ ...}
Spring (Spring Boot없이)을 사용하면 조금 더 복잡해야하지만 오랫동안 Spring Boot없이 Spring을 사용하지 않았기 때문에 바보 같은 말을 선호하지 않습니다.
참고 사항 : @Value
설정할 필드 가 많은 경우 주석이 달린 클래스로 필드를 추출하는 @ConfigurationProperties
것이 더 관련이 있습니다. 인자가 너무 많은 생성자를 원하지 않기 때문입니다.