Security - 대칭키/비대칭키/CA

2026. 1. 1. 13:56·CKA

이 글은 “클라이언트-서버 통신을 안전하게 만들려면 무엇이 필요한가?”를 대칭키 → 문제점 → 키를 주고받지 않고 대칭키를 만드는 방법(키 교환) → 비대칭키 → 비대칭키의 한계 → 가짜 서버(MITM) 문제 → CA/PKI로 해결 순서로 차근차근 설명합니다. 중간중간 “해커가 가로채면 무엇이 위험해지는지”와 “현실에서 어떻게 막는지”도 함께 정리합니다.


0. 우리가 지키려는 보안 목표 3가지

클라이언트(브라우저/앱)와 서버가 통신할 때 보통 3가지를 지키고 싶습니다.

  1. 기밀성(Confidentiality): 중간에서 봐도 내용을 못 알아봐야 함
  2. 무결성(Integrity): 중간에서 내용을 바꾸면 들켜야 함
  3. 인증(Authentication): 내가 말하는 상대가 “진짜 그 상대”여야 함 (가짜 서버/가짜 클라 방지)

대칭키/비대칭키/CA는 이 3가지를 달성하기 위한 퍼즐 조각입니다.


1. 대칭키(Symmetric Key)란?

1-1. 정의

대칭키 암호화는 같은 키 하나로

  • 암호화(Encrypt)
  • 복호화(Decrypt)
    를 모두 하는 방식입니다.

예:

  • 클라이언트와 서버가 “같은 키 K”를 공유하고 있다고 가정하면,
    • 클라이언트: Encrypt(K, "text") → 암호문
    • 서버: Decrypt(K, 암호문) → "text"

1-2. 장점

대칭키는 현실에서 매우 중요합니다.

  • 빠릅니다. (대량 데이터 암호화에 적합)
  • 구현이 널리 표준화되어 있고 성능이 좋습니다.
  • 그래서 실제 인터넷 트래픽(HTTPS)의 “본문 데이터”는 대부분 대칭키로 암호화됩니다.

2. 대칭키의 근본 문제: “키를 어떻게 안전하게 공유하나?”

대칭키는 빠르고 좋지만 치명적인 문제가 있습니다.

2-1. 키를 전달하는 순간이 위험하다

클라이언트가 서버에게 “우리의 키 K”를 보내야 공유가 되는데, 그 전달 과정에서 해커가 네트워크를 스니핑(도청)하면:

  • 해커가 키 K를 얻음
  • 그러면 해커는 암호문도 복호화 가능

즉, “데이터는 암호화했는데 키를 뺏겨서 끝”이 됩니다.

2-2. 흔한 오해

“그럼 키도 암호화해서 보내면 되지 않나?”
→ 그런데 키를 암호화하려면 또 다른 키가 필요하고, 그 키도 안전하게 공유해야 합니다.
결국 같은 문제가 반복됩니다(무한 루프).


3. 해결 아이디어 1: 키를 “주고받지 않고” 대칭키를 만드는 방법 (키 교환)

여기서 등장하는 핵심이 키 교환(Key Exchange) 입니다.
대표적으로 (EC)DHE, ECDH 같은 방식이 사용됩니다.

3-1. 핵심 직관

  • 클라이언트: 비밀값 a를 만들고, 이를 가공한 공개값 A를 서버에 보냅니다.
  • 서버: 비밀값 b를 만들고, 이를 가공한 공개값 B를 클라이언트에 보냅니다.
  • 클라이언트는 (내 비밀 a + 서버 공개값 B)를 계산 → 값 S 도출
  • 서버는 (내 비밀 b + 클라이언트 공개값 A)를 계산 → 값 S 도출
  • 수학적으로 두 S는 동일한 값이 나옵니다!

중요: 이 방식에서는 대칭키를 네트워크로 보내지 않습니다.
각자 “계산”으로 같은 키를 만들어냅니다.

