본문 바로가기
카테고리 없음

Cognito를 이용한 AWS 사용자 관리 서비스

by mizuiro 2025. 1. 12.
  • 서비스 목표
  • IAM VS Identity Pool

    • IAM 역할특정 그룹이나 AWS 리소스에 대한 권한을 정의해 놓은 책입니다.
      • 이 책에는 누가 어떤 리소스에 접근할 수 있는지, 어떤 작업을 할 수 있는지 상세하게 적혀 있습니다.
      • 책 자체는 언제든 사용할 준비가 되어 있지만, 직접 읽으려면 누군가가 이 역할(책의 내용)을 "수행(Assume)"해야 합니다.
    • Identity Pool도서관의 대출 서비스처럼 동작합니다.
      • 사용자가 인증되면, Identity Pool은 해당 사용자에게 특정한 "책"(IAM 역할)을 빌려줍니다.
      • 다만, 이 대출은 기한이 정해져 있는 임시 권한입니다.
      • 대출 기한(임시 자격 증명의 유효 기간)이 지나면 책을 반납해야 하고, 다시 사용하려면 대출 절차를 거쳐야 합니다.

    이 비유를 통해 이해하기

    1. IAM 역할:
      • 역할 자체는 대출 기한이 없습니다. 그냥 서가에 있는 상태로 누구든 가져갈 준비가 되어 있습니다.
      • 그러나, 책을 빌려주는 절차(AssumeRole)는 Identity Pool이나 다른 AWS 서비스에 의해 제어됩니다.
    2. Identity Pool:
      • 사용자가 자격을 인증하면, Identity Pool은 적절한 책(IAM 역할)을 찾아서 일정 시간 동안 빌려줍니다.
      • 빌릴 수 있는 책은 사용자 속성(예: 그룹, JWT 클레임)에 따라 결정됩니다.
      • 이 대출이 완료되면 사용자는 AWS 리소스에 접근할 수 있는 임시 자격 증명을 사용합니다.
    3. JWT와 Identity Pool의 관계:
      • 사용자는 "도서관 회원증"(JWT)을 사용하여 자신이 인증된 사용자임을 증명합니다.
      • 회원증의 속성(예: 그룹 정보)을 기준으로 도서관(Identity Pool)이 적절한 책을 빌려줍니다.

    정리

    당신의 비유는 매우 적절하며, 핵심은 다음과 같습니다:

    • IAM 역할: 정적이고, 특정 권한을 정의한 "책".

    • Identity Pool: 인증된 사용자가 이 "책"을 일정 기간 동안 사용할 수 있도록 임시로 빌려주는 시스템.

      따라서 IAM 역할Identity Pool은 서로 보완적인 관계로 사용됩니다. 멋진 정리네요! 😊 추가로 궁금한 점이 있다면 언제든지 물어보세요!

      비교: IAM 역할 vs Identity Pool의 임시 역할

      항목 IAM 역할 Identity Pool 임시 역할
      권한 설정 방식 정적 설정 (IAM 정책 기반) 동적 매핑 (Identity Pool 정책 기반)
      사용자 인증 필요 여부 인증과 독립적으로 설정 가능 인증된 사용자에 의해 역할이 부여됨
      임시 자격 증명 발급 직접 제공하지 않음 (STS 필요 시 사용) 자동으로 임시 자격 증명 발급
      유효 기간 고정된 IAM 역할은 만료되지 않음 발급된 자격 증명은 기본 1시간 (최대 12시간)
      주요 사용 대상 AWS 서비스, 시스템 계정 인증된 최종 사용자
      권한 세분화 IAM 정책으로 제한 가능 사용자 속성(그룹, 클레임) 기반으로 세분화
      AWS 리소스 직접 접근 주로 서버 측 서비스에서 사용 모바일 앱 또는 클라이언트 측에서 사용

서비스 개요

인증 및 인가란?

1. 인증 (Authentication)

  • 정의: 사용자가 누구인지 확인하는 과정
  • 목적:
    • 시스템 또는 서비스에 접근하려는 사용자의 신원을 검증
    • 허가받지 않은 접근을 방지
  • 방법
    • ID와 비밀번호: 가장 일반적인 방식
    • 소셜 로그인: Facebook, Google 등 외부 인증 제공자를 통한 인증
    • 멀티팩터 인증(MFA): 비밀번호 + 추가 인증 (예: OTP, 생체인식)
    • 토큰 기반 인증: JWT 토큰 등을 사용한 인증 방식

2. 인가 (Authorization)

  • 정의: 사용자가 특정 리소스나 기능에 접근할 수 있는 권리를 결정하는 과정
  • 목적:
    • 인증된 사용자에게 적절한 권한을 부여하여 시스템 보호
    • 사용자가 허가되지 않은 리소스에 접근하지 못하도록 제한.
  • 방법:
    • 역할 기반 접근 제어(RBAC): 사용자에게 특정 역할(Role)을 할당해 권한을 부여
      • 예: Admin, User, Guest 등
    • 정책 기반 접근 제어(Policy): 조건에 따라 권한을 정의 (예: AWS IAM 정책)
    • 리소스 기반 제어: 특정 리소스에 대해 사용자가 수행할 수 있는 작업을 정의
