Prepared Statement(준비된 문장)는 SQL 쿼리의 **실행 구조(틀)**와 **데이터(값)**를 분리하여 처리하는 방식이다. 쿼리문을 미리 컴파일(Prepare)하고, 나중에 데이터를 바인딩(Bind)하여 실행함으로써 보안성과 성능을 동시에 확보한다.
' OR '1'='1)이 쿼리 구조를 변경하지 못하도록 원천 차단한다..)나 복잡한 따옴표(') 처리가 줄어들어 코드가 정돈된다.`// 1. 쿼리 준비 (Named Placeholder 사용) $stmt = $pdo->prepare("SELECT * FROM members WHERE MW_SEQ = :MW_SEQ");
// 2. 파라미터 바인딩 $stmt->bindParam(":MW_SEQ", $MW_SEQ);
// 3. 실행 및 결과 페치 $stmt->execute(); $row = $stmt->fetch(PDO::FETCH_ASSOC);`
| 비교 항목 | PHP (PDO) | Java (JDBC) | 설명 |
|---|---|---|---|
| 객체 생성 | $pdo->prepare($sql) |
conn.prepareStatement(sql) |
쿼리 구조 정의 |
| 치환자 | :name (이름 기반) |
? (순서 기반) |
PDO는 이름 기반 방식 지원(권장) |
| 값 할당 | $stmt->bindParam() |
stmt.setXxx() |
실제 데이터를 안전하게 주입 |
| 실행 | $stmt->execute() |
stmt.executeQuery() |
DB 서버에 명령 전달 |
| 결과 반환 | $stmt->fetch() |
rs.next() |
결과 셋에서 데이터를 한 행씩 가져옴 |
클래스가 없는 레거시 환경이라 하더라도 DB 연동 시에는 위와 같은 PDO Prepared Statement 방식을 준수해야 한다. 이는 Java 개발자가 습관적으로 사용하는 PreparedStatement와 동일한 안전성을 보장하므로, 신규 로직 작성 시에도 이 패턴을 유지하는 것을 권장한다.