Skip to main content

identity-center-guide


IAM Identity Center — Consumer Deployment Guide

Overview

The oceansoft/iam-identity-center/aws module provisions and manages AWS IAM Identity Center (SSO) resources for multi-account AWS Organizations. It manages 14 resource types across the full Identity Center lifecycle:

Resource CategoryResource Types
Identity StoreUsers, Groups, Group Memberships
Permission SetsPermission Sets, AWS Managed Policy Attachments, Customer Managed Policy Attachments, Inline Policies, Permissions Boundaries (AWS + Customer)
Account AssignmentsAccount Assignments, Instance Access Control Attributes
ApplicationsApplications, Application Assignment Configurations, Application Access Scopes, Application Assignments

Cost: $0/month — IAM Identity Center has no per-resource charges. You pay only for the AWS accounts you assign.

Registry: registry.terraform.io/modules/oceansoft/iam-identity-center/aws


Prerequisites

Before deploying this module:

  1. AWS Organizations must be enabled with your management account.
  2. IAM Identity Center must be enabled in us-east-1 (the service is global but delegates to us-east-1). Enable via the AWS Console: IAM Identity Center > Enable.
  3. Terraform >= 1.11.0 — required for S3 native state locking and tftest.hcl snapshot testing.
  4. AWS Provider >= 6.28, < 7.0 — pinned per ADR-003.
  5. Caller must have sso:* and identitystore:* permissions in the management account.

Quick Start

Minimal configuration to create one group, one permission set, and one account assignment:

module "identity_center" {
source = "oceansoft/iam-identity-center/aws"
version = "~> 0.1"

sso_groups = {
platform_admins = {
group_name = "PlatformAdmins"
group_description = "Platform engineering team — full administrative access"
}
}

permission_sets = {
AdministratorAccess = {
description = "Full administrative access"
session_duration = "PT8H"
aws_managed_policies = [
"arn:aws:iam::aws:policy/AdministratorAccess"
]
tags = {
DataClassification = "restricted"
}
}
}

account_assignments = {
platform_admins_mgmt = {
principal_name = "PlatformAdmins"
principal_type = "GROUP"
principal_idp = "INTERNAL"
permission_sets = ["AdministratorAccess"]
account_ids = ["123456789012"]
}
}

default_tags = {
CostCenter = "platform"
Project = "landing-zone"
Environment = "prod"
DataClassification = "internal"
}
}

Multi-Account Patterns

3-Account Landing Zone

A minimal APRA-aligned landing zone with management, security, and workload accounts:

locals {
account_ids = {
management = "111111111111"
security = "222222222222"
workload = "333333333333"
}
}

module "identity_center" {
source = "oceansoft/iam-identity-center/aws"
version = "~> 0.1"

sso_groups = {
cloud_admins = { group_name = "CloudAdmins" }
security_team = { group_name = "SecurityTeam" }
developers = { group_name = "Developers" }
readonly_users = { group_name = "ReadOnlyUsers" }
}

permission_sets = {
AdministratorAccess = {
description = "Full admin — management account only"
session_duration = "PT4H"
aws_managed_policies = ["arn:aws:iam::aws:policy/AdministratorAccess"]
}
PowerUserAccess = {
description = "Power user — workload accounts"
session_duration = "PT8H"
aws_managed_policies = ["arn:aws:iam::aws:policy/PowerUserAccess"]
}
ReadOnlyAccess = {
description = "Read-only — all accounts"
session_duration = "PT12H"
aws_managed_policies = ["arn:aws:iam::aws:policy/ReadOnlyAccess"]
}
SecurityAudit = {
description = "Security audit — security account"
session_duration = "PT8H"
aws_managed_policies = ["arn:aws:iam::aws:policy/SecurityAudit"]
}
}

account_assignments = {
admins_management = {
principal_name = "CloudAdmins"
principal_type = "GROUP"
principal_idp = "INTERNAL"
permission_sets = ["AdministratorAccess"]
account_ids = [local.account_ids.management]
}
admins_workload = {
principal_name = "CloudAdmins"
principal_type = "GROUP"
principal_idp = "INTERNAL"
permission_sets = ["PowerUserAccess"]
account_ids = [local.account_ids.workload]
}
security_audit = {
principal_name = "SecurityTeam"
principal_type = "GROUP"
principal_idp = "INTERNAL"
permission_sets = ["SecurityAudit"]
account_ids = [local.account_ids.security, local.account_ids.management]
}
developers_workload = {
principal_name = "Developers"
principal_type = "GROUP"
principal_idp = "INTERNAL"
permission_sets = ["PowerUserAccess"]
account_ids = [local.account_ids.workload]
}
readonly_all = {
principal_name = "ReadOnlyUsers"
principal_type = "GROUP"
principal_idp = "INTERNAL"
permission_sets = ["ReadOnlyAccess"]
account_ids = values(local.account_ids)
}
}

default_tags = {
CostCenter = "platform"
Project = "landing-zone"
Environment = "prod"
DataClassification = "internal"
}
}

ABAC for Environment-Scoped Access

Use sso_instance_access_control_attributes to pass ABAC context from user attributes into session policies:

module "identity_center" {
source = "oceansoft/iam-identity-center/aws"
version = "~> 0.1"

sso_instance_access_control_attributes = [
{
attribute_name = "Environment"
source = ["$${path:enterprise.Environment}"]
},
{
attribute_name = "CostCenter"
source = ["$${path:enterprise.CostCenter}"]
}
]

# ... groups, permission_sets, account_assignments as above
}

ABAC attributes are injected into session tags. Use aws:PrincipalTag/Environment in IAM condition keys within inline or customer-managed policies to restrict access by environment.


YAML Configuration API

For APRA CPS 234 audit trails, the module supports a config_path variable pointing to a directory containing permission_sets.yaml and account_assignments.yaml. YAML values take precedence over HCL variable values on key collision.

Directory structure:

config/
permission_sets.yaml
account_assignments.yaml

permission_sets.yaml:

AdministratorAccess:
description: "Full administrative access"
session_duration: "PT4H"
aws_managed_policies:
- "arn:aws:iam::aws:policy/AdministratorAccess"
tags:
DataClassification: "restricted"

ReadOnlyAccess:
description: "Read-only access"
session_duration: "PT12H"
aws_managed_policies:
- "arn:aws:iam::aws:policy/ReadOnlyAccess"
tags:
DataClassification: "internal"

account_assignments.yaml:

admins_management:
principal_name: "CloudAdmins"
principal_type: "GROUP"
principal_idp: "INTERNAL"
permission_sets:
- "AdministratorAccess"
account_ids:
- "111111111111"

Enable YAML mode in HCL:

module "identity_center" {
source = "oceansoft/iam-identity-center/aws"
version = "~> 0.1"
config_path = "${path.module}/config"

default_tags = {
CostCenter = "platform"
Project = "landing-zone"
Environment = "prod"
DataClassification = "internal"
}
}

config_path must contain only alphanumeric characters, dots, underscores, hyphens, and forward slashes. The YAML files are read at plan time via Terraform's file() and yamldecode() functions — no external tooling required.


APRA CPS 234 Compliance

The module enforces the following controls relevant to APRA CPS 234 (Information Security):

ControlImplementation
DataClassification tagRequired in default_tags. Validated at plan time — missing key causes terraform plan error.
Session durationISO 8601 format enforced (PT<n>H or PT<n>M). Invalid values fail at plan time.
Least privilegeUse ReadOnlyAccess as the baseline; escalate only with PowerUserAccess or AdministratorAccess for named groups.
Audit trailconfig_path YAML API provides version-controlled, auditor-readable permission configuration outside HCL.
Tag inheritance_effective_default_tags merges 5 canonical tags (CostCenter, Project, Environment, ServiceName, DataClassification) onto every permission set.

Minimum default_tags for CPS 234 compliance:

default_tags = {
CostCenter = "platform" # maps to FOCUS ServiceCategory
Project = "landing-zone" # maps to FOCUS SubAccountName
Environment = "prod" # ABAC: environment scoping
DataClassification = "restricted" # CPS 234: mandatory for privileged access
}

HITL Gates

The following deployment steps require human-in-the-loop (HITL) approval due to blast radius or irreversibility:

GateActionReason
G1: First deployterraform apply to management accountCreates SSO instance-level resources; affects all accounts in Org
G2: Permission set changesAny terraform apply modifying aws_ssoadmin_permission_set.*Active sessions may be invalidated
G3: Account assignment removalRemoving entries from account_assignmentsImmediately revokes access for affected principals
G4: Break-glass reviewApplying AdministratorAccess to any new accountRequires second approver (4-eyes principle)

Deployment order (avoid dependency errors):

  1. aws_ssoadmin_permission_set (permission sets)
  2. aws_ssoadmin_managed_policy_attachment / inline / boundary
  3. aws_ssoadmin_account_assignment (assign to accounts last)

Rollback procedure:

# Identify the last known-good state
terraform state list | grep account_assignment

# Remove a specific account assignment without destroying the permission set
terraform state rm 'module.identity_center.aws_ssoadmin_account_assignment.account_assignment["admins_management"]'

# Re-import if needed after manual console fix
terraform import 'module.identity_center.aws_ssoadmin_account_assignment.account_assignment["admins_management"]' \
"<instance_arn>,<permission_set_arn>,GROUP,<group_id>,<account_id>"

For full rollback: revert the account_assignments variable to the prior Git commit and run terraform apply. The for_each reconciliation removes excess assignments idempotently.