Backend/SQL

[SQL]JDBC

해로몬 2024. 10. 30. 17:26

JDBC

: 자바 응용 프로그램과 여러 종류의 데이터베이스 사이를 연결하는 표준 인터페이스.

작동방식의 이해

 

데이터베이스 연결

        try {
            // MariaDB JDBC 드라이버 로드
            Class.forName("org.mariadb.jdbc.Driver");
        } catch (ClassNotFoundException e) {
            System.out.println("[에러] 드라이버 로딩 실패: " + e.getMessage());
        }

        // 데이터베이스 연결 정보
        String url = "jdbc:mariadb://localhost:3306/[    ]"; // 데이터베이스 URL
        String user =  // 데이터베이스 사용자 이름
        String password = // 데이터베이스 비밀번호

        Connection conn = null;

        try {
            // 데이터베이스에 연결
            conn = DriverManager.getConnection(url, user, password); //->!!데이터베이스 연결!!
            System.out.println("데이터베이스 연결 성공");
        }
        
        ...
        
        } finally {
            // 데이터베이스 연결 종료
            if (conn != null) {
                try {
                    conn.close(); //->!!연결 종료!!
                    System.out.println("데이터베이스 연결 해제");
                } catch (SQLException e) {
                    System.out.println("[에러] 연결 해제 실패: " + e.getMessage());
                }
            }
        }

ㄴConnection클래스

  • 역할
    • Connection 객체는 애플리케이션과 데이터베이스 간의 실제 연결을 나타냄.
    • Connection이 활성화 상태일 때 데이터베이스와의 모든 상호작용이 가능함.
  • 주요 기능
    • 데이터베이스와의 연결을 설정하고, 트랜잭션을 관리
    • SQL 쿼리를 실행할 Statement, PreparedStatement 객체를 생성함.
  • 주요 메서드
    • close() : 데이터베이스 연결을 해제하여 리소스 반환
    • commit() : 수동 트랜잭션 모드에서 작업을 확정
    • rollback() : 트랜잭션 중 오류가 발생했을 때 이전 상태로 복귀

 

Statement 객체

Statement 클래스란?

  • Statement는 SQL 쿼리를 데이터베이스에 전달하고, 그 결과를 반환받는 객체
  • 데이터베이스와 연결된 Connection 객체를 사용하여 Statement 객체를 생성
  • Statement는 데이터 조작(SQL 실행)과 데이터 정의(테이블 생성 등)를 수행하는 데 사용
  • Connection.createStatement() 메서드를 통해 생성됩니다
  • 주로 정적 SQL 쿼리에 사용되며, INSERT, UPDATE, DELETE, SELECT 등의 쿼리를 실행
  • 주요 메서드
    • executeQuery() - SELECT 쿼리를 실행하고 결과료 ResultSet을 반환
    • executeUpdate() - INSERT, UPDATE, DELETE 쿼리를 실행하고 영향을 받은 행 수를 반환
public static void main(String[] args) {
        
        ...

        Connection conn = null;
        Statement stmt = null;
        try {
            
            ...
            
            //Statement 객체 생성!!!!!
            stmt = conn.createStatement();

            // SQL 쿼리 작성 및 실행
            //데이터 삽입!!!
            String sql = "INSERT INTO dept2 VALUES (53, '연구부', '대전')";
            int rowsAffected = stmt.executeUpdate(sql); // 쿼리 실행 -> 행의 개수를 반환!!

            System.out.println("쿼리 실행 성공, 영향받은 행 수: " + rowsAffected);

        }  
        
        ...
        
        finally {
            // Statement 객체 닫기
            if (stmt != null) {
                try { stmt.close(); } catch (SQLException e) { }
            }
            // Connection 객체 닫기
            if (conn != null) {
                try { conn.close(); } catch (SQLException e) { }
            }
        }

 

예시 2) DDL 쿼리 작성

