Code development platform for open source projects from the European Union institutions

Skip to content
Snippets Groups Projects
Unverified Commit 14c92737 authored by Waleed's avatar Waleed Committed by GitHub
Browse files

Feature/kms alias (#183)

* wip

* Add restrictions to the EKS KMS key

* AWS KMS module is now reusable

* undo resource restriction

* Update docs, move kms key policy to root data.tf

* undo the aws_region resource delete

* Update kms key policy check method
parent 97bbf34c
No related branches found
No related tags found
No related merge requests found
......@@ -9,7 +9,7 @@ repos:
- id: detect-private-key
- id: detect-aws-credentials
args: ['--allow-missing-credentials']
- repo: git://github.com/antonbabenko/pre-commit-terraform
- repo: https://github.com/antonbabenko/pre-commit-terraform
rev: v1.53.0
hooks:
- id: terraform_fmt
......
......@@ -141,9 +141,9 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
| Name | Version |
|------|---------|
| <a name="provider_aws"></a> [aws](#provider\_aws) | >= 3.66.0 |
| <a name="provider_aws"></a> [aws](#provider\_aws) | 3.71.0 |
| <a name="provider_http"></a> [http](#provider\_http) | 2.4.1 |
| <a name="provider_kubernetes"></a> [kubernetes](#provider\_kubernetes) | >= 2.7.1 |
| <a name="provider_kubernetes"></a> [kubernetes](#provider\_kubernetes) | 2.7.1 |
## Modules
......@@ -157,18 +157,20 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
| <a name="module_aws_managed_prometheus"></a> [aws\_managed\_prometheus](#module\_aws\_managed\_prometheus) | ./modules/aws-managed-prometheus | n/a |
| <a name="module_eks_tags"></a> [eks\_tags](#module\_eks\_tags) | ./modules/aws-resource-tags | n/a |
| <a name="module_emr_on_eks"></a> [emr\_on\_eks](#module\_emr\_on\_eks) | ./modules/emr-on-eks | n/a |
| <a name="module_kms"></a> [kms](#module\_kms) | ./modules/aws-kms | n/a |
## Resources
| Name | Type |
|------|------|
| [aws_kms_key.eks](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/kms_key) | resource |
| [kubernetes_config_map.amazon_vpc_cni](https://registry.terraform.io/providers/hashicorp/kubernetes/latest/docs/resources/config_map) | resource |
| [kubernetes_config_map.aws_auth](https://registry.terraform.io/providers/hashicorp/kubernetes/latest/docs/resources/config_map) | resource |
| [aws_availability_zones.available](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/availability_zones) | data source |
| [aws_caller_identity.current](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/caller_identity) | data source |
| [aws_eks_cluster.cluster](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/eks_cluster) | data source |
| [aws_eks_cluster_auth.cluster](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/eks_cluster_auth) | data source |
| [aws_iam_policy_document.eks_key](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/iam_policy_document) | data source |
| [aws_iam_session_context.current](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/iam_session_context) | data source |
| [aws_partition.current](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/partition) | data source |
| [aws_region.current](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/region) | data source |
| [http_http.eks_cluster_readiness](https://registry.terraform.io/providers/terraform-aws-modules/http/2.4.1/docs/data-sources/http) | data source |
......@@ -186,6 +188,7 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
| <a name="input_cluster_log_retention_in_days"></a> [cluster\_log\_retention\_in\_days](#input\_cluster\_log\_retention\_in\_days) | Number of days to retain log events. Default retention - 90 days. | `number` | `90` | no |
| <a name="input_cluster_log_retention_period"></a> [cluster\_log\_retention\_period](#input\_cluster\_log\_retention\_period) | Number of days to retain cluster logs | `number` | `7` | no |
| <a name="input_create_eks"></a> [create\_eks](#input\_create\_eks) | Create EKS cluster | `bool` | `false` | no |
| <a name="input_eks_cluster_kms_key_policy"></a> [eks\_cluster\_kms\_key\_policy](#input\_eks\_cluster\_kms\_key\_policy) | A valid KMS key policy JSON document. Although this is a key policy, not an IAM policy, an aws\_iam\_policy\_document, in the form that designates a principal, can be used. | `string` | `null` | no |
| <a name="input_emr_on_eks_teams"></a> [emr\_on\_eks\_teams](#input\_emr\_on\_eks\_teams) | EMR on EKS Teams config | `any` | `{}` | no |
| <a name="input_enable_amazon_prometheus"></a> [enable\_amazon\_prometheus](#input\_enable\_amazon\_prometheus) | Enable AWS Managed Prometheus service | `bool` | `false` | no |
| <a name="input_enable_emr_on_eks"></a> [enable\_emr\_on\_eks](#input\_enable\_emr\_on\_eks) | Enable EMR on EKS | `bool` | `false` | no |
......
......@@ -43,3 +43,125 @@ data "http" "eks_cluster_readiness" {
ca_certificate = base64decode(data.aws_eks_cluster.cluster.0.certificate_authority.0.data)
timeout = 300
}
data "aws_iam_session_context" "current" {
arn = data.aws_caller_identity.current.arn
}
data "aws_iam_policy_document" "eks_key" {
statement {
sid = "Allow access for all principals in the account that are authorized"
effect = "Allow"
actions = [
"kms:Encrypt",
"kms:Decrypt",
"kms:ReEncrypt*",
"kms:GenerateDataKey*",
"kms:CreateGrant",
"kms:DescribeKey"
]
resources = ["*"]
principals {
type = "AWS"
identifiers = [
"arn:aws:iam::${data.aws_caller_identity.current.account_id}:root"
]
}
condition {
test = "StringEquals"
variable = "kms:CallerAccount"
values = [data.aws_caller_identity.current.account_id]
}
condition {
test = "StringEquals"
variable = "kms:ViaService"
values = ["eks.${data.aws_region.current.name}.amazonaws.com"]
}
}
statement {
sid = "Allow direct access to key metadata to the account"
effect = "Allow"
actions = [
"kms:Describe*",
"kms:Get*",
"kms:List*",
"kms:RevokeGrant"
]
resources = ["*"]
principals {
type = "AWS"
identifiers = [
"arn:aws:iam::${data.aws_caller_identity.current.account_id}:root"
]
}
}
statement {
sid = "Allow access for Key Administrators"
effect = "Allow"
actions = [
"kms:*"
]
resources = ["*"]
principals {
type = "AWS"
identifiers = [
"arn:aws:iam::${data.aws_caller_identity.current.account_id}:role/${local.cluster_iam_role_name}",
data.aws_iam_session_context.current.issuer_arn
]
}
}
statement {
sid = "Allow use of the key"
effect = "Allow"
actions = [
"kms:Encrypt",
"kms:Decrypt",
"kms:ReEncrypt*",
"kms:GenerateDataKey*",
"kms:DescribeKey"
]
resources = ["*"]
principals {
type = "AWS"
identifiers = [
"arn:aws:iam::${data.aws_caller_identity.current.account_id}:role/${local.cluster_iam_role_name}"
]
}
}
# Permission to allow AWS services that are integrated with AWS KMS to use the CMK,
# particularly services that use grants.
statement {
sid = "Allow attachment of persistent resources"
effect = "Allow"
actions = [
"kms:CreateGrant",
"kms:ListGrants",
"kms:RevokeGrant"
]
resources = ["*"]
principals {
type = "AWS"
identifiers = [
"arn:aws:iam::${data.aws_caller_identity.current.account_id}:role/${local.cluster_iam_role_name}"
]
}
condition {
test = "Bool"
variable = "kms:GrantIsForAWSResource"
values = ["true"]
}
}
}
......@@ -88,7 +88,7 @@ terraform destroy
| Name | Version |
|------|---------|
| <a name="provider_aws"></a> [aws](#provider\_aws) | >= 3.66.0 |
| <a name="provider_aws"></a> [aws](#provider\_aws) | 3.71.0 |
## Modules
......
......@@ -83,5 +83,5 @@ locals {
platform_teams_config_map = module.aws_eks_teams.platform_teams_config_map
application_teams_config_map = module.aws_eks_teams.application_teams_config_map
cluster_iam_role_name = "${module.eks_tags.tags.name}-cluster-role"
}
......@@ -28,14 +28,22 @@ module "eks_tags" {
tags = local.tags
}
# Create the cluster's KMS key
module "kms" {
source = "./modules/aws-kms"
alias = "alias/${module.eks_tags.id}"
description = "${module.eks_tags.id} EKS cluster secret encryption key"
deletion_window_in_days = 30
enable_key_rotation = true
policy = var.eks_cluster_kms_key_policy == null ? data.aws_iam_policy_document.eks_key.json : var.eks_cluster_kms_key_policy
tags = module.eks_tags.tags
}
# ---------------------------------------------------------------------------------------------------------------------
# EKS CONTROL PLANE
# ---------------------------------------------------------------------------------------------------------------------
resource "aws_kms_key" "eks" {
description = "EKS Cluster Secret Encryption Key"
}
module "aws_eks" {
source = "terraform-aws-modules/eks/aws"
version = "v17.20.0"
......@@ -43,8 +51,9 @@ module "aws_eks" {
create_eks = var.create_eks
manage_aws_auth = false
cluster_name = module.eks_tags.id
cluster_version = var.kubernetes_version
cluster_name = module.eks_tags.id
cluster_version = var.kubernetes_version
cluster_iam_role_name = local.cluster_iam_role_name
# NETWORK CONFIG
vpc_id = var.vpc_id
......@@ -70,7 +79,7 @@ module "aws_eks" {
# CLUSTER ENCRYPTION
cluster_encryption_config = [
{
provider_key_arn = aws_kms_key.eks.arn
provider_key_arn = module.kms.key_arn
resources = ["secrets"]
}
]
......
# AWS KMS module
Terraform module that creates an AWS KMS key and assigns it an alias, policy, and tags.
Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
SPDX-License-Identifier: MIT-0
Permission is hereby granted, free of charge, to any person obtaining a copy of this
software and associated documentation files (the "Software"), to deal in the Software
without restriction, including without limitation the rights to use, copy, modify,
merge, publish, distribute, sublicense, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
## Usage
``` terraform
module "kms" {
source = "./modules/aws-kms"
alias = "alias/example"
description = "Example encryption key"
policy = data.aws_iam_policy_document.key.json
tags = local.tags
}
```
<!--- BEGIN_TF_DOCS --->
## Requirements
No requirements.
## Providers
| Name | Version |
|------|---------|
| <a name="provider_aws"></a> [aws](#provider\_aws) | n/a |
## Modules
No modules.
## Resources
| Name | Type |
|------|------|
| [aws_kms_alias.this](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/kms_alias) | resource |
| [aws_kms_key.this](https://registry.terraform.io/providers/hashicorp/aws/latest/docs/resources/kms_key) | resource |
## Inputs
| Name | Description | Type | Default | Required |
|------|-------------|------|---------|:--------:|
| <a name="input_alias"></a> [alias](#input\_alias) | The display name of the alias. The name must start with the word 'alias' followed by a forward slash (alias/) | `string` | n/a | yes |
| <a name="input_deletion_window_in_days"></a> [deletion\_window\_in\_days](#input\_deletion\_window\_in\_days) | The waiting period, specified in number of days. After the waiting period ends, AWS KMS deletes the KMS key. If you specify a value, it must be between 7 and 30, inclusive. If you do not specify a value, it defaults to 30. | `number` | `30` | no |
| <a name="input_description"></a> [description](#input\_description) | The description of the key. | `string` | n/a | yes |
| <a name="input_enable_key_rotation"></a> [enable\_key\_rotation](#input\_enable\_key\_rotation) | Specifies whether annual key rotation is enabled. | `bool` | `true` | no |
| <a name="input_policy"></a> [policy](#input\_policy) | A valid KMS key policy JSON document. Although this is a key policy, not an IAM policy, an aws\_iam\_policy\_document, in the form that designates a principal, can be used. | `string` | n/a | yes |
| <a name="input_tags"></a> [tags](#input\_tags) | A map of tags to assign to the object. | `map(string)` | n/a | yes |
## Outputs
| Name | Description |
|------|-------------|
| <a name="output_key_arn"></a> [key\_arn](#output\_key\_arn) | The Amazon Resource Name (ARN) of the key. |
| <a name="output_key_id"></a> [key\_id](#output\_key\_id) | The globally unique identifier for the key. |
<!--- END_TF_DOCS --->
/*
* Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
* SPDX-License-Identifier: MIT-0
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of this
* software and associated documentation files (the "Software"), to deal in the Software
* without restriction, including without limitation the rights to use, copy, modify,
* merge, publish, distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
* PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
* OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
# Create a KMS customer managed key
resource "aws_kms_key" "this" {
description = var.description
policy = var.policy
enable_key_rotation = var.enable_key_rotation
deletion_window_in_days = var.deletion_window_in_days
tags = var.tags
}
# Assign an alias to the key
resource "aws_kms_alias" "this" {
name = var.alias
target_key_id = aws_kms_key.this.key_id
}
/*
* Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
* SPDX-License-Identifier: MIT-0
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of this
* software and associated documentation files (the "Software"), to deal in the Software
* without restriction, including without limitation the rights to use, copy, modify,
* merge, publish, distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
* PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
* OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
output "key_id" {
value = aws_kms_key.this.key_id
description = "The globally unique identifier for the key."
}
output "key_arn" {
value = aws_kms_key.this.arn
description = "The Amazon Resource Name (ARN) of the key."
}
/*
* Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
* SPDX-License-Identifier: MIT-0
*
* Permission is hereby granted, free of charge, to any person obtaining a copy of this
* software and associated documentation files (the "Software"), to deal in the Software
* without restriction, including without limitation the rights to use, copy, modify,
* merge, publish, distribute, sublicense, and/or sell copies of the Software, and to
* permit persons to whom the Software is furnished to do so.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
* PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
* OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
variable "policy" {
type = string
description = "A valid KMS key policy JSON document. Although this is a key policy, not an IAM policy, an aws_iam_policy_document, in the form that designates a principal, can be used."
}
variable "description" {
type = string
description = "The description of the key."
}
variable "alias" {
type = string
description = "The display name of the alias. The name must start with the word 'alias' followed by a forward slash (alias/)"
}
variable "enable_key_rotation" {
type = bool
default = true
description = "Specifies whether annual key rotation is enabled."
}
variable "deletion_window_in_days" {
type = number
default = 30
description = "The waiting period, specified in number of days. After the waiting period ends, AWS KMS deletes the KMS key. If you specify a value, it must be between 7 and 30, inclusive. If you do not specify a value, it defaults to 30."
}
variable "tags" {
type = map(string)
description = "A map of tags to assign to the object."
}
......@@ -228,3 +228,9 @@ variable "platform_teams" {
type = any
default = {}
}
variable "eks_cluster_kms_key_policy" {
type = string
default = null
description = "A valid KMS key policy JSON document. Although this is a key policy, not an IAM policy, an aws_iam_policy_document, in the form that designates a principal, can be used."
}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment