Skip to content

Commit

Permalink
Merge pull request #817 from ministryofjustice/feature/workflow-for-o…
Browse files Browse the repository at this point in the history
…rg-sec

Add OIDC provider and pipelines
  • Loading branch information
davidkelliott authored Oct 12, 2023
2 parents 4918b4b + 64108be commit 0c0c0dd
Show file tree
Hide file tree
Showing 15 changed files with 302 additions and 43 deletions.
38 changes: 38 additions & 0 deletions .github/workflows/organisation-security-apply.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
name: terraform apply (organisation-security)

on:
push:
paths:
- 'organisation-security/terraform/**'
- 'modules/**'
- '.github/workflows/organisation-security-plan.yml'
- '.github/workflows/organisation-security-apply.yml'
branches:
- main

jobs:
apply:
runs-on: ubuntu-latest
permissions:
id-token: write
contents: read
defaults:
run:
working-directory: ./organisation-security/terraform
steps:
- uses: actions/checkout@c85c95e3d7251135ab7dc9ce3241c5835cc595a9 # v3.5.3
- uses: aws-actions/configure-aws-credentials@5fd3084fc36e372ff1fff382a39b10d03659f355 # v2.2.0
with:
role-to-assume: arn:aws:iam::${{secrets.AWS_SECURITY_ACCOUNT_ID}}:role/github-actions-apply
role-session-name: GitHubActions
aws-region: eu-west-2
- uses: hashicorp/setup-terraform@633666f66e0061ca3b725c73b2ec20cd13a8fdd1 # v2.0.3
with:
terraform_version: 1.5.2
- run: terraform fmt -check
continue-on-error: true
- run: terraform init
- run: terraform validate -no-color
- run: terraform plan -no-color
- run: terraform apply -auto-approve
if: github.event.ref == 'refs/heads/main'
36 changes: 36 additions & 0 deletions .github/workflows/organisation-security-plan.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
name: terraform plan (organisation-security)

on:
pull_request:
paths:
- 'organisation-security/terraform/**'
- 'modules/**'
- '.github/workflows/organisation-security-plan.yml'
- '.github/workflows/organisation-security-apply.yml'
workflow_dispatch:

jobs:
plan:
runs-on: ubuntu-latest
permissions:
id-token: write
contents: read
defaults:
run:
working-directory: ./organisation-security/terraform
steps:
- uses: actions/checkout@c85c95e3d7251135ab7dc9ce3241c5835cc595a9 # v3.5.3
- uses: aws-actions/configure-aws-credentials@5fd3084fc36e372ff1fff382a39b10d03659f355 # v2.2.0
with:
role-to-assume: arn:aws:iam::${{secrets.AWS_SECURITY_ACCOUNT_ID}}:role/github-actions-plan
role-session-name: GitHubActions
aws-region: eu-west-2
- uses: hashicorp/setup-terraform@633666f66e0061ca3b725c73b2ec20cd13a8fdd1 # v2.0.3
with:
terraform_version: 1.5.2
- run: terraform fmt -check
continue-on-error: true
- run: terraform init
- run: terraform validate -no-color
- run: terraform plan -no-color

39 changes: 39 additions & 0 deletions management-account/terraform/kms.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
# State bucket key

resource "aws_kms_key" "terraform_state_s3_bucket" {
policy = data.aws_iam_policy_document.terraform_state_s3_bucket_kms.json
is_enabled = true
enable_key_rotation = true
}

resource "aws_kms_alias" "terraform_state_s3_bucket" {
name = "alias/terraform-state-s3-bucket"
target_key_id = aws_kms_key.terraform_state_s3_bucket.id
}

data "aws_iam_policy_document" "terraform_state_s3_bucket_kms" {
statement {
effect = "Allow"
actions = ["kms:*"]
resources = ["*"]

principals {
type = "AWS"
identifiers = ["arn:aws:iam::${data.aws_caller_identity.current.account_id}:root"]
}
}

statement {
effect = "Allow"
actions = [
"kms:GenerateDataKey",
"kms:Decrypt"
]
resources = ["*"]

principals {
type = "AWS"
identifiers = ["arn:aws:iam::${resource.aws_organizations_account.organisation_security.id}:root"]
}
}
}
5 changes: 5 additions & 0 deletions management-account/terraform/outputs.tf
Original file line number Diff line number Diff line change
Expand Up @@ -20,3 +20,8 @@ output "guardduty_administrator_detector_ids" {
"sa_east_1" = module.guardduty_sa_east_1.administrator_detector_id
}
}

