IAM(Identity and Access Management)은 AWS 리소스에 대한 액세스를 안전하게 제어하는 서비스다. 누가(인증) 무엇을(권한) 할 수 있는지 관리한다.


IAM이란?

핵심 기능

기능 설명
인증 (Authentication) 사용자가 누구인지 확인
권한 부여 (Authorization) 어떤 작업을 할 수 있는지 결정
액세스 관리 리소스별 세밀한 권한 제어
연합 자격 증명 외부 ID 공급자 연동

특징

- 글로벌 서비스 (리전 선택 불필요)
- 무료 서비스
- 최종 일관성 모델 (변경사항 전파에 시간 소요)
- AWS 계정과 통합

핵심 구성 요소

1. 사용자 (User)

AWS에 액세스하는 개인 또는 애플리케이션을 나타낸다.

사용자 = 자격 증명 + 권한

자격 증명 유형:

유형 용도
콘솔 암호 AWS Management Console 로그인
액세스 키 (Access Key + Secret Key) CLI, SDK, API 호출
# AWS CLI 자격 증명 설정
aws configure
# AWS Access Key ID: AKIAIOSFODNN7EXAMPLE
# AWS Secret Access Key: wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY
# Default region name: ap-northeast-2
# Default output format: json

2. 그룹 (Group)

사용자의 집합. 그룹에 정책을 연결하면 모든 그룹 구성원에게 권한이 적용된다.

개발팀 그룹
  ├── 개발자 A (User)
  ├── 개발자 B (User)
  └── 개발자 C (User)
      ↓
  S3, EC2 접근 정책 적용

특징:

  • 사용자는 여러 그룹에 속할 수 있음
  • 그룹은 다른 그룹을 포함할 수 없음 (중첩 불가)
  • 기본 그룹 없음 (명시적 생성 필요)

3. 역할 (Role)

AWS 서비스나 외부 사용자가 임시로 권한을 얻기 위해 사용한다.

역할 = 신뢰 정책 + 권한 정책

사용 사례:

시나리오 설명
EC2 → S3 EC2 인스턴스가 S3에 접근
Lambda → DynamoDB Lambda 함수가 DynamoDB 접근
교차 계정 다른 AWS 계정의 리소스 접근
연합 자격 증명 외부 사용자(Google, SAML)가 AWS 접근
// 신뢰 정책 (Trust Policy) - 누가  역할을 맡을  있는가
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "Service": "ec2.amazonaws.com"
      },
      "Action": "sts:AssumeRole"
    }
  ]
}

4. 정책 (Policy)

권한을 정의하는 JSON 문서. 어떤 리소스에 어떤 작업을 허용/거부할지 명시한다.


정책 (Policy) 상세

정책 구조

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Sid": "AllowS3Read",
      "Effect": "Allow",
      "Action": [
        "s3:GetObject",
        "s3:ListBucket"
      ],
      "Resource": [
        "arn:aws:s3:::my-bucket",
        "arn:aws:s3:::my-bucket/*"
      ],
      "Condition": {
        "IpAddress": {
          "aws:SourceIp": "192.168.1.0/24"
        }
      }
    }
  ]
}

정책 요소

요소 필수 설명
Version O 정책 언어 버전 (“2012-10-17” 권장)
Statement O 권한 명세 배열
Sid X 문장 식별자
Effect O Allow 또는 Deny
Action O 허용/거부할 작업
Resource O 대상 리소스 ARN
Condition X 조건부 적용
Principal * 정책 적용 대상 (리소스 기반 정책)

정책 유형

1. 자격 증명 기반 정책 (Identity-based)

사용자, 그룹, 역할에 연결

// 관리형 정책 - AWS 제공 또는 고객 생성
// 인라인 정책 - 특정 자격 증명에 직접 포함
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": "ec2:*",
      "Resource": "*"
    }
  ]
}

2. 리소스 기반 정책 (Resource-based)

S3 버킷, SQS 큐 등 리소스에 직접 연결

// S3 버킷 정책 예시
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "AWS": "arn:aws:iam::123456789012:user/alice"
      },
      "Action": "s3:GetObject",
      "Resource": "arn:aws:s3:::my-bucket/*"
    }
  ]
}

정책 평가 로직

1. 기본적으로 모든 요청은 거부 (암시적 거부)
2. 명시적 Allow가 있으면 허용
3. 명시적 Deny가 있으면 무조건 거부 (Allow보다 우선)
                    요청
                      ↓
              명시적 Deny 있음?
              ↙        ↘
            Yes         No
             ↓           ↓
           거부    명시적 Allow 있음?
                    ↙        ↘
                  Yes         No
                   ↓           ↓
                 허용        거부