public static void main(String[] args) {
       
       ...

        try {
        
            ...

            // Statement 객체 생성
            stmt = conn.createStatement();

            // DDL 쿼리 작성 - 테이블 생성
            String sql = "CREATE TABLE dept4 (" +
                         "deptno INT(2), " +
                         "dname VARCHAR(14), " +
                         "loc VARCHAR(13)" +
                         ")";
            int result = stmt.executeUpdate(sql); // 쿼리 실행

            System.out.println("테이블 생성 성공, 반환 값: " + result);

        } 
         ...
        
        } finally {
            if (stmt != null) { try { stmt.close(); } catch (SQLException e) {} }
            if (conn != null) { try { conn.close(); } catch (SQLException e) {} }
        }

        System.out.println("끝");
    }

 

ResultSet 객체 (SELECT 쿼리 결과)

ResultSet이란?

  • ResultSet은 SQL의 SELECT 쿼리 결과를 담고 있는 객체입니다.
  • Statement.executeQuery()나 PreparedStatement.executeQuery() 메서드가 반환하는 객체입니다.
  • 쿼리 결과 데이터를 행 단위로 접근하여 각 열의 값을 읽어올 수 있습니다.
  • while (rs.next())와 같은 반복문을 통해 행을 순차적으로 접근하며 데이터를 처리합니다.
  • 주요 메서드
    • next() : 다음 행으로 이동하며, 데이터가 있으면 true, 없으면 false를 반환
    • getInt(), getString() : 특정 열의 데이터를 가져올 때 사용
public static void main(String[] args) {
        
        ...

        try {
           
           ...
           
            // Statement 객체 생성
            stmt = conn.createStatement();

            // SQL 쿼리 작성 - 데이터 조회
            String sql = "SELECT * FROM dept2";
            rs = stmt.executeQuery(sql); // 쿼리 실행 및 결과 저장

            // ResultSet을 사용해 결과 출력
            while (rs.next()) {
                int deptno = rs.getInt("deptno"); // "deptno" 열의 값 가져오기
                String dname = rs.getString("dname"); // "dname" 열의 값 가져오기
                String loc = rs.getString("loc"); // "loc" 열의 값 가져오기

                System.out.printf("부서번호: %d, 부서명: %s, 위치: %s%n", deptno, dname, loc);
            }

        } 
        ...
        
    }

 

 

PreparedStatement

PreparedStatement는 자바의 JDBC에서 SQL 쿼리를 사전에 컴파일하여 파라미터를 동적으로 설정할 수 있도록 하는 객체

보안성과 성능을 높이는데 유용하며, 특히 SQL 인젝션 공격을 방지하는 데 중요한 역할을 함.

 

PreparedStatement 사용 단계

  1. SQL 쿼리 작성: SQL 문을 준비할 때 파라미터 자리(?)를 미리 정의합니다.
  2. PreparedStatement 생성: Connection.prepareStatement() 메서드를 사용해 PreparedStatement 객체를 생성합니다.
  3. 파라미터 바인딩: 각 파라미터에 대해 타입에 맞는 setX() 메서드를 호출해 값을 설정합니다.
  4. 쿼리 실행: executeQuery()나 executeUpdate() 메서드를 사용해 쿼리를 실행합니다.

 

PreparedStatement 주요 메서드

  • 파라미터 설정 메서드:
    • setInt(int parameterIndex, int x) 
    • setString(int parameterIndex, String x)
    • setDouble(int parameterIndex, double x)
    • setDate(int parameterIndex, java.sql.Date x)
  • 쿼리 실행 메서드:
  • executeQuery() : SELECT문 실행(ResultSet 반환)
  • executeUpdate() : INSERT, UPDATE, DELETE 실행 (영향받은 행의 수 반환)

 