항목 인증 (Authentication) 인가 (Authorization)
목적 사용자가 누구인지 확인 사용자가 무엇을 할 수 있는지 결정
시점 시스템 접근 전에 수행 시스템 접근 후 수행
질문 "당신은 누구입니까?" "당신은 이 작업을 할 수 있습니까?"
결과 사용자 신원을 확인 작업 가능 여부를 결정
예시 비밀번호 입력, 소셜 로그인, OTP 입력 Admin만 데이터 삭제 가능, 특정 리소스 조회 가능
방법 - 비밀번호 인증: 사용자 ID와 비밀번호를 입력해 확인.- 소셜 로그인: 외부 인증 제공자(Facebook, Google) 이용.- JWT 토큰 인증: 발급받은 토큰을 통해 신원을 확인.- MFA: 2단계 인증(예: OTP, 이메일 인증). - 역할 기반 접근 제어(RBAC): 사용자에게 Admin, User 등 역할(Role)을 부여.- 정책 기반 제어: 조건에 따라 권한을 정의(AWS IAM 정책 등).- 리소스 기반 제어: 특정 리소스에 대한 접근 권한 설정.- ACL(Access Control List): 개별 사용자 또는 그룹의 권한 정의.

Amazon Cognito란?

1. 정의

Amazon Cognito는 AWS에서 제공하는 사용자 인증 및 권한 부여를 관리하는 서비스입니다

  • 인증(Authentication): 사용자가 누구인지 확인하고, 안전하게 시스템에 로그인하도록 지원
  • 인가(Authorization): 인증된 사용자에게 적절한 리소스 접근 권한을 부여

2. 주요 역할

  • 사용자의 신원 확인(ID Verification) 및 액세스 제어를 간소화
  • 웹 및 모바일 애플리케이션에서 인증 및 권한 관리를 쉽게 구현하도록 지원
  • OAuth 2.0, OpenID Connect, SAML 등의 표준을 활용하여 인증 및 권한을 처리

3. Cognito의 구성 요소

  1. 사용자 풀 (User Pool)
    • 사용자 인증에 초점을 둔 서비스.
    • 사용자의 로그인 및 등록 기능 제공
    • 소셜 로그인(Facebook, Google, Apple)과 연동 가능
    • 토큰(JWT) 발급: Access Token, ID Token, Refresh Token
    • 멀티팩터 인증(MFA) 지원.
  2. ID 풀 (Identity Pool)
    • 인증된 사용자에게 AWS 리소스에 접근할 수 있는 임시 자격 증명 부여.
    • 역할(Role) 기반 권한 관리
    • Federated Identity를 지원해 사용자 풀, 소셜 로그인, SAML 등을 통합 가능.
    • AWS 서비스(S3, DynamoDB 등)에 접근 가능하도록 설정.

