XSS와 CSRF 차이: 출력 인코딩·CSP·요청 검증을 적용하는 방법
1장 개념과 보호 목표#
XSS는 신뢰하지 않는 데이터가 브라우저에서 실행 코드로 해석되는 취약점입니다. CSRF는 사용자의 인증 상태를 이용해 의도하지 않은 요청을 보내게 하는 공격입니다. 발생 조건과 핵심 방어가 달라 별도로 검증해야 합니다.
2장 원리와 구분#
XSS에는 HTML·속성·URL·JavaScript 문맥에 맞는 출력 처리가 필요합니다. HTML 입력을 허용한다면 검증된 정화 도구를 사용하고 위험한 DOM 삽입 API를 점검합니다. CSP는 보완 통제입니다. 쿠키 기반 인증의 상태 변경 요청은 CSRF 토큰과 origin 확인 등을 적용하며 SameSite는 배치 환경에 맞는 추가 방어로 사용합니다.
3장 비교와 판단 기준#
| 문제 | 발생 조건 | 핵심 통제 |
|---|---|---|
| XSS | 데이터가 실행 코드로 해석 | 문맥별 인코딩·안전한 DOM |
| HTML 입력 | 태그·속성의 위험 | 검증된 정화와 허용 정책 |
| CSRF | 브라우저가 인증 정보 자동 전송 | 요청 토큰·origin 검증 |
| 보완 통제 | 추가 방어 | CSP·SameSite·쿠키 속성 |
4장 브라우저가 데이터를 코드로 해석하는 경계#
사용자 이름이나 게시글은 데이터지만 HTML·속성·스크립트에 잘못 삽입하면 실행 문법이 될 수 있습니다. 입력에 나쁜 단어가 있는지보다 어디에 출력되는지가 중요합니다. 서버 렌더링·프런트엔드·DOM 조작·미리보기의 모든 경로를 확인합니다.
원하는 결과: 입력을 화면의 텍스트로 표시
위험한 결과: 입력을 HTML·JavaScript 코드로 해석
검토할 위치: 템플릿·속성·URL·DOM 삽입·스크립트 문맥5장 저장형·반사형·DOM XSS#
저장형은 저장한 값이 나중에 출력되는 경로, 반사형은 요청 값이 응답에 나타나는 경로, DOM XSS는 브라우저의 데이터·코드 처리에서 생기는 경로로 이해할 수 있습니다. 실제 구현은 겹칠 수 있으며 저장 위치만으로 안전성을 결정하지 않습니다.
서버가 안전하게 JSON을 보냈어도 클라이언트가 위험한 DOM API로 삽입하면 문제가 생길 수 있습니다. 입력의 출처부터 마지막 표시까지 따라가야 합니다.
6장 문맥별 출력 인코딩#
HTML 본문·속성·URL·JavaScript는 다른 문법을 갖습니다. 한 가지 인코딩을 모든 위치의 정답으로 쓰지 않습니다. 가능하면 동적 데이터를 실행 문맥에 넣지 않고 프레임워크의 안전한 텍스트 출력 기능을 사용합니다.
속성 따옴표·URL 스킴·이벤트 속성·스크립트 조합의 위험을 확인합니다. 데이터가 여러 문맥을 순서대로 거치면 최종 해석의 조건까지 검토해야 합니다.
7장 textContent와 위험한 HTML 삽입#
일반 텍스트를 보여 주려면 텍스트 삽입 API를 검토합니다. HTML을 의도하지 않는데 innerHTML 등의 문맥으로 넣으면 데이터가 태그와 실행 구조로 해석될 수 있습니다. 안전한 템플릿을 쓰는 부분과 직접 DOM을 다루는 부분을 구분합니다.
flowchart LR
D["외부 데이터"] --> T["일반 텍스트인가?"]
T --> P["안전한 텍스트 출력"]
T --> H["HTML 허용 기능인가?"]
H --> S["검증된 정화와 제한된 정책"]
S --> V["출력 후 추가 변형 경로 검토"]8장 HTML 입력을 허용하는 경우#
허용 태그·속성·URL의 정책을 정하고 유지보수되는 정화 도구를 사용합니다. 정규식 몇 개로 모든 HTML 문법을 제거하려는 방식은 피합니다. 정화 뒤 다시 위험한 문자열을 결합하거나 오래된 라이브러리를 사용하는지도 확인합니다.
서버 저장본·미리보기·모바일 화면·관리자 화면의 정책이 일치하는지 시험합니다. 사용자 화면에서 안전해도 관리자 뷰에서 취약하면 중요한 세션이 영향을 받을 수 있습니다.
9장 CSP의 역할과 한계#
CSP는 스크립트·자원 출처 등을 제한하는 보완 통제입니다. 광범위한 허용과 위험한 예외가 정책의 효과를 약화할 수 있습니다. 실제 페이지·서드파티 스크립트·보고서를 보고 필요한 범위로 강화합니다.
CSP가 있으므로 출력 인코딩 결함을 남겨도 된다는 결론은 틀립니다. 핵심 코드와 문맥 처리를 수정하고 CSP는 추가 보호로 연결합니다.
10장 CSRF에서 브라우저의 자동 인증 전달#
쿠키 기반 인증에서는 브라우저가 조건에 맞는 요청에 쿠키를 자동으로 붙일 수 있습니다. 다른 사이트가 상태 변경 요청을 유도할 때 사용자의 로그인 상태가 악용될 수 있습니다. POST라는 메서드만으로 이 문제를 막았다고 판단하지 않습니다.
flowchart LR
X["외부 페이지의 요청 유도"] --> B["사용자의 브라우저"]
B -->|"자동으로 포함될 수 있는 쿠키"| S["로그인된 서비스"]
S --> V["CSRF 토큰·출처·업무 상태 검증"]
V --> R["사용자 의도에 맞는 변경만 수행"]11장 토큰·origin·SameSite를 적용한다#
프레임워크의 CSRF 방어와 출처 검증을 해당 인증 구조에 맞춰 사용합니다. SameSite는 추가 보호가 될 수 있지만 로그인 연동·서브도메인·브라우저·교차 사이트 흐름의 조건을 실제 배포에서 확인해야 합니다. 값을 켰다는 사실만으로 모든 요청이 안전한 것은 아닙니다.
상태 변경을 GET으로 수행하지 않고 중요한 변경에는 재인증과 변경 알림을 검토합니다. CSRF 검증 실패가 권한 검사를 생략하는 우회 경로가 되지 않게 합니다.
12장 XSS는 CSRF 통제도 위협할 수 있다#
같은 출처에서 실행되는 악성 스크립트는 사용자의 세션으로 요청을 수행하거나 화면과 데이터를 조작할 수 있습니다. HttpOnly 쿠키의 값 자체를 못 읽어도 피해가 남을 수 있습니다. 두 취약점을 별도의 목록으로만 검토하지 말고 연결된 영향도 조사합니다.
인증·세션 회수·중요 행위 확인을 함께 적용하되 스크립트 실행 경로 자체를 제거하는 것이 핵심입니다.
13장 출력 경로와 상태 변경 경로를 따로 시험한다#
게시글·검색·관리자 화면의 문맥은 XSS 시험에, 계정 변경·거래·알림 설정의 요청은 CSRF 시험에 연결합니다. 정상 유니코드·허용 HTML과 거부해야 하는 문맥을 구분합니다. 다른 출처·토큰 누락·만료·중복·실패도 검증해야 합니다.
실제 브라우저에서 결과를 확인하고 서버 코드뿐 아니라 프런트엔드와 응답 헤더까지 검토합니다. 입력 필터 하나와 쿠키 옵션 하나를 모든 경계의 해결책으로 취급하지 않습니다.
14장 적용 사례와 운영 방법#
게시글 미리보기에서 입력을 innerHTML로 바로 넣으면 서버 템플릿이 안전해도 DOM XSS가 생길 수 있습니다. 비밀번호 변경은 GET으로 수행하지 않고 인증·재인증과 요청 검증을 적용합니다. XSS가 존재하면 브라우저 안에서 CSRF 방어를 우회할 수 있으므로 두 통제를 함께 검토해야 합니다.
15장 입력을 저장하는 위치보다 출력 문맥이 중요하다#
사용자 입력을 HTML 본문에 표시할 때와 HTML 속성·URL·JavaScript에 넣을 때는 위험한 문법이 다릅니다. 범용 인코딩 하나를 모든 위치에 적용하면 빈틈이 생깁니다. 일반 텍스트는 안전한 텍스트 삽입 API를 사용하고, HTML을 허용하는 기능은 검증된 정화 도구의 정책을 사용합니다. 정화한 뒤 다시 위험한 문자열 조합을 하는지도 확인해야 합니다.
CSP는 허용 스크립트와 출처를 제한하는 보완 방어입니다. 광범위한 허용이나 unsafe 옵션이 필요한 이유를 점검하고, 보고서를 관찰한 뒤 실제 정책을 강화합니다. CSP 적용을 근거로 위험한 DOM API나 출력 인코딩 결함을 그대로 남겨서는 안 됩니다.
16장 상태 변경 요청을 사용자의 의도와 연결하기#
쿠키는 브라우저가 자동으로 전송할 수 있어 외부 사이트가 요청을 유도하는 CSRF를 검토해야 합니다. 상태 변경은 적절한 메서드와 CSRF 토큰·출처 확인 등 해당 프레임워크의 방어를 적용합니다. SameSite는 도움을 주지만 서브도메인·로그인 연동·실제 브라우저 동작을 고려해야 합니다.
프로필 표시의 XSS와 비밀번호 변경의 CSRF를 각각 시험합니다. XSS가 있으면 같은 출처의 악성 코드가 정상 세션으로 요청할 수 있으므로 두 문제는 연계됩니다. 중요한 변경은 재인증·변경 알림·세션 회수 정책까지 연결합니다.
17장 적용 전 확인할 사항#
- 출력 위치와 DOM 삽입 API를 식별한다
- 쿠키 기반 상태 변경 요청을 검증한다
- CSP·쿠키 속성은 핵심 코드 수정과 함께 적용한다
18장 자주 묻는 질문#
HttpOnly 쿠키면 XSS 피해가 없나요?#
쿠키 값을 읽기 어렵게 하지만 공격 코드가 같은 출처에서 요청을 수행하는 피해까지 없애지는 않습니다. 스크립트 실행 경로 자체를 제거해야 합니다.
JSON으로 응답하면 XSS가 발생하지 않나요?#
응답 형식만으로 이후 브라우저의 삽입 방식이 안전해지지는 않습니다. 프런트엔드가 데이터를 실행 문맥이나 위험한 DOM API에 넣는지 확인해야 합니다.
POST 요청이면 CSRF를 막을 수 있나요?#
외부 페이지에서도 POST를 유도할 수 있습니다. 메서드 변경만으로 충분하지 않으며 요청 검증과 인증 구조에 맞는 방어가 필요합니다.