본문 바로가기

면접질문[CS]/네트워크 & 보안

OAuth2.0에 대하여... [ 보안 + 서비스 + 네트워크 ] [면접 질문] [2022]

들어가며....

 

면접에서 OAuth 사용한 경험에 대한 질문을 받았다.

 

자소서에 OAuth + JWT 기반으로 토이 프로젝트를 진행한 경험이 있다고 작성했음에도..

OAuth에 대한 답변을 제대로 하지 못했다. [ 1~2 단계 깊게 질문이 들어왔는데 답변을 못했다. ]

 

예전에 "스프링 부트와 AWS로 혼자 구현하는 웹서비스"에서 OAuth를 사용한 경험이 있다.

 

해당 경험만 언급하고 세부적인 개념에 대한 답변은 못했다. 상당히 부끄럽다.

 

자소서에서 들어올 수 있는 질문에 대한 답변은 준비했어야 했는데... 미흡했다.

 

이번 기회에 OAuth의 개념을 제대로 잡아보고자 한다.

 

"생활 코딩" 유튜브 동영상에서 가장 큰 도움을 받았다.

 

로그인

많은 플랫폼들이 OAuth를 제공한다.

도메인 모델 + 비즈니스 로직 처리에 대한 구현이 완료되면 "영속성"에 대한 고민을 하게 된다.

 

영속성에 대한 고민까지 끝마쳤다면 사용자의 입력을 받아서 처리하고 결과를 보여주는 단계가 남게 된다.

 

해당 단계가 끝났으면 웹 서비스가 제작된 것이다. 

 

마지막으로 "보안"을 추가하면 사용자에게 안전한 웹 서비스로 탄생한다. 

 

사용자의 데이터를 안전하게 관리하고 특정 사용자를 위한 데이터에 접근할 수 있도록 만들기 위해서는

 

우리 서비스의 사용자를 식별할 수 있는 기능들을 마련해야 한다.

 

해당 기능이 바로 "로그인(Log in)"이다.

 

직접 로그인을 구현하면 다음의 기능들도 고민해야 한다.

 

1. 로그인 이후의 보안 메커니즘 [ 해당 정보들을 어떻게 관리할 것인지. ] 

 

2. 비밀번호 찾기 [ 휴대전화, 이메일, 질문 등등... ]

 

3. 비밀번호 변경

 

4. 회원정보 변경

 

5. 회원가입을 위한 인증 [이메일, 전화번호]

 

로그인을 제대로 구현하는 것은 정말 어려운 일이다. 

 

OAuth는 이런 일들에 대한 짐을 덜어준다. 

 

사용자의 식별정보에 대한 저장의 부담을 줄여주면서 필요한 기능과 정보만을

 

OAuth 서버로부터 받아와서 사용자에게 서비스를 제공하는 것이다.

 

로그인(ID & PW)에 대한 정보를 OAuth를 제공하는 서버에 "위임"할 수 있는 것이다.

+ 추가로 부분적인 기능 활용을 요구할 수도 있다.

 

스프링 시큐리티를 통해 OAuth 2.0을 사용할 수 있는데 해당 내용은 책의 한 챕터를 담당할 정도로 양이 방대하다.

 

이번 글에서는 개념에 대한 이해이다. 구현에 대한 세부적인 내용은 별도의 글이나 자료를 참고하길 바란다. 

 

정의

 

OAuth는 인터넷 사용자들이 비밀번호를 제공하지 않고 다른 웹사이트 상의 자신들의 정보에 대해 웹사이트나 애플리케이션의 "접근 권한"을 부여할 수 있는 공통적인 수단(표준)이다. 

 

클라이언트(웹 서비스) 입장에서 제삼자인 리소스 서버를 통해 사용자(리소스 주인)의 신원을 확인할 수 있다는 것이

가장 큰 장점이다.

 

제3자 자원 서버(Resource Server)는 신뢰할 수 있는 서버여야 한다. [ 구글, 페이스북, 네이버, 카카오 등등.. ]

 

신뢰할 수 있는 서버는 Access Token을 발급하여 사용자의 식별자(ID & PW를 대체)로 활용할 수 있게 해 준다.

 

OAuth를 통해서 많은 서비스들이 ID & PW를 활용해서 서로의 서비스를 사용하는 것이 아닌

 

ID & PW를 대체하는 Access Token(접근 토큰)을 통해서 서비스를 이용하게 된다.

 

 

주요 키워드들

 

위의 문장들에서 주요한 주체들은 다음과 같다.

 

클라이언트(Client)

 

보편적으로 웹 서비스에서 클라이언트는 "서비스를 사용하는 측"을 의미한다.

 

그래서 사용자가 클라이언트로 묶여서 표현되는데 OAuth에서는 리소스 서버를 사용하는 대상을 의미한다.

 

즉 로그인과 같은 리소스 서버의 기능을 활용할 서비스를 "클라이언트"라고 부른다.

 

