################################################################################ # v0.33.x - v0.37.x Controller IAM Policy ################################################################################ data "aws_iam_policy_document" "v033" { count = local.create_iam_role ? 1 : 0 statement { sid = "AllowScopedEC2InstanceActions" resources = [ "arn:${local.partition}:ec2:*::image/*", "arn:${local.partition}:ec2:*::snapshot/*", "arn:${local.partition}:ec2:*:*:spot-instances-request/*", "arn:${local.partition}:ec2:*:*:security-group/*", "arn:${local.partition}:ec2:*:*:subnet/*", "arn:${local.partition}:ec2:*:*:launch-template/*", ] actions = [ "ec2:RunInstances", "ec2:CreateFleet" ] } statement { sid = "AllowScopedEC2InstanceActionsWithTags" resources = [ "arn:${local.partition}:ec2:*:*:fleet/*", "arn:${local.partition}:ec2:*:*:instance/*", "arn:${local.partition}:ec2:*:*:volume/*", "arn:${local.partition}:ec2:*:*:network-interface/*", "arn:${local.partition}:ec2:*:*:launch-template/*", "arn:${local.partition}:ec2:*:*:spot-instances-request/*", ] actions = [ "ec2:RunInstances", "ec2:CreateFleet", "ec2:CreateLaunchTemplate" ] condition { test = "StringEquals" variable = "aws:RequestTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringLike" variable = "aws:RequestTag/karpenter.sh/nodepool" values = ["*"] } } statement { sid = "AllowScopedResourceCreationTagging" resources = [ "arn:${local.partition}:ec2:*:*:fleet/*", "arn:${local.partition}:ec2:*:*:instance/*", "arn:${local.partition}:ec2:*:*:volume/*", "arn:${local.partition}:ec2:*:*:network-interface/*", "arn:${local.partition}:ec2:*:*:launch-template/*", "arn:${local.partition}:ec2:*:*:spot-instances-request/*", ] actions = ["ec2:CreateTags"] condition { test = "StringEquals" variable = "aws:RequestTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "ec2:CreateAction" values = [ "RunInstances", "CreateFleet", "CreateLaunchTemplate", ] } condition { test = "StringLike" variable = "aws:RequestTag/karpenter.sh/nodepool" values = ["*"] } } statement { sid = "AllowScopedResourceTagging" resources = ["arn:${local.partition}:ec2:*:*:instance/*"] actions = ["ec2:CreateTags"] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.sh/nodepool" values = ["*"] } condition { test = "ForAllValues:StringEquals" variable = "aws:TagKeys" values = [ "karpenter.sh/nodeclaim", "Name", ] } } statement { sid = "AllowScopedDeletion" resources = [ "arn:${local.partition}:ec2:*:*:instance/*", "arn:${local.partition}:ec2:*:*:launch-template/*" ] actions = [ "ec2:TerminateInstances", "ec2:DeleteLaunchTemplate" ] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.sh/nodepool" values = ["*"] } } statement { sid = "AllowRegionalReadActions" resources = ["*"] actions = [ "ec2:DescribeAvailabilityZones", "ec2:DescribeImages", "ec2:DescribeInstances", "ec2:DescribeInstanceTypeOfferings", "ec2:DescribeInstanceTypes", "ec2:DescribeLaunchTemplates", "ec2:DescribeSecurityGroups", "ec2:DescribeSpotPriceHistory", "ec2:DescribeSubnets" ] condition { test = "StringEquals" variable = "aws:RequestedRegion" values = [local.region] } } statement { sid = "AllowSSMReadActions" resources = coalescelist(var.ami_id_ssm_parameter_arns, ["arn:${local.partition}:ssm:${local.region}::parameter/aws/service/*"]) actions = ["ssm:GetParameter"] } statement { sid = "AllowPricingReadActions" resources = ["*"] actions = ["pricing:GetProducts"] } dynamic "statement" { for_each = local.enable_spot_termination ? [1] : [] content { sid = "AllowInterruptionQueueActions" resources = [try(aws_sqs_queue.this[0].arn, null)] actions = [ "sqs:DeleteMessage", "sqs:GetQueueAttributes", "sqs:GetQueueUrl", "sqs:ReceiveMessage" ] } } statement { sid = "AllowPassingInstanceRole" resources = var.create_node_iam_role ? [aws_iam_role.node[0].arn] : [var.node_iam_role_arn] actions = ["iam:PassRole"] condition { test = "StringEquals" variable = "iam:PassedToService" values = ["ec2.${local.dns_suffix}"] } } statement { sid = "AllowScopedInstanceProfileCreationActions" resources = ["*"] actions = ["iam:CreateInstanceProfile"] condition { test = "StringEquals" variable = "aws:RequestTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:RequestTag/topology.kubernetes.io/region" values = [local.region] } condition { test = "StringLike" variable = "aws:RequestTag/karpenter.k8s.aws/ec2nodeclass" values = ["*"] } } statement { sid = "AllowScopedInstanceProfileTagActions" resources = ["*"] actions = ["iam:TagInstanceProfile"] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:ResourceTag/topology.kubernetes.io/region" values = [local.region] } condition { test = "StringEquals" variable = "aws:RequestTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:ResourceTag/topology.kubernetes.io/region" values = [local.region] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.k8s.aws/ec2nodeclass" values = ["*"] } condition { test = "StringLike" variable = "aws:RequestTag/karpenter.k8s.aws/ec2nodeclass" values = ["*"] } } statement { sid = "AllowScopedInstanceProfileActions" resources = ["*"] actions = [ "iam:AddRoleToInstanceProfile", "iam:RemoveRoleFromInstanceProfile", "iam:DeleteInstanceProfile" ] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:ResourceTag/topology.kubernetes.io/region" values = [local.region] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.k8s.aws/ec2nodeclass" values = ["*"] } } statement { sid = "AllowInstanceProfileReadActions" resources = ["*"] actions = ["iam:GetInstanceProfile"] } statement { sid = "AllowAPIServerEndpointDiscovery" resources = ["arn:${local.partition}:eks:${local.region}:${local.account_id}:cluster/${var.cluster_name}"] actions = ["eks:DescribeCluster"] } dynamic "statement" { for_each = var.iam_policy_statements content { sid = try(statement.value.sid, null) actions = try(statement.value.actions, null) not_actions = try(statement.value.not_actions, null) effect = try(statement.value.effect, null) resources = try(statement.value.resources, null) not_resources = try(statement.value.not_resources, null) dynamic "principals" { for_each = try(statement.value.principals, []) content { type = principals.value.type identifiers = principals.value.identifiers } } dynamic "not_principals" { for_each = try(statement.value.not_principals, []) content { type = not_principals.value.type identifiers = not_principals.value.identifiers } } dynamic "condition" { for_each = try(statement.value.conditions, []) content { test = condition.value.test values = condition.value.values variable = condition.value.variable } } } } } ################################################################################ # v1.0.x Controller IAM Policy ################################################################################ data "aws_iam_policy_document" "v1" { count = local.create_iam_role ? 1 : 0 statement { sid = "AllowScopedEC2InstanceAccessActions" resources = [ "arn:${local.partition}:ec2:${local.region}::image/*", "arn:${local.partition}:ec2:${local.region}::snapshot/*", "arn:${local.partition}:ec2:${local.region}:*:security-group/*", "arn:${local.partition}:ec2:${local.region}:*:subnet/*", "arn:${local.partition}:ec2:${local.region}:*:capacity-reservation/*", ] actions = [ "ec2:RunInstances", "ec2:CreateFleet" ] } statement { sid = "AllowScopedEC2LaunchTemplateAccessActions" resources = [ "arn:${local.partition}:ec2:${local.region}:*:launch-template/*" ] actions = [ "ec2:RunInstances", "ec2:CreateFleet" ] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.sh/nodepool" values = ["*"] } } statement { sid = "AllowScopedEC2InstanceActionsWithTags" resources = [ "arn:${local.partition}:ec2:${local.region}:*:fleet/*", "arn:${local.partition}:ec2:${local.region}:*:instance/*", "arn:${local.partition}:ec2:${local.region}:*:volume/*", "arn:${local.partition}:ec2:${local.region}:*:network-interface/*", "arn:${local.partition}:ec2:${local.region}:*:launch-template/*", "arn:${local.partition}:ec2:${local.region}:*:spot-instances-request/*", ] actions = [ "ec2:RunInstances", "ec2:CreateFleet", "ec2:CreateLaunchTemplate" ] condition { test = "StringEquals" variable = "aws:RequestTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:RequestTag/eks:eks-cluster-name" values = [var.cluster_name] } condition { test = "StringLike" variable = "aws:RequestTag/karpenter.sh/nodepool" values = ["*"] } } statement { sid = "AllowScopedResourceCreationTagging" resources = [ "arn:${local.partition}:ec2:${local.region}:*:fleet/*", "arn:${local.partition}:ec2:${local.region}:*:instance/*", "arn:${local.partition}:ec2:${local.region}:*:volume/*", "arn:${local.partition}:ec2:${local.region}:*:network-interface/*", "arn:${local.partition}:ec2:${local.region}:*:launch-template/*", "arn:${local.partition}:ec2:${local.region}:*:spot-instances-request/*", ] actions = ["ec2:CreateTags"] condition { test = "StringEquals" variable = "aws:RequestTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:RequestTag/eks:eks-cluster-name" values = [var.cluster_name] } condition { test = "StringEquals" variable = "ec2:CreateAction" values = [ "RunInstances", "CreateFleet", "CreateLaunchTemplate", ] } condition { test = "StringLike" variable = "aws:RequestTag/karpenter.sh/nodepool" values = ["*"] } } statement { sid = "AllowScopedResourceTagging" resources = ["arn:${local.partition}:ec2:${local.region}:*:instance/*"] actions = ["ec2:CreateTags"] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.sh/nodepool" values = ["*"] } condition { test = "StringEqualsIfExists" variable = "aws:RequestTag/eks:eks-cluster-name" values = [var.cluster_name] } condition { test = "ForAllValues:StringEquals" variable = "aws:TagKeys" values = [ "eks:eks-cluster-name", "karpenter.sh/nodeclaim", "Name", ] } } statement { sid = "AllowScopedDeletion" resources = [ "arn:${local.partition}:ec2:${local.region}:*:instance/*", "arn:${local.partition}:ec2:${local.region}:*:launch-template/*" ] actions = [ "ec2:TerminateInstances", "ec2:DeleteLaunchTemplate" ] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.sh/nodepool" values = ["*"] } } statement { sid = "AllowRegionalReadActions" resources = ["*"] actions = [ "ec2:DescribeAvailabilityZones", "ec2:DescribeImages", "ec2:DescribeInstances", "ec2:DescribeInstanceTypeOfferings", "ec2:DescribeInstanceTypes", "ec2:DescribeLaunchTemplates", "ec2:DescribeSecurityGroups", "ec2:DescribeSpotPriceHistory", "ec2:DescribeSubnets" ] condition { test = "StringEquals" variable = "aws:RequestedRegion" values = [local.region] } } statement { sid = "AllowSSMReadActions" resources = coalescelist(var.ami_id_ssm_parameter_arns, ["arn:${local.partition}:ssm:${local.region}::parameter/aws/service/*"]) actions = ["ssm:GetParameter"] } statement { sid = "AllowPricingReadActions" resources = ["*"] actions = ["pricing:GetProducts"] } dynamic "statement" { for_each = local.enable_spot_termination ? [1] : [] content { sid = "AllowInterruptionQueueActions" resources = [try(aws_sqs_queue.this[0].arn, null)] actions = [ "sqs:DeleteMessage", "sqs:GetQueueUrl", "sqs:ReceiveMessage" ] } } statement { sid = "AllowPassingInstanceRole" resources = var.create_node_iam_role ? [aws_iam_role.node[0].arn] : [var.node_iam_role_arn] actions = ["iam:PassRole"] condition { test = "StringEquals" variable = "iam:PassedToService" values = ["ec2.${local.dns_suffix}"] } } statement { sid = "AllowScopedInstanceProfileCreationActions" resources = ["arn:${local.partition}:iam::${local.account_id}:instance-profile/*"] actions = ["iam:CreateInstanceProfile"] condition { test = "StringEquals" variable = "aws:RequestTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:RequestTag/eks:eks-cluster-name" values = [var.cluster_name] } condition { test = "StringEquals" variable = "aws:RequestTag/topology.kubernetes.io/region" values = [local.region] } condition { test = "StringLike" variable = "aws:RequestTag/karpenter.k8s.aws/ec2nodeclass" values = ["*"] } } statement { sid = "AllowScopedInstanceProfileTagActions" resources = ["arn:${local.partition}:iam::${local.account_id}:instance-profile/*"] actions = ["iam:TagInstanceProfile"] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:ResourceTag/topology.kubernetes.io/region" values = [local.region] } condition { test = "StringEquals" variable = "aws:RequestTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:RequestTag/eks:eks-cluster-name" values = [var.cluster_name] } condition { test = "StringEquals" variable = "aws:RequestTag/topology.kubernetes.io/region" values = [local.region] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.k8s.aws/ec2nodeclass" values = ["*"] } condition { test = "StringLike" variable = "aws:RequestTag/karpenter.k8s.aws/ec2nodeclass" values = ["*"] } } statement { sid = "AllowScopedInstanceProfileActions" resources = ["arn:${local.partition}:iam::${local.account_id}:instance-profile/*"] actions = [ "iam:AddRoleToInstanceProfile", "iam:RemoveRoleFromInstanceProfile", "iam:DeleteInstanceProfile" ] condition { test = "StringEquals" variable = "aws:ResourceTag/kubernetes.io/cluster/${var.cluster_name}" values = ["owned"] } condition { test = "StringEquals" variable = "aws:ResourceTag/topology.kubernetes.io/region" values = [local.region] } condition { test = "StringLike" variable = "aws:ResourceTag/karpenter.k8s.aws/ec2nodeclass" values = ["*"] } } statement { sid = "AllowInstanceProfileReadActions" resources = ["arn:${local.partition}:iam::${local.account_id}:instance-profile/*"] actions = ["iam:GetInstanceProfile"] } statement { sid = "AllowAPIServerEndpointDiscovery" resources = ["arn:${local.partition}:eks:${local.region}:${local.account_id}:cluster/${var.cluster_name}"] actions = ["eks:DescribeCluster"] } dynamic "statement" { for_each = var.iam_policy_statements content { sid = try(statement.value.sid, null) actions = try(statement.value.actions, null) not_actions = try(statement.value.not_actions, null) effect = try(statement.value.effect, null) resources = try(statement.value.resources, null) not_resources = try(statement.value.not_resources, null) dynamic "principals" { for_each = try(statement.value.principals, []) content { type = principals.value.type identifiers = principals.value.identifiers } } dynamic "not_principals" { for_each = try(statement.value.not_principals, []) content { type = not_principals.value.type identifiers = not_principals.value.identifiers } } dynamic "condition" { for_each = try(statement.value.conditions, []) content { test = condition.value.test values = condition.value.values variable = condition.value.variable } } } } }