3-2. 스니핑에 강한 이유

해커는 중간에서 공개값을 다 봐도,

  • 비밀값(클라의 a, 서버의 b)을 모르기 때문에
  • 같은 공유비밀 S를 계산하기가 매우 어렵습니다.

따라서 “키를 전달하다가 털리는 문제”가 크게 줄어듭니다.


4. 하지만 여기서 또 남는 문제: “가짜 서버(MITM)”는 어떻게 막지?

키 교환은 “키를 안전하게 만들기”에는 강하지만, 상대가 진짜인지까지 자동으로 해결해주진 않습니다.

4-1. 중간자 공격(MITM) 시나리오

클라이언트는 my-bank.com에 접속하려고 했는데, 해커가 중간에서 가로채서 이렇게 만들었다고 합시다.

  • 클라이언트 ↔ 해커 ↔ 진짜 서버

해커는 이런 식으로 할 수 있습니다.

  1. 클라이언트와 “키 교환”을 따로 해서 클라-해커 대칭키를 만들고
  2. 진짜 서버와도 “키 교환”을 따로 해서 해커-서버 대칭키를 만든다
  3. 해커는 가운데에서 데이터를 복호화 → 읽고/변조 → 다시 암호화해서 전달한다

즉, 키 교환만 있으면 해커는 “양쪽과 각각 안전한 연결”을 만들고 그 사이를 중계할 수 있습니다.
이게 MITM의 핵심입니다.

결론: 키 교환은 “도청”은 어렵게 하지만, “가짜 서버(중간자)”까지 자동으로 막아주진 않습니다.
그래서 상대 신원 인증이 반드시 필요합니다.


5. 해결 아이디어 2: 비대칭키(Asymmetric Key)로 “신원 확인”을 한다

5-1. 비대칭키란?

비대칭키는 키가 두 개입니다.

  • 개인키(Private Key): 본인만 보관(비밀)
  • 공개키(Public Key): 누구나 알아도 됨

비대칭키가 핵심 역할을 하는 곳은 보통 두 가지입니다.

  1. 서명(Signature): 개인키로 서명 → 공개키로 검증
  2. (과거 방식/일부 상황) 키 전달(암호화): 공개키로 암호화 → 개인키로 복호화
    • 하지만 현대 시스템은 “대량 데이터”를 공개키로 암호화하지 않고, 대체로 “서명+키교환+대칭암호” 조합을 씁니다.

5-2. 서명(Sign)과 검증(Verify)

“내가 나다”를 증명하는 가장 중요한 패턴이 이겁니다.

  • 서버(또는 클라이언트)가 어떤 메시지 M에 대해:
    • Sig = Sign(개인키, M)
  • 상대는:
    • Verify(공개키, M, Sig) == True인지 확인

이게 의미하는 바:

  • 서명은 개인키가 있어야만 만들 수 있고
  • 공개키로는 “진짜인지 검증”만 가능하다

6. 비대칭키만 써도 여전히 남는 문제: “공개키를 누가 보증하지?”

여기서 많은 사람이 걸립니다.

6-1. “공개키만 있으면 검증 가능”의 함정

맞습니다. 하지만 전제가 있습니다.

  • “그 공개키가 진짜 my-bank.com의 공개키”라는 보장이 있어야 합니다.

만약 해커가 중간에서

  • 자기 공개키를 “my-bank.com의 공개키”라고 속여서 클라이언트에게 주면?

클라이언트는 해커 공개키로 서명을 검증하고 “진짜구나” 착각할 수 있습니다.

즉, 비대칭키는 “검증” 메커니즘은 제공하지만,
‘처음 공개키를 어떻게 믿을 것인가’ 문제를 남깁니다.

이게 바로 웹에서 CA가 필요한 이유입니다.


7. CA(인증기관)는 왜 필요하고, 무엇을 해결하나?

7-1. 문제 정의: 첫 만남의 신뢰(First Contact Trust)