=> 클라이언트는 리소스 서버가 제공하는 자원을 사용하는 애플리케이션을 의미한다.

[ 대표적으로 OAuth를 통해 다양한 플랫폼에 로그인 기능을 위임한다. ] 

 

제3자 리소스(자원) 서버(Resource Server)

 

구글, 페이스북, 카카오와 같이 사용자에 대한 정보를 안전하게 보관하는 신뢰할 수 있는 서버를 의미한다.

 

데이터를 담당하는 리소스 서버와 인증과 관련된 정보를 담당하는 Authorization(권한) 서버를 묶어서

 

Resource Server라고 한다.

 

클라이언트는 리소스 서버에 자신의 정보를 등록해야 한다.

 

사용자는 리소스 서버에 회원가입을 해야 클라이언트 서비스의 OAuth를 활용할 수 있다.

 

사용자(Owner)

 

클라이언트가 제공하는 서비스를 활용하려는 사용자이다.

 

동시에 리소스 서버에 사용자여야 한다.

 

OAuth를 통해 실제 로그인하는 사용자를 의미한다.

 

Access Token [ 접근 토큰 ]

 

OAuth를 통해 최종적으로 발급되는 정보로 보안에 취약한 방식인 ID & PW 방식의 로그인을 대체해준다.

 

접근 토큰에는 자원 서버에서 사용할 수 있는 기능의 범위(Scope)와 접근 가능한 유효 시간에 대한 정보가 담겨있다.

 

Refresh [재발급]

 

보편적으로 접근 토큰과 함께 재발급용 토큰을 같이 전달한다. [정책에 따라 다르다 ]

 

접근 토큰의 유효기간이 종료되어 새로운 접근 토큰을 발급받아야 할 때 재발급 토큰이 사용된다.

 

OAuth의 세부적인 과정 [ 생활 코딩 추천 ]

추상적인 flow는 위와 같다. [프로토콜 방식에 따라서 다르게 처리] 

1. Client 등록과정

Client는 OAuth를 제공하는 리소스 서버에 자신의 정보를 등록한다.

 

리소스 서버와 Client는 Client_ID, Client_Secret, Redirect_URL을 공유한다.

 

- Client_ID는 클라이언트 식별자이고

- Secret은 클라이언트 식별자를 위한 비밀키이다. [ 비밀키는 공개되어선 안된다!! ]

- Redirect URL은 리소스 서버에서 사용자의 인증이 끝나면 클라이언트 페이지로 넘어갈 URL이다.

 

2. Client는 사용자가 OAuth를 활용할 수 있도록 URL을 제작한다.

 

사용자는 OAuth 프로토콜 방식으로 리소스 서버의 자신의 정보를 넘겨야 한다.

Client가 사용자로 하여금 리소스 서버로 요청하도록 URL을 제작한다.

URL에는 리소스 서버의 OAuth 프로토콜 방식 & Client ID & Redirect URL & Scope이 명시되어 있다.

 

3. 사용자의 로그인 시도

 

사용자는 Client에서 만든 URL로 이동해 로그인을 시도한다. 로그인 정보는 리소스 서버로 향하고

 

리소스 서버는 해당 로그인 정보(ID & PW)를 확인해서 사용자를 확인한 경우

 

Client가 ~~ 기능의 Scope을 요구한다고 사용자에게 알린다. [ 확인되지 않으면 로그인 실패이다. ]

 

사용자는 해당 권한 목록을 살펴보고 리소스 서버로 하여금 해당 권한을 "허가"한다는 것을 동의할지를 결정한다.

 

허용한 경우 리소스 서버는 권한 코드(Authentication Code)를 사용자에게 넘긴다.

 

4. Client로 권한 코드 넘기기.

 

사용자는 리소스 서버로부터 받은 권한 코드를 클라이언트로 넘긴다.

 

클라이언트는 권한 코드 + 클라이언트 ID + 시크릿 값 + 리다이렉트 URI를 리소스 서버로 전송한다.

 

5. 리소스 서버의 클라이언트 확인

 

리소스 서버는 클라이언트가 보낸 값들을 자신이 가지고 있는 값들과 대조하면서 문제가 없는지 확인한다.

[ 클라이언트 ID & Secret. 사용자에게 전달한 권한 코드 값. 리다이렉트 URL ]

 

문제가 없다는 것을 확인하면 사용자 & 리소스 서버 & 클라이언트 모두 OAuth의 절차를 거친 것이다.

 

리소스 서버는 Access Token을 클라이언트로 전송한다. 이제 권한 코드는 사용되지 않고 Access Token을 사용한다.

 

Access Token에는 사용자의 Scope 정보와 기간 정보가 담겨 있다.

 

클라이언트는 Access Token을 기억하고 리소스 서버로의 요청이 필요할 때 access Token을 전송한다.

 

리소스 서버는 Acess Token을 확인하고 해당 토큰과 매칭 되는 사용자를 찾아서 요청된 자원을 클라이언트로 전송한다.

 