Cognito의 사용 이유

  1. 인증 및 권한 관리 간소화

  2. 다양한 인증 옵션 지원

  3. 확장성과 고가용성

  4. AWS 리소스와의 통합

  5. 보안 강화

  6. 비용 효율성

  7. 개발 및 유지보수 효율성

  • spring sequrity와 연관지은 이유

    AWS Cognito로 변환한 이유 (개조식)

    1. MSA 구조에 적합한 인증 및 인가 관리
      • Spring Security는 모놀리식 환경에 적합하지만, MSA에서는 각 서비스마다 인증/인가를 관리하기 복잡함.
      • Cognito는 중앙 집중형 인증 서버 역할을 하여 모든 MSA 서비스(API Gateway, Lambda, ECS 등)와 통합 가능.
    2. AWS 서비스와의 긴밀한 통합
      • Cognito는 API Gateway, Lambda, DynamoDB와 기본적으로 연동되며, 설정이 간단.
      • Spring Security로는 이러한 통합을 위해 별도의 추가 구현 및 설정 작업 필요.
    3. 서버리스 기반의 자동 확장성
      • Cognito는 서버리스(Serverless) 아키텍처로, 대규모 트래픽 처리 시 별도의 확장 작업 없이 자동으로 확장.
      • Spring Security 기반 인증 서버는 확장 시 ECS/Fargate 인프라를 추가로 설정해야 함.
    4. 관리형 서비스로 운영 부담 감소
      • Cognito는 사용자 관리, 비밀번호 정책, 멀티팩터 인증(MFA) 등 인증 관련 작업을 AWS가 관리.
      • Spring Security에서는 이러한 기능을 직접 구현하고 유지보수해야 함.
    5. 소셜 로그인 및 표준 프로토콜 지원
      • Cognito는 Google, Facebook, Apple 등 소셜 로그인을 기본적으로 지원.
      • OAuth 2.0, OpenID Connect, SAML 등 표준 프로토콜을 바로 사용할 수 있음.
      • Spring Security에서는 소셜 로그인 및 OAuth 설정을 직접 구현해야 함.
    6. 비용 효율성
      • Cognito는 사용량 기반 요금제(PAYG)로 초기 비용이 낮고, 대규모 트래픽에서도 비용 효율적.
      • Spring Security는 인증 서버를 ECS/Fargate 위에 배포해야 하며, 인프라 비용이 추가로 발생.
    7. 보안 표준 준수
      • Cognito는 AWS의 글로벌 보안 표준을 따르며, 기본적으로 멀티팩터 인증(MFA), 토큰 암호화, HTTPS 지원 제공.
      • Spring Security에서는 보안 설정을 직접 구현하고 관리해야 함.
    8. 중앙 집중형 인증 관리
      • Cognito는 사용자 인증 및 권한 부여를 중앙에서 관리하며, 모든 MSA 서비스에서 일관된 인증 흐름 제공.
      • Spring Security로는 각 서비스마다 인증 로직을 통합하거나 공유하기 어려움.
    9. 서버리스와 컨테이너 기반 서비스 혼합 지원
      • Cognito는 AWS Lambda 기반의 서버리스 서비스와 ECS/Fargate 기반 컨테이너 서비스 모두에서 인증과 권한 관리를 지원.
      • Spring Security는 컨테이너 기반 서비스와는 잘 맞지만, Lambda와의 통합이 복잡함.
    10. 유연한 확장 및 변경 가능성
      • Cognito는 MSA에서 인증 서버와 리소스 서버의 역할을 분리하고, 다양한 인증 요구사항에 쉽게 대응 가능.
      • Spring Security는 모놀리식에서 MSA로 전환 시 인증 로직 변경에 큰 부담이 있음.
  • 사용 이유 설명

    1. 인증 및 권한 관리 간소화

    • 복잡한 인증 로직 제거:
      • 사용자 인증, 소셜 로그인, MFA 같은 기능을 AWS에서 자동 처리.
      • 직접 인증 로직을 구현하지 않아도 됨.
    • OAuth 2.0 및 OpenID Connect 지원:
      • 업계 표준 프로토콜을 사용해 안전하고 호환 가능한 인증 구현 가능.

    2. 다양한 인증 옵션 지원

    • 다중 인증 방식:
      • 사용자 이름 + 비밀번호, 소셜 로그인(Facebook, Google, Apple), SAML 등을 모두 지원.
      • 멀티팩터 인증(MFA) 활성화 가능.
    • 커스터마이징:
      • Lambda 트리거를 통해 사용자 정의 인증 플로우 구현 가능.

    3. 확장성과 고가용성

    • 수백만 명의 사용자 지원:
      • Cognito는 AWS의 글로벌 인프라를 활용하여 수백만 명의 동시 사용자를 처리 가능.
    • 서버리스 구조:
      • 별도 서버를 운영하지 않아도 되며, 자동 확장 기능 제공.

    4. AWS 리소스와의 통합

    • ID 풀(Identity Pool):
      • AWS 리소스(S3, DynamoDB 등)에 대한 세분화된 접근 제어 가능.
    • IAM 역할 기반 접근 제어:
      • 사용자 그룹에 따라 역할(Role)을 할당하여 AWS 리소스 권한 관리.

    5. 보안 강화

    • 강력한 보안 기능:
      • MFA, 비밀번호 정책 설정, 토큰 암호화, 데이터 보호 제공.
    • HTTP-only 쿠키:
      • 클라이언트-서버 통신 시 토큰을 안전하게 관리.

    6. 비용 효율성

    • 사용량 기반 요금제:
      • 사용자 풀: 활성 사용자 수에 따라 요금 부과.
      • ID 풀: AWS 리소스 사용에 따른 비용만 지불.
    • 작은 규모의 프로젝트부터 대규모 애플리케이션까지 적합.

    7. 글로벌 사용자를 위한 지원

    • 다국어 지원:
      • 로그인 화면과 이메일 템플릿을 다국어로 제공 가능.
    • 지리적 확장성:
      • AWS 리전에서 동작하며 전 세계 사용자를 대상으로 빠르고 안전한 서비스 제공.

    8. 개발 및 유지보수 효율성

    • 빠른 개발:
      • 소셜 로그인, 사용자 인증 등의 기능을 빠르게 통합 가능.
      • AWS CLI 및 SDK를 통한 간편한 설정.
    • 자동화:
      • 사용자 동의 처리, 암호 재설정, 이메일 인증 등을 AWS가 자동으로 처리.

    9. 유연한 사용 사례 지원

    • B2C 및 B2B 애플리케이션:
      • 개인 사용자 인증(B2C) 및 조직 기반 인증(B2B) 모두 가능.
    • IoT 및 서버리스 애플리케이션:
      • IoT 장치 및 서버리스 애플리케이션에 적합한 인증과 권한 관리 제공.

Amazon Cognito의 장단점

