6주차 Unit 3.2 — JDBC의 표준화 효과

Psj·2026년 5월 29일

F-lab

목록 보기
192/238

Unit 3.2 — JDBC의 표준화 효과

F-LAB JAVA · 6주차 · Phase 3 · JDBC 표준화의 등장


📌 학습 목표

이 Unit을 끝내면 다음을 답할 수 있어야 한다.

  • JDBC = 자바 DB 접근 표준 API 의 의미는?
  • 같은 코드, 다른 DB (URL/드라이버) 는?
  • JDBC 가 해결한 것 (연결/실행/결과) 은?
  • DriverManager 의 역할 은?
  • 드라이버 로딩 방식은?
  • JDBC 핵심 인터페이스 (Connection/Statement/ResultSet) 는?
  • JDBC 가 닮은 5주차 패턴 (전략/인터페이스) 은?
  • DB 교체 시 변경 범위 는?
  • JDBC 의 추상화 구조 는?

🎯 핵심 한 문장

JDBC 는 자바의 DB 접근 표준 API 로, 연결·SQL 실행·결과 처리 방식을 통일하여 DB 를 교체해도 URL 과 드라이버만 바꾸면 나머지 코드는 그대로 동작하며, 이는 5주차의 전략 패턴·인터페이스 추상화와 똑같은 구조다.
JDBC 는 자바의 DB 접근 표준 API 로, 모든 DB 를 같은 방식으로 다룰 수 있게 한다.
덕분에 같은 코드, 다른 DB 가 가능해 — jdbc:mysql://..., jdbc:oracle:thin:@..., jdbc:postgresql://... 처럼 URL 과 드라이버만 바꾸면 이후 코드 (DriverManager.getConnection, prepareStatement, executeQuery) 는 동일하다.
JDBC 가 해결한 것은 (1) DB 연결 방식 통일, (2) SQL 실행 방식 통일, (3) 결과 처리 방식 통일이며, DriverManager 가 등록된 드라이버 중 적절한 것을 골라 Connection 을 만들어준다.
이 구조는 5주차의 전략 패턴·인터페이스 추상화 와 똑같다 — Connection, Statement, ResultSet 은 인터페이스이고 각 DB 드라이버가 그 구현체로, 애플리케이션은 인터페이스에만 의존한다.

비유 — 만능 어댑터 (표준 플러그)

JDBC = 만능 어댑터:

표준 API (만능 어댑터):
  - 어느 나라 콘센트든 (DB)
  - 같은 플러그 (코드)
  - 어댑터만 교체 (드라이버)

같은 코드, 다른 DB:
  - 어댑터 헤드만 바꿈 (URL/드라이버)
  - 기기 (코드) 그대로

DriverManager (어댑터 관리자):
  - 등록된 어댑터들 보관
  - URL 보고 맞는 어댑터 선택
  - 연결 제공

JDBC 인터페이스 (표준 규격):
  - Connection (연결)
  - Statement (명령)
  - ResultSet (결과)
  - 규격만 정의, 구현은 드라이버

5주차 전략 패턴:
  - 인터페이스 + 구현 주입
  - JDBC 도 같은 구조

→ JDBC = 자바 DB 표준 API, URL/드라이버만 교체, 인터페이스(전략 패턴 구조).


🧭 9개 섹션 로드맵

1. JDBC = 표준 API
2. 같은 코드, 다른 DB
3. JDBC가 해결한 것
4. DriverManager
5. 드라이버 로딩
6. 핵심 인터페이스
7. 5주차 패턴과 닮음
8. DB 교체 변경 범위
9. 면접 + 자기 점검

1️⃣ JDBC = 표준 API

1.1 JDBC

JDBC (Java Database Connectivity):

  자바의 DB 접근 표준 API:
    - 모든 DB 같은 방식
    - 인터페이스 표준
    - 구현은 드라이버

1.2 표준의 의미

표준의 의미:

  한 번 배우면:
    - 모든 DB 접근
    - 같은 코드
    - DB 독립

1.3 java.sql 패키지

java.sql 패키지:

  JDBC 표준 인터페이스:
    - Connection
    - Statement / PreparedStatement
    - ResultSet
    - DriverManager

1.4 ILIC 의 맥락

// JDBC 표준 API (ILIC)
public class ShipmentDao {
    public Shipment get(Long id) throws Exception {
        // 표준 JDBC (DB 무관)
        Connection c = DriverManager.getConnection(url, user, pwd);
        PreparedStatement ps = c.prepareStatement(
            "select * from shipments where id = ?");
        ps.setLong(1, id);
        ResultSet rs = ps.executeQuery();
        // ... 표준 코드
        rs.close(); ps.close(); c.close();
        return null;
    }
    String url = "jdbc:mysql://localhost/ilic";
    String user = "root";
    String pwd = "password";
}
class Shipment {}

