Mybatis: #, $
0. #, $ 비교
SELECT *
FROM TEMP
WHERE 1=1
AND TEMP_ID = #{tempId}
| cs |
1) DB에서는
SELECT *
FROM TEMP
WHERE 1=1
AND TEMP_ID = ?
| cs |
이렇게 쿼리문에 대한 의미 파악 시작
2) 구문 분석 및 파싱 진행 = PreparedStatement
- 단, DB 옵티마이저의 수행계획은 동일
- 인덱스 스캔으로 인한 성능 저하 가능성 존재
--------------------------------------------------------------------------------------------------
SELECT *
FROM TEMP
WHERE 1=1
AND TEMP_ID = ${tempId}
| cs |
SELECT *
FROM TEMP
WHERE 1=1
AND TEMP_ID = 1
| cs |
1) ${tempId}가 1인 경우 위 쿼리로 실행
- DB에서는 의미 파악, 파싱 시작= Statement
- 상수로 치환하여 수행 = 값이 변경될 때마다 파싱 진행
2) SQL injection에 취약
※ PreparedStatement, Statement
- 두 인터페이스의 가장 큰 차이점은 cache의 사용 여부
1. Statement
- 쿼리분석 / 컴파일 / 실행
- 실행할 때마다 3단계를 거친 후 작동
- 매번 컴파일 = 성능상 이슈 존재
String str = "SELECT name, empNo FROM TEMP02 WHERE empNo"+empNo
Statement stmt = conn.credateStatement();
ResultSet rs = stmt.executeQuery(str);
| cs |
str 실행 시 결과 값을 생성
2. PreparedStatement
- 쿼리분석 / 컴파일 / 실행
- 3단계를 처음 1번 실행한 후 cache에 담아서 재사용
- 컴파일이 미리 되어 있기에 재사용성이 높음
- ? 부분만 변화를 주어 지속적으로 SQL문을 수행 = 가독성은 떨어짐
String str = "SELECT name, empNo FROM TEMP02 WHERE empNo = ?"
PreparedStatement pstmt = conn.prepareStatement (str);
pstmt.setInt(1, empNo);
ResultSet prs = pstmt.executeQuery();
| cs |
str은 생성할 때 실행
3. API
Statement
1) Statement 오브젝트마다 1개의 ResultSet이 오픈됨
2) 실행 중인 ResultSet의 read()외에 다른 read()가 존재한다면 그것은 다른 ResultSet의 것
= 다른 Statement 오브젝트에 의해 생성된 것
3) Statement의 execution은 이미 실행 중인 ResultSet이 있다면 암묵적으로 종료시킴
PreparedStatement
1) Statement를 상속받음
2) SQL문은 먼저 컴파일되어 PreparedStatement 오브젝트 내에 저장됨
4. 사용
1) statement
String str = null;
Statement stmt = null;
ResultSet rs = nul;
for(int i = 0; i < 100; i++){
str = "SELECT name, empNo FROM TEMP03 WHERE empNo"+empNo
stmt = conn.credateStatement();
rs = stmt.executeQuery(str);
}
| cs |
2)preparedStatement
String str = null;
PreparedStatement pstmt = null;
ResultSet prs = null;
str = "SELECT name, empNo FROM TEMP03 WHERE empNo = ?"
pstmt = conn.prepareStatement(str);
for(int i = 0; i < 100; i++){
pstmt.setIn(1, i);
prs = pstmt.executeQuery();
}
| cs |
4-1. 의미없는 이야기: 반복문을 사용할 때는 주로 statement 구문을 사용