항목 장점 단점
1. 인증 관리 간소화 - 사용자의 로그인, 인증, 비밀번호 관리 등을 자동화.- OAuth 2.0, OpenID Connect, SAML 등 표준 지원. - 인증 로직 커스터마이징이 제한적.- 복잡한 인증 시 Lambda 트리거와 함께 사용해야 함.
2. 다양한 인증 옵션 - 소셜 로그인(Facebook, Google, Apple)과의 간단한 통합.- 멀티팩터 인증(MFA) 기본 제공. - 소셜 로그인 설정 시 초기 설정이 다소 복잡.- 일부 사용 사례에서는 외부 인증 시스템과의 연동 필요.
3. AWS 리소스와의 통합 - Identity Pool을 통해 IAM 역할을 자동으로 연결.- AWS 리소스(S3, DynamoDB 등)에 세분화된 접근 제어 가능. - IAM 정책과의 통합이 기본적 수준에 머물러 복잡한 권한 로직 구현이 어려움.
4. 확장성 - 서버리스(Serverless) 아키텍처로 설계되어 수백만 명의 사용자를 지원 가능.- 트래픽 변화에 자동 확장. - 대규모 사용자 관리 시 복잡한 사용자 데이터 동기화나 분석 기능은 제한적.
5. 보안 - 멀티팩터 인증(MFA), 비밀번호 정책, 토큰 암호화 제공.- HTTP-only 쿠키로 안전한 클라이언트-서버 통신. - 초기 보안 설정을 올바르게 구성하지 않으면 데이터 유출 위험 발생 가능.
6. 비용 효율성 - 활성 사용자에 따라 요금 부과(PAYG).- Identity Pool은 AWS 리소스 사용에만 비용 발생. - 인증이 간단한 애플리케이션의 경우 비용이 상대적으로 높게 느껴질 수 있음.
7. 유연한 사용자 관리 - 사용자 풀(User Pool)을 통해 사용자를 그룹화하고, 커스텀 속성 추가 가능.- 사용자 기반의 트리거 구현 가능. - Lambda 트리거를 활용한 고도화 작업이 필요할 경우 복잡성이 증가.
8. 글로벌 지원 - AWS 리전을 통해 글로벌 사용자 인증 지원.- 다국어 이메일 템플릿 및 로그인 화면 제공. - 일부 리전에서는 서비스 제한이 있을 수 있음.- 글로벌 배포 시 데이터 규정 준수 문제 고려 필요.
9. 빠른 개발 - AWS CLI, SDK, 콘솔을 통한 간편한 설정.- 빠른 소셜 로그인 통합으로 초기 개발 시간 단축. - 사용자 지정 인증 플로우(Custom Auth Flow) 개발 시 추가 시간 소요.
10. 커뮤니티와 지원 - AWS의 공식 문서 및 포럼 지원.- 다양한 사례 기반의 기술 자료와 SDK 활용 가능. - 특정 사용 사례에서는 필요한 기술 문서가 부족하거나 AWS 지원 의존도가 높음.

인가 방식 (Lambda Authorizer)

1. Lambda Authorizer의 역할

  • 동적 권한 부여: 요청 시점에 Lambda 함수를 호출하여 사용자의 토큰 또는 요청 정보를 기반으로 인가 정책을 동적으로 생성.
  • API 보호: 인증된 사용자만 API Gateway를 통해 리소스에 접근하도록 제한.
  • 사용자 지정 로직: 표준 인증 방식(Cognito, IAM)으로 처리할 수 없는 복잡한 인가 로직을 구현 가능.

2. Lambda Authorizer의 동작 방식

Lambda Authorizer는 클라이언트가 API Gateway로 요청을 보낼 때 동작하며, 다음과 같은 과정을 거칩니다:

  1. 클라이언트 요청
    • 클라이언트는 HTTP 요청과 함께 인증 정보(예: JWT 토큰, API 키, 헤더 등)를 포함하여 API Gateway로 전송.
  2. API Gateway에서 Lambda Authorizer 호출
    • API Gateway는 요청 정보를 Lambda Authorizer로 전달.
  3. Lambda Authorizer의 정책 생성
    • Lambda 함수는 요청 정보(예: 헤더, 쿼리 매개변수, 토큰 등)를 분석.
    • 유효성을 검증하고, 사용자가 API를 호출할 수 있는지 결정.
    • 사용자의 역할(Role), 그룹, 조건에 따라 인가 정책(IAM 정책)을 생성.
  4. API Gateway에서 인가 결과 적용
    • Lambda Authorizer가 반환한 정책에 따라 요청을 승인하거나 거부.
    • 요청이 승인되면 API Gateway는 요청을 백엔드 서비스로 전달.

3. Lambda Authorizer의 유형

Lambda Authorizer는 Token-basedRequest-based 두 가지 유형으로 나뉩니다:

유형 설명 사용 사례
Token-based 요청 헤더(Authorization)에 포함된 토큰(JWT 등)을 검증하여 정책을 생성. - JWT 기반 인증.- Amazon Cognito 또는 다른 IdP에서 발급된 토큰 검증.
Request-based 요청의 헤더, 쿼리 매개변수, 바디 등 전체 요청을 분석하여 정책을 생성. - 요청 메타데이터(IP, 메서드 등)를 기반으로 접근 제어.- API 키 검증 등.

4. Lambda Authorizer와 Amazon Cognito의 비교

항목 Lambda Authorizer Amazon Cognito
역할 요청 시점에 동적 인가 처리. 사용자 인증 및 정적 권한(Role) 부여.
정책 생성 방식 요청 데이터를 기반으로 Lambda 함수에서 동적으로 생성. 사용자 그룹에 따라 IAM 역할을 미리 정의.
사용 사례 세밀한 요청 기반 접근 제어. 인증 및 간단한 그룹 기반 권한 제어.
기술 요구 사항 Lambda 함수 작성 필요. AWS에서 제공하는 인증 프로세스 사용.

4. Cognito와 Lambda Authorizer의 인가 비교

항목 Amazon Cognito Lambda Authorizer
역할 사용자 인증 및 기본 권한 부여 요청마다 동적이고 세밀한 권한 부여
권한 부여 단위 사용자 그룹별 IAM 역할(Role) API 요청별 커스텀 정책
정책 생성 방식 IAM 역할 및 그룹 설정 Lambda 함수에서 동적으로 정책 생성
제어 가능 수준 고정적(사용자 그룹, IAM 역할 기반) 세밀하고 동적(요청 정보, 사용자 속성 기반)
주요 사용 사례 - AWS 리소스에 대한 정적 권한 부여- 사용자 그룹 기반의 단순한 접근 제어 - API 접근에 대한 세밀한 권한 부여- 요청별로 조건이 다른 권한 처리
단독 사용의 한계 - 요청마다 세부 조건을 적용하기 어려움- API 레벨의 권한 제어 미흡 - 별도의 인증 서버가 필요(Cognito 또는 자체 인증 필요)
보완 관계 Lambda Authorizer에 사용자 인증 정보(JWT 토큰)를 제공 Cognito의 JWT 토큰을 기반으로 세밀한 권한 정책 생성