웹은 불특정 다수가, 수많은 사이트에 “처음” 접속합니다.

SSH처럼 매번:

  • “이 서버 지문을 저장할까요? yes/no”
    를 사용자에게 묻게 하면,
  • 사용자는 습관적으로 yes를 누르고
  • 첫 접속 MITM에 취약해집니다.

그래서 웹은 “사용자에게 판단을 맡기지 않고” 자동으로 검증하도록 설계했습니다.

7-2. CA가 하는 일

CA는 한 줄로 말하면:

“이 도메인(my-bank.com)을 통제하는 주체에게만 인증서(공개키 포함)를 발급해주는 기관”

CA는 인증서를 발급할 때 도메인 통제 검증(DCV) 을 합니다. 예:

  • DNS에 특정 TXT 레코드 넣기
  • 웹서버 특정 경로에 토큰 파일 올리기
  • (제한적으로) 이메일 검증

해커는 보통 my-bank.com의 DNS/웹서버를 제어할 권한이 없으므로 발급에 실패합니다.

7-3. 브라우저는 왜 CA를 믿나?

브라우저/OS에는 이미 “신뢰할 루트 CA 목록”이 내장되어 있습니다.

  • 서버가 인증서 체인을 보내면
  • 브라우저는 그 체인이 “내가 신뢰하는 루트 CA”까지 이어지는지 검사합니다.

즉, 웹은 known_hosts 대신 브라우저 내장 신뢰 저장소 + CA 체인으로 첫 접속부터 신뢰를 자동화합니다.


8. “가짜 서버로 유도”를 TLS가 막는 전체 흐름(핵심만)

8-1. 공격자 시나리오: my-bank.com 트래픽을 자기 서버로 유도

클라이언트가 my-bank.com으로 접속했는데 실제로는 공격자 서버(A)로 갔다고 합시다.

공격자가 “진짜 my-bank.com 인증서를 복사해서” 내밀면 될까요?

→ 안 됩니다.

왜냐하면 TLS는 단순히 인증서를 보여주는 게 아니라, 서버가 그 인증서 공개키의 개인키를 실제로 가지고 있다는 증명을 반드시 요구합니다(서명).

정리:

  1. 공격자 A가 진짜 my-bank.com 인증서(공개키)를 베껴서 보여준다
  2. 클라이언트는 “그럼 그 개인키로 핸드셰이크 내용에 서명해봐”를 요구한다
  3. 공격자 A는 개인키가 없으므로 서명을 만들 수 없다
  4. 클라이언트는 검증 실패로 연결을 끊는다

즉:

  • 인증서(공개키)만으로는 부족
  • 개인키 소유 증명(서명)이 있어야 한다

8-2. 공격자가 성공하는 현실적 조건

공격자가 진짜로 성공하려면 보통 다음 중 하나가 필요합니다.

  • 서버 개인키 유출(서버 침해)
  • 클라이언트 PC가 공격자 루트 CA를 신뢰하도록 오염됨(악성 루트 인증서 설치 등)
  • CA의 오발급(드물지만 역사적으로 사고는 존재)

9. 정리: 현실에서 HTTPS는 어떻게 안전하게 되나?

웹(HTTPS)은 보통 다음 “3단 결합”으로 안전을 만듭니다.

  1. CA/인증서: “이 서버가 my-bank.com 맞다” (도메인 신원 확인)
  2. 키 교환(ECDHE 등): 대칭키를 “주고받지 않고” 안전하게 합의
  3. 대칭 암호(AES-GCM/ChaCha20 등): 실제 데이터(HTTP 요청/응답)를 빠르게 암호화 + 위변조 방지

10. 보안 리스크와 방어 체크리스트(현실적인 관점)

