SQL 인젝션(SQL Injection) 은 웹 애플리케이션에서 사용자의 입력값이 SQL 쿼리에 안전하게 처리되지 않을 때 발생하는 보안 취약점입니다. 공격자는 이 취약점을 이용해 쿼리를 조작하여 인증을 우회하거나, 데이터를 조작하거나, 테이블 자체를 삭제할 수도 있습니다.
예를 들어, 로그인 검증 시 아래와 같은 코드를 사용한다고 가정해 보겠습니다.
public boolean login(String username, String password) {
String sql = "SELECT * FROM users WHERE username = '" + username + "' AND password = '" + password + "'";
try (Connection conn = DriverManager.getConnection("url");
Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery(sql)) {
return rs.next();
} catch (SQLException e) {
throw new RuntimeException("Database error", e);
}
}
사용자가 로그인 폼에 아래와 같이 입력한다면
username: admin' --
password: (아무거나)
생성되는 쿼리는 다음과 같이 변형됩니다.
SELECT * FROM users WHERE username = 'admin' -- ' AND password = '1q2w3e4r!';
-- 이후는 주석 처리되므로, 비밀번호 조건은 무시되어 admin 사용자에 대한 정보가 반환됩니다. 이처럼 공격자는 SQL 쿼리를 조작하여 인증을 우회하거나 데이터베이스의 정보를 탈취할 수 있습니다.
이 외에도 공격자는 다음과 같은 페이로드를 사용할 수 있습니다.
- ' OR '1'='1: 항상 참이 되는 조건
- ' UNION SELECT * FROM accounts --: 다른 테이블의 정보 조회
- '; DROP TABLE users; --: 테이블 삭제
SQL 인젝션을 방지하는 방법은 무엇인가요?
- PreparedStatement를 사용하면 place holder(?)에 값을 바인딩하고 내부적으로 이스케이프 처리하기 때문에 SQL 인젝션을 방지할 수 있습니다.
String sql = "SELECT * FROM users WHERE username = ? AND password = ?"; PreparedStatement pstmt = conn.prepareStatement(sql); pstmt.setString(1, username); pstmt.setString(2, password); - JPA, Hibernate와 같은 ORM 프레임워크를 사용하면 SQL 쿼리를 직접 작성하지 않고도 데이터베이스와 상호작용할 수 있습니다.
- 사용자 입력에 대해 공격에 사용되는 SQL 구문의 포함 여부를 검증합니다.
- 웹 애플리케이션에서 사용하는 데이터베이스 계정에 최소한의 권한만 부여합니다.
- SQL 오류나 예외 메시지를 사용자에게 직접 노출하지 않도록 합니다.
LIST
'Software > Maker(Spring & Python & node)' 카테고리의 다른 글
| AI가 LeetCode를 3초에 푸는 시대, 코딩테스트는 어디로 가는가 (0) | 2026.03.24 |
|---|---|
| 기술은 빨라지고, 경력은 싸진다 — 백엔드 개발자의 프리미엄은 어디로 가는가 (0) | 2026.03.24 |
| 커링이란 (0) | 2026.03.24 |
| SI 산출물은 왜 따로 노는가 — 요구사항부터 테스트까지 ‘연결’로 설계하는 방법 (0) | 2026.03.23 |
| SI 프로젝트 산출물의 본질 — 요구사항부터 테스트까지, 제대로 만드는 기준 (0) | 2026.03.23 |