1.5 자기 점검 답변

JDBC = 자바 DB 접근 표준 API 의 의미는?

:
1. JDBC:

  • 자바 DB 표준 API
  1. 표준:

    • 모든 DB 같은 방식
  2. 패키지:

    • java.sql
  3. 독립:

    • DB 무관 코드

2️⃣ 같은 코드, 다른 DB

2.1 URL 만 다름

// URL 만 다름
// MySQL
String url = "jdbc:mysql://localhost:3306/mydb";
// Oracle
String url = "jdbc:oracle:thin:@localhost:1521:xe";
// PostgreSQL
String url = "jdbc:postgresql://localhost:5432/mydb";

// 이후 코드는 동일!
Connection conn = DriverManager.getConnection(url, user, pwd);

2.2 이후 동일

이후 동일:

  연결 후:
    - prepareStatement (같음)
    - executeQuery (같음)
    - ResultSet (같음)

→ DB 무관 코드

2.3 URL 형식

JDBC URL 형식:

  jdbc:<DB종류>:<상세>

  - jdbc:mysql://host:port/db
  - jdbc:oracle:thin:@host:port:sid
  - jdbc:postgresql://host:port/db

2.4 ILIC 의 맥락

// 같은 코드, 다른 DB (ILIC)
public class ShipmentDao {
    private final String url;   // DB 별로 다름
    
    public ShipmentDao(String url) {
        this.url = url;
    }
    
    public void add(Shipment s) throws Exception {
        Connection c = DriverManager.getConnection(url, "user", "pwd");
        // ↓ 이 코드는 DB 무관 (동일)
        PreparedStatement ps = c.prepareStatement(
            "insert into shipments(id, bl_no) values(?, ?)");
        ps.setLong(1, s.getId());
        ps.setString(2, s.getBlNo());
        ps.executeUpdate();
        ps.close(); c.close();
    }
}

// 고객사별 (URL 만 다름)
// new ShipmentDao("jdbc:mysql://customerA/ilic")
// new ShipmentDao("jdbc:oracle:thin:@customerB:1521:ilic")
// → add() 코드는 그대로
class Shipment {
    Long getId() { return null; }
    String getBlNo() { return null; }
}

2.5 자기 점검 답변

같은 코드, 다른 DB (URL/드라이버) 는?

:
1. URL 만 다름:

  • jdbc:mysql/oracle/postgresql
  1. 이후 동일:

    • prepareStatement 등
  2. URL 형식:

    • jdbc:DB종류:상세
  3. 독립:

    • 코드 그대로

3️⃣ JDBC가 해결한 것

3.1 세 가지 통일

JDBC 가 해결한 것:

1. DB 연결 방식 통일
2. SQL 실행 방식 통일
3. 결과 처리 방식 통일

+ DB 교체 시 URL/드라이버만

3.2 연결 통일

연결 통일:

  모든 DB:
    - DriverManager.getConnection
    - Connection 인터페이스

→ 통일된 연결

3.3 실행 통일

실행 통일:

  모든 DB:
    - prepareStatement
    - executeQuery / executeUpdate

→ 통일된 실행

3.4 결과 통일

결과 통일:

  모든 DB:
    - ResultSet
    - rs.next(), rs.getXxx()

→ 통일된 결과

3.5 ILIC 의 맥락

// JDBC 가 해결한 3가지 (ILIC)
public class ShipmentDao {
    public List<Shipment> findAll() throws Exception {
        // 1. 연결 통일
        Connection c = DriverManager.getConnection(url, user, pwd);
        
        // 2. 실행 통일
        PreparedStatement ps = c.prepareStatement(
            "select * from shipments");
        ResultSet rs = ps.executeQuery();
        
        // 3. 결과 통일
        List<Shipment> result = new ArrayList<>();
        while (rs.next()) {
            Shipment s = new Shipment();
            s.setId(rs.getLong("id"));
            s.setBlNo(rs.getString("bl_no"));
            result.add(s);
        }
        
        rs.close(); ps.close(); c.close();
        return result;
    }
    String url = "jdbc:mysql://localhost/ilic";
    String user = "root", pwd = "pwd";
}
class Shipment {
    void setId(Long id) {}
    void setBlNo(String s) {}
}
// 연결/실행/결과 모두 표준 (DB 무관)