10-1. MITM 방어

  • 브라우저: CA 체인 검증 + 도메인(SAN) 검증이 기본으로 켜져 있음
  • 서버 운영자:
    • HSTS 적용(가능하면)
    • 최신 TLS 설정(TLS 1.2/1.3, 강한 cipher)
    • 인증서 관리 자동화(예: ACME/Let’s Encrypt 사용 시 운영 안정성)

10-2. 키 유출 방어(서버 개인키)

  • 개인키 파일 접근권한 최소화
  • 키 관리/보관(HSM/KMS 등 고급 옵션)
  • 키 회전(rotate) 절차 준비
  • 침해 대응(유출 의심 시 즉시 교체)

10-3. 클라이언트 측 오염 방지(루트 CA 설치)

  • 알 수 없는 루트 인증서 설치 금지
  • 기업 프록시/보안SW가 설치한 루트 CA의 의미를 이해(합법적일 수도 있음)
  • 브라우저 경고 무시 금지

결론 요약

  • 대칭키는 빠르고 실전 데이터 암호화에 필수지만, “키 공유”가 문제다.
  • 키 교환은 키를 “전송하지 않고” 계산으로 만들어 스니핑 위험을 줄인다.
  • 하지만 가짜 서버(MITM) 문제는 남는다.
  • 이를 해결하려면 “상대가 진짜인지”를 비대칭키 서명/검증으로 증명해야 한다.
  • 웹에서는 첫 접속부터 자동 검증이 필요하므로 CA/PKI가 들어간다.
  • 최종적으로 HTTPS는 CA(신원) + 키교환(키 합의) + 대칭암호(데이터 보호) 조합으로 완성된다.

 

'CKA' 카테고리의 다른 글

Security - TLS in Kubernetes  (0) 2026.01.01
Security - SSH 프로세스 정리  (0) 2026.01.01
Security - Authentication 기초  (0) 2025.12.31
Security - 개요  (0) 2025.12.31
Cluster Maintenance - 총 정리  (0) 2025.12.31
'CKA' 카테고리의 다른 글
  • Security - TLS in Kubernetes
  • Security - SSH 프로세스 정리
  • Security - Authentication 기초
  • Security - 개요
5jyan5
5jyan5
  • 5jyan5
    jyan
    5jyan5
  • 전체
    오늘
    어제
    • 분류 전체보기 (243)
      • 김영한의 스프링 핵심 원리(기본편) (8)
      • 김영한의 스프링 핵심 원리 - 고급편 (11)
      • 김영한의 스프링 MVC 1편 (1)
      • 김영한의 스프링 DB 1편 (3)
      • 김영한의 스프링 MVC 2편 (3)
      • 김영한의 ORM 표준 JPA 프로그래밍(기본편) (9)
      • 김영한의 스프링 부트와 JPA 활용2 (2)
      • 김영한의 실전 자바 - 중급 1편 (1)
      • 김영한의 실전 자바 - 고급 1편 (9)
      • 김영한의 실전 자바 - 고급 2편 (9)
      • Readable Code: 읽기 좋은 코드를 작성.. (2)
      • 김영한의 실전 자바 - 고급 3편 (9)
      • CKA (119)
      • 개발 (37)
      • 경제 (4)
      • 리뷰 (1)
      • 정보 (2)
  • 블로그 메뉴

    • 링크

    • 공지사항

    • 인기 글

    • 태그

      jpq
      Target
      log trace
      단방향 맵핑
      스레드
      Thread
      버퍼
      프록시
      프록시 팩토리
      페치 조인
      자바
      cglib
      WAS
      typequery
      gesingleresult
      @discriminatorcolumn
      reentarantlock
      @discriminatorvalue
      JPQL
      김영한
      jdk 동적 프록시
      @args
      빈 후처리기
      락
      조회 성능 최적화
      고급
      requset scope
      @within
      hibernate5module
      양방향 맵핑
    • 최근 댓글

    • 최근 글

    • hELLO· Designed By정상우.v4.10.2
    5jyan5
    Security - 대칭키/비대칭키/CA
    상단으로

    티스토리툴바