Day 16/30: Terraform으로 AWS IAM 사용자 관리 마스터하기

발행: (2025년 12월 11일 오후 10:43 GMT+9)
5 min read
원문: Dev.to

Source: Dev.to

Architecture

Architecture diagram

IAM은 대규모 조직에서 사용자와 권한을 관리하는 핵심 요소입니다. 이 데모는 Terraform을 사용해 IAM 사용자, 그룹 및 멤버십을 관리하는 방법을 보여줍니다—Azure AD 사용자 관리의 AWS‑중심 대안—그리고 Terraform의 반복 구조(for_each, for 표현식, 조건부 필터링)를 시연합니다.

What This Demo Does

  • Retrieves AWS Account Information – 현재 AWS 계정 ID를 가져옵니다.
  • Reads User Data from CSV – CSV 파일에서 사용자 정보를 로드합니다.
  • Creates IAM Users – 일관된 네이밍 규칙으로 사용자를 자동 생성합니다.
  • Sets Up Login Profiles – 비밀번호 재설정이 필수인 콘솔 접근을 구성합니다.
  • Creates IAM Groups – 조직 그룹(교육, 관리자, 엔지니어)을 설정합니다.
  • Manages Group Memberships – 사용자 속성에 따라 그룹에 할당합니다.

Mini Project Overview

Goal: users.csv를 기반으로 26명의 IAM 사용자를 일괄 생성합니다.

Key Features

  • 동적 그룹 할당(교육, 엔지니어, 관리자).
  • 임시 비밀번호를 사용한 콘솔 로그인.
  • 상태 관리를 위한 S3 원격 백엔드.
  • 사용자 이름 형식: 첫 글자 + 성(예: Michael Scott → mscott).

What Gets Created

  • 콘솔 접근이 가능한 26명의 IAM 사용자.
  • 3개의 IAM 그룹(교육, 관리자, 엔지니어).
  • 사용자 속성에서 파생된 그룹 멤버십.
  • 메타데이터(DisplayName, Department, JobTitle)를 포함한 사용자 태그.

Project Setup

day16/
├── backend.tf          # S3 backend configuration for state
├── provider.tf         # AWS provider configuration
├── versions.tf         # Terraform version and required providers
├── main.tf             # Main user creation logic
├── groups.tf           # IAM groups and membership management
├── users.csv           # User data source

CSV Processing

Terraform의 csvdecode() 함수는 CSV 파일을 맵 리스트로 변환하며, 이를 반복해서 사용할 수 있습니다.

CSV format

first_name,last_name,department,job_title
Michael,Scott,Education,Regional Manager
Dwight,Schrute,Sales,Assistant to the Regional Manager

Local variable

locals {
  users = csvdecode(file("users.csv"))
}

users.csv 파일을 Terraform 설정 파일과 동일한 디렉터리에 두세요.

IAM User Creation

resource "aws_iam_user" "users" {
  for_each = { for user in local.users : user.first_name => user }

  name = lower("${substr(each.value.first_name, 0, 1)}${each.value.last_name}")
  path = "/users/"

  tags = {
    DisplayName = "${each.value.first_name} ${each.value.last_name}"
    Department  = each.value.department
    JobTitle    = each.value.job_title
  }
}
  • Username: {first_initial}{last_name}(소문자).
  • Tags는 부서와 직책을 포함해 이후 그룹 필터링에 활용됩니다.

Console Login Profiles

resource "aws_iam_user_login_profile" "users" {
  for_each = aws_iam_user.users

  user                     = each.value.name
  password_reset_required = true

  lifecycle {
    ignore_changes = [password_reset_required, password_length]
  }
}

첫 로그인 시 비밀번호 재설정을 강제하는 콘솔 로그인 프로필을 생성합니다. lifecycle 블록은 비밀번호가 바뀔 때 불필요한 재생성을 방지합니다.

Create Groups and Memberships

Create IAM Groups

resource "aws_iam_group" "education" {
  name = "Education"
  path = "/groups/"
}

resource "aws_iam_group_membership" "education_members" {
  name  = "education-group-membership"
  group = aws_iam_group.education.name

  users = [
    for user in aws_iam_user.users : user.name
    if user.tags.Department == "Education"
  ]
}

EngineersManagers에 대해서도 유사한 블록을 만들 수 있습니다. if 절이 포함된 for 표현식은 Department 태그를 기준으로 사용자를 필터링합니다.

Manager Group Logic (Advanced)

resource "aws_iam_group_membership" "managers_members" {
  name  = "managers-group-membership"
  group = aws_iam_group.managers.name

  users = [
    for user in aws_iam_user.users :
    user.name
    if contains(keys(user.tags), "JobTitle") &&
       can(regex("Manager|CEO", user.tags.JobTitle))
  ]
}

can() 함수는 JobTitle 키가 존재하는지 안전하게 확인하고, 직함에 “Manager” 또는 “CEO”가 포함된 경우 해당 사용자를 Managers 그룹에 할당합니다.

Execution Commands

# Initialize Terraform (download providers, configure backend)
terraform init

# Review the planned changes
terraform plan

# Apply the configuration
terraform apply

구성을 실행하면 총 58개의 리소스가 프로비저닝됩니다:

  • 26 IAM 사용자
  • 26 IAM 사용자 로그인 프로필
  • 3 IAM 그룹
  • 3 IAM 그룹 멤버십

Happy Terraforming!

Back to Blog

관련 글

더 보기 »