3.6 자기 점검 답변

JDBC가 해결한 것 (연결/실행/결과) 은?

:
1. 3가지 통일:

  • 연결/실행/결과
  1. 연결:

    • DriverManager/Connection
  2. 실행:

    • prepareStatement/execute
  3. 결과:

    • ResultSet

4️⃣ DriverManager

4.1 DriverManager

DriverManager:

  드라이버 관리자:
    - 등록된 드라이버 관리
    - URL 보고 적절한 드라이버 선택
    - Connection 생성

4.2 역할

DriverManager 역할:

  getConnection(url):
    - URL 분석 (jdbc:mysql → MySQL)
    - 맞는 드라이버 찾음
    - 드라이버가 Connection 생성
    - 반환

4.3 드라이버 선택

드라이버 선택:

  여러 드라이버 등록 시:
    - URL 의 DB 종류로
    - 적절한 드라이버
    - 자동 선택

4.4 팩토리 역할

팩토리 역할:

  DriverManager:
    - Connection 팩토리
    - getConnection (생성)

→ 5주차 팩토리 패턴

4.5 ILIC 의 맥락

// DriverManager (ILIC)
public class ConnectionExample {
    public Connection getConnection() throws Exception {
        // DriverManager 가:
        // 1. URL 분석 (jdbc:mysql → MySQL 드라이버)
        // 2. 등록된 MySQL 드라이버 선택
        // 3. 드라이버가 Connection 생성
        return DriverManager.getConnection(
            "jdbc:mysql://localhost/ilic",   // URL
            "ilic_user",                      // 계정
            "password");                      // 비밀번호
    }
    
    // 여러 DB 드라이버 등록 시
    // jdbc:mysql → MySQL 드라이버
    // jdbc:oracle → Oracle 드라이버
    // → DriverManager 가 URL 로 자동 선택
}

4.6 자기 점검 답변

DriverManager의 역할은?

:
1. DriverManager:

  • 드라이버 관리자
  1. 역할:

    • URL → 드라이버 선택
  2. 선택:

    • DB 종류로 자동
  3. 팩토리:

    • Connection 생성

5️⃣ 드라이버 로딩

5.1 드라이버 로딩

드라이버 로딩:

  과거:
    - Class.forName 명시

  현재 (JDBC 4.0+):
    - 자동 로딩 (SPI)
    - 의존성만 추가

5.2 과거 방식

// 과거 (명시적 로딩)
Class.forName("com.mysql.jdbc.Driver");
Connection c = DriverManager.getConnection(url, user, pwd);
// Class.forName 으로 드라이버 등록

5.3 현재 방식

// 현재 (JDBC 4.0+, 자동)
// Class.forName 불필요
Connection c = DriverManager.getConnection(url, user, pwd);
// 의존성에 드라이버 있으면 자동 로딩 (SPI)

5.4 SPI 메커니즘

SPI (Service Provider Interface):

  자동 발견:
    - META-INF/services
    - 드라이버 자동 등록

→ Class.forName 불필요

5.5 ILIC 의 맥락

// 드라이버 로딩 (ILIC)

// build.gradle 에 드라이버 의존성
// runtimeOnly 'com.mysql:mysql-connector-j'

public class ShipmentDao {
    public void add(Shipment s) throws Exception {
        // JDBC 4.0+ : Class.forName 불필요 (자동 로딩)
        Connection c = DriverManager.getConnection(
            "jdbc:mysql://localhost/ilic", "user", "pwd");
        // mysql-connector-j 가 SPI 로 자동 등록됨
    }
    // 과거:
    // Class.forName("com.mysql.cj.jdbc.Driver");  // 명시 (불필요)
}
class Shipment {}

5.6 자기 점검 답변

드라이버 로딩 방식은?

:
1. 과거:

  • Class.forName 명시
  1. 현재:

    • 자동 (JDBC 4.0+)
  2. SPI:

    • META-INF/services
  3. 의존성:

    • 추가만

6️⃣ 핵심 인터페이스

6.1 핵심 인터페이스

JDBC 핵심 인터페이스:

  - Connection (연결)
  - Statement / PreparedStatement (명령)
  - ResultSet (결과)
  - DriverManager (관리, 클래스)

6.2 Connection

Connection:

  DB 연결:
    - 세션 표현
    - Statement 생성
    - 트랜잭션 제어

6.3 PreparedStatement

PreparedStatement:

  미리 컴파일된 SQL:
    - 파라미터 (?)
    - SQL 인젝션 방어
    - 성능 (재사용)

6.4 ResultSet

