➣ 인증은 회원가입과 로그인을 하는 것이라고 할 수 있다.
➣ 인증이 필요한 이유 : 우리 서비스를 누가 쓰는지 어떻게 사용하는지 추적이 가능하도록 하기 위해 필요
➣ 인증에 필요한 것은 무엇일까? ( => 회원가입, 로그인 할 때 필요한 것이 무엇인지를 생각해보자)
➣➣ 아이디, 이메일주소, 비밀번호(가장 중요) 등이 있다.
access token
을 클라이언트에게 전송access token
을 첨부해서 request를 서버에 전송함으로서 매번 로그인 해도 되지 않도록 한다.database에 저장 시 개인 정보를 해싱하여 복원할 수 없도록 해야 한다.
통신 시 개인 정보를 주고받을 때 SSL을 적용하여 암호화(HTTPS)한다.
SSL이란? Security Socket Layer의 약자로 서버와 브라우저 간 보안을 위해 만든 프로토콜
- 서버와 클라이언트 간의 통신 과정
- 클라이언트가 SSL로 암호화된 페이지를 요청한다(https)
- 서버는 Public key를 인증서와 함께 전송한다.
- 클라이언트는 인증서가 Trusted root CA(인증기관)로부터 서명된 것인지, 날짜 등이 유효한지를 확인한다.
- 인증을 확인한 클라이언트는 Public key로 URL, http 데이터들과 자신의 대칭키를 암호화하여 전송한다.
- 서버는 인증서에 대한 Private key로 요청을 복호화하고 전달받은 대칭키로 응답을 암호화해서 전송한다.
- 브라우저는 대칭키로 응답을 복호화해서 사용자에게 보여준다.
이렇게 대칭키를 공개키 암호화방식으로 암호화해서 전송한 후 대칭키로 통신하는 프로토콜을 SSL 방식이라고 한다.
본래 해쉬(hash)함수는 자료구조에서 빠른 자료의 검색, 데이터의 위변조 체크를 위해서 쓰이지만, 복원이 불가능한 단방향 해쉬함수는 암호학적 용도로 사용한다. MD5, SHA-1(둘은 보안취약), SHA-256등이 있다.
예를 들어 '1234'를 SHA-256 해싱하면 다음과 같다.
03ac674216f3e15c761ee1a5e255f067953623c8b388b4459e13f978d7c846f4
결과만 봐서는 당장 식별이 불가능하므로 완벽해보이지만 같은 알고리즘으로 '1234'를 다시 해싱하면 항상 같은 결과가 도출된다.
Rainbow Table이라고 하는 해시 함수를 사용하여 만들어낼 수 있는 값들을 왕창 저장한 표도 존재한다.
이같은 허점을 보완하고자 salting과 Key Stretching이라는 아이디어가 생겨났다. 비밀번호와 임의로 생성한 문자열(Salt)를 합쳐서 해싱하여 이 해시값을 저장하는 방법이다.
단순해쉬값이 해킹에 쉽게 노출되기 때문에 Salting이라는 아이디어가 생겨났다.
입력한 비밀번호와 임의로 생성한 문자열(Salt)를 합쳐서 해싱해서 이 해시값을 저장하는 방법이다.
물론 이때 비교를 위해 해시값과 소금(Salt)값을 같이 저장해야 한다.
여기에 해커가 패스워드 무작위 대입을 통해 해시값을 계산하는데 필요한 시간을 대폭 늘리기 위해 Salting 및 해싱을 여러번 반복해서 원본 값을 유추하기 어렵게 만드는 것이 키 스트랫칭(Key Stretching)이다.
bcrypt는 비밀번호를 단방향 암호화 하기 위해 만들어진 해쉬함수이다.
In [40]: import bcrypt
In [41]: bcrypt.hashpw(b"secrete password", bcrypt.gensalt())
Out[41]: b'$2b$12$.XIJKgAepSrI5ghrJUaJa.ogLHJHLyY8ikIC.7gDoUMkaMfzNhGo6'
In [42]: bcrypt.hashpw(b"secrete password", bcrypt.gensalt()).hex()
Out[42]: '243262243132242e6b426f39757a69666e344f563852694a43666b5165445469397448446c4d366635613542396847366d5132446d62744b70357353'
사용자가 서버에 로그인하면 해당 사용자가 맞는지 확인하는 과정이 바로 인가이다. 즉, 유저가 요청하는 request를 실행할 수 있는 권한이 있는 유저인가를 확인하는 절차이다.
✔️ 서버는 사용자가 로그인했을 경우, 로그인했다는 것을 어떻게 알 수 있을까?
access token
을 생성한다. access token
에는 유저 정보를 확인할 수 있는 정보가 들어가 있어야 한다. (ex. user id)access token
을 첨부해서 보낸다.access token
을 복호화 한다.