output "organizations_organization" {
value = aws_organizations_organization.default
description = "Organization details"
}
39 changes: 38 additions & 1 deletion management-account/terraform/s3.tf
Original file line number Diff line number Diff line change
Expand Up @@ -136,15 +136,52 @@ module "terraform_state_s3_bucket" {

bucket_name = "moj-aws-root-account-terraform-state"

attach_policy = true
policy = data.aws_iam_policy_document.terraform_state_s3_bucket.json
server_side_encryption_configuration = {
rule = {
apply_server_side_encryption_by_default = {
sse_algorithm = "aws:kms"
sse_algorithm = "aws:kms"
kms_master_key_id = resource.aws_kms_key.terraform_state_s3_bucket.id
}
}
}
}

data "aws_iam_policy_document" "terraform_state_s3_bucket" {
statement {
sid = "AllowReadAccessFromSecurityAccount"
effect = "Allow"
actions = [
"s3:ListBucket",
"s3:GetObject"
]
resources = [
module.terraform_state_s3_bucket.bucket.arn,
"${module.terraform_state_s3_bucket.bucket.arn}/*"
]

principals {
type = "AWS"
identifiers = ["arn:aws:iam::${resource.aws_organizations_account.organisation_security.id}:root"]
}
}

statement {
sid = "AllowAccessFromSecurityAccount"
effect = "Allow"
actions = [
"s3:PutObject"
]
resources = ["${module.terraform_state_s3_bucket.bucket.arn}/organisation-security/*"]

principals {
type = "AWS"
identifiers = ["arn:aws:iam::${resource.aws_organizations_account.organisation_security.id}:root"]
}
}
}

