26/05/28 IL (I Learned)

1. 🌐 window

자바스크립트 최상위 전역 객체인 window
우리가 쓰는 alert(), setTimeout(), 그리고 HTML 문서를 다루는 document까지 전부 이 window라는 객체의 주머니 속에 들어있다.

console.log(this); // 브라우저 환경에선 이게 바로 window 객체
window.alert("안녕"); // 원래는 이렇게 써야 하지만
alert("안녕"); // 전역 객체라서 window. 을 생략해도 브라우저가 다 알아듣는다.

2. DOM (Document Object Model): HTML을 객체 트리로 바꾼 지도

브라우저는 텍스트로 된 HTML 파일을 읽으면, 자바스크립트가 알아들을 수 있는 객체(Object)들의 거대한 나무 트리 구조로 메모리에 다시 그린다. 이게 바로 DOM이다.

과거에 쓰던 getElementsByClassName 같은 구식 API는 브라우저 상태가 바뀔 때마다 값이 실시간으로 변해서 버그를 만들기 쉬웠다. 이제는 CSS 선택자 문법을 그대로 쓰는 querySelector 시리즈가 표준이다.

const p1 = document.querySelector("p"); 
// -> 문서 전체에서 '가장 먼저 나오는 딱 하나의 p 태그'만 가져옴

const p4 = document.querySelectorAll(".job"); 
// -> 클래스명이 'job'인 모든 p 태그들을 묶어서 NodeList라는 주머니에 담아줘
// 주머니 통째로는 다루기 힘드니 p4[0], p4[1]처럼 인덱스로 꺼내 쓰거나 
// ...p4 (스프레드 연산자)로 알맹이만 풀어서 쓴다.

textContent vs innerHTML (보안의 핵심)

자바스크립트로 화면에 글자를 집어넣을 때, 무심코 innerHTML을 쓰면 대형 사고가 날 수 있다.

// ❌ 위험한 코드
box.innerHTML = `<button>클릭</button>`;

innerHTML은 사용자가 입력한 문자열에 <script>onclick 같은 위험한 HTML 마크업이 섞여 있어도 그걸 그대로 브라우저에 실행시켜 버린다. (이걸 XSS 공격이라고 한다.)

box.textContent = content;

반면 textContent는 주입된 문자열을 단순 '텍스트'로만 취급한다. 사용자가 아무리 악성 스크립트를 밀어 넣어도 화면에는 그냥 글자 그대로 보여주기 때문에 훨씬 안전하다. 게다가 브라우저가 화면을 새로 계산(렌더링)할 필요가 없어서 속도도 훨씬 빠르다.


3. Event: 유저의 행동에 반응하는 신호

이벤트는 유저가 클릭을 하거나, 키보드를 누르는 등의 '사건'을 자바스크립트에게 알려주는 신호다.

이벤트 연결 방식의 진화 (03_event-listener.html)

이벤트를 연결하는 방식은 크게 세 단계를 거쳐 발전했다.

  1. 인라인 방식: <button> (HTML과 JS가 뒤섞여 유지보수가 최악이라 절대 금지)
  2. DOM 프로퍼티 방식: btn.onclick = function() { ... }
  • 치명적인 약점이 있다. 변수에 값을 대입하는 형식이라 새로운 함수를 등록하면 이전 함수가 지워지고 덮어쓰기가 된다.
  1. addEventListener (현대 표준):
btn3.addEventListener("click", () => { console.log("첫 번째 할 일"); });
btn3.addEventListener("click", () => { console.log("두 번째 할 일"); });
// 덮어쓰지 않고 대기열에 쌓여서 두 작업이 모두 안전하게 실행된다.

폼 제출을 멈추는 마법

form.addEventListener("submit", (event) => {
  event.preventDefault(); // 브라우저의 기본 행동을 막는다.
});

HTML의 <form> 태그는 제출(submit) 버튼을 누르면 무조건 페이지를 새로고침하면서 서버로 날아가려는 기본 동작이 있다. 현대 웹(SPA)에서는 페이지 새로고침 없이 자바스크립트가 부드럽게 데이터를 처리해야 하므로, event.preventDefault()를 최상단에 적어 브라우저의 기본 동작을 억제해야 한다.


4. BOM & Web Storage

BOM은 주소창, 타이머, 방문 기록 등 HTML 문서 바깥의 '브라우저 자체'를 제어하는 도구 모음이다. 오늘 가장 흥미로웠던 부분은 데이터를 브라우저에 저장하는 Web Storage클립보드 복사 API다.

sessionStorage vs localStorage

두 저장소 모두 서버를 거치지 않고 내 브라우저에 키-값 형태로 데이터를 쓱 저장해 두는 공간이다.

  • sessionStorage: 현재 열려 있는 탭(세션) 안에서만 살아있다. 탭을 닫으면 데이터가 사라진다. (임시 입력 폼 저장)
  • localStorage: 컴퓨터를 끄든 브라우저를 닫든 지우기 전까지 영원히 살아있다. (다크모드 설정값 유지)

스토리지 쓸 때 주의점

웹 스토리지는 무조건 문자열(String)만 저장한다. 자바스크립트 객체({})를 그대로 넣으면 브라우저가 강제로 문자로 바꾸면서 데이터가 깨져버린다.

const o = { name: "윌", job: "백반집 사장" };

// ❌ 나쁜 예시
localStorage.setItem("o", o); 
console.log(localStorage.getItem("o")); // 출력: "[object Object]" (데이터가 다 깨져서 복구 불가)

//  좋은 예시 (JSON)
localStorage.setItem("o2", JSON.stringify(o)); 
// -> 객체를 문자열 형태('{"name":"윌",...}')로 변환(직렬화)해서 안전하게 보관

const savedO2 = JSON.parse(localStorage.getItem("o2"));
// -> 꺼낼 때는 다시 진짜 자바스크립트 객체로 조립(역직렬화)
console.log(savedO2.name); // "윌"

5. Clipboard API

웹 페이지에서 흔히 보는 "링크 복사하기" 버튼의 원리도 직접 구현해 보았다. 최신 브라우저의 navigator.clipboard API를 쓴다.

document.querySelector("#copy").addEventListener("click", async () => {
  try {
    // OS의 클립보드 메모리를 건드리는 건 시간이 걸리는 작업이라 '비동기(async/await)'로 처리한다
    await navigator.clipboard.writeText("내가 복사하고 싶은 텍스트!");
    alert("클립보드에 복사 완료");
  } catch (error) {
    console.error("복사 실패:", error);
  }
});

브라우저가 클립보드를 보호하는 이유

만약 아무 제약이 없다면, 나쁜 웹사이트가 유저 몰래 자바스크립트로 내 클립보드에 악성 코드를 심거나 내 클립보드에 있던 비밀번호를 훔쳐 갈 수 있을 것이다.
그래서 브라우저는 두 가지 강력한 자물쇠를 채워놨다.

  1. 반드시 사용자가 버튼을 직접 클릭(click 이벤트)했을 때만 작동할 것
  2. 보안이 철저한 https:// 환경에서만 작동할 것

profile
예 마 함 가보입시더

0개의 댓글