I used to hand code this so it’s great that there’s a library to do it now – and a Homebrew recipe!
Category Archives: IAM
aws_iam_role: Error Updating IAM Role – Assume Role Policy: MalformedPolicyDocument: Has prohibited field Resource
I recently ran into two errors when using Terraform:
1. Has prohibited field Resource
aws_iam_role: Error Updating IAM Role - Assume Role Policy: MalformedPolicyDocument: Has prohibited field Resource
also experienced here: https://stackoverflow.com/questions/34188013/aws-create-role-has-prohibited-field
The policy looked like this:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
assume_role_policy = <<POLICY { "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "Service": "ec2.amazonaws.com" }, "Action": "sts:AssumeRole" } ] } POLICY |
and
2. Has prohibited field Principal
When I pasted this into AWS Policy Editor here:
https://console.aws.amazon.com/iam/home?#/policies$new?step=edit
I would get:
This policy contains the following error: Has prohibited field Principal For more information about the IAM policy grammar, see AWS IAM Policies
Looking at AWS IAM Policies > Policy Grammar Notes:
- The principal_block element is required in resource-based policies (for example, in Amazon S3 bucket policies) and in trust policies for IAM roles. It must not be included in identity-based policies.
Some notes:
a. Policy Types
- Identity: attach to IAM identities: must NOT have principal
- Resource: attach to resources such as S3: must have principal
- Trust Policies are resource-based policies attached to a role and define which principals can assume the role
Examples:
Identity-based policies (must NOT have Principal):
https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_examples_aws-dates.html
Resource-based policies (must have Principal):
b. Policy Permission Categories:
- Permissions policies
https://docs.aws.amazon.com/IAM/latest/UserGuide/access_policies.html#access_policy-types
and https://docs.aws.amazon.com/IAM/latest/UserGuide/id_roles_terms-and-concepts.html
b. Also related
https://www.terraform.io/docs/providers/aws/r/iam_role.html
assume_role_policy – (Required) The policy that grants an entity permission to assume the role.
NOTE: This assume_role_policy is very similar but slightly different than just a standard IAM policy and cannot use an aws_iam_policy resource. It can however, use an aws_iam_policy_document data source, see example below for how this could work.
IAM Policies
Breaking down a Policy:
https://start.jcolemorrison.com/aws-iam-policies-in-a-nutshell/
E.g.
Version: just use "Version": "2012-10-17"
Statement: the meat of the Policy
The Statement contains:
Effect: Allow or Deny
Principal: Who
Notes:
- if we’re attaching Policies to IAM users, groups or roles then
Principal
isn’t needed as the policy assumes the user, group or role is thePrincipal
- differences between attaching a policy to an IAM user vs a resource (e.g. S3 or EC2):
- if it’s with the user, we check the policy and are done
- if it’s with the resource then we need to have a Principal to make sure who’s allowed this resource
Beginner’s Guide to IAM: IAM, Roles, Policies, Policy Attachments with Terraform
IAM
is short for Identity and Access Management
.
- What’s the difference between an IAM user and role?
An IAM user has long term credentials and directly interacts with AWS services. An IAM role does not have any credentials and don’t directly access AWS services. IAM roles are assumed by entities (such as users, applications or services like EC2).
https://aws.amazon.com/iam/faqs/
2. What’s an IAM Policy?
An IAM Policy allows access -i.e. they define permissions. You create a policy then attach it to an IAM identity or AWS resource.
https://docs.aws.amazon.com/IAM/latest/UserGuide/access_policies.html
3. what’s an IAM Role Policy Attachment?
This can be found in Terraform. e.g.
https://www.terraform.io/docs/providers/aws/r/iam_role_policy_attachment.html
It attaches an IAM Policy to an IAM role and typically looks like this:
resource “aws_iam_role_policy_attachment” “test-attach” {
role = “${aws_iam_role.role.name}”
policy_arn = “${aws_iam_policy.policy.arn}”
}
https://www.terraform.io/docs/providers/aws/r/iam_role_policy_attachment.html
4. Principal
The Principal
element specifies the AWS user, account, service that is allowed or denied access to a resource.
https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_principal.html
5. assume_role_policy
is very similar but slightly different than a standard IAM policy
https://www.terraform.io/docs/providers/aws/r/iam_role.html
6. Service Roles are IAM roles that can be assumed by an AWS service
e.g.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
{ "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Principal": { "Service": [ "elasticmapreduce.amazonaws.com", "datapipeline.amazonaws.com" ] }, "Action": "sts:AssumeRole" } ] } |
Note how there are 2 Services listed. The Service key must be unique. So it’s value must be a list.
https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_policies_elements_principal.html
https://docs.aws.amazon.com/IAM/latest/UserGuide/using-service-linked-roles.html
and a list of Services that work with IAM: https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_aws-services-that-work-with-iam.html