5. Amazon Cognito와 Lambda Authorizer에서의 활용

  1. Cognito의 역할
    • 권한 부여: Cognito는 사용자 그룹(Role)과 IAM 정책을 기반으로 권한(Permission)을 정의합니다.
    • 인가 수행: ID 토큰 및 Access 토큰을 통해 기본적인 인가(Authorization)를 수행합니다.
  2. Lambda Authorizer의 역할
    • 권한 평가 및 동적 인가: Lambda Authorizer는 Cognito에서 발급한 토큰을 기반으로 정책을 동적으로 생성하여 요청을 승인(인가)하거나 거부합니다.
    • 조건에 따라 세밀한 정책 적용 가능: 특정 시간, IP, 요청 메서드 등에 따라 권한이 동적으로 변경.

6. Lambda Authorizer의 장점과 단점

항목 설명
장점 동적 정책 생성 가능: 사용자 요청에 따라 실시간으로 접근 정책을 생성하여 유연한 권한 제어 가능
복잡한 조건 기반 접근 제어: 다양한 요청 데이터(헤더, 쿼리, 토큰 등)를 활용한 정교한 인증 로직 구현 가능
외부 인증 시스템 통합: 타사 인증 시스템 및 맞춤형 데이터베이스와의 연동 용이.
단점 요청 지연 증가: Lambda 호출로 인해 API 요청 처리 시간이 늘어날 수 있음
관리 복잡성: 함수 작성, 정책 생성 로직 설계 및 유지보수가 어려울 수 있음
성능 문제: 복잡한 로직 작성 시 성능 저하 가능.

현재 서비스에서의 Cognito 의 인증 방식

  • 일반 Cognito 인증 사용자

    ALLOW_USER_PASSWORD_AUTH: username과 password로 인증

  • Ouath 2.0 인증 사용자

    ALLOW_CUSTOM_FLOW_AUTH + Ouath2.0 (Grant type : authorization_code) 인증

Amazon Cognito 사용자 풀(User Pool) 인증 플로우

인증 플로우 설명 사용 사례 특징
ALLOW_USER_PASSWORD_AUTH 사용자 이름(Username)과 비밀번호(Password)를 이용해 인증. 전통적인 로그인 방식의 웹/모바일 애플리케이션 - 사용자 이름과 비밀번호를 검증- Access Token과 ID Token 반환
ALLOW_ADMIN_USER_PASSWORD_AUTH 관리자가 사용자 계정을 대신 인증. 관리자 또는 시스템이 인증 과정을 대신 처리해야 하는 경우 - AdminInitiateAuth API를 사용- 일반 사용자가 직접 비밀번호를 입력하지 않음
ALLOW_REFRESH_TOKEN_AUTH 기존에 발급된 Refresh Token을 사용하여 새로운 Access Token을 요청. 토큰 만료 주기가 짧은 애플리케이션 - 사용자가 다시 로그인할 필요 없음- Refresh Token을 통해 토큰 재발급
ALLOW_CUSTOM_AUTH Lambda 트리거를 사용하여 맞춤형(Custom) 인증 플로우 구현. OTP, 생체 인증 등 맞춤형 인증이 필요한 경우 - 개발자가 인증 과정을 세부적으로 정의 가능- 복잡한 인증 요건 처리 가능
ALLOW_USER_SRP_AUTH SRP(Secure Remote Password) 프로토콜을 사용하여 비밀번호를 안전하게 처리. 보안이 중요한 시스템의 인증 프로세스 - SRP를 통해 암호화된 상태로 비밀번호 전송- 클라이언트 라이브러리 필요
ALLOW_DEVICE_AUTH 등록된 디바이스를 통한 인증. 디바이스 기반의 인증이 필요한 IoT 애플리케이션 - 사용자가 인증한 디바이스를 저장 및 활용 가능
ALLOW_SMS_MFA SMS를 통해 전달된 OTP를 사용하여 인증. 추가적인 보안 레벨이 필요한 서비스 (금융, 의료 등) - 멀티팩터 인증(MFA)의 한 방식- 사용자 경험 향상을 위해 선택적 또는 필수로 설정 가능

Ouath 인증 그랜트 방식

그랜트 타입 설명 사용 사례 장단점
Authorization Code 사용자가 애플리케이션에 로그인하면, 권한 부여 서버에서 코드를 발급하고 이를 통해 액세스 토큰을 교환함. 웹 애플리케이션에서 서버 간 안전한 통신이 필요한 경우 장점: 높은 보안(클라이언트가 비밀 키를 안전하게 저장 가능). 단점: 구현이 복잡
Implicit 사용자가 로그인하면, 권한 부여 서버가 직접 액세스 토큰을 발급 브라우저 기반 애플리케이션(싱글 페이지 애플리케이션)에서 주로 사용됨. 장점: 간단한 구현
단점: 보안 취약(토큰 노출 가능성).
Resource Owner Password Credentials 사용자가 자신의 자격 증명(아이디와 비밀번호)을 직접 애플리케이션에 입력하여 액세스 토큰을 발급받음. 신뢰할 수 있는 애플리케이션에서 사용(예: 동일한 기업의 앱과 서비스) 장점: 간단하고 빠름. 단점: 사용자의 자격 증명이 노출될 위험
Client Credentials 클라이언트 애플리케이션이 자체 자격 증명으로 권한 부여 서버에서 액세스 토큰을 요청함 서버 간 통신이나 비사용자 관련 애플리케이션(예: API 호출) 장점: 높은 보안(사용자 정보 불필요).
단점: 사용자 액세스에는 적합하지 않음