PreparedStatement 활용 시 주의사항

  • 파라미터 인덱스: 1부터 시작하며, SQL 문의 물음표(?) 순서와 일치해야 합니다.
  • 자원 관리: 사용 후 PreparedStatement와 Connection은 반드시 close()를 호출하여 리소스를 반환합니다.
  • 예외 처리: SQL 실행 도중 발생할 수 있는 SQLException에 대비하여 적절히 예외를 처리하는 것이 좋습니다.

 

PreparedStatement의 특징과 장점

  • 보안성: 쿼리 파라미터가 SQL 문에 직접 포함되지 않고 바인딩되므로, SQL 인젝션 공격을 방지할 수 있습니다.
  • 성능 향상: PreparedStatement는 쿼리를 사전에 컴파일하고, 동일한 쿼리를 여러 번 실행할 때 재사용하므로 성능이 향상됩니다.
  • 유연한 파라미터 바인딩: 다양한 데이터 타입에 대해 setInt(), setString() 등으로 파라미터 값을 설정할 수 있습니다.
try{
	

	...


// SQL 쿼리를 준비한 PreparedStatement 객체 생성
            pstmt = conn.prepareStatement("insert into dept2 values(?,?,?)");

            // 데이터 삽입을 위한 값 설정
            String deptno = "53";     // 부서 번호
            String dname = "연구부";   // 부서 이름
            String loc = "대전";       // 부서 위치

            // PreparedStatement에 각 파라미터 값 설정
            pstmt.setString(1, deptno);   // 첫 번째 파라미터에 deptno 설정
            pstmt.setString(2, dname);    // 두 번째 파라미터에 dname 설정
            pstmt.setString(3, loc);      // 세 번째 파라미터에 loc 설정

            // SQL 실행 및 데이터베이스에 삽입
            pstmt.executeUpdate();
            System.out.println("쿼리 실행 성공");
            
            
            ...

}

 

 

 


<전체 흐름>

1.JDBC 드라이버 로딩

Class.forName("org.mariadb.jdbc.Driver"); // 예: MariaDB 드라이버 로딩

2. 데이터베이스 연결

Connection conn = DriverManager.getConnection("jdbc:mariadb://localhost:3306/test", "user", "password");

3. Statement 생성

Statement,PreparedStatement, CallableStatement 중 하나를 생성

  • Statement : 정적 SQL 문 실행
  • PreparedStatement : 파라미터화된 SQL문을 실행할 때 사용, 보안성과 성능이 향상
  • CallableStatement : 저장 프로시저를 호출할 때 사용.
Statement stmt = conn.createStatement();PreparedStatement pstmt = 
	conn.prepareStatement("INSERT INTO employees (empno, ename) VALUES (?, ?)");

4. SQL문 생성

  • Statement나 PreparedStatement 객체를 통해 데이터베이스로 전송하여 실행
  • SQL 문이 Select,insert,Update, Delete와 같은 DML 문인지에 따라 다른 메서드 사용

설명

  • executeQuery() : SELECT 문을 실행하고, 결과로 ResultSet을 반환
  • executeUpdate() : INSERT,UPDATE,DELETE문을 실행 -> 영향받은 행의 수 반환
ResultSet rs = stmt.executeQuery("Select * from employees");
int rowsAffected = pstmt.executeUpdate();

 

5. 결과받기

  • ResultSet 객체에 실행결과 저장 -> 조회된 데이터를 행단위로 접근 ->행의 열 데이터를 가져옴
while(rs.next()){
	int empno = rs.getInt("empno");
    String ename = rs.getString("ename");
}

6.연결 해제

  • Connection,Statement,ResultSet 등의 리소스 해제
  • close()
rs.close();
stmt.close();
conn.close();

 

 

 

'Backend > SQL' 카테고리의 다른 글

[SQL] INDEX  (0) 2024.10.30
[SQL]데이터베이스 집합 연산  (0) 2024.10.29
[SQL]데이터베이스 백업/복원  (0) 2024.10.29
[SQL] DCL(Data Control Language)  (0) 2024.10.29
[SQL] 데이터베이스 사용자  (1) 2024.10.29