최근에 스터디 팀원들과 배포를 하고있었다. HTTPS 적용을 위해서 SSL 인증서 구입하고 Nginx 설정파일을 수정하는 과정들을 진행했는데 그 과정에서 팀원들의 물음에 제대로 답변하지 못했다. 그래서 아직 HTTPS에 대해서 잘 이해하지 못한 것 같아서 좀 더 자세히 알아보고자 한다.
이전에 공부를 하면서 알아본 HTTP에서는
위의 웹 어플리케이션과 같이 HTTP를 사용해서 데이터를 주고 받게되면 데이터가 그대로 평문으로 보내진다고 한다.
실제로 wireshark를 이용해서 패킷을 확인해보니 아래와 같이 평문으로 보여지게 되고 이런 상황에서 누군가가 해당 패킷을 가로채면 내용이 노출되는 보안 문제가 발생할 수 있다. 그래서 이를 해결해주는 프로토콜이 바로 HTTPS이다.
HTTPS
는 SSL(Secure Socket Layer), TLS(Transport Layer Security)을 이용하여 암호화 된 데이터를 주고 받을 수 있는 프로토콜이다.
SSL과 TLS
같은 말이다. 네스케이프에 의해서 SSL이 발명되었고, 이것이 점차 폭넓게 사용되다가 표준화 기구인 IETF의 관리로 변경되면서 TLS라는 이름으로 바뀌었다. TLS 1.0은 SSL 3.0을 계승한다. 하지만 TLS라는 이름보다 SSL이라는 이름이 훨씬 많이 사용되고 있다.
- https://www.opentutorials.org/course/228/4894 -
실제로 HTTPS를 사용하여 데이터를 주고 받게 되면 다음과 같이 패킷의 내용이 암호화된것을 확인할 수 있다.
그렇다면 브라우저와 서버가 데이터를 어떻게 암호화하고 복호화하는지에 대해서 궁금해질텐데 이를 알기 위해서는 대칭키와 공개키를 알고 있어야한다.
대칭키는 데이터를 암호화, 복호화 하는데 사용되는 암호키를 동일하게 둔 방식이다.
하지만 대칭키 방식은 데이터를 암호화, 복호화 하기 위해 통신을 할때 대칭키를 상대방에게 전달해줘야하는데 이 과정에서 대칭키가 유출되면 키를 획득한 공격자는 암호의 내용을 복호화할 수 있기 때문에 곤란하다...
그래서 이런 배경에서 나온 암호화 방식이 공개키방식이다.
대칭키와 다르게 데이터를 암호화, 복호화 하는데 사용되는 암호키를 따로 둔 방식으로 비대칭키라고도 불린다. 공개키로는 보통 데이터를 암호화는데 사용하며 개인키로는 데이터를 복호화하는데 사용한다. (개인키는 말그대로 Key 발행자만이 갖는 키)
이제 공개키를 공유해도 개인키를 모르면 복호화를 할 수 없기 때문에 비교적 안전하지만 매번 이 과정을 반복하기에는 복잡하기 때문에 실제로는 대칭키를 서로 주고 받기 전까지는 공개키 암호화 방식을 사용하고 이후에 대칭키 암호화 방식한다고 한다.
그 과정은 다음과 같다.
A와 B간에 서로 통신을 한다고 가정하면,
A가 B의 공개키
로 대칭키
를 암호화해서 B에게 보낸다
B는 자신의 개인키
로 이를 복호화해서 대칭키
를 얻는다.
이제 서로간에 대칭키를 알기 때문에 대칭키
를 사용해서 암호화하고 복호화
하여 정보를 주고 받는다. (B가 대칭키를 사용해서 데이터를 암호화 -> A는 동일한 대칭키를 사용하여 데이터를 복호화)
여기에서 핵심은 보안문제를 해결하기 위해 대칭키를 교환하는 과정인데 이때 사용되는게 SSL(Secure Socket Layer)로 이 과정에서 CA(Certificate Authority)를 통해 서로간에 신뢰를 확보하는 것이다.
그러면 실제로 서버와 브라우저간에 HTTPS를 사용해서 통신하는 과정을 알아보자.
우선, 서버에서 한쌍의 공개키, 개인키를 생성 한 다음 공개키를 CA에 전달하여 SSL 인증서 생성을 요청한다.
CA(Certificate Authority)
누구나가 객관적으로 신뢰할 수 있는 기관으로 SSL 인증서를 발급, 관리해주는 기관
그러면 CA에서 SSL 인증서를 발급을 해주는데 이 인증서에는 방금 전달한 공개키, 공개키를 암호화 하는 방법등이 담겨있다. CA에도 CA만의 공개키, 개인키를 가지고 있기 때문에 SSL 인증서를 CA의 개인키로 암호화하여 서버에게 전달해준다.
이제 브라우저로부터 첫 요청이 오게되면 서버는 이 암호화된 인증서를 준다. 그렇다면 브라우저 측에서 신뢰성이 검증된 CA의 공개키를 사용해 인증서를 해독하여 '서버의 공개키'를 얻게 된다. (이제 브라우저는 서버의 공개키를 확보)
드디어 브라우저에서 실제 데이터 암호화, 복호화에 사용 될 '대칭키'를 만들고 '서버의 공개키'를 사용하여 암호화 후 서버로 보내게 된다.(대칭키와 공개키의 1번 과정이라고 생각하면 된다.)
이후에 서버는 자신의 공개키를 사용하여 복호화 후 '대칭키'를 얻는다.(대칭키와 공개키의 2번 과정이라고 생각하면 된다.)
이제 이 대칭키를 사용하여 데이터를 암호화하고 복호화하고 통신을 하는 것이다.(대칭키와 공개키의 3번 과정이라고 생각하면 된다.)