OAuth Authorization Code 방식 흐름

  1. 사용자가 로그인 요청
    • 사용자가 Google 로그인 URL에 접속하여 로그인.
  2. Authorization Code 생성
    • Google은 로그인한 사용자에 대해 Authorization Code를 생성.
  3. Redirect URL로 Authorization Code 전달
    • Google은 Authorization Code를, Google Developer 설정에서 미리 지정한 Redirect URL로 전달.
    • Redirect URL은 클라이언트(프론트엔드)일 수도 있고, 백엔드일 수도 있음.
      • 현재 방식에서는 백엔드로 전달.
  4. Authorization Code를 Google에 재전송
    • 백엔드는 Google로부터 받은 Authorization Code를 다시 Google로 전달.
  5. 토큰 발급
    • Google은 Authorization Code가 유효한지 확인한 뒤, Access Token, Refresh Token, ID Token을 발급.
  6. 백엔드에서 토큰 저장
    • 백엔드는 Google로부터 받은 토큰들을 저장.
  • Federation + Ouath2.0

    FederationOAuth 2.0은 인증 및 권한 부여를 처리하는 데 사용되며, 두 개념은 상호 보완적으로 작동할 수 있습니다. Federation은 주로 사용자 인증 및 아이덴티티 관리를, OAuth 2.0은 권한 부여 및 액세스 토큰 관리를 다룹니다.


    Federation

    • Federation은 여러 신뢰할 수 있는 아이덴티티 제공자(IdP)를 통해 사용자 인증을 통합하는 기술입니다.
    • 사용자는 Facebook, Google, Microsoft, Apple과 같은 소셜 로그인 또는 엔터프라이즈 SAML 제공자를 통해 애플리케이션에 로그인할 수 있습니다.
    • Federation의 주요 역할은 중앙화된 인증 관리로, 다양한 인증 소스를 하나의 통합된 시스템에서 처리할 수 있도록 돕습니다.

    OAuth 2.0

    • OAuth 2.0은 권한 부여를 처리하기 위한 표준 프로토콜로, 사용자 인증이 완료된 후 액세스 토큰을 발급받아 애플리케이션이 특정 리소스에 접근할 수 있도록 합니다.
    • 주로 권한 위임(Delegated Authorization)에 사용되며, 사용자가 인증된 상태에서 다른 시스템(S3, Google API 등)의 리소스에 접근할 권한을 애플리케이션에 위임합니다.

    Federation과 OAuth 2.0의 관계

    1. Federation을 통한 OAuth 2.0 인증:
      • Federation은 OAuth 2.0의 일부로 동작하여 사용자의 인증을 처리합니다.
      • 예를 들어, 사용자가 Google로 로그인하면 Google은 OAuth 2.0 인증 서버로 동작하며, 인증이 완료되면 애플리케이션에 OAuth 2.0 액세스 토큰을 발급합니다.
    2. 역할 분담:
      • Federation은 사용자의 신원을 확인(IdP를 통해)하는 데 중점을 둡니다.
      • OAuth 2.0은 사용자가 인증된 후 리소스에 대한 액세스를 관리하는 데 중점을 둡니다.
    3. 실제 사용 사례:
      • 소셜 로그인: 사용자가 Google 또는 Facebook을 통해 로그인하면, 이 과정은 Federation으로 사용자 인증을 처리하며, 이후 OAuth 2.0 프로토콜을 통해 애플리케이션이 사용자 데이터를 가져오도록 허용합니다.
      • AWS Cognito: Cognito는 Federation을 지원하며, OAuth 2.0을 사용해 사용자 인증 이후 액세스 토큰, ID 토큰 등을 발급합니다.

    연계 예시 (Google 로그인):

    1. 사용자가 Google 로그인 버튼을 클릭.
    2. OAuth 2.0을 통해 Google의 인증 서버로 리다이렉션되어 사용자 인증 수행.
    3. 인증 완료 후, Google은 액세스 토큰을 애플리케이션에 반환.
    4. 애플리케이션은 액세스 토큰을 사용해 Google API 또는 사용자 데이터를 가져옴.

    장점

    • Federation과 OAuth 2.0을 함께 사용하면 다양한 인증 제공자를 지원하면서도 권한 부여를 표준화할 수 있음.
    • 사용자 경험 개선: 한 번의 로그인으로 다수의 리소스에 접근 가능(Single Sign-On, SSO).

    단점

    • 초기 설정의 복잡성: Federation과 OAuth 2.0을 함께 설정하려면 인증 제공자와 애플리케이션 간의 설정 작업이 필요.
    • 보안 문제: 잘못된 토큰 관리나 권한 부여 로직으로 인해 데이터 유출 가능성 존재.

서비스 Architecture

Cognito 일반 회원

