자바스크립트 속성 숨기기
아래와 같이 인스턴스를 만들어보았다
아래 인스턴스에서는 _color는 외부에서 접근이 불가능하게 하고싶지만 가능한 상황이다
ZnVuY3Rpb24gTXlTdHJ1Y3R1cmUoKSB7CiAgIHRoaXMuX2NvbG9yOyAvLyBQcml2YXRlIO2VmOqyjCDsgqzsmqntlZjqs6DtlIgg67OA7IiY7J207KeA66eMIG1zLl9jb2xvciDroZwg7KCR6re87J20IOqwgOuKpQogICB0aGlzLmVsZW1lbnQgPSBkb2N1bWVudC5jcmVhdGVFbGVtZW50KCdkaXYnKTsKICAgdGhpcy5zZXRfY29sb3IgPSBjb2xvciA9PiB7CiAgICAgIHRoaXMuX2NvbG9yID0gY29sb3I7IC8vIO2ZlOyCtO2RnO2VqOyImOyViOyXkOyEnCB0aGlz66W8IOyngOy5re2VmOuptCDsg4HsnITsiqTsvZTtlITsnZggdGhpc+ulvCDqsIDrpqztgqTqsozrkKgKICAgICAgdGhpcy5lbGVtZW50LmlubmVyVGV4dCA9IGNvbG9yOwogICAgICB0aGlzLmVsZW1lbnQuc3R5bGUuYmFja2dyb3VuZCA9IGNvbG9yOwogICB9OwogICB0aGlzLmdldF9jb2xvciA9ICgpID0+IHRoaXMuX2NvbG9yOwp9CmxldCBtcyA9IG5ldyBNeVN0cnVjdHVyZSgpOwpkb2N1bWVudC5ib2R5LmFwcGVuZENoaWxkKG1zLmVsZW1lbnQpOwptcy5zZXRfY29sb3IoJ3llbGxvdycpOwpjb25zb2xlLmxvZyhtcy5nZXRfY29sb3IoKSk7CmNvbnNvbGUubG9nKG1zLl9jb2xvcik7IC8vIOygkeq3vCDqsIDriqU=
function MyStructure() {
this._color; // Private 하게 사용하고픈 변수이지만 ms._color 로 접근이 가능
this.element = document.createElement('div');
this.set_color = color => {
this._color = color; // 화살표함수안에서 this를 지칭하면 상위스코프의 this를 가리키게됨
this.element.innerText = color;
this.element.style.background = color;
};
this.get_color = () => this._color;
}
let ms = new MyStructure();
document.body.appendChild(ms.element);
ms.set_color('yellow');
console.log(ms.get_color());
console.log(ms._color); // 접근 가능
그래서 아래와 같이 바꾸어보았다
인스턴스 안에 내부적으로 privates 라는 변수를 만들고 이 안에 {}를 담았다
이 privates변수는 인스턴스의 프로퍼티는 아니다.
즉 instance.privates 이런식으로 접근할 수 없다.
따라서 privates의 속성으로써 외부에서 접근을 하지 않기를 바라는 속성들을 여기에 담는 방법으로 Private함을 구현할 수 있다.
ZnVuY3Rpb24gTXlTdHJ1Y3R1cmUyKCkgewogICBjb25zdCBwcml2YXRlcyA9IHt9OyAvLyBQcml2YXRlIO2VnCDrs4DsiJjrpbwg64u07J2EIOqwneyytCBtczIucHJpdmF0ZXMg7J2065+w7Iud7Jy866GcIOygkeq3vOydtCDrtojqsIDriqUKICAgdGhpcy5lbGVtZW50ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7IC8vIG1zMi5lbGVtZW50IOydtOufsOyLneycvOuhnCDsoJHqt7zsnbQg6rCA64qlCiAgIHRoaXMuc2V0X2NvbG9yID0gY29sb3IgPT4gewogICAgICBwcml2YXRlcy5jb2xvciA9IGNvbG9yOyAvLyDsiqTsvZTtlITssrTsnbjsnYQg65Sw65287IScIO2YhCDsiqTsvZTtlITsl5AgcHJpdmF0ZXPqsIAg7KG07J6s7ZWY7KeAIOyViuycvOuLiCDsg4HsnITsiqTsvZTtlITsl5Ag7J6I64qUIHByaXZhdGVz66W8IOywuOyhsO2VmOqyjCDrkKgKICAgICAgdGhpcy5lbGVtZW50LmlubmVyVGV4dCA9IGNvbG9yOyAvLyDtmZTsgrTtkZztlajsiJjslYjsl5DshJwgdGhpc+ulvCDsp4Dsua3tlZjrqbQg7IOB7JyE7Iqk7L2U7ZSE7J2YIHRoaXPrpbwg6rCA66as7YKk6rKM65CoCiAgICAgIHRoaXMuZWxlbWVudC5zdHlsZS5iYWNrZ3JvdW5kID0gY29sb3I7CiAgIH07CiAgIHRoaXMuZ2V0X2NvbG9yID0gKCkgPT4gcHJpdmF0ZXMuY29sb3I7Cn0KbGV0IG1zMiA9IG5ldyBNeVN0cnVjdHVyZTIoKTsKZG9jdW1lbnQuYm9keS5hcHBlbmRDaGlsZChtczIuZWxlbWVudCk7Cm1zMi5zZXRfY29sb3IoJ2dyZWVuJyk7CmNvbnNvbGUubG9nKG1zMi5nZXRfY29sb3IoKSk7CmNvbnNvbGUubG9nKG1zMi5jb2xvcik7IC8vIOygkeq3vCDrtojqsIDriqU=
function MyStructure2() {
const privates = {}; // Private 한 변수를 담을 객체 ms2.privates 이런식으로 접근이 불가능
this.element = document.createElement('div'); // ms2.element 이런식으로 접근이 가능
this.set_color = color => {
privates.color = color; // 스코프체인을 따라서 현 스코프에 privates가 존재하지 않으니 상위스코프에 있는 privates를 참조하게 됨
this.element.innerText = color; // 화살표함수안에서 this를 지칭하면 상위스코프의 this를 가리키게됨
this.element.style.background = color;
};
this.get_color = () => privates.color;
}
let ms2 = new MyStructure2();
document.body.appendChild(ms2.element);
ms2.set_color('green');
console.log(ms2.get_color());
console.log(ms2.color); // 접근 불가능
덤으로 set_color, get_color 함수의 사용방식을 아래서처럼 마치 프로퍼티에 접근하듯 사용하는 방식으로 바꿔 볼수있다
ZnVuY3Rpb24gTXlTdHJ1Y3R1cmUzKCkgewogICBjb25zdCBwcml2YXRlcyA9IHt9OyAvLyBQcml2YXRlIO2VnCDrs4DsiJjrpbwg64u07J2EIOqwneyytCBtczMucHJpdmF0ZXMg7J2065+w7Iud7Jy866GcIOygkeq3vOydtCDrtojqsIDriqUKICAgdGhpcy5lbGVtZW50ID0gZG9jdW1lbnQuY3JlYXRlRWxlbWVudCgnZGl2Jyk7IC8vIG1zMy5lbGVtZW50IOydtOufsOyLneycvOuhnCDsoJHqt7zsnbQg6rCA64qlCiAgIE9iamVjdC5kZWZpbmVQcm9wZXJ0eSh0aGlzLCAnY29sb3InLCB7CiAgICAgIGVudW1lcmFibGU6IGZhbHNlLCAvLyBmYWxzZeuhnCDtlZjqsowg65CY66m0IE9iamVjdC5rZXlzKG1zMykg66W8IO2WiOydhOuVjCBjb2xvcuqwgCDtj6ztlajrkJjsp4Ag66q77ZWoCiAgICAgIGNvbmZpZ3VyYWJsZTogZmFsc2UsIC8vIGZhbHNl66GcIO2VmOqyjCDrkJjrqbQgZGVsZXRlIG1zMy5jb2xvciDrpbwg7Ya17ZW0IOygnOqxsO2VmOyngCDrqrvtlagKICAgICAgc2V0KGNvbCkgeyAvLyBtczMuY29sb3IgPSAnY3lhbicg7J2065286rOgIO2VmOqyjOuQmOuptCDrp6TqsJzrs4DsiJggY29s7J20ICdjeWFuJ+ydtCDrkKgKICAgICAgICAgcHJpdmF0ZXMuY29sb3IgPSBjb2w7IC8vIOyKpOy9lO2UhOyytOyduOydhCDrlLDrnbzshJwg7ZiEIOyKpOy9lO2UhOyXkCBwcml2YXRlc+qwgCDsobTsnqztlZjsp4Ag7JWK7Jy864uIIOyDgeychOyKpOy9lO2UhOyXkCDsnojripQgcHJpdmF0ZXPrpbwg7LC47KGw7ZWY6rKMIOuQqAogICAgICAgICB0aGlzLmVsZW1lbnQuaW5uZXJUZXh0ID0gY29sOyAvLyDsl6zquLDshJwgdGhpcyDrnbwg7ZWo7J2AIG1zM+ydhCDsnZjrr7jtlZjqsowg65CoCiAgICAgICAgIHRoaXMuZWxlbWVudC5zdHlsZS5iYWNrZ3JvdW5kID0gY29sOwogICAgICB9LAogICAgICBnZXQoKSB7IC8vIGNvbnNvbGUubG9nKG1zMy5jb2xvcikg7J2065+w7Iud7Jy866GcIOywuOyhsOulvCDtlZjqsozrkKDrlYwg7J20IO2VqOyImOqwgCDsi6TtlonrkJjqsowg65CoCiAgICAgICAgIHJldHVybiBwcml2YXRlcy5jb2xvcjsKICAgICAgfSwKICAgfSk7Cn0KbGV0IG1zMyA9IG5ldyBNeVN0cnVjdHVyZTMoKTsKZG9jdW1lbnQuYm9keS5hcHBlbmRDaGlsZChtczMuZWxlbWVudCk7Cm1zMy5jb2xvciA9ICdjeWFuJzsgLy8gc2V0KCkg7ZWo7IiY6rCAIOyLpO2WieuQqC4g7Iuk7ZaJ65Co7JeQIOuUsOudvCBlbGVtZW507J2YIOyKpO2DgOydvOuzgOqyveuPhCDtlajqu5gg7IiY7ZaJ7ZWoCmNvbnNvbGUubG9nKG1zMy5jb2xvcik7IC8vIGdldCgpIO2VqOyImOqwgCDsi6TtlonrkKjsl5Ag65Sw6528IHByaXZhdGVzLmNvbG9yIOulvCDrpqzthLTrsJvsnYwuIHByaXZhdGVz64qUIOyZuOu2gOyXkOyEnCBtczMucHJpdmF0ZXMg7J2065+w7Iud7Jy866GcIOygkeq3vCDsp4HsoJHrtojqsIDriqUKY29uc29sZS5sb2coT2JqZWN0LmtleXMobXMzKSk7IC8vIGVsZW1lbnTrp4wg7ZmV7J2465CoLiBPYmplY3QuZGVmaW5lZFByb3BlcnR57JeQ7IScIGVudW1lcmFibGXrpbwgdHJ1ZeuhnCDtlZjrqbQgY29sb3Lrj4Qg7ZmV7J2465CY6rKMIOuQqA==
function MyStructure3() {
const privates = {}; // Private 한 변수를 담을 객체 ms3.privates 이런식으로 접근이 불가능
this.element = document.createElement('div'); // ms3.element 이런식으로 접근이 가능
Object.defineProperty(this, 'color', {
enumerable: false, // false로 하게 되면 Object.keys(ms3) 를 했을때 color가 포함되지 못함
configurable: false, // false로 하게 되면 delete ms3.color 를 통해 제거하지 못함
set(col) { // ms3.color = 'cyan' 이라고 하게되면 매개변수 col이 'cyan'이 됨
privates.color = col; // 스코프체인을 따라서 현 스코프에 privates가 존재하지 않으니 상위스코프에 있는 privates를 참조하게 됨
this.element.innerText = col; // 여기서 this 라 함은 ms3을 의미하게 됨
this.element.style.background = col;
},
get() { // console.log(ms3.color) 이런식으로 참조를 하게될때 이 함수가 실행되게 됨
return privates.color;
},
});
}
let ms3 = new MyStructure3();
document.body.appendChild(ms3.element);
ms3.color = 'cyan'; // set() 함수가 실행됨. 실행됨에 따라 element의 스타일변경도 함께 수행함
console.log(ms3.color); // get() 함수가 실행됨에 따라 privates.color 를 리턴받음. privates는 외부에서 ms3.privates 이런식으로 접근 직접불가능
console.log(Object.keys(ms3)); // element만 확인됨. Object.definedProperty에서 enumerable를 true로 하면 color도 확인되게 됨