리플렉션이란 ?
구체적인 클래스 타입을 알지 못해도 런타임에 클래스, 인터페이스, 필드, 메서드 등을 검사하거나 수정할 수 있는 자바의 강력한 기능을 말한다.
리플렉션이란, 거울이라는 뜻을 가지고 있는데 거울과 같이 객체 내부 구조를 들여다보고 조작하는 것과 같다. 일반적으로 코드는 컴파일 시점에 타입이 결정되지만, 리플렉션은 실행 중인 애플리케이션의 메타데이터에 접근하여 동작을 제어한다.
jvm에서 학습했듯이 클라스 파일을 로드할 때, 해당 클래스의 정보를 담은 Class 객체를 생성하여 heap 메모리에 저장한다. 리플렉션을 이 객체를 통해 해당 클래서의 정보를 가져온다.
| 구분 | 내용 |
| 장점 | 유연성: 컴파일 시점에 타입을 몰라도 동적으로 객체를 생성하고 실행할 수 있다. 확장성: 프레임워크(Spring, Hibernate)나 라이브러리 개발 시 필수적. |
| 단점 | 성능 저하: JVM의 최적화를 방해하며, 일반적인 메서드 호출보다 속도가 느리다. 보안 취약점: private 멤버에 접근할 수 있어 캡슐화를 깨뜨릴 수 있다. 컴파일 에러 미발생: 런타임에 에러가 발생하므로 디버깅이 어렵다. |
실제 예시
- Spring Framework: @Service, @Component 같은 어노테이션이 붙은 클래스를 찾아 자동으로 객체를 생성(DI)할 때 사용.
- JUnit: 테스트 클래스 내에서 @Test 어노테이션이 붙은 메서드들을 찾아 실행할 때 사용.
- IntelliJ / Eclipse: 코드 자동 완성 기능을 제공하기 위해 클래스의 메서드와 필드 정보를 읽어올 때 사용.
취약점
- 자바의 핵심 원칙인 캡슐화(Encapsulation)를 무력화할 수 있음.
- private 멤버 강제 접근: field.setAccessible(true) 코드를 한 줄만 추가하면, 외부에서 절대 접근할 수 없어야 하는 private 필드나 메서드에 접근하고 값을 수정할 수 있음
- 코드 주입 위험: 외부 사용자로부터 클래스 이름이나 메서드 이름을 입력받아 리플렉션을 수행할 경우, 공격자가 의도하지 않은 시스템 명령(java.lang.Runtime)을 실행하거나 악성 클래스를 로드하여 실행하는 원격 코드 실행(RCE) 공격에 노출될 수 있음.
- 컴파일 시점에는 오류를 잡을 수 없어서 Runtime Exception 발생할 수 있음.
* 자바 9 버전부터, 리플렉션을 통핸 내부 api접근을 제한하고 있다.
활용
① 프레임워크나 라이브러리 개발
② 테스트 코드 작성 시
③ *동적 프록시(Dynamic Proxy) 생성
*cf. Spring AOP와의 연결고리
@Transactional 어노테이션이 대표적인 예
스프링은 리플렉션으로 이 어노테이션을 확인하고, 해당 빈(Bean)을 동적 프록시 객체로 바꿔치기.
-> 메서드가 호출되면 프록시가 먼저 connection.setAutoCommit(false)를 호출(트랜잭션 시작)하고, 실제 로직이 끝나면 commit()을 호출. 개발자는 트랜잭션 코드를 한 줄도 안 써도 된다.
'Java' 카테고리의 다른 글
| [Java] static - 2 (0) | 2026.01.18 |
|---|---|
| [Java] static class와 static method (0) | 2026.01.16 |
| [Java] 인터페이스와 추상클래스 (0) | 2026.01.10 |
| [Java] 객체지향 - final 2 (0) | 2026.01.09 |
| [Java] 객체지향 (0) | 2026.01.08 |