회원가입 및 이메일 인증 흐름

  1. 회원가입 요청
    • 사용자가 클라이언트의 회원가입 페이지에서 username, password, email을 입력하고 /signup 엔드포인트로 요청을 전송
  2. 회원 등록 요청 처리
    • 요청은 API Gateway를 통과하여 signup.js Lambda 함수로 전달
    • Lambda 함수는 Cognito에 App Client ID와 함께 회원 등록 요청을 보냄
  3. Cognito에서 이메일 인증 코드 전송
    • Cognito는 회원 등록 후 사용자의 email 상태를 확인하기 위해, 사용자의 이메일로 인증 코드를 전송
  4. 이메일 인증 코드 확인 요청
    • 사용자는 이메일로 받은 인증 코드를 클라이언트의 인증 코드 입력 페이지에 입력.
    • 클라이언트는 입력받은 인증 코드를 /confirm 엔드포인트로 전송
  5. Lambda에서 인증 코드 검증
    • confirm 요청은 Lambda를 통해 Cognito로 전달
    • Cognito는 인증 코드를 확인하고, 사용자의 email 상태를 '확인됨(Verified)'으로 변경
    • 인증 성공 메시지를 반환
  6. 회원가입 완료 페이지 표시
    • 사용자는 클라이언트에서 회원가입 완료 페이지를 보게 됨

사용자 로그인 및 토큰 발급 흐름

  1. 로그인 요청
    • 사용자가 클라이언트의 로그인 페이지에 접속하여 usernamepassword를 입력하고 /signup 엔드포인트로 요청을 전송
  2. 로그인 요청 처리
    • 요청은 API Gateway를 통과하여 Lambda 함수로 전달
    • Lambda 함수는 Cognito로 AuthFlow: "USER_PASSWORD_AUTH"를 사용해 App Client ID와 함께 사용자 입력 정보를 전달
  3. Cognito에서 사용자 확인 및 토큰 발급
    • Cognito는 입력받은 정보를 기반으로 사용자가 존재하는지 확인
    • 인증이 성공하면 Access Token, Refresh Token, ID Token을 생성하여 반환
  4. 토큰을 브라우저로 전달
    • Lambda 함수는 Cognito에서 받은 토큰들을 HTTP 쿠키로 변환하여 브라우저에 전달

Ouath2.0 기반 사용자

Google OAuth 로그인 흐름

  1. Google 로그인 버튼 클릭
    • 사용자가 클라이언트 페이지에서 Google 로그인 버튼을 클릭.
    • 클라이언트는 /auth/google?mode=signup 엔드포인트로 Google 로그인 URL 생성 요청을 보냄.
  2. Google 로그인 URL 생성
    • 백엔드는 Google Client IDRedirect URL(백엔드 주소)을 사용해 Google 로그인 URL을 생성.
    • 생성된 URL을 클라이언트로 전달.
  3. 클라이언트에서 Google 로그인 페이지 접속
    • 클라이언트는 전달받은 Google URL로 이동하여 Google 로그인 페이지에 접속.
    • 사용자가 로그인 성공 시, Google은 미리 설정한 Redirect URLAuthorization Code를 전달.
  4. Authorization Code 수신
    • Redirect URL(예: /auth/google/callback)에서 Authorization Code를 수신.
  5. Google 서버로 인증 요청
    • 백엔드는 Google의 OAuth Token 인증 엔드포인트로 Authorization Code를 전달.
  6. Google 토큰 발급
    • Google은 인증 코드를 확인한 뒤 Access Token, Refresh Token, ID Token을 백엔드로 반환.
  7. 토큰 검증 및 사용자 정보 추출
    • 백엔드는 받은 토큰의 유효성을 검사.
    • 유효한 경우, 사용자의 emailsub(googleId)를 추출하여 처리.

회원가입 흐름

  1. 사용자 정보 준비
    • 사용자 속성으로 다음 정보를 설정:
      • username: 이메일 주소로 설정.
      • email: 사용자 이메일.
      • googleId: Google 계정 ID.
      • group: googleusers 그룹에 할당.
  2. 회원 등록 요청
    • 위 사용자 속성을 포함하여 Cognito에 회원 등록 요청 전송.
  3. 사용자 정보 저장
    • Cognito는 요청받은 사용자 정보를 사용자 풀(User Pool)에 저장.

CUSTOM_AUTH를 통한 사용자 인증 흐름

1. 사용자 요청

  • 사용자가 Google 로그인을 하기 위해 /auth/google?mode=signin URL로 요청을 보냅니다.
  • Google 토큰(email, idToken)을 받는 방식은 회원가입 과정과 동일합니다.

2. 백엔드에서 Cognito로 로그인 요청

  • 백엔드는 Google email, Google idToken, 그리고 AuthFlow: "CUSTOM_AUTH"를 사용해 Cognito 로그인을 요청합니다.
  • Cognito는 사용자 인증 과정을 시작합니다.

3. CUSTOM_AUTH 주요 동작

