크로스 사이트 스크립팅 (XSS)

Cross-site Scripting (XSS)

설명

크로스 사이트 스크립팅(XSS)은 웹 애플리케이션이 사용자 입력값을 적절히 검증하지 않고 웹 페이지에 반영할 때 발생하는 취약점입니다. jQuery의 html() 함수는 입력된 내용을 HTML로 해석하여 DOM에 삽입하므로, 만약 사용자가 악의적인 스크립트를 입력하면 브라우저에서 그대로 실행될 수 있습니다. 이를 통해 공격자는 피해자의 브라우저에서 악성 코드를 실행하거나, 세션 탈취, 계정 도용, 피싱 등 다양한 공격을 할 수 있습니다.

잠재적 영향

  • 정보 탈취 (개인정보, 세션 쿠키 등): 공격자가 사용자의 세션 쿠키나 민감한 정보를 획득할 수 있습니다.
  • 브라우저 악성코드 실행: 사용자 브라우저에 악성 스크립트를 실행할 수 있습니다.
  • UI 변조 및 피싱: 정상적인 화면에 피싱 화면을 삽입하여 사용자를 속일 수 있습니다.

해결 방법

  • 텍스트를 출력할 때는 jQuery의 html() 대신 text()를 사용하세요.
  • HTML 본문에 텍스트를 넣어야 한다면 HTML 이스케이프를 적용하세요. 실제 마크업을 허용해야 한다면 검증된 HTML 정화 도구로 태그와 속성을 제한하세요.
  • 출력 위치에 맞는 처리를 적용하고, HTML 인코딩을 JavaScript나 URL 검증의 대체 수단으로 사용하지 마세요.

예시

변경 전

javascript
// XSS 취약 코드 예시
function showMessage(userInput) {
    $("#message").html(userInput);
}
// 사용자가 <script>alert('XSS')</script> 를 입력하면 스크립트가 실행됩니다.

변경 후

다음 두 방법은 각각 사용하는 대안입니다. 첫 번째는 텍스트로 출력하고, 두 번째는 HTML 본문에 넣을 문자열을 인코딩합니다.

javascript
// 안전한 코드 예시 1 (text() 사용)
function showMessage(userInput) {
    $("#message").text(userInput);
}

// 안전한 코드 예시 2 (HTML 이스케이프 처리)
function escapeHtml(str) {
    return str.replace(/[&<>"']/g, function(tag) {
        const chars = {'&':'&amp;', '<':'&lt;', '>':'&gt;', '"':'&quot;', "'":'&#39;'};
        return chars[tag] || tag;
    });
}
function showMessage(userInput) {
    $("#message").html(escapeHtml(userInput));
}

설명:

  • 변경 전: 사용자 입력값을 html() 함수에 직접 전달하면, 입력에 포함된 스크립트가 실행되어 XSS 공격에 노출됩니다.
  • 변경 후: 변경 후에는 text() 함수로 사용자 입력을 출력하여 HTML 태그와 스크립트가 해석되지 않도록 하거나, HTML로 삽입할 경우 입력값을 이스케이프 처리하여 악성 스크립트가 동작하지 않도록 막습니다.

참조