JavaScript Reflect API의 주요 메서드와 활용

JavaScript의 Reflect는 intercept 가능한 JavaScript 작업에 대한 메서드를 제공하는 내장 객체입니다. Math 객체와 유사하게 Reflect는 함수 객체가 아니며 생성자로 사용할 수 없습니다. 즉, new 연산자를 통해 인스턴스를 생성할 수 없으며 모든 메서드는 정적(static)으로 호출됩니다.

Reflect.apply()

대상 함수를 지정된 인수와 함께 호출합니다. 이는 Function.prototype.apply()와 유사한 역할을 수행합니다.

// Reflect.apply(target, thisArgument, argumentsList)

function greet(user) {
  return `안녕하세요, ${user}님!`;
}

// 기본 사용법
const message = Reflect.apply(greet, null, ['홍길동']);
console.log(message); // "안녕하세요, 홍길동님!"

// Math.max 활용 예시
const numbers = [10, 20, 30, 40];
const maxVal = Reflect.apply(Math.max, undefined, numbers);
console.log(maxVal); // 40

// String.prototype.includes 호출
const str = "Hello World";
const hasWorld = Reflect.apply(String.prototype.includes, str, ["World"]);
console.log(hasWorld); // true

Reflect.construct()

new 연산자와 동일한 기능을 수행합니다. 가변 인자를 사용하여 생성자를 호출할 때 유용합니다.

function Person(name, age) {
  this.name = name;
  this.age = age;
}

// new Person('Kim', 25)와 동일
const member = Reflect.construct(Person, ['Kim', 25]);
console.log(member.name); // "Kim"

// Array 생성 예시
const items = Reflect.construct(Array, [5]); // 길이가 5인 배열 생성
console.log(items.length); // 5

Reflect.defineProperty()

객체에 새로운 속성을 정의하거나 기존 속성을 수정합니다. Object.defineProperty()와 비슷하지만, 성공 여부를 Boolean으로 반환한다는 차이점이 있습니다.

const config = {};

if (Reflect.defineProperty(config, 'version', { value: '1.0.0', writable: false })) {
  console.log('속성 정의 성공');
} else {
  console.log('속성 정의 실패');
}

Reflect.deleteProperty()

객체의 속성을 삭제합니다. delete 연산자와 기능적으로 동일하며, 작업의 성공 여부를 논리값으로 반환합니다.

const session = { id: 1, token: 'abc' };

const success = Reflect.deleteProperty(session, 'token');
console.log(success); // true
console.log(session); // { id: 1 }

Reflect.get() 및 Reflect.set()

속성 값을 읽거나 설정합니다. 객체의 프로퍼티 접근자(obj[key])와 할당문 역할을 수행합니다.

const state = { count: 0 };

// 값 설정
Reflect.set(state, 'count', 10);

// 값 조회
const currentCount = Reflect.get(state, 'count');
console.log(currentCount); // 10

Reflect.has()

객체에 특정 속성이 존재하는지 확인합니다. in 연산자와 동일하게 작동합니다.

const meta = { title: 'JS Guide' };

console.log(Reflect.has(meta, 'title')); // true
console.log(Reflect.has(meta, 'author')); // false

Reflect.getPrototypeOf() 및 Reflect.setPrototypeOf()

객체의 프로토타입을 조회하거나 변경합니다. Object의 관련 메서드와 유사하지만 일관된 반환 형식을 제공합니다.

const proto = { base: true };
const instance = Object.create(proto);

console.log(Reflect.getPrototypeOf(instance) === proto); // true

const newProto = { base: false };
Reflect.setPrototypeOf(instance, newProto);
console.log(Reflect.getPrototypeOf(instance).base); // false

Reflect.ownKeys()

객체 자체의 모든 속성 키(문자열 및 Symbol 모두 포함)를 배열로 반환합니다. Object.getOwnPropertyNames()Object.getOwnPropertySymbols()를 합친 것과 같습니다.

const uniqueId = Symbol('id');
const metadata = {
  [uniqueId]: 101,
  tag: 'alpha'
};

Reflect.defineProperty(metadata, 'hidden', {
  value: 'secret',
  enumerable: false
});

// 모든 종류의 키를 추출
console.log(Reflect.ownKeys(metadata)); 
// Output: ["tag", "hidden", Symbol(id)]

Reflect.isExtensible() 및 Reflect.preventExtensions()

객체의 확장 가능 여부를 확인하거나 확장을 금지합니다.

const schema = { type: 'object' };

console.log(Reflect.isExtensible(schema)); // true

Reflect.preventExtensions(schema);
console.log(Reflect.isExtensible(schema)); // false

태그: JavaScript Reflect-API ES6 web-development Metaprogramming

7월 19일 21:04에 게시됨