CUSTOM_AUTH는 사용자 인증 과정을 단계별로 처리하며, 세 가지 주요 트리거(Define-Auth-Challenge, Create-Auth-Challenge, Verify-Auth-Challenge)를 통해 흐름이 진행됩니다.

  1. Define-Auth-Challenge.js:
    • 사용자에게 어떤 인증 방식(OAuth 방식)을 사용할지 정의합니다.
    • CHALLENGE_NAME을 통해 Google OAuth 인증 방식이 사용됨을 설정합니다.
    • 전체 인증 흐름의 시작점을 관리합니다.
  2. Create-Auth-Challenge.js:
    • 사용자 인증을 위한 구체적인 인증 방식을 정의합니다.
    • Google OAuth의 idToken에서 추출한 sub 값(googleId)을 기반으로 사용자 인증을 수행하도록 설정합니다.
  3. Verify-Auth-Challenge.js:
    • 사용자가 제출한 인증 응답(예: email과 Google sub 값)을 검증합니다.
    • 제출된 Google sub 값과 Cognito에 저장된 sub 값이 일치하는지 확인하여 인증을 완료합니다.

4. 상세 인증 흐름

  1. Cognito로 로그인 요청
    • 백엔드는 Cognito에 App Client ID, email, AuthFlow: "CUSTOM_AUTH"를 전달하여 로그인 요청을 보냅니다.
  2. Define Auth Challenge 트리거
    • Cognito는 Define Auth Challenge 트리거를 호출하여 사용자 인증 방식(OAuth)을 정의합니다.
    • Google OAuth 인증 방식에 맞는 challenge session을 생성합니다.
  3. Create Auth Challenge 트리거
    • Cognito는 Create Auth Challenge 트리거를 호출하여 OAuth 방식의 인증 챌린지를 생성합니다.
    • 이 단계에서 Google의 idToken에서 추출한 sub(googleId) 값을 사용해 사용자 인증 조건을 정의합니다.
  4. 백엔드가 Create Auth Challenge 응답 처리
    • 백엔드는 emailGoogle sub 값(idToken)을 포함한 응답을 Cognito로 전달합니다.
  5. Verify Auth Challenge 트리거
    • Cognito는 Verify Auth Challenge 트리거를 호출하여 사용자의 응답을 검증합니다.
    • 사용자가 제출한 Google sub 값과 Cognito에 저장된 sub 값이 일치하면 인증이 성공합니다.
  6. Define Auth Challenge로 인증 완료 알림
    • Cognito는 인증 성공 정보를 Define Auth Challenge 트리거에 전달하고, Define Auth Challenge는 인증 세션을 종료하며 Cognito에게 토큰 발급을 요청합니다.
  7. Cognito에서 토큰 발급
    • Cognito는 Access Token, Refresh Token, ID Token을 생성하여 백엔드로 전달합니다.
  8. 백엔드에서 사용자에게 토큰 전달
    • 백엔드는 Cognito로부터 받은 토큰을 쿠키 형태로 사용자 브라우저에 전달합니다.

5. 주요 포인트

  1. Define-Auth-Challenge.js:
    • OAuth 방식(Google OAuth)에 맞는 인증 흐름을 정의하며, CHALLENGE_NAME을 설정합니다.
  2. Create-Auth-Challenge.js:
    • Google OAuth의 idToken에서 사용자 식별 값을 기반으로 인증 챌린지를 생성합니다.
  3. Verify-Auth-Challenge.js:
    • 사용자가 제출한 응답(email, Google sub 값)을 검증하여 인증 여부를 판단합니다.
  4. Cognito와 백엔드 간 협력:
    • Cognito는 전체 인증 흐름과 토큰 발급을 관리하며, 백엔드는 사용자에게 최종 토큰을 전달합니다.

6. 최종 결과

  • 사용자 인증이 성공적으로 완료되면:
    • Cognito는 백엔드에 Access Token, Refresh Token, ID Token을 반환합니다.
    • 백엔드는 이 토큰들을 사용자 브라우저에 쿠키로 전달하여 인증 상태를 유지합니다.

서비스 Endpoints

서비스 분류 엔드 포인트 요청 파라미터 응답 데이터
일반 Cognito 사용자 로그인 POST
auth/v1/signin { "username": "test1", "password": "abcde123!",} {
"message": "Login successful",
}
일반 Cognito 사용자 회원가입 POST
auth/v1/signup { "username": "test1", "password": "abcde123!",
"name" : "사용자",
"email": "test@gamil.com",
"birthdate": "2000-05-18",
"gender": "남",
"phone_number": "010-1234-5678"}
회원 로그인 GET
auth/v1/signout
Ouath (google) 회원가입 또는 로그인 페이지 전송 GET
auth/v1/google?mode=signin
Ouath (google) 회원가입 또는 로그인 페이지 전송 GET
auth/v1/google?mode=signup
Ouath 인증 코드 받기 GET
auth/google/callback
일반 Cognito 사용자 이메일 확인 POST
auth/v1/confirm { "username" : "test1", "confirmationCode" : "12656432" }
일반 Cognito 사용자 이메일 확인 코드 재전송 POST
auth/v1/resend { "username" : "test1"
} {
" message:" "Confirmation code has been resent.",
}
사용자 accessToken, idToken 재발급 GET
auth/refresh
사용자 cognito 정보 조회 GET
auth/v1/info { "username" : "test1" }
사용자 개인정보 조회 GET
auth/v1/user { "username": "test1", "name" : "사용자", "email": "test@gamil.com", "birthdate": "2000-05-18", "gender": "남", "phone_number": "010-1234-5678"}
사용자 개인정보 수정 PUT
auth/v1/user { "username": "test1", "name" : "사용자님", "email": "test@gamil.com", "birthdate": "2000-05-18", "gender": "남", "phone_number": "010-1234-5678"}