AWS 관리형 정책

자주 사용되는 AWS 제공 정책

정책 이름 설명
AdministratorAccess 모든 AWS 리소스 전체 권한
PowerUserAccess IAM 제외 모든 서비스 권한
ReadOnlyAccess 모든 리소스 읽기 전용
AmazonS3FullAccess S3 전체 권한
AmazonS3ReadOnlyAccess S3 읽기 전용
AmazonEC2FullAccess EC2 전체 권한
AmazonRDSFullAccess RDS 전체 권한
AWSLambdaBasicExecutionRole Lambda 기본 실행 (CloudWatch Logs)

실전 정책 예시

EC2 특정 리전만 허용

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": "ec2:*",
      "Resource": "*",
      "Condition": {
        "StringEquals": {
          "aws:RequestedRegion": "ap-northeast-2"
        }
      }
    }
  ]
}

특정 태그가 있는 리소스만 접근

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
        "ec2:StartInstances",
        "ec2:StopInstances"
      ],
      "Resource": "*",
      "Condition": {
        "StringEquals": {
          "ec2:ResourceTag/Environment": "Development"
        }
      }
    }
  ]
}

S3 특정 버킷 + 폴더 접근

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": [
        "s3:ListBucket"
      ],
      "Resource": "arn:aws:s3:::my-bucket",
      "Condition": {
        "StringLike": {
          "s3:prefix": ["home/${aws:username}/*"]
        }
      }
    },
    {
      "Effect": "Allow",
      "Action": [
        "s3:GetObject",
        "s3:PutObject",
        "s3:DeleteObject"
      ],
      "Resource": "arn:aws:s3:::my-bucket/home/${aws:username}/*"
    }
  ]
}

MFA 필수 정책

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Deny",
      "Action": "*",
      "Resource": "*",
      "Condition": {
        "BoolIfExists": {
          "aws:MultiFactorAuthPresent": "false"
        }
      }
    }
  ]
}

역할 (Role) 활용

EC2 인스턴스 프로파일

EC2가 다른 AWS 서비스에 접근할 때 사용

# 1. 역할 생성 (AWS Console 또는 CLI)
aws iam create-role \
  --role-name EC2-S3-Access \
  --assume-role-policy-document file://trust-policy.json

# 2. 정책 연결
aws iam attach-role-policy \
  --role-name EC2-S3-Access \
  --policy-arn arn:aws:iam::aws:policy/AmazonS3ReadOnlyAccess

# 3. 인스턴스 프로파일 생성
aws iam create-instance-profile \
  --instance-profile-name EC2-S3-Access-Profile

# 4. 역할을 인스턴스 프로파일에 추가
aws iam add-role-to-instance-profile \
  --instance-profile-name EC2-S3-Access-Profile \
  --role-name EC2-S3-Access

# 5. EC2 인스턴스에 연결
aws ec2 associate-iam-instance-profile \
  --instance-id i-1234567890abcdef0 \
  --iam-instance-profile Name=EC2-S3-Access-Profile

Lambda 실행 역할

// 신뢰 정책
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "Service": "lambda.amazonaws.com"
      },
      "Action": "sts:AssumeRole"
    }
  ]
}

교차 계정 접근

계정 A의 S3 버킷을 계정 B 사용자가 접근

// 계정 A: S3 버킷 정책
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "AWS": "arn:aws:iam::ACCOUNT_B_ID:root"
      },
      "Action": "s3:*",
      "Resource": [
        "arn:aws:s3:::shared-bucket",
        "arn:aws:s3:::shared-bucket/*"
      ]
    }
  ]
}
// 계정 B: 사용자 정책
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": "s3:*",
      "Resource": [
        "arn:aws:s3:::shared-bucket",
        "arn:aws:s3:::shared-bucket/*"
      ]
    }
  ]
}

보안 모범 사례

1. 루트 계정 보호

- 루트 계정 사용 최소화
- MFA 활성화 필수
- 액세스 키 생성 금지
- 강력한 암호 사용

2. 최소 권한 원칙

- 필요한 권한만 부여
- 와일드카드(*) 사용 최소화
- 정기적인 권한 검토

3. MFA (Multi-Factor Authentication)

# 가상 MFA 디바이스 활성화
aws iam enable-mfa-device \
  --user-name alice \
  --serial-number arn:aws:iam::123456789012:mfa/alice \
  --authentication-code1 123456 \
  --authentication-code2 789012

4. 암호 정책 설정

aws iam update-account-password-policy \
  --minimum-password-length 14 \
  --require-symbols \
  --require-numbers \
  --require-uppercase-characters \
  --require-lowercase-characters \
  --allow-users-to-change-password \
  --max-password-age 90 \
  --password-reuse-prevention 12