ResultSet:

  조회 결과:
    - 행 단위 커서
    - rs.next() (다음 행)
    - rs.getXxx() (컬럼 값)

6.5 ILIC 의 맥락

// 핵심 인터페이스 (ILIC)
public class ShipmentDao {
    public Shipment get(Long id) throws Exception {
        // Connection (연결)
        Connection c = DriverManager.getConnection(url, user, pwd);
        
        // PreparedStatement (명령, 파라미터)
        PreparedStatement ps = c.prepareStatement(
            "select * from shipments where id = ?");
        ps.setLong(1, id);   // ? 바인딩 (SQL 인젝션 방어)
        
        // ResultSet (결과)
        ResultSet rs = ps.executeQuery();
        Shipment s = null;
        if (rs.next()) {                      // 커서 이동
            s = new Shipment();
            s.setId(rs.getLong("id"));        // 컬럼 값
            s.setBlNo(rs.getString("bl_no"));
        }
        
        rs.close(); ps.close(); c.close();
        return s;
    }
    String url = "jdbc:mysql://localhost/ilic", user = "u", pwd = "p";
}
class Shipment {
    void setId(Long id) {}
    void setBlNo(String s) {}
}
// 모두 인터페이스 (구현은 드라이버)

6.6 자기 점검 답변

JDBC 핵심 인터페이스는?

:
1. 핵심:

  • Connection/Statement/ResultSet
  1. Connection:

    • 연결/세션
  2. PreparedStatement:

    • 파라미터, 인젝션 방어
  3. ResultSet:

    • 결과 커서

7️⃣ 5주차 패턴과 닮음

7.1 인터페이스 추상화

인터페이스 추상화 (5주차):

  JDBC:
    - Connection (인터페이스)
    - 드라이버 (구현)

  5주차:
    - ConnectionMaker (인터페이스)
    - 구현체

→ 같은 추상화

7.2 전략 패턴

전략 패턴:

  JDBC:
    - 인터페이스 (전략)
    - 드라이버 (구체 전략)
    - 런타임 선택 (URL)

→ 5주차 전략 패턴

7.3 DIP

DIP:

  애플리케이션:
    - Connection (추상) 의존
    - 구체 드라이버 모름

→ 5주차 DIP

7.4 OCP

OCP:

  새 DB 지원:
    - 새 드라이버 추가 (확장)
    - 애플리케이션 코드 변경 X (닫힘)

→ 5주차 OCP

7.5 ILIC 의 맥락

// JDBC = 5주차 패턴의 실제 구현

// 인터페이스 (추상) — 5주차 ConnectionMaker 처럼
// java.sql.Connection (JDBC 인터페이스)

public class ShipmentDao {
    public void add(Shipment s) throws Exception {
        // Connection 인터페이스에만 의존 (DIP)
        Connection c = DriverManager.getConnection(url);
        // c 는 어떤 구현? MySQL? Oracle? 모름 (추상)
        // 드라이버가 구현 (전략)
    }
    String url = "jdbc:mysql://localhost/ilic";
}
class Shipment {}

// 5주차 매핑:
// Connection (인터페이스) = ConnectionMaker (인터페이스)
// MySQL Connection (구현) = NConnectionMaker (구현)
// DriverManager = 팩토리/조립
// → JDBC 가 5주차 원칙의 실제 사례

7.6 자기 점검 답변

JDBC가 닮은 5주차 패턴은?

:
1. 인터페이스 추상화:

  • Connection (인터페이스)
  1. 전략 패턴:

    • 드라이버 (전략)
  2. DIP:

    • 추상 의존
  3. OCP:

    • 새 드라이버 (확장)

8️⃣ DB 교체 변경 범위

8.1 변경 범위

DB 교체 변경 범위:

  JDBC:
    - URL 변경
    - 드라이버 변경 (의존성)
    - SQL 방언 일부 (다음 Unit)

→ 최소 변경

8.2 JDBC 전 vs 후

JDBC 전 vs 후:

전 (Unit 3.1):
  - 전체 재작성

후 (JDBC):
  - URL/드라이버만
  - 코드 그대로

8.3 변경 격리

변경 격리:

  DB 변경 영향:
    - URL (설정)
    - 드라이버 (의존성)
    - 애플리케이션 코드 X

→ OCP 효과

8.4 한계 예고

한계 예고:

  JDBC 도 완벽 X:
    - SQL 문법 차이 (방언)
    - LIMIT vs ROWNUM
    - → Unit 3.3

8.5 ILIC 의 맥락

// DB 교체 변경 범위 (ILIC)

