# 등장배경
서드파티 어플리케이션이 사용자 대신 페북에 영향을 주거나 정보를 가져오려고 한다고 가정해 봅시다.
가장 기본적인 방법은 서드파티가 id, pw를 사용자로부터 입력 받아서 서드파티가 다른 서비스에 대신 로그인해서 접근하는 방식입니다.
하지만 이 방법에 치명적인 단점이 있는데 페북 id, pw를 서드파티가 관리할만큼 믿을만 한가에 대한 의문입니다.
즉, 서드파티의 보안수준이 페북의 보안수준이 되어버리는 문제가 발생합니다.
이를 해결하기 위해 서비스별로 여러가지 auth방식이 나왔는데 이를 OAuth로 통일시키기로했습니다.
# OAuth란
다양한 플랫폼의 특정한 사용자 데이터에 접근하기 위해 제3자 클라이언트(우리의 서비스)가 사용자의 접근 권한을 위임(Delegated Authorization)받을 수 있는 표준 프로토콜입니다.
1. Resource Owner - 플랫폼에서 리소스를 소유하고 있는 사용자
2. Authorization & Resource Server - Client에게 액세스 토큰을 발급해주는 서버 ex) google
3. Client - Resource Server의 자원을 이용하고자 하는 서비스, 보통 우리가 개발하려는 서비스
# OAuth 동작 방식
0. 어플리케이션 등록
Client를 Resource Server 에 등록해야합니다. 이때, Redirect URI를 등록합니다. (https만 허용)
Client ID, Client Secret
등록과정을 마치면, Client ID와 Client Secret를 얻을 수 있습니다. 발급된 Client ID와 Client Secret은 액세스 토큰을 획득하는데 사용됩니다. 이때, Client ID는 공개되어도 상관없지만, Client Secret은 절대 유출되어서는 안됩니다.
1 ~ 2. 로그인 요청
response_type : 반드시 code 로 값을 설정
client_id : 애플리케이션을 생성했을 때 발급받은 Client ID
redirect_uri : 애플리케이션을 생성할 때 등록한 Redirect URI
scope : 클라이언트가 부여받은 리소스 접근 권한
3 ~ 4. 로그인 페이지 제공, ID/PW 제공
클라이언트가 빌드한 Authorization URL로 이동된 Resource Owner는 제공된 로그인 페이지에서 ID와 PW 등을 입력하여 인증할 것입니다..
5 ~ 6. Authorization Code 발급, Redirect URI로 리디렉트
인증이 성공되었다면, Authorization Server 는 제공된 Redirect URI로 사용자를 리디렉션시킵니다. 이때, Redirect URI에 Authorization Code를 포함하여 사용자를 리디렉션 시킵니다.
이때, Authorization Code란 Client가 Access Token을 획득하기 위해 사용하는 임시 코드입니다. 이 코드는 수명이 매우 짧습니다. (일반적으로 1~10분)
7 ~ 8. Authorization Code와 Access Token 교환
Client는 Authorization Server에 Authorization Code를 전달하고, Access Token을 응답받습니다. Client는 발급받은 Resource Owner의 Access Token을 저장하고, 이후 Resource Server에서 Resource Owner의 리소스에 접근하기 위해 Access Token을 사용합니다.
9. 로그인 성공
위 과정을 성공적으로 마치면 Client는 Resource Owner에게 로그인이 성공하였음을 알립니다.
10 ~ 13. Access Token으로 리소스 접근
이후 Resource Owner가 Resource Server의 리소스가 필요한 기능을 Client에 요청합니다. Client는 위 과정에서 발급받고 저장해둔 Resource Owner의 Access Token을 사용하여 제한된 리소스에 접근하고, Resource Owner에게 자사의 서비스를 제공합니다.
# Authorization Code가 왜 필요한 것 인가?
Redirect URI를 통해 Authorization Code를 발급하는 과정이 생략된다면, Authorization Server가 Access Token을 Client에 전달하기 위해 Redirect URI를 통해야 합니다. 이때, Redirect URI를 통해 데이터를 전달할 방법은 URL 자체에 데이터를 실어 전달하는 방법밖에 존재하지 않습니다. 브라우저를 통해 데이터가 곧바로 노출됩니다.
Redirect URI를 프론트엔드 주소로 설정하여, Authorization Code를 프론트엔드로 전달합니다. 그리고 이 Authorization Code는 프론트엔드에서 백엔드로 전달됩니다. 코드를 전달받은 백엔드는 비로소 Authorization Server의 token 엔드포인트로 요청하여 Access Token을 발급합니다.
# Token의 종류
1. Access Token
이 토큰은 보호된 리소스에 접근할 때 권한 확인용으로 사용됩니다. 문자열 형태이며 클라이언트에 발급된 권한을 대변하게 됩니다. 계정 아이디와 비밀번호 등 계정 인증에 필요한 형태들을 이 토큰 하나로 표현함으로써, 리소스 서버는 여러 가지 인증 방식에 각각 대응 하지 않아도 권한을 확인 할 수 있게 됩니다.
2. Refresh Token
위 그림에서는 나오지 않은 토큰입니다. 하지만 이 토큰도 대게 같이 사용됩니다. 이 토큰이 존재하는 이유는 jwt는 발급이후 삭제가 불가능하기 때문에 access token이 탈취되는것을 방지하기 위해 유효시간을 부여합니다. 유효시간을 줄이자니 로그인을 자주해야하고 그렇다고 늘리자니 탈취 되었을때 위험해집니다. 이를 해결하기 위해서 refresh token을 두어서 access token이 만료되었을때 refresh token의 유효성을 확인하고 access token을 재발급해줍니다. 로그아웃시에는 refresh token도 사라집니다. 단 권한 서버에서만 활용되며 리소스 서버에는 전송되지 않습니다.
# 토큰의 갱신 과정
1. 클라이언트가 권한 증서를 가지고 권한서버에 Access Token 을 요청
2. 권한 서버는 Access Token과 Refresh Token 을 함께 클라이언트에 알려줍니다.
3. 클라이언트는 Access Token을 사용하여 리소스 서버에 각종 필요한 리소스들을 요청하는 과정을 반복
4. 일정한 시간이 흐른 후 액세스 토큰이 만료되면, 리소스 서버는 이후 요청들에 대해 정상 결과 대신 오류를 응답
5. 전에 받아 두었던 Refresh Token을 권한 서버에 보내어 새로운 액세스 토큰을 요청
6. 갱신 요청을 받은 권한 서버는 Refresh Token 의 유효성을 검증한 후, 문제가 없다면 새로운 액세스 토큰을 발급
# Reference
https://hwannny.tistory.com/92
https://www.okta.com/kr/identity-101/saml-vs-oauth/
https://showerbugs.github.io/2017-11-16/OAuth-%EB%9E%80-%EB%AC%B4%EC%97%87%EC%9D%BC%EA%B9%8C
'Back-end > Spring-login project' 카테고리의 다른 글
Spring Security 인증 과정 (Authentication 부분) (0) | 2023.06.13 |
---|---|
Spring Security의 기초와 구조 (0) | 2023.06.12 |
고민의 흔적 (~ing) (0) | 2023.04.22 |
요구사항과 설계 (0) | 2023.03.21 |