기간이 만료된 경우 Refresh Token을 통해 접근 토큰을 재발급받을 수 있다.

 

4가지 프로토콜

1. Authorization Code Grant [인가 코드 승인 방식]

- 권한 서버가 클라이언트와 리소스 서버 간의 중재를 해준다.

- 서버사이드 방식의 인증으로 인증을 서버에서 처리한다.

URL에 response-type=code으로 넘긴다.

 

2. Implicit Grant [암묵적 승인]

- Client 기반의 애플리케이션이나 모바일 애플리케이션에 주로 사용한다. [ JS기반의 프론트 서버 혹은 안드로이드, iOS]

- 권한 코드를 따로 발급하지 않아 보안에는 취약하다. [ 사용자에게 권한 코드를 넘기고 클라이언트가 권한 코드를 받아서 매칭 해보는 과정이 없다. ]

- 주로 자원을 "읽기 전용"으로 사용한다.

URL에 response-type=token으로 넘긴다.

 

3. Resource Owner Password Credentials Grant : 리소스 소유자 암호 자격 승인

- Client에 ID & PW를 저장해놓고 ID & PW로 직접 토큰을 받아오는 방식이다. 

- Client가 신뢰할 수 없는 경우 보안에 취약하다.

 

4. Client Credentials Grant

- id와 secret을 가지고 인증하는 방식이다.

 

대표적으로 위의 4가지가 존재한다. [실제로는 다양한 방식이 존재하나 자주 사용되는 방식은 위의 4가지이다. ]

 

OAuth 구현 시 OAuth를 제공할 대상에 따라 다른 프로토콜을 선택해야 한다.

 

전체적인 flow는 비슷하나 프로토콜에 따라 세부적으로 다른 부분들이 존재한다.

 

여기서 모든 것을 정리하기에는 무리가 있다.

 

 

마무리

 

신뢰의 형성의 과정에 집중해보자.

 

1. 클라이언트와 리소스 서버와의 신뢰 : Client_Id와 Secret키, Redirect URL 공유

 

2. 사용자와 리소스 서버와의 신뢰 : 사용자의 로그인 ID와 PW 공유

 

3. 클라이언트 & 리소스 서버 & 사용자와의 신뢰 

 

사용자는 리소스서버가 제공한 권한 코드를 클라이언트와 공유한다.

 

클라이언트는 권한 코드를 리소스 서버와 매칭해본다.

 

이렇게 사용자 - 클라이언트 - 리소스 서버의 신뢰가 구축되고 단시간 동안 신뢰 활동을 보장하는 Access Token을 형성하게 된다.

 

여기서 가장 중요한 것은 OAuth의 중심을 담당하는 신뢰성 있는 리소스 서버일 것이다.

 

리소스 서버는 다양한 OAuth 프로토콜을 제공해줘야 하며 사용자의 정보를 강력하게 보호해야 한다.

 

더 깊게 들어가면 끝도 없이 들어갈 것 같아서 표면적인 수준에서 이해한 내용을 정리해 본다.

 

더 많은 자료는 참고자료를 통해 접근하기를 바란다.

 

다음에는 JWT에 대해서 살펴보고자 한다.

 

OAuth 프로세스를 통해서 ID & PW의 사용을 한 곳(리소스 서버)에 집중할 수 있게 되었으며 식별 정보를 대체할 수

있는 Access Token을 통해 보안에 대한 기능의 제한과 시간에 대한 제한을 얻을 수 있게 되었다.

 

식별 정보를 대체할 수 있는 토큰기반으로 서버의 API를 활용할 수 있게 되면서 서비스간의 연동성을 높여줬다는

장점을 가져다 주었다. [ 놀라운 생태계 변화이다. ]

 

다만 ID & PW의 처리가 리소스 서버에서 담당하게 되니 그로 인해서 생기는 보안적인 문제와

 

구글, 페이스북, 카카오, 네이버가 정말로 신뢰할 만한 서버들인가에 대해선 약간의 의문이 남는다.

 

그들도 남는 장사를 하기 위해선 사용자의 정보를 활용할 수 있어야 한다. [ 어떤 사이트를 얼마나 자주 접근하는지 등등에 정보를 얻을 수 있을 것이다. ]

 

나중에 어디서 문제가 될지는 모르겠으나 OAuth는 현재 광범위하게 활용되고 있다.


참고자료

  • 생활코딩 유튜브 : OAuth2.0 : youtube [ 강력 추천. ]
  • undefcat님의 글 : OAuth2.0 간단 정리 [ 큰 그림으로 이해하기 정말 좋다 ] : link
  • RyanGomdoriPooh님의 글 : 간단한 정리 : link [ 메타포 ]
  • shower bug : OAuth란 무엇일까 : link [ 배경 + 이해 ]
  • 우아한 테크 블로그 : OAuth 개념 및 동작 방식 이해하기 : link [ 실제 예시]
  • digital ocean : 다양한 프로토콜에 대한 설명[영문] : link
반응형