JavaScript:Object
Object prorotype
JavaScript에서 모든 객체들은 Object
의 자손입니다. 모든 객체는 Object.prototype
으로부터 메서드와 속성을 상속하는데, 나중에 덮어 쓸(Overriding) 수도 있습니다.
-
Object.prototype.toString()
- 객체의 문자열 표현을 반환합니다.
defineProperty
Object.defineProperty()
정적 메서드는 객체에 직접 새로운 속성을 정의하거나 이미 존재하는 속성을 수정한 후, 그 객체를 반환합니다.
Key/Values/Entries
- Object.keys, values, entries
-
Object.keys(obj)
– 키가 담긴 배열을 반환합니다. -
Object.values(obj)
– 값이 담긴 배열을 반환합니다. -
Object.entries(obj)
–[key, value]
쌍이 담긴 배열을 반환합니다.
Troubleshooting
Object prototype mismatch
- Stackoverflow - Typescript - Extending Error class
- TypeScript-wiki/Breaking-Changes.md at main · microsoft/TypeScript-wiki
다음과 같은 클래스가 있을 때,
class CustomError extends Error {
constructor(message: string) {
super(`Lorem "${message}" ipsum dolor.`);
this.name = 'CustomError';
}
}
throw new CustomError('foo');
예상되는 출력은 Uncaught CustomError: Lorem "foo" ipsum dolor.
이지만, 실제 출력은 Uncaught Error: Lorem "foo" ipsum dolor.
이다.
이 경우, tsconfig.json에서 target
이 es5
되어있지 않나 확인해 보자. ES5에서 관련 이슈가 있다. 이를 해결하기 위해, 생성자에서 super(...)
호출 직후 프로토타입을 수동으로 조정해야 한다.
class CustomError extends Error {
constructor(message?: string) {
// 'Error' breaks prototype chain here
super(message);
// restore prototype chain
const actualProto = new.target.prototype;
if (Object.setPrototypeOf) {
Object.setPrototypeOf(this, actualProto);
} else {
this.__proto__ = actualProto;
}
}
}
-
Object.setPrototypeOf
를 지원하지 않는 런타임의 경우 대신__proto__
를 사용하도록 조정해야 한다. - 불행히도 이러한 해결 방법은 Internet Explorer 10 및 이전 버전에서 작동하지 않습니다. 프로토타입에서 인스턴스 자체로 메소드를 수동으로 복사할 수 있지만(i.e.
FooError.prototype
onto this) 프로토타입 체인 자체는 수정할 수 없습니다. - 이렇게 수정한 모든 하위 클래스도 수동으로 프로토타입을 설정해야 합니다. <- (가장 큰 문제)
차라리 간단하게. tsconfig.json의 target
버전을 높이자. 나는 esnext
로 했다. 어차피 babel이 호환성 작업 알아서 해주겠지...