Skip to content

Terraform module to Automatically suppress findings recorded by the AWS Security Hub service based on a pre-defined and configurable suppression list, integrates with Jira and ServiceNow for creation of tickets when findings are generated by AWS Security Hub.

License

Notifications You must be signed in to change notification settings

schubergphilis/terraform-aws-mcaf-securityhub-findings-manager

Repository files navigation

Security Hub Findings Manager

Automated scanning and finding consolidation are essential for evaluating your security posture. AWS Security Hub is the native solution for this task within AWS. The number of findings it generates can initially be overwhelming. Additionally, some findings may be irrelevant or have less urgency for your specific situation.

The Security Hub Findings Manager is a framework designed to automatically manage findings recorded by AWS Security Hub, including its AWS service integrations, based on a configurable rules list. Its primary aim is to reduce noise and help you prioritize genuine security issues.

Supported Functionality:

  • Suppressing findings to manage irrelevant or less urgent issues effectively.
  • Automated ticket creation in Jira and ServiceNow for non-suppressed findings exceeding a customizable severity threshold.

Tip

Deploy this module in the Audit/Security Account of an AWS reference multi-account setup. This setup receives events from all child accounts, providing a comprehensive overview of the organization's security posture.

Important

This module relies heavily on awsfindingsmanagerlib. For detailed suppression logic information, refer to the library's documentation.

Components

Here's a high-level overview of the components. For more details, see Resources and Modules.

  • Rules backend (currently only S3 supported).
  • Three Lambda Functions:
    • Security Hub Findings Manager Events: triggered by EventBridge for new Security Hub findings.
    • Security Hub Findings Manager Triggers: responds to changes in the S3 backend rules list, putting suppression rules on SQS.
    • Security Hub Findings Manager Trigger Worker: activated by suppression rules on SQS.
  • Infrastructure supporting Lambda functions (IAM role, EventBridge integration, S3 Trigger Notifications, SQS queue).
  • Optional Jira integration components.
  • Optional ServiceNow integration components.

Deployment Modes

Three deployment modes are available:

Important

During the first deployment, be aware that S3 triggers might take time to become fully functional. Re-create the rules object later to apply rules to your findings history.

Default (Without Jira & ServiceNow Integration)

Deploys two Lambda functions:

  • securityhub-findings-manager-events: target for the EventBridge rule Security Hub Findings - Imported events.
  • securityhub-findings-manager-trigger: target for the S3 PutObject trigger.

With Jira Integration

  • Enable by setting the variable jira_integration to true (default = false).
  • Deploys an additional Jira lambda function and a Step function for orchestration, triggered by an EventBridge rule.
  • Non-suppressed findings with severity above a threshold result in ticket creation and workflow status update from NEW to NOTIFIED.
  • Auto-closing can be activated with jira_integration.autoclose_enabled (default = false). Using the issue number in the finding note, the function transitions issues using jira_integration.autoclose_transition_name and jira_integration.autoclose_comment. Criteria for being forwarded for automatic ticket closure are:
    • Workflow Status "RESOLVED"
    • Workflow Status "NOTIFIED" and one of:
      • Record State "ARCHIVED"
      • Compliance State "PASSED" or "NOT_AVAILABLE"

Only findings with a normalized severity level above the threshold (default 70) initiate Jira integration.

Normalized severity levels:

  • 0 - INFORMATIONAL
  • 1–39 - LOW
  • 40–69 - MEDIUM
  • 70–89 - HIGH
  • 90–100 - CRITICAL

Step Function Graph

With ServiceNow Integration

Reference design

  • Enable by setting the variable servicenow_integration to true (default = false).
  • Deploys resources supporting ServiceNow integration, including an SQS Queue, EventBridge Rule, and required IAM user.
  • EventBridge triggers events for Security Hub, placing them on an SQS Queue.
  • Configure which findings are forwarded via severity_label_filter.
  • ServiceNow retrieves events from the SQS queue using SCSyncUser credentials.

Warning

Generate the access_key & secret_access_key in the AWS Console. If you prefer Terraform to handle this (and output them), set the variable create_servicenow_access_keys to true (default = false).

Formatting the rules.yaml File