# moj-cur-reports
module "cur_reports_s3_bucket" {
source = "../../modules/s3"
Expand Down
4 changes: 4 additions & 0 deletions modules/s3/outputs.tf
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
output "bucket_name" {
value = aws_s3_bucket.default.id
}

output "bucket" {
value = aws_s3_bucket.default
}
20 changes: 20 additions & 0 deletions organisation-security/terraform/.terraform.lock.hcl

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion organisation-security/terraform/config-aggregation.tf
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
# in that you can do MRMAA without delivering configuration changes to a central S3 bucket.
locals {
enrolled_into_config = [
{ id = data.aws_caller_identity.root.id, name = "MoJ root account" }
{ id = local.root_account_id, name = "MoJ root account" }
]
}

Expand Down
10 changes: 1 addition & 9 deletions organisation-security/terraform/data.tf
Original file line number Diff line number Diff line change
@@ -1,15 +1,7 @@
data "aws_caller_identity" "current" {}

data "aws_caller_identity" "root" {
provider = aws.root
}

data "aws_organizations_organization" "default" {
provider = aws.root
}

data "aws_organizations_organizational_units" "organizational_units" {
parent_id = data.aws_organizations_organization.default.roots[0].id
parent_id = local.organizations_organization.roots[0].id
}

data "aws_organizations_organizational_units" "platforms_and_architecture" {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -190,7 +190,7 @@ data "aws_iam_policy_document" "guardduty_kms_key_policy" {
principals {
type = "AWS"
identifiers = [
"arn:aws:iam::${data.aws_caller_identity.root.id}:root", # Allow the root account to manage this key
"arn:aws:iam::${local.root_account_id}:root", # Allow the root account to manage this key
"arn:aws:iam::${data.aws_caller_identity.current.id}:root" # Allow the organisation-security account to manage this key
]
}
Expand Down
2 changes: 1 addition & 1 deletion organisation-security/terraform/iam-roles.tf
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ data "aws_iam_policy_document" "read_only_role" {
actions = ["sts:AssumeRole"]
principals {
type = "AWS"
identifiers = ["arn:aws:iam::${data.aws_caller_identity.root.id}:root"]
identifiers = ["arn:aws:iam::${local.root_account_id}:root"]
}
}
}
Expand Down
76 changes: 76 additions & 0 deletions organisation-security/terraform/iam.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
####################################
# OIDC Provider for GitHub actions #
####################################

module "github_oidc" {
source = "github.com/ministryofjustice/modernisation-platform-github-oidc-provider?ref=82f546bd5f002674138a2ccdade7d7618c6758b3" # v3.0.0
role_name = "github-actions-plan"
additional_permissions = data.aws_iam_policy_document.oidc_assume_role_plan.json
github_repositories = ["ministryofjustice/aws-root-account:pull_request"]
tags_common = { "Name" = "GitHub Actions Plan" }
tags_prefix = ""
}

data "aws_iam_policy_document" "oidc_assume_role_plan" {
statement {
sid = "AllowOIDCToDecryptKMS"
effect = "Allow"
resources = ["*"]
actions = ["kms:Decrypt"]
}

statement {
sid = "AllowOIDCReadState"
effect = "Allow"
resources = ["arn:aws:s3:::moj-aws-root-account-terraform-state/*", "arn:aws:s3:::moj-aws-root-account-terraform-state/"]
actions = ["s3:Get*",
"s3:List*"]
}
}

module "github_actions_apply_role" {

source = "github.com/ministryofjustice/modernisation-platform-github-oidc-role?ref=9d9a2d23cf569348cbdb665c979fcbaed76bb2f4" # v3.1.0

github_repositories = ["ministryofjustice/aws-root-account:ref:refs/heads/main"]
role_name = "github-actions-apply"
policy_arns = ["arn:aws:iam::aws:policy/AdministratorAccess"]
policy_jsons = [data.aws_iam_policy_document.oidc_assume_role_apply.json]
subject_claim = "pull_request"
tags = { "Name" = "GitHub Actions Apply" }

}

data "aws_iam_policy_document" "oidc_assume_role_apply" {
statement {
effect = "Allow"
actions = [
"account:*AlternateContact",
"apigateway:*",
"budgets:*",
"ce:*",
"cloudtrail:*",
"config:*",
"cur:DescribeReportDefinitions",
"events:*",
"fms:*",
"guardduty:*",
"iam:*",
"identitystore:ListGroups",
"identitystore:GetGroupId",
"identitystore:DescribeGroup",
"kms:Decrypt",
"lambda:*",
"license-manager:*",
"logs:*",
"organizations:Describe*",
"organizations:List*",
"route53:*",
"s3:*",
"secretsmanager:*",
"securityhub:*",
"sns:*",
]
resources = ["*"]
}
}
2 changes: 1 addition & 1 deletion organisation-security/terraform/license-manager.tf
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ resource "aws_cloudformation_stack" "oracleblts" {
IsDelegatedAdministrator = true
ArtifactsS3Bucket = "license-manager-artifact-bucket"
AdministratorAccountId = data.aws_caller_identity.current.id
OrganizationId = data.aws_organizations_organization.default.id
OrganizationId = local.organizations_organization.id
TargetOUs = local.ou_modernisation_platform_member_id
TargetRegions = "eu-west-2"
TargetKey = "tag:OracleDbLTS-ManagedInstance"
Expand Down
14 changes: 11 additions & 3 deletions organisation-security/terraform/locals.tf
Original file line number Diff line number Diff line change
@@ -1,11 +1,19 @@
locals {
organizations_organization = data.terraform_remote_state.management_account.outputs.organizations_organization

root_account_id = coalesce([
for account in local.organizations_organization.accounts :
account.id
if account.name == "MOJ Master"
]...)

organisation_security_account_id = coalesce([
for account in data.aws_organizations_organization.default.accounts :
for account in local.organizations_organization.accounts :
account.id
if account.name == "organisation-security"
]...)

organisation_account_numbers = [for account in data.aws_organizations_organization.default.accounts : account.id]
organisation_account_numbers = [for account in local.organizations_organization.accounts : account.id]

# AWS Organizational Units
ou_opg = coalesce([
Expand Down Expand Up @@ -137,7 +145,7 @@ locals {
# Accounts map
accounts = {
active_only_not_self : {
for account in data.aws_organizations_organization.default.accounts :
for account in local.organizations_organization.accounts :
account.name => account.id
if account.status == "ACTIVE" && account.name != "organisation-security"
}
Expand Down
Loading

0 comments on commit 0c0c0dd

Please sign in to comment.