// application.yml (설정만)
// spring:
//   datasource:
//     url: jdbc:mysql://localhost/ilic       # MySQL
//     # url: jdbc:oracle:thin:@host:1521:ilic  # Oracle (변경)
//     driver-class-name: com.mysql.cj.jdbc.Driver

// 애플리케이션 코드는 그대로
public class ShipmentDao {
    public void add(Shipment s) throws Exception {
        Connection c = DriverManager.getConnection(url);
        // 이 코드 변경 X (DB 교체해도)
    }
    String url;   // 설정에서 주입
}
class Shipment {}

// DB 교체:
// 1. URL 변경 (설정)
// 2. 드라이버 의존성 추가
// 3. SQL 방언 조정 (일부)
// → 코드 거의 그대로 (JDBC 전과 천지차)

8.6 자기 점검 답변

DB 교체 시 변경 범위는?

:
1. 변경 범위:

  • URL/드라이버
  1. 전 vs 후:

    • 재작성 vs URL만
  2. 격리:

    • 코드 변경 X
  3. 한계:

    • SQL 방언 (3.3)

9️⃣ 면접 + 자기 점검

9.1 면접 단골 질문 매핑

Q핵심 답변
JDBC?자바 DB 표준 API
같은 코드 다른 DB?URL/드라이버만
해결한 것?연결/실행/결과 통일
DriverManager?드라이버 선택, Connection
드라이버 로딩?자동 (JDBC 4.0+)
핵심 인터페이스?Connection/Statement/ResultSet
5주차 패턴?전략/인터페이스/DIP
DB 교체?URL/드라이버
OCP?새 드라이버 확장
PreparedStatement?파라미터, 인젝션 방어

9.2 자기 점검 체크리스트

JDBC

  • 표준 API

같은 코드

  • URL/드라이버

해결

  • 연결/실행/결과

DriverManager

  • 역할

드라이버 로딩

  • 자동

핵심 인터페이스

  • 3개

5주차 패턴

  • 전략/DIP

DB 교체

  • 범위

9.3 추가 심화 질문

Q1: Statement vs PreparedStatement?

답:

  • Statement: 단순, SQL 인젝션 위험
  • PreparedStatement: 파라미터, 안전, 성능
  • PreparedStatement 권장
  • 미리 컴파일

Q2: SQL 인젝션?

답:

  • 악의적 SQL 주입
  • 문자열 연결 위험
  • PreparedStatement 방어
  • 파라미터 바인딩

Q3: ResultSet 커서?

답:

  • 행 가리키는 포인터
  • next() 로 이동
  • 기본 forward-only
  • scrollable 옵션

Q4: 자원 해제 순서?

답:

  • ResultSet → Statement → Connection
  • 역순 (생성 반대)
  • try-with-resources
  • finally

Q5: JDBC 4.x SPI?

답:

  • ServiceLoader
  • META-INF/services/java.sql.Driver
  • 자동 드라이버 등록
  • Class.forName 대체

🎯 핵심 요약 — 3줄 정리

1. JDBC = 표준 API

  • 자바 DB 접근 표준, 연결·실행·결과 통일
  • 같은 코드, 다른 DB (URL/드라이버만 변경)

2. DriverManager + 인터페이스

  • DriverManager: URL 보고 드라이버 선택, Connection 생성
  • Connection/Statement/ResultSet 인터페이스 (구현은 드라이버)

3. 5주차 패턴의 실제

  • 전략 패턴/인터페이스 추상화/DIP/OCP 의 실제 구현
  • DB 교체 = URL/드라이버만 (코드 그대로)

📚 다음으로...

Unit 3.3 — JDBC가 해결하지 않는 것 (Phase 3 완주)

이번 Unit에서 JDBC 표준화를 봤다면, 다음은 JDBC 의 한계 (Phase 3 마지막).

  • SQL 문법 차이 (LIMIT vs ROWNUM)
  • API 통일했지만 SQL 은 그대로
  • ORM/MyBatis 등장
  • Dialect

Phase 3 진행 상황

💾 Phase 3 — JDBC 표준화의 등장
  ✅ Unit 3.1 JDBC 없던 시절의 고통
  ✅ Unit 3.2 JDBC의 표준화 효과 ← 여기
  ⏭ Unit 3.3 JDBC가 해결하지 않는 것 — Phase 3 완주

6주차 누적 진행

🧪 Part A (9 Unit) ✅
💾 Part B — DB 접근의 진화
  Phase 3 — JDBC (2/3 진행)

총: 11/28 Unit
profile
Software Developer

0개의 댓글