오늘부터 가볍게 면접 준비도 할 겸 헷갈리는 개념도 바로 잡을 겸 이 글을 보는 다른 학생들에게 도움도 될 겸! CS/보안 기초 개념을 정리할까 한다.
쿠키
와 세션
을 이해하려면, 먼저 쿠키와 세션이 쓰이는 프로토콜인 http
에 대해 이해해야 한다.
HTTP
HTTP는 클라이언트-서버 사이에 이루어지는 요청/응답(request/response) 프로토콜이다. 예를 들어 클라이언트(웹 브라우저)가 특정 웹 페이지에 접속할 경우 HTTP를 통해 해당 웹 페이지의 그림 정보 등을 서버에 요청하고, 서버는 이 요청에 응답하여 필요한 정보를 클라이언트에 전달하는 식이다.
HTTP는 다음 두 가지 특징을 지닌다.
- Connectionless (비연결성)
- Stateless (무상태성)
두 성질의 차이를 쉽게 이해하려면 Connectionless한 성질 때문에 Stateless 해진다
라고 생각하면 좋을 것 같다.Connectionless (비연결성)
은, 연결을 맺은 서버-클라이언트 관계에서 클라이언트의 요청에 대해 서버가 응답을 마치면 그 연결을 끊는 성질을 의미한다.
이로 인해 A 클라이언트가 보내는 5번의 요청을 서버는 모두 A 클라이언트의 요청인지, A ~ E 클라이언트가 보내는 각각의 요청인지 식별할 수 없어진다. 서버는 매 요청마다 클라이언트를 식별할 필요성이 생긴 것이다. 이를 클라이언트의 상태를 저장하지 않는 무상태성, 즉 Stateless한 성질
이라고 표현하였다.
HTTP는 왜 Connectionless하고 Stateless할까?
HTTP는 인터넷 상 불특정 다수의 통신 환경을 기초로 설계되었다. 따라서 한 번 맺은 연결을 지속적으로 유지한다면 쓸데 없이 많은 자원이 소요될 것이다. 매번 연결을 맺는 편이 지속적 연결 유지에 자원을 쓰는 것보다 효율적일 것이다.
클라이언트의 상태를 기억하기 위한 수단, 쿠키와 세션
앞서 http
프로토콜의 비연결성
과 무상태성
의 특징으로 인해 서버가 클라이언트의 상태를 기억해야 할 필요성이 있다고 언급하였다. 이를 위해 http
가 선택한 수단이 바로 쿠키
와 세션
이다.
쿠키 (Cookie)
쿠키는 서버에 인증하기 위한 클라이언트의 정보를 클라이언트 단에 저장하는 값이다.
우리는 아주 쉽게 쿠키 값을 확인할 수 있다.
개발자 모드의 Console 탭에서 document.cookie
를 입력해보자.
출력된 값의 자세한 태그들은 이곳에 잘 설명되어 있다.
쿠키가 담긴 헤더도 쉽게 볼 수 있다.
개발자 모드의 Network 탭을 열고 구글 검색창에 아무 말이나 써보자. 검색 창 밑에 내가 입력한 키워드와 관련된 연관 검색어나 연관 이미지가 뜰 것이다. 이는 동시에 Network 탭에도 기록된다. 위 사진처럼 기록된 목록 중 하나를 선택하고 Headers 탭을 보면 그 짧은 사이 오고 간 요청 헤더와 응답 헤더를 볼 수 있다.
사진을 자세히 보면 헤더 속 쿠키 값과 관련된 이름이 다른 것을 확인할 수 있다.
set-cookie
는 HTTP 응답 헤더에서 서버가 클라이언트 측에 쿠키를 전송하기 위해 사용된다.cookie
는 HTTP 요청 헤더에서 이전에 서버로부터 받은 set-cookie 값을 포함한 값을 클라이언트가 전송하기 위해 사용된다.
이 쯤 되면 그래서 쿠키가 언제 생기는건가? 하는 의문이 들 것이다. 아래와 같은 단계로 이해하면 쉬울 것 같다. 핵심은 HTTP의 stateless한 성질이 어떻게 보완되느냐에 있다.
- 클라이언트가 서버에게 페이지 정보를 요청
- 서버는 클라이언트에 대한 쿠키 생성 후, HTTP 응답 헤더에 쿠키를 포함하여 응답 (HTTP response 헤더의 'set-cookie')
- 클라이언트의 요청과 서버의 응답이 끝나면 HTTP의 비연결성으로 인해 연결 끊김
- 새로운 요청을 할 경우, 이전에 받은 쿠키값을 보관하고 있다가 HTTP 요청 헤더에 값을 포함하여 요청 (HTTP request 헤더의 'cookie')
- 서버는 쿠키값을 보고 이전에 요청을 보낸 클라이언트를 인식하여 상태를 기억하여 HTTP의 Stateless한 성질을 보완
쿠키의 장단점
먼저, 쿠키의 장점을 보자.
- 사용자 입장에서, 별도의 인증 과정을 거치지 않고 서버가 나를 쉽게 기억하도록 할 수 있다. ID-PW를 굳이 입력하지 않아도 되는 자동완성 기능, 지난 번 읽었던 글이 다시 새로운 글에 업데이트 되지 않도록 하는 기능 등 무상태성인 HTTP에게 상태 정보를 기억하게 하는 가벼운 일에 쿠키가 쓰인다.
쿠키의 단점은 이렇다.
- 쿠키값은 쉽게 수정 가능하다.텍스트로 저장되다 보니 더욱 더. 따라서 악의적인 공격자에 의해 변조될 가능성도 크다. 쿠키가 서버에 나를 기억하게 하는 용도인 동시에 보안적 약점이 있다보니 쿠키에는 그다지 중요하지 않은 정보만 저장해야 할 것이다.
세션 (Session)
세션은 쿠키와 달리 쿠키는 서버에 인증하기 위한 클라이언트의 정보를 서버 단에서 저장 및 관리하는 방식이다.
쿠키가 쿠키값을 통해 클라이언트의 상태를 기억하게 한다면, 세션은 서버가 클라이언트에 부여한 세션 ID을 통해 기억하게 한다.
그런데 이 세션 ID는 사실 쿠키를 통해 관리된다.
구글에 로그인한 다음, EditThisCookie 익스텐션으로 쿠키값을 살펴보자. 아래 그림과 같이 SSID
라는 이름의 쿠키가 존재한다. 이것이 서버로부터 발급받은 세션 ID를 쿠키를 통해 관리한다는 의미다.
조금 더 자세한 세션의 작동 방식은 다음과 같다.
- 클라이언트가 서버에게 페이지 정보를 요청
- 서버는 클라이언트에 대한 쿠키 생성 후, HTTP 응답 헤더에 세션 ID 값이 담긴 쿠키를 포함하여 응답 (HTTP response 헤더의 'set-cookie')
- 클라이언트의 요청과 서버의 응답이 끝나면 HTTP의 비연결성으로 인해 연결 끊김
- 새로운 요청을 할 경우, 이전에 받은 쿠키값을 보관(SSID, JSESSIONID 등)하고 있다가 HTTP 요청 헤더에 세션 ID 값이 담긴 쿠키를 포함하여 요청 (HTTP request 헤더의 'cookie')
- 서버는 쿠키 내 세션 ID 값을 보고 이전에 요청을 보낸 클라이언트를 인식하여 상태를 기억하여 HTTP의 Stateless한 성질을 보완
말 그대로 쿠키를 통해 세션 ID가 저장 및 관리되다 보니 쿠키의 작동 방식과 거의 같다. 한 가지 다른 점은 단순한 쿠키값이 아니라, 쿠키 값 내 서버가 준 세션 ID에 대한 정보를 서버와 클라이언트가 주고 받으며 서버에 클라이언트를 인증하는 것이다. 세션 ID는 서버가 발급하고, 관리하기 때문이다.
세션의 장단점
장점은 이렇다.
- 쿠키에 비해서는 그나마 안전하다. 세션 ID는 클라이언트에 저장된다고 해도 클라이언트의 정보 자체는 서버에 저장되어 있기 때문이다.
- 로그인 정보를 유지하여 자동 로그인 되는 기능은 정말 좋다.
세션의 단점은 다음과 같다.
- 쿠키에 비해 조금 느리다. 쿠키는 서버의 헤더를 바로 참조하면 되지만 세션은 세션ID를 주고 받은 다음 인증을 거쳐 서버의 데이터를 참조해야 하므로 속도가 비교적 조금 느리다.
- 세션은 서버의 자원을 사용한다. 한계가 존재하는 서버 자원을 사용하므로 속도 저하나 오버헤드 등 서버에 부하를 줄 수 있다.
- 그럼에도 불구하고 해킹의 위험성은 여전하다. 대표적으로 세션 하이재킹 (Session Hi-jacking)이 있다.
참고