SQLi

사이버 범죄자가 웹 애플리케이션의 입력값을 조작하여 원래 의도와 다른 SQL 쿼리를 실행하게 만드는 보안 취약점이다. 이를 통해 인증 우회, 데이터 조회, 데이터 삭제 등 다양한 악의적 행동이 가능하다.

이 공격은 웹 기반 입력 양식에서 사용자가 생성한 SQL 문이 데이터베이스를 직접 쿼리할 수 있을 때 성공한다. 이러한 공격은 기본 코드 패턴에 취약성이 포함된 WordPress 플러그인과 같은 공유 코드베이스를 사용하면서 확산되었다. 이 취약성은 전체 애플리케이션으로 전달되고, 공유 코드를 사용하는 수십만 개의 웹사이트에 영향을 미칠 수 있다.

 

‼️ SQLi 예시

예를 들어, 사용자가 제품 id 값을 입력하면, 제품 이름과 설명에 액세스할 수 있다.

SELECT product_name, product_description
FROM products
WHERE product_id = [입력값];

 

⚔️ 공격 URL → 입력 값에 ‘999 OR 1=1’ 가 들어감

<http://www.ecommercesite.com/products/products.asp?productid=999> OR 1=1

 

 

🔨 변형된 쿼리

SELECT product_name, product_description
FROM products
WHERE product_id = 999 OR 1=1;

 

결과 : 1=1은 항상 참(True) 이므로, 조건이 무의미해지기 때문에 모든 제품 정보가 노출됨

 

또다른 예시로 아래와 같이 입력하면,

<http://www.ecommercesite.com/products/products.asp?productid=999>; DROP TABLE users;
SELECT product_name, product_description
FROM products
WHERE product_id = 999;
DROP TABLE users;

 

위와 같이 쿼리가 변형되어,

제품 조회 이후 users 테이블이 삭제됨 → 매우..심각한 피해 🥹

 

 

방지

1. Prepared Statements (파라미터 바인딩)

가장 강력하고 표준적인 방어 방법 !

SQL 쿼리의 구조와 데이터 입력값을 분리 → 입력값이 절대 SQL 코드로 해석되지 않도록 함.

String query = "SELECT * FROM users WHERE username = ? AND password = ?";
PreparedStatement stmt = connection.prepareStatement(query);
stmt.setString(1, inputUsername);
stmt.setString(2, inputPassword);
ResultSet rs = stmt.executeQuery();

 

공격자가 inputUsername = ‘ OR 1=1 을 입력해도 SQL 구문으로 작동하지 않고 문자열로 처리 됨 !

 

 

2. 입력값 유효성 검사 (Input Validation)

사용자로부터 입력받은 값이 의도한 형식과 일치하는 지 검사하여 이상한 문법, 특수문자 등을 사전에 차단함.

  • 길이 제한이나 숫자만 들어와야 하는 필드에 숫자 외 문자를 제한
  • 논리 연산자가 포함된 문자열 필터링

 

3. Web Application Firewall (WAF) 적용

SQLi를 필터링하고 잠재적 위협을 차단하기 위해 기업은 웹 애플리케이션 방화벽(WAF)을 설치할 수 있다.

WAF는 알려진 서명의 많은 목록에 대해 애플리케이션에 대한 입력을 일치시켜 악성 SQL 쿼리를 찾아내고 차단한다.

이 목록은 정기적으로 업데이트되고 패치되어 진화하는 위협 동향을 따라갈 수 있도록 

 

+ Recent posts