목표
자바의 애노테이션에 대해 학습하세요.
학습할 것 (필수)
- 애노테이션 정의하는 방법
- @retention
- @target
- @documented
- 애노테이션 프로세서
마감일시
2021년 2월 6일 토요일 오후 1시까지.
애노테이션이란?
애노테이션, 즉 Annotation은 클래스나 메소드 선언 시에 @ 를 사용하는 것을 말한다. Annotation은 어노테이션, 애노테이션, 메타데이터(Metadata) 등으로 불린다. Jdk 5부터 등장했다.
애노테이션의 사용
- 컴파일러에게 정보를 알려주기
- 컴파일할 때와 설치시의 작업 지정
- 실행할 때 별도의 처리가 필요할 때
애노테이션은 클래스, 메소드, 변수 등 모든 요소에 선언 가능하다.
java.lang.annotion
안에 들어있다.
애노테이션의 용도
( 용도를 나타내기 위한 것일뿐이다. 스프링 애노테이션이 들어갈 수 있으니, 단순한 참고만을 부탁한다)
- 제약사항 등을 선언하기 위해:
@Deprecated
,@Override
,@NotNull
- 용도를 나타내기:
@Entity
,@TestCase
,@WebService
- 행위를 나타내기:
@Statefull
,@Transaction
- 처리를 나타내기:
@Column
,@XmlElement
애노테이션 정의하는 방법
애노테이션을 정의하는 방법은 사용하려는 클래스 혹은 메소드 앞에 애노테이션을 붙여주면된다.
package com.livestudy.twelveth;
import study.Car;
public class AnnotationTest implements Car {
@Override
public boolean isHybrid() {
return false;
}
}
애노테이션의 종류
자바 언어에서 사용하기 위해 정해진 애노테이션은 3개가 있고, 어노테이션을 선언하기 위한 메타 애노테이션이 4개가 있다.
자바 SDK 에서 지원하는 애노테이션이다.
@Override
: 해당 메소드가 상위 클래스의 메소드를 오버라이드하고 있다는 것을 컴파일러에게 명시적으로 알려주는 애노테이션@Deprecated
: 마커 애노테이션. 차후 버전이 지원되지 않아 더이상 사용을 지양할 것을 권장하는 어노테이션.- 물론 경고일 뿐, 에러는 아니다.
- 컴파일 시 deprecated message를 확인하기 위해서는
-Xlint:deprecation
옵션을 이용한다. - 이 기능을 사용하는 개발자들에게 경고를 보여줄 수 있고, 향 후 사용을 검토중인 개발자에게 사용을 지양하게 할 수 있다.
@SuppressWarning
: 경고를 제거하는 애노테이션-Xlint:deprecation
옵션을 이용해도 경고가 나오지 않게 된다.
애노테이션을 선언하기 위한 메타 애노테이션
애노테이션을 선언할 때 사용하는 애노테이션이다.
메타애노테이션의 종류는 @Target
, @Retention
,@Documented
,@Inherited
가 있다.
@Target
@Target
애노테이션은 자바 컴파일러가 애노테이션이 어디에 적용될 지 결정하기 위해 사용한다.
@Target(ElemType.요소)
형식으로 사용되고, 다음과 같은 요소가 들어갈 수 있다.
- CONSTRUCTOR: 생성자 선언 시
- FIELD: enum 상수를 포함한 필드 값 선언 시
- LOCAL_VARIABLE: 지역변수 선언 시
- METHOD: 메소드 선언 시
- PACKAGE: 패키지 선언 시
- PARAMETER: 매개 변수 선언 시
- TYPE: 클래스, 인터페이스, Enum 등 선언시
@Target(ElementType.FIELD)
@Retention
얼마나 오래 애노테이션 정보가 유지되는지를 선언한다.
@Retention(RetentionPolicy.RUNTIME)
괄호 안에 지정하는 적용가능한 대상은 다음과 같다.
- SOURCE: 애노테이션 정보가 컴파일 시 사라진다.
- CLASS: 클래스 파일에 있는 애노테이션 정보가 컴파일러에 의해 참조가능하다. 하지만, JVM 에서는 사라진다.
- RUNTIME: 실행시 애노테이션 정보가 가상 머신에 의해서 참조 가능하다.
@Documented
해당 어노테이션에 대한 정보가 Javadocs API 문서에 포함된다는 것을 선언한다.
@Inherited
@Inherited
애노테이션은 애노테이션을 사용한 상위 클래스를 상속한 하위 클래스에서도 해당 애노테이션을 갖도록 하기 위해 사용한다.
추가적으로
@interface
라는 애노테이션을 알아둬야 한다. 이 애노테이션은 애노테이션을 선언할 때 사용한다.
애노테이션을 선언해보자
package hello.core.order;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.METHOD) // 해당 어노테이션 사용 대상. 이 어노테이션은 메소드에서 사용가능
@Retention(RetentionPolicy.RUNTIME) // 어노테이션 유지 정보. 이 어노테이션은 실행시에 이것을 참조한다.
public @interface UserAnnotation {
public int number();
public String text() default "This is annotation";
// default 예약어. 이 이어노테이션을 사용할때, 기본값을 지정 가능/
}
import java.lang.reflect.Method;
public class UserAnnotationSample {
@UserAnnotation(number = 3)
public static void main(String[] args) {
UserAnnotationSample test = new UserAnnotationSample();
test.checkAnnotations(UserAnnotationSample.class);
}
private void checkAnnotations(Class useClass) {
Method[] methods = useClass.getDeclaredMethods(); // 리플렉션 API 를 활용해 내가 선언한 어노테이션 정보를 확인가능하다
for (Method method : methods) {
UserAnnotation userAnnotation = method.getAnnotation(UserAnnotation.class);
if (userAnnotation != null) {
int number = userAnnotation.number();
String text = userAnnotation.text();
System.out.println(method.getName() + ": " + number + " " + text);
}
}
}
}
애노테이션은 상속이 안된다.
enum 클래스가 상속을 지원하지 않는 것 처럼 애노테이션을 선언할 때에도 확장이 불가능하다. 즉, extends
예약어를 사용할 수 없다.
애노테이션 프로세서
- 자바 컴파일러의 컴파일 단계에서, 유저가 정의한 어노테이션의 소스코드를 분석하고 처리하기 위해 사용되는 훅이다. 컴파일 에러나 컴파일 경고를 만들어 내거나, 소스코드(.java)와 바이트코드(.class)를 내보내기도 한다
어노테이션 프로세서 사용 예제
- Lombok
- AutoService : java.util.ServiceLoader 용 파일 생성 유틸리티
- @Override
- Dangger 2 : 컴파일 타임 DI 제공
어노테이션 프로세서 장점
- 런타임 비용이 없음(컴파일 타임에 조작이 완료된 상황이기 때문에)
어노테이션 프로세싱의 애플리케이션
- 소스 레벨 어노테이션 프로세싱은 Java5부터 나타났다. 이는 컴파일 단계에서 추가 소스 파일을 생성하는 편리한 기술이다
- 소스 파일이 Java 파일 일 필요는 없다. 소스 코드의 어노테이션을 기반으로 모든 종류의 설명, 메타 데이터, 문서, 리소스 또는 기타 모든 유형의 파일을 생성할 수 있다.
- 중요한 점은 어노테이션 프로세서 API의 한계이다. 기존 파일을 변경하지 않고 새 파일을 생성하는 데만 사용할 수 있다.
참고 문헌
https://velog.io/@zayson/백기선님과-함께하는-Live-Study-12주차-애노테이션
https://b-programmer.tistory.com/264
자바의 신
andole98.github.io/java/java-annotation-process/#
medium.com/@jintin/annotation-processing-in-java-3621cb05343a
https://lob-dev.tistory.com/entry/Live-StudyWeek-12-Annotation
'스프링, 자바' 카테고리의 다른 글
자바의 I.O (0) | 2021.02.20 |
---|---|
자바의 맵 (0) | 2021.02.19 |
자바의 제네릭 (2) | 2021.02.03 |
스프링 핵심 원리 -기본편 (0) | 2021.02.02 |
김영한 강사님의 스프링 입문 나머지 (0) | 2021.01.31 |