5. 액세스 키 관리

# 액세스 키 나열
aws iam list-access-keys --user-name alice

# 액세스 키 비활성화
aws iam update-access-key \
  --user-name alice \
  --access-key-id AKIAIOSFODNN7EXAMPLE \
  --status Inactive

# 액세스 키 삭제
aws iam delete-access-key \
  --user-name alice \
  --access-key-id AKIAIOSFODNN7EXAMPLE

# 90일 이상 사용하지 않은 키 조회
aws iam generate-credential-report
aws iam get-credential-report --output text --query Content | base64 -d

IAM Access Analyzer

외부에서 접근 가능한 리소스를 분석하고 보안 위험을 식별한다.

# Access Analyzer 생성
aws accessanalyzer create-analyzer \
  --analyzer-name my-analyzer \
  --type ACCOUNT

# 분석 결과 조회
aws accessanalyzer list-findings \
  --analyzer-arn arn:aws:access-analyzer:ap-northeast-2:123456789012:analyzer/my-analyzer

분석 대상:

  • S3 버킷
  • IAM 역할
  • KMS 키
  • Lambda 함수
  • SQS 큐
  • Secrets Manager

AWS CLI 주요 명령어

사용자 관리

# 사용자 생성
aws iam create-user --user-name alice

# 사용자 목록
aws iam list-users

# 사용자 삭제
aws iam delete-user --user-name alice

# 콘솔 암호 설정
aws iam create-login-profile \
  --user-name alice \
  --password "P@ssw0rd123!" \
  --password-reset-required

# 액세스 키 생성
aws iam create-access-key --user-name alice

그룹 관리

# 그룹 생성
aws iam create-group --group-name Developers

# 사용자를 그룹에 추가
aws iam add-user-to-group --user-name alice --group-name Developers

# 그룹에서 사용자 제거
aws iam remove-user-from-group --user-name alice --group-name Developers

정책 관리

# 정책 생성
aws iam create-policy \
  --policy-name MyPolicy \
  --policy-document file://policy.json

# 정책 연결 (사용자)
aws iam attach-user-policy \
  --user-name alice \
  --policy-arn arn:aws:iam::123456789012:policy/MyPolicy

# 정책 연결 (그룹)
aws iam attach-group-policy \
  --group-name Developers \
  --policy-arn arn:aws:iam::123456789012:policy/MyPolicy

# 정책 연결 (역할)
aws iam attach-role-policy \
  --role-name MyRole \
  --policy-arn arn:aws:iam::123456789012:policy/MyPolicy

역할 관리

# 역할 생성
aws iam create-role \
  --role-name MyRole \
  --assume-role-policy-document file://trust-policy.json

# 역할 맡기 (Assume Role)
aws sts assume-role \
  --role-arn arn:aws:iam::123456789012:role/MyRole \
  --role-session-name my-session

IAM 정책 시뮬레이터

정책이 예상대로 동작하는지 테스트한다.

# CLI로 정책 시뮬레이션
aws iam simulate-principal-policy \
  --policy-source-arn arn:aws:iam::123456789012:user/alice \
  --action-names s3:GetObject \
  --resource-arns arn:aws:s3:::my-bucket/file.txt

웹 콘솔: https://policysim.aws.amazon.com/


STS (Security Token Service)

임시 보안 자격 증명을 발급한다.

# 임시 자격 증명 획득
aws sts get-session-token \
  --duration-seconds 3600 \
  --serial-number arn:aws:iam::123456789012:mfa/alice \
  --token-code 123456

# 현재 자격 증명 확인
aws sts get-caller-identity

반환 값:

{
  "Credentials": {
    "AccessKeyId": "ASIAXXX...",
    "SecretAccessKey": "xxx...",
    "SessionToken": "xxx...",
    "Expiration": "2024-01-02T12:00:00Z"
  }
}

정리

구성 요소 설명
사용자 (User) 개인 또는 애플리케이션의 AWS 자격 증명
그룹 (Group) 사용자 집합, 정책 일괄 적용
역할 (Role) 임시 권한, 서비스/교차 계정 접근
정책 (Policy) 권한 정의 JSON 문서

핵심 원칙

1. 루트 계정 사용 금지
2. MFA 활성화
3. 최소 권한 원칙
4. 역할 사용 우선 (액세스 키 대신)
5. 정기적인 자격 증명 교체
6. Access Analyzer로 모니터링

IAM은 AWS 보안의 기초다. 잘못된 IAM 설정은 심각한 보안 사고로 이어질 수 있으니 신중하게 관리하자.