프로퍼티 데코레이터란
클래스의 프로퍼티에 적용되어 해당 프로퍼티의 동작을 제어할 수 있습니다. 값을 읽거나 설정할 때 추가 로직을 실행합니다. 사용하려면 tsconfig.json 파일이나 커맨드라인 옵션에서 experimentalDecorators를 활성화해야 합니다.
- target: 인스턴스 프로퍼티인 경우 클래스의 프로토타입, 정적 프로퍼티인 경우 생성자 함수입니다.
- propertyKey: 데코레이터가 적용된 속성의 이름
데코레이터 함수는 Object.defineProperty를 사용해 getter와 setter를 재정의할 수 있습니다.
데코레이터 예제
function LogValue(target: any, propertyKey: string) {
let storedValue: any;
const getter = () => storedValue;
const setter = (newValue: any) => {
console.log(`${propertyKey} 값이 ${storedValue}에서 ${newValue}로 변경됨`);
storedValue = newValue;
};
Object.defineProperty(target, propertyKey, {
get: getter,
set: setter,
enumerable: true,
configurable: true,
});
}
class Item {
@LogValue
public price: number;
constructor(price: number) {
this.price = price;
}
}
const item = new Item(1000);
console.log(item.price); // 출력: 1000
item.price = 1500; // 출력: price 값이 1000에서 1500로 변경됨
console.log(item.price); // 출력: 1500
@LogValue는 price 속성의 변경을 추적하며, 설정 시 로그를 남깁니다.
function LimitLength(maxLength: number) {
return (target: any, propertyKey: string) => {
let value: string;
const getter = () => value;
const setter = (newValue: string) => {
if (typeof newValue === "string" && newValue.length <= maxLength) {
value = newValue;
} else {
console.error(`${propertyKey}는 ${maxLength}자를 넘을 수 없습니다.`);
}
};
Object.defineProperty(target, propertyKey, {
get: getter,
set: setter,
enumerable: true,
configurable: true,
});
};
}
class Profile {
@LimitLength(10)
public nickname: string;
constructor(nickname: string) {
this.nickname = nickname;
}
}
const profile = new Profile("지훈");
console.log(profile.nickname); // 출력: 지훈
profile.nickname = "너무긴닉네임입니다"; // 출력: nickname는 10자를 넘을 수 없습니다.
console.log(profile.nickname); // 출력: 지훈 (변경 안 됨)
@LimitLength는 최대 길이를 설정하며, 초과 시 오류를 출력합니다.
function ReadOnly(target: any, propertyKey: string) {
let value: any;
Object.defineProperty(target, propertyKey, {
get: () => value,
set: (newValue) => {
if (value === undefined) value = newValue; // 초기 설정만 허용
},
enumerable: true,
configurable: true,
});
}
class Config {
@ReadOnly
public version: string;
constructor(version: string) {
this.version = version;
}
}
const config = new Config("1.0.0");
console.log(config.version); // 출력: 1.0.0
config.version = "2.0.0"; // 무시됨
console.log(config.version); // 출력: 1.0.0
@ReadOnly는 초기값 설정 후 변경을 막습니다.
'TypeScript' 카테고리의 다른 글
[TypeScript] 함수 타입 정의하기 (0) | 2025.02.26 |
---|---|
[TypeScript] 타입 좁히기(Narrowing): 타입을 안전하게 다루기 (1) | 2025.02.26 |
[TypeScript] 제네릭 인터페이스 (0) | 2025.02.26 |
[TypeScript] 인터페이스와 클래스 언제 사용할까? (1) | 2025.02.25 |
[TypeScript] 상속: 코드 재사용의 핵심 (0) | 2025.02.25 |