An example file is available under examples/rules.yaml. For detailed information, see the Rule Syntax section in the awsfindingsmanagerlib documentation.

Local Development on Python Code

A lambda layer provides aws-lambda-powertools. To have these dependencies locally, use requirements-dev.txt from the source code.

Requirements

Name Version
terraform >= 1.3.0
archive >= 2.0
aws >= 4.9
external >= 2.0
local >= 1.0
null >= 2.0

Providers

Name Version
aws >= 4.9

Modules

Name Source Version
findings_manager_bucket schubergphilis/mcaf-s3/aws ~> 0.14.1
findings_manager_events_lambda schubergphilis/mcaf-lambda/aws ~> 1.4.1
findings_manager_trigger_lambda schubergphilis/mcaf-lambda/aws ~> 1.4.1
findings_manager_worker_lambda schubergphilis/mcaf-lambda/aws ~> 1.4.1
jira_eventbridge_iam_role schubergphilis/mcaf-role/aws ~> 0.3.2
jira_lambda schubergphilis/mcaf-lambda/aws ~> 1.4.1
jira_step_function_iam_role schubergphilis/mcaf-role/aws ~> 0.3.2
servicenow_integration ./modules/servicenow/ n/a

Resources

Name Type
aws_cloudwatch_event_rule.securityhub_findings_events resource
aws_cloudwatch_event_target.findings_manager_events_lambda resource
aws_cloudwatch_event_target.jira_orchestrator resource
aws_cloudwatch_log_group.log_group_jira_orchestrator_sfn resource
aws_lambda_event_source_mapping.sqs_to_worker resource
aws_lambda_permission.eventbridge_invoke_findings_manager_events_lambda resource
aws_lambda_permission.s3_invoke_findings_manager_trigger_lambda resource
aws_s3_bucket_notification.findings_manager_trigger resource
aws_s3_object.findings_manager_lambdas_deployment_package resource
aws_s3_object.jira_lambda_deployment_package resource
aws_s3_object.rules resource
aws_sfn_state_machine.jira_orchestrator resource
aws_sqs_queue.dlq_for_findings_manager_rule_q resource
aws_sqs_queue.findings_manager_rule_q resource
aws_sqs_queue_policy.findings_manager_rule_sqs_policy resource
aws_sqs_queue_redrive_allow_policy.dead_letter_allow_policy resource
aws_sqs_queue_redrive_policy.redrive_policy resource
aws_caller_identity.current data source
aws_iam_policy_document.findings_manager_lambda_iam_role data source
aws_iam_policy_document.findings_manager_rule_sqs_policy_doc data source
aws_iam_policy_document.jira_eventbridge_iam_role data source
aws_iam_policy_document.jira_lambda_iam_role data source
aws_iam_policy_document.jira_step_function_iam_role data source
aws_region.current data source

Inputs

