
AWS IAM 완전 정복: '누가, 무엇을, 어디서 할 수 있는가'를 결정하는 기술
AWS에서 발생하는 보안 사고의 대부분은 IAM 설정 실수다. '최소 권한 원칙'이 왜 중요하고, 사용자·역할·정책이 어떻게 작동하며, GitHub에 노출된 IAM 키가 어떤 참사를 불러오는지 — 클라우드 보안의 기반인 IAM을 실전 사례와 함께 풀어본다.

AWS에서 발생하는 보안 사고의 대부분은 IAM 설정 실수다. '최소 권한 원칙'이 왜 중요하고, 사용자·역할·정책이 어떻게 작동하며, GitHub에 노출된 IAM 키가 어떤 참사를 불러오는지 — 클라우드 보안의 기반인 IAM을 실전 사례와 함께 풀어본다.
AWS를 처음 배우는 개발자에게 가장 흔한 유혹:
"IAM이 복잡하니까, 일단 모든 서비스에 AdministratorAccess를 주자. 나중에 줄이면 되잖아."
이것은 집의 모든 방에 같은 마스터키를 쓰고, 그 키를 현관 앞에 놓아두는 것과 같다. 편리하다. 누구나 어디든 갈 수 있다. 그리고 어느 날, 그 키가 유출되면 — 모든 것이 끝난다.
IAM은 AWS에서 가장 중요한 서비스다. EC2가 없으면 서버를 못 쓰고, S3가 없으면 파일을 못 저장하지만, IAM이 없으면 어떤 서비스도 안전하게 쓸 수 없다. 그리고 IAM을 잘못 설정하면, 다른 모든 보안이 무너진다.
IAM(Identity and Access Management)은 AWS 리소스에 대한 접근을 안전하게 제어하는 서비스다. **"누가(Identity), 무엇을(Action), 어디에(Resource) 할 수 있는가(Allow/Deny)"**를 정의한다.
| IAM 개념 | 건물 비유 | 역할 |
|---|---|---|
| AWS 계정 | 건물 전체 | 모든 리소스의 최상위 컨테이너 |
| 루트 사용자 | 건물주 (마스터키 보유) | 모든 권한. 절대 일상 업무에 쓰지 말 것 |
| IAM 사용자 | 직원 (개인 출입증) | 개인별 자격증명 (ID/비밀번호, 액세스 키) |
| IAM 그룹 | 부서 | 같은 권한이 필요한 사용자 묶음 |
| IAM 역할(Role) | 임시 출입증 (반납 필요) | 서비스나 사용자가 일시적으로 착용하는 권한 |
| IAM 정책(Policy) | 출입 규칙서 | "이 출입증으로 어떤 방에 갈 수 있는가" |
| MFA | 지문 인식 (2차 인증) | 비밀번호 외에 추가 인증 수단 |
모든 AWS API 호출에서 IAM은 세 가지를 확인한다:
2006년 AWS 출시 초기에는 AWS 계정 하나에 루트 자격증명 하나만 있었다. 팀원이 10명이면 모두 같은 루트 계정으로 로그인했다. 누가 뭘 했는지 추적 불가능.
AWS가 IAM을 출시하며 개별 사용자, 그룹, 정책 개념을 도입했다. 팀원마다 별도 사용자를 만들고, 각자 필요한 권한만 부여할 수 있게 됐다.
EC2 인스턴스가 S3에 접근해야 할 때, 과거에는 인스턴스 안에 액세스 키를 파일로 저장했다. 이것은 보안 재앙의 씨앗이었다 — 그 파일이 유출되면 끝이다.
IAM 역할(Role) 이 이 문제를 해결했다. EC2에 역할을 부여하면, 인스턴스가 자동으로 임시 자격증명을 받아 AWS 서비스에 접근한다. 키 파일이 필요 없다.
IAM 정책은 JSON으로 작성되며, **"누가, 무엇을, 어디에, 어떤 조건에서 할 수 있는가"**를 정의한다.
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"s3:GetObject",
"s3:PutObject"
],
"Resource": "arn:aws:s3:::my-bucket/uploads/*",
"Condition": {
"IpAddress": {
"aws:SourceIp": "203.0.113.0/24"
}
}
}
]
}
이 정책의 의미: "my-bucket의 uploads/ 경로에 대해 읽기·쓰기를 허용하되, 203.0.113.0/24 IP 대역에서만 가능."
| AWS 관리형 정책 | 커스텀 정책 | |
|---|---|---|
| 생성 | AWS가 미리 만들어 놓음 | 직접 작성 |
| 업데이트 | AWS가 자동 업데이트 | 직접 관리 |
| 예시 | AmazonS3ReadOnlyAccess, AmazonEC2FullAccess | 위의 JSON 같은 세밀한 정책 |
| 장점 | 빠른 시작, 모범 사례 반영 | 최소 권한에 정확히 맞출 수 있음 |
| 단점 | 필요 이상의 권한이 포함될 수 있음 | 작성·관리에 시간 소요 |
AmazonS3FullAccess는 계정 내 모든 S3 버킷의 모든 작업을 허용한다. 하나의 Lambda 함수가 하나의 버킷만 읽으면 되는데, 모든 버킷을 삭제할 수 있는 권한까지 주는 것이다. 가능하면 커스텀 정책으로 필요한 버킷, 필요한 작업만 허용하라.가장 흔하고 가장 치명적인 IAM 보안 사고: AWS 액세스 키가 GitHub에 커밋되는 것.
이것은 가상 시나리오가 아니다. 매일 수천 건 발생하고 있다.
"각 주체(사용자, 역할, 서비스)에게 업무 수행에 필요한 최소한의 권한만 부여한다."
NIST(미국 국립표준기술연구소)의 제로 트러스트 아키텍처(SP 800-207)에서 핵심 원칙으로 정의하고 있다.
나쁜 예:
{
"Effect": "Allow",
"Action": "s3:*",
"Resource": "*"
}
→ 모든 S3 버킷의 모든 작업 허용. Capital One 사고의 원인.
좋은 예:
{
"Effect": "Allow",
"Action": ["s3:GetObject"],
"Resource": "arn:aws:s3:::my-app-uploads/*"
}
→ 특정 버킷의 읽기만 허용. 이 키가 유출되어도 피해가 제한적.
수동으로 최소 권한 정책을 작성하는 것은 어렵다. AWS는 이를 돕는 도구를 제공한다:
| 번호 | 하지 마라 | 왜? |
|---|---|---|
| 1 | 루트 계정으로 일상 업무 | 루트 = 모든 권한. 탈취 시 회사가 사라질 수 있음 |
| 2 | 코드에 액세스 키 하드코딩 | GitHub에 올라가면 4분 안에 악용됨 |
| 3 | IAM 사용자 간 키 공유 | 누가 뭘 했는지 추적 불가능 |
| 4 | MFA 없이 콘솔 접근 | 비밀번호만으로는 불충분 |
| 5 | * 리소스에 * 액션 허용 | 최소 권한 원칙 완전 위반 |
| 번호 | 해야 한다 | 방법 |
|---|---|---|
| 1 | 루트 계정 MFA 활성화 | 물리 보안 키(YubiKey) 권장 |
| 2 | IAM 역할 사용 (서비스) | EC2, Lambda, ECS → 역할 부여 |
| 3 | 정기적 자격증명 회전 | 90일마다 액세스 키 교체 |
| 4 | CloudTrail 활성화 | 모든 API 호출 로깅 |
| 5 | IAM Access Analyzer 활성화 | 외부 접근 가능 리소스 자동 감지 |
| AWS IAM | Azure AD (Entra ID) | Google Cloud IAM | |
|---|---|---|---|
| 인증 | IAM 사용자, 역할, Federation | Azure AD (기업 디렉토리) | Google 계정, 서비스 계정 |
| 세분화 | 리소스 ARN 수준 | RBAC + ABAC | 리소스 수준 |
| 멀티 계정 | IAM Identity Center, Organizations | Azure AD 테넌트 | 프로젝트/폴더 |
| MFA | TOTP, 보안 키, PassKey | MS Authenticator, FIDO2 | Google Authenticator, 보안 키 |
| SSO | SAML, OIDC 연동 | 네이티브 SSO | Google Workspace SSO |
| 강점 | 세밀한 정책 제어 | 엔터프라이즈 ID 관리 | 간결한 구조 |
| IAM | Cognito | |
|---|---|---|
| 대상 | 개발자, 서비스, 관리자 | 앱의 최종 사용자 (고객) |
| 용도 | AWS 리소스 접근 제어 | 앱 로그인/회원가입 |
| 인증 방식 | 액세스 키, 역할, 콘솔 | 이메일/비밀번호, 소셜 로그인, MFA |
| 비유 | 회사 사원증 | 앱의 로그인 화면 |
NIST SP 800-207 "Zero Trust Architecture"(2020)이 제로 트러스트를 공식 프레임워크로 정의한 이후, AWS도 IAM을 제로 트러스트 방향으로 강화하고 있다:
Netflix는 수천 개의 마이크로서비스에 각각 전용 IAM 역할을 부여한다. 추천 서비스는 추천 DB만 접근 가능, 결제 서비스는 결제 API만 호출 가능. 한 서비스가 침해되어도 다른 서비스의 데이터에는 접근 불가.
Airbnb는 CloudTrail 로그를 실시간 분석하여 비정상적 IAM 활동(새벽에 관리자 로그인, 알 수 없는 리전에서 API 호출, 대량의 리소스 생성)을 자동 감지하고 알림한다.
이 시리즈의 모든 서비스는 IAM 위에서 동작한다:
| 서비스 | IAM과의 관계 |
|---|---|
| EC2 | 인스턴스 역할로 AWS 서비스 접근 |
| Lambda | 실행 역할(execution role)로 DynamoDB, S3 등 접근 |
| ECS | 태스크 역할로 컨테이너에 권한 부여 |
| S3 | 버킷 정책 + IAM 정책으로 접근 제어 |
| RDS | IAM 인증으로 DB 접속 |
| Bedrock | IAM으로 어떤 모델을 누가 호출할 수 있는지 제어 |
| API Gateway | Lambda Authorizer 또는 IAM 인증 |
| CloudWatch | IAM으로 로그·메트릭 접근 제어 |
IAM이 무너지면 이 모든 것이 무너진다. VPC가 네트워크의 기반이라면, IAM은 접근 제어의 기반이다. 두 가지 모두 보이지 않지만, 없으면 모든 것이 위험하다.
Code Spaces는 IAM 실수로 회사가 사라졌다. Capital One은 IAM 과도 권한으로 1억 명의 데이터가 유출됐다. 이 교훈은 분명하다: IAM은 "나중에" 신경 쓸 것이 아니라, "가장 먼저" 제대로 설정해야 할 것이다.
코어닷투데이의 모든 AWS 서비스는 최소 권한 원칙 위에 구축되어 있다. AI 추론 서비스는 Bedrock 호출 권한만, 데이터 파이프라인은 지정된 S3 버킷 접근만, 모니터링은 CloudWatch 읽기 권한만 — 각 서비스가 자기 일에 필요한 최소한의 열쇠만 가지고 있다. 그것이 "잠이 올 수 있는" 보안의 시작이다.