
Access Token (+ Refresh Token)Access Token + ID Token (+ Refresh Token)이때 ID Token을 열어본다 -> "이 사람은 sub: 12345번 유저고 이메일은 test@gmail.com이구나. DB에 저장하자."
이때 Access Token을 사용한다 -> "이 토큰을 구글 서버에 보내서 이 사람의 지난달 구글 포토 사진들을 가져와야지."
| 항목 | ID Token | Access Token |
|---|---|---|
| 본질 | 신분증 (Identity Card) | 출입 열쇠 (Access Key) |
| 사용 대상 | Client (백엔드 앱) | Resource Server (Google API 등) |
| 형식 | 반드시 JWT | 규격 제한 없음 (주로 Opaque 혹은 JWT) |
| 핵심 질문 | 이 사용자는 누구인가? | 이 앱이 내 데이터에 접근해도 되는가? |
| 민감 정보 | 사용자 프로필 정보 포함 | 포함하지 않음 (권한 정보 위주) |
Opaque Token
그 자체로는 아무런 의미가 없는 무작위 문자열 ex)f83j2-sh23-92kf-s02
- 정보의 부재: 토큰 안에 사용자 ID나 만료 시간 같은 정보가 들어있지 않음
- 참조(Reference) 역할: 이 토큰은 '은행의 번호표'나 '물품 보관함 키'와 같다. 번호표 자체에는 돈이 얼마 있는지 적혀 있지 않지만, 은행원(서버)에게 주면 은행 전산망(DB)을 조회해 정보를 확인하는 방식
ID Token의 Payload에는 다음과 같은 표준화된 정보가 담긴다.
iss (Issuer): 토큰을 발행한 곳 (예: 구글).
sub (Subject): 사용자의 고유 ID (절대 변하지 않는 값).
aud (Audience): 이 토큰을 받을 대상 (내 앱의 Client ID).
email, name, picture: 사용자의 실제 프로필 정보.
내 서버는 ID Token을 보고 "Elena가 로그인했구나"라고 판단
구글 서버는 Access Token을 보고 "이 앱이 Elena의 사진첩을 봐도 되는구나"라고 판단
ID Token은 클라이언트(나의 앱)가 직접 뜯어보기 위해 설계되었다.
Access Token은 클라이언트가 내용을 알 필요가 없다. 그저 리소스 서버에 '제시'만 하면 됨
사용자가 나의 앱에 구글 로그인을 한다고 해서 사용자의 모든 구글 데이터를 다 볼 수 있으면 안 됨. 그래서 서로 합의된 권한의 범위를 정하는 것이 바로 scope
| 스코프 이름 | 설명 | 포함되는 주요 클레임 (ID Token 내) |
|---|---|---|
| openid | (필수) OIDC를 사용하겠다는 선언 | sub, iss, aud, exp 등 |
| profile | 사용자의 기본 프로필 정보 | name, family_name, gender, picture 등 |
| 사용자의 이메일 정보 | "email, email_verified" | |
| address | 사용자의 주소 정보 | address (세부 주소 객체) |
| phone | 사용자의 전화번호 정보 | phone_number |
https://accounts.google.com/o/oauth2/v2/auth?
client_id=YOUR_CLIENT_ID&
response_type=code&
scope=openid profile email& // scope
redirect_uri=YOUR_REDIRECT_URI
openid가 있으면: 결과물로 ID Token과 Access Token이 모두 옴
openid가 없으면: 순수 OAuth 2.0으로 동작하여 Access Token만 옴