Name Description Type Default Required
kms_key_arn The ARN of the KMS key used to encrypt the resources string n/a yes
s3_bucket_name The name for the S3 bucket which will be created for storing the function's deployment package string n/a yes
findings_manager_events_lambda Findings Manager Lambda settings - Manage Security Hub findings in response to EventBridge events
object({
name = optional(string, "securityhub-findings-manager-events")
log_level = optional(string, "ERROR")
memory_size = optional(number, 256)
timeout = optional(number, 300)

security_group_egress_rules = optional(list(object({
cidr_ipv4 = optional(string)
cidr_ipv6 = optional(string)
description = string
from_port = optional(number, 0)
ip_protocol = optional(string, "-1")
prefix_list_id = optional(string)
referenced_security_group_id = optional(string)
to_port = optional(number, 0)
})), [])
})
{} no
findings_manager_trigger_lambda Findings Manager Lambda settings - Manage Security Hub findings in response to S3 file upload triggers
object({
name = optional(string, "securityhub-findings-manager-trigger")
log_level = optional(string, "ERROR")
memory_size = optional(number, 256)
timeout = optional(number, 300)

security_group_egress_rules = optional(list(object({
cidr_ipv4 = optional(string)
cidr_ipv6 = optional(string)
description = string
from_port = optional(number, 0)
ip_protocol = optional(string, "-1")
prefix_list_id = optional(string)
referenced_security_group_id = optional(string)
to_port = optional(number, 0)
})), [])
})
{} no
findings_manager_worker_lambda Findings Manager Lambda settings - Manage Security Hub findings in response to SQS trigger
object({
name = optional(string, "securityhub-findings-manager-worker")
log_level = optional(string, "ERROR")
memory_size = optional(number, 256)
timeout = optional(number, 900)

security_group_egress_rules = optional(list(object({
cidr_ipv4 = optional(string)
cidr_ipv6 = optional(string)
description = string
from_port = optional(number, 0)
ip_protocol = optional(string, "-1")
prefix_list_id = optional(string)
referenced_security_group_id = optional(string)
to_port = optional(number, 0)
})), [])
})
{} no
jira_eventbridge_iam_role_name The name of the role which will be assumed by EventBridge rules for Jira integration string "SecurityHubFindingsManagerJiraEventBridge" no
jira_integration Findings Manager - Jira integration settings
object({
enabled = optional(bool, false)
autoclose_enabled = optional(bool, false)
autoclose_comment = optional(string, "Security Hub finding has been resolved. Autoclosing the issue.")
autoclose_transition_name = optional(string, "Close Issue")
credentials_secret_arn = string
exclude_account_ids = optional(list(string), [])
finding_severity_normalized_threshold = optional(number, 70)
issue_custom_fields = optional(map(string), {})
issue_type = optional(string, "Security Advisory")
project_key = string

security_group_egress_rules = optional(list(object({
cidr_ipv4 = optional(string)
cidr_ipv6 = optional(string)
description = string
from_port = optional(number, 0)
ip_protocol = optional(string, "-1")
prefix_list_id = optional(string)
referenced_security_group_id = optional(string)
to_port = optional(number, 0)
})), [])

lambda_settings = optional(object({
name = optional(string, "securityhub-findings-manager-jira")
log_level = optional(string, "INFO")
memory_size = optional(number, 256)
timeout = optional(number, 60)
}), {
name = "securityhub-findings-manager-jira"
iam_role_name = "SecurityHubFindingsManagerJiraLambda"
log_level = "INFO"
memory_size = 256
timeout = 60
security_group_egress_rules = []
})

step_function_settings = optional(object({
log_level = optional(string, "ERROR")
retention = optional(number, 90)
}), {
log_level = "ERROR"
retention = 90
})

})
{
"credentials_secret_arn": null,
"enabled": false,
"project_key": null
}
no
jira_step_function_iam_role_name The name of the role which will be assumed by AWS Step Function for Jira integration string "SecurityHubFindingsManagerJiraStepFunction" no
lambda_runtime The version of Python to use for the Lambda functions string "python3.12" no
rules_filepath Pathname to the file that stores the manager rules string "" no
rules_s3_object_name The S3 object containing the rules to be applied to Security Hub findings manager string "rules.yaml" no
servicenow_integration ServiceNow integration settings
object({
enabled = optional(bool, false)
create_access_keys = optional(bool, false)
cloudwatch_retention_days = optional(number, 365)
severity_label_filter = optional(list(string), [])
})
{
"enabled": false
}
no
subnet_ids The subnet ids where the Lambda functions needs to run list(string) null no
tags A mapping of tags to assign to the resources map(string) {} no

Outputs

Name Description
findings_manager_events_lambda_sg_id This will output the security group id attached to the lambda_findings_manager_events Lambda. This can be used to tune ingress and egress rules.
findings_manager_trigger_lambda_sg_id This will output the security group id attached to the lambda_findings_manager_trigger Lambda. This can be used to tune ingress and egress rules.
findings_manager_worker_lambda_sg_id This will output the security group id attached to the lambda_findings_manager_worker Lambda. This can be used to tune ingress and egress rules.
jira_lambda_sg_id This will output the security group id attached to the jira_lambda Lambda. This can be used to tune ingress and egress rules.

About

Terraform module to Automatically suppress findings recorded by the AWS Security Hub service based on a pre-defined and configurable suppression list, integrates with Jira and ServiceNow for creation of tickets when findings are generated by AWS Security Hub.

Topics

Resources

License

Stars

Watchers

Forks

Packages

No packages published