Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to enforce IAM users to use multi factor authentication to use the console?

I'd like to require the usage of MFA to IAM users when they log into the AWS Console. I know that's possible to do that for API access, but not sure whether is possible to achieve the same when logging into the Console.

like image 450
Andres Avatar asked Feb 20 '14 19:02

Andres


People also ask

How can I enforce MFA authentication for IAM users that use the AWS console?

To configure MFA device enforcement for your users Open the IAM Identity Center console . In the left navigation pane, choose Settings. On the Settings page, choose the Network & security tab, and then choose Configure.

How do I enforce an MFA for a user?

To the right of the table of users, click the “Enable” option that appears. On the confirmation screen, click “Enable Multi-Factor Authentication.” This will enable MFA for the user, and the next time they login to Office 365 on the web, they'll have to go through a process of setting up MFA.

How do you enable MFA with IAM users?

Enable the MFA device. IAM users with virtual or hardware MFA devices: Enable from the AWS Management Console, AWS CLI, or the IAM API. IAM users with FIDO security keys: Enable from the AWS Management Console only. AWS account root users with any type of MFA device: Enable from the AWS Management Console only.


2 Answers

Update

You can enforce your requirement with an IAM Policy based on an IAM condition that specifies the aws:MultiFactorAuthAge key as outlined in section IAM Policies with MFA Conditions within Configuring MFA-Protected API Access - you can enforce this at two levels:

  • Existence — To simply verify that the user has been authenticated with MFA, check that the aws:MultiFactorAuthAge key is not null. (If the user has not been authenticated with MFA, this key doesn't exist and therefore is null.)
  • Duration — If you want to grant access only within a specified time after MFA authentication, use a numeric condition type to compare the key's age to a value (such as 3600 seconds).

Accordingly, a generic IAM policy for all AWS actions that simply tests for the existence of MFA authentication might look as follows:

{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Action": "*",
      "Resource": "*", 
      "Condition":
      {
          "Null":{"aws:MultiFactorAuthAge":"false"}
      }
    }
  ]
}

Initial Answer

This is a case of 'it just works', i.e. there's nothing to be done regarding MFA-Protected Access for the AWS Management Console specifically, insofar the console uses the API in turn and calls every API action with the logged in user's IAM credentials accordingly (once a user has configured and enabled an MFA device, the login page will require entering the MFA token automatically) - see also section Using MFA-Protected APIs Through the Console within Configuring MFA-Protected API Access:

AWS evaluates MFA-protected API policies for actions in the console, such as terminating an Amazon EC2 instance. Set up the IAM user with an MFA device and enable an MFA-protected API policy. The user can then simply log into the console with MFA authentication and is subject to the policies for MFA-protected APIs. For users who already have an assigned MFA device, the console experience doesn't change (except for optional time limits on certain MFA-protected APIs that require more frequent re-authentication). For more information on setting up an IAM user with an MFA device, see Setting Up an MFA Device.

like image 167
Steffen Opel Avatar answered Dec 28 '22 22:12

Steffen Opel


Requiring MFA for the Web Console

The IAM policy listed here will do the following:

  • Allow users to change their own password
  • Allow users to view and edit their own MFA devices (a necessary component to requiring them to have MFA)
  • Prevent users from doing most things if they logged in to the console without MFA
  • Still allow users to set up MFA if they logged in without it
  • Use API keys regardless of MFA

It is best to create this as an IAM policy, and then attach it to the user groups that have console users. You can also attach the policy to a user directly, but that's harder to manage.

Note that adding an MFA device to your account is insufficient to be able to access AWS resources; you need to have logged in with that MFA device for it to work. Thus, to get set up with MFA, you need to do the following steps:

  1. Sign in to the AWS console.
  2. In the top right, click the dropdown labeled with your username
  3. Go to "Security Credentials"
  4. Add an MFA device
  5. Log out
  6. Log back in using MFA; you can now use the AWS console normally

The IAM policy is the following:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "iam:ChangePassword",
                "iam:CreateVirtualMFADevice",
                "iam:EnableMFADevice",
                "iam:ResyncMFADevice",
                "iam:DeleteVirtualMFADevice",
                "iam:DeactivateMFADevice",
                "iam:ListMFADevices",
                "iam:ListVirtualMFADevices",
                "iam:ListAccessKeys",
                "iam:GetAccessKeyLastUsed",
                "iam:GetUser"
            ],
            "Resource": [
                "arn:aws:iam::*:mfa/${aws:username}",
                "arn:aws:iam::*:user/${aws:username}"
            ]
        },
        {
            "Sid": "BlockMostAccessUnlessSignedInWithMFA",
            "Effect": "Deny",
            "NotAction": [
                "iam:CreateVirtualMFADevice",
                "iam:ListVirtualMFADevices",
                "iam:EnableMFADevice",
                "iam:ResyncMFADevice",
                "iam:DeleteVirtualMFADevice",
                "iam:DeactivateMFADevice",
                "iam:ListAccountAliases",
                "iam:ListUsers",
                "iam:ListSSHPublicKeys",
                "iam:ListAccessKeys",
                "iam:GetAccessKeyLastUsed",
                "iam:ListServiceSpecificCredentials",
                "iam:ListMFADevices",
                "iam:GetAccountSummary",
                "iam:ChangePassword",
                "iam:GetUser",
                "sts:GetSessionToken"
            ],
            "Resource": "*",
            "Condition": {
                "Bool": {
                    "aws:MultiFactorAuthPresent": "false"
                }
            }
        }
    ]
}

Note that while this allows use of most of the AWS API without needing MFA, some API calls won't work. In particular, any calls that use temporary AWS authentication credentials will fail. For example:

  • Using ECR login, as this generates a temporary key that it gives to docker
  • Retrieving a value from AWS Secrets Manager, as this uses temporary credentials to talk to KMS
  • Elastic Beanstalk operations, as these seem to use temporary credentials internally

In order to do these things, you need to get MFA API credentials (see below). The other option (especially good for ECR login) is to create a less privileged user in a group that doesn't have the MFA Required policy to use for making the API calls in question.

Requiring MFA Everywhere

For enhanced security, you can require MFA access for both the web console and the API. To do this, change the condition in the above policy to be the following:

"Condition": {
    "BoolIfExists": {
        "aws:MultiFactorAuthPresent": "false"
    }
}

The reason that this works is that API calls with permanent credentials don't pass the MultiFactorAuthPresent key at all, whereas console requests always do. Changing this condition from Bool to BoolIfExists changes the condition to resolve to true if the MultiFactorAuthPresent key does not exist, which in turn blocks the requests.

To use the API with MFA, you need to use the sts get-session-token command. For example, with the AWS CLI:

# Get the serial number of your MFA device
aws --profile <PROFILE_NAME> iam list-mfa-devices --user-name <IAM_USER_NAME>

# Get temporary API keys that will pass MFA verification
aws --profile <PROFILE_NAME> sts get-session-token --serial-number <MFA_SERIAL_NUMBER> --token-code <MFA_TOKEN>

# Export the temporary credentials for use in subsequent calls
export AWS_ACCESS_KEY_ID=<KEY>
export AWS_SECRET_ACCESS_KEY=<SECRET>
export AWS_SESSION_TOKEN=<SESSION_TOKEN>

If you prefer a script that manages the credential acquisition process, use the command-line tool iam-mfa: https://github.com/zagaran/iam-mfa. (Disclaimer: I am the primary author of this tool.)

like image 29
Zags Avatar answered Dec 28 '22 23:12

Zags