안녕하세요! 👋 OWASP Top 10 시리즈, 오늘은 20년 가까이 보안 위협 목록에서 빠지지 않는 단골손님이자 가장 위험한 취약점 중 하나인 A03:2021-인젝션(Injection)에 대해 알아보겠습니다.
"인젝션"은 우리말로 '주입'이라는 뜻이죠. 해커가 애플리케이션에 악의적인 코드를 주입하여, 마치 원래 그런 명령어였던 것처럼 시스템을 속여 실행하게 만드는 무서운 공격입니다. 2021년 버전에서는 이전 버전의 크로스 사이트 스크립팅(XSS)까지 이 항목에 포함되면서 그 범위가 더욱 넓어졌습니다.

🤔 인젝션 공격, 도대체 뭔가요?
가장 쉽게 비유하자면, 식당에 가서 주문서에 메뉴 대신 "음식값은 받지 말고, 주방에 있는 현금을 전부 꺼내와!" 라고 몰래 적는 것과 같아요. 📜💥
정상적인 시스템이라면 주문서에서 메뉴 이름만 읽어야 하지만, 만약 시스템이 주문서 내용을 그대로 '명령'으로 인식하고 실행해버린다면 어떻게 될까요? 바로 주방장이 현금을 들고나오는 끔찍한 상황이 발생하겠죠.
인젝션 공격은 이처럼 사용자가 입력하는 데이터에 악의적인 '명령어'를 몰래 숨겨서, 데이터를 처리하는 해석기(Interpreter) - 예를 들어 데이터베이스, 운영체제, 웹 브라우저 - 가 이를 실행하도록 만드는 공격 기법입니다. 근본적인 원인은 "사용자의 입력을 신뢰하기 때문"에 발생합니다.
🕵️♂️ 인젝션 공격의 악명 높은 유형들
인젝션은 코드를 주입하는 대상에 따라 여러 종류로 나뉩니다. 가장 유명한 3인방을 만나보시죠.
1. SQL 인젝션 (SQL Injection, SQLi)
인젝션 공격의 대명사이자, 가장 파괴적인 공격 중 하나입니다. 데이터베이스(DB)에 보내는 SQL 쿼리문에 악의적인 구문을 주입하는 방식입니다.
- 공격 시나리오 🧑💻
- 사용자 아이디를 입력받아 정보를 보여주는 로그인 페이지가 있습니다. 서버는 내부적으로 이런 쿼리를 실행합니다: SELECT * FROM users WHERE userId = '입력받은_ID';
- 해커가 ID 입력창에 ' or '1'='1 이라는 값을 입력합니다.
- 서버가 이 값을 그대로 쿼리에 붙이면 어떻게 될까요? SELECT * FROM users WHERE userId = '' or '1'='1';
- '1'='1'은 항상 참(True)이기 때문에, WHERE 조건절이 무력화되고 결국 users 테이블의 모든 사용자 정보가 유출됩니다! 😱
- 피해: 데이터베이스 정보 유출, 데이터 파괴, 인증 우회, 서버 장악
2. 크로스 사이트 스크립팅 (Cross-Site Scripting, XSS)
사용자의 웹 브라우저를 공격 대상으로 삼는 인젝션입니다. 웹사이트에 악성 자바스크립트(JavaScript) 코드를 주입하여, 해당 페이지를 보는 다른 사용자의 브라우저에서 실행되도록 만듭니다.
- 공격 시나리오 📌
- 해커가 웹사이트 게시판의 댓글에 악성 스크립트를 포함한 글을 작성합니다. 안녕하세요!
- 다른 사용자가 이 댓글이 포함된 게시글을 엽니다.
- 사용자의 브라우저는 <script> 태그를 그대로 실행하여, 자신의 세션 쿠키 정보를 해커의 사이트로 전송해버립니다.
- 해커는 이 쿠키를 이용해 해당 사용자인 척 로그인하여 정보를 탈취할 수 있습니다.
- 피해: 세션 하이재킹(계정 도용), 피싱 사이트 유도, 악성코드 유포
3. 운영체제(OS) 커맨드 인젝션 (Command Injection)
가장 치명적인 공격 중 하나로, 운영체제가 실행하는 명령어를 조작합니다.
- 공격 시나리오 💥
- 웹사이트에 IP 주소를 입력하면 해당 주소로 ping을 보내주는 기능이 있습니다. 서버는 내부적으로 ping [입력받은_IP] 명령을 실행합니다.
- 해커가 IP 주소 대신 8.8.8.8; ls -al 와 같은 값을 입력합니다. (;는 여러 명령어를 실행하게 하는 구분자입니다)
- 서버는 ping 8.8.8.8 명령을 실행한 뒤, 이어서 ls -al (현재 디렉토리 파일 목록 보기) 명령까지 실행해버립니다.
- 해커는 이 방식으로 서버의 파일을 보거나, 삭제하거나, 악성코드를 다운로드하여 실행할 수도 있습니다.
- 피해: 서버 시스템 완전 장악, 데이터 유출 및 파괴, 악성코드 감염
🛡️ 어떻게 막을 수 있을까요? (방어 방법)
인젝션의 근본 원인은 "사용자 입력을 신뢰하는 것"이므로, 방어의 핵심은 "절대 사용자 입력을 믿지 말고, 데이터와 명령어를 명확히 분리하는 것"입니다.
- 매개변수화된 쿼리 사용 (Parameterized Queries) ⚙️ SQL 인젝션을 막는 가장 효과적인 방법입니다. 쿼리문은 틀(템플릿)만 만들고, 사용자 입력은 나중에 매개변수(parameter)로 전달하는 방식입니다. 이렇게 하면 데이터베이스는 사용자 입력을 절대로 명령어로 해석하지 않고, 순수한 데이터로만 취급합니다.
- 입력값 검증 (Input Validation) 🤨 사용자로부터 입력된 값이 내가 예상한 형식과 내용이 맞는지 항상 검증해야 합니다. 예를 들어, 전화번호 필드에는 숫자와 하이픈(-)만 허용하는 식입니다. 허용할 문자 목록(Whitelist)을 만들어 관리하는 것이 가장 안전합니다.
- 출력값 이스케이핑/인코딩 (Output Escaping/Encoding) XSS 공격을 막는 가장 효과적인 방법입니다. 사용자 입력값을 웹 페이지에 표시하기 전에, <, >, ", ' 등 HTML에서 특별한 의미를 갖는 문자들을 안전한 문자(예: < -> <)로 변환해주는 것입니다. 이렇게 하면 브라우저는 스크립트를 실행하지 않고, 단순한 텍스트로만 화면에 보여줍니다.
- 최소 권한의 원칙 적용 데이터베이스나 시스템에 접근하는 계정에 꼭 필요한 최소한의 권한만 부여하세요. 만약 인젝션 공격에 당하더라도 피해를 최소화할 수 있습니다.
✨ 마치며
인젝션 공격은 아주 사소한 입력값 처리 실수에서 시작되어 서버 전체를 장악하는 끔찍한 결과로 이어질 수 있습니다. 개발자는 항상 "모든 외부 입력은 잠재적인 공격이다"라는 보안 의식을 가지고, 데이터와 명령어를 철저히 분리하는 습관을 들여야 합니다. 안전한 코딩 습관이 곧 가장 강력한 보안 대책입니다!
'일반IT > IT보안' 카테고리의 다른 글
| 🛡️ 공격자의 눈으로 우리 서비스를 보자! OWASP 위협 모델링 프로세스 완벽 가이드 (0) | 2025.09.29 |
|---|---|
| 🏗️ 잘못된 첫 단추, 모든 것을 무너뜨린다! OWASP 4위, 안전하지 않은 설계 (0) | 2025.09.29 |
| 🔐 내 비밀번호는 안전할까? OWASP 2위, 암호화 실패 파헤치기 (0) | 2025.09.29 |
| 👑 OWASP 1위! 깨진 접근 통제 (Broken Access Control) 파헤치기 (0) | 2025.09.29 |
| 🔗 n8n으로 SecOps 자동화, 복잡한 워크플로를 코딩 없이! 🚀 (1) | 2025.09.20 |