IAM Commands


1. Find Owner And Creator From Access Key ID#

可以通过 access key ID 查到它属于哪个 IAM user,但“属于谁”和“谁创建的”是两个问题。

owner:
    this access key belongs to which IAM user
    use IAM GetAccessKeyLastUsed

creator:
    which principal called CreateAccessKey
    use CloudTrail CreateAccessKey event

Find owner:

export ACCESS_KEY_ID="AKIAxxxxxxxxxxxxxxxx"

aws iam get-access-key-last-used \
  --access-key-id "$ACCESS_KEY_ID" \
  --query '{UserName:UserName,LastUsed:AccessKeyLastUsed}' \
  --output json

Typical output:

{
  "UserName": "deploy-user",
  "LastUsed": {
    "LastUsedDate": "2026-05-31T08:12:00+00:00",
    "ServiceName": "s3",
    "Region": "ap-east-1"
  }
}

Notes:

works for:
    long-lived IAM user access key

does not answer:
    who created the key
    which human used an assumed role
    temporary STS key owner, for example ASIA...

requires:
    iam:GetAccessKeyLastUsed

Find creator from recent CloudTrail management events:

export ACCESS_KEY_ID="AKIAxxxxxxxxxxxxxxxx"
export REGION="us-east-1"

aws cloudtrail lookup-events \
  --region "$REGION" \
  --lookup-attributes AttributeKey=EventName,AttributeValue=CreateAccessKey \
  --query 'Events[].CloudTrailEvent' \
  --output text |
jq -r --arg ak "$ACCESS_KEY_ID" '
  fromjson
  | select(.responseElements.accessKey.accessKeyId == $ak)
  | {
      eventTime,
      creatorArn: .userIdentity.arn,
      creatorType: .userIdentity.type,
      createdUser: .requestParameters.userName,
      accessKeyId: .responseElements.accessKey.accessKeyId,
      sourceIPAddress,
      userAgent
    }
'

If CloudTrail Event history is not enough:

CloudTrail Event history:
    only recent management events, Region by Region
    good for quick investigation

organization trail / CloudTrail Lake:
    required for older events and central audit
    search all accounts and all regions from security/log account

common pitfall:
    lookup by AttributeKey=AccessKeyId means the access key used to sign the API call
    it is not necessarily the newly created access key in responseElements

Incident response:

aws iam update-access-key \
  --user-name "<UserNameFromGetAccessKeyLastUsed>" \
  --access-key-id "$ACCESS_KEY_ID" \
  --status Inactive

Then review CloudTrail events signed by this key:

aws cloudtrail lookup-events \
  --region "$REGION" \
  --lookup-attributes AttributeKey=AccessKeyId,AttributeValue="$ACCESS_KEY_ID" \
  --max-items 50

Production rule:

prod:
    no IAM user access key
    no human long-lived access key
    CI/CD uses OIDC assume role
    emergency access uses break-glass SSO role