🚀 Solution Landing Page | 🚧 Feature request | 🐛 Bug Report
Automated Security Response (ASR) on AWS is a solution that enables AWS Security Hub customers to remediate findings with a single click using sets of predefined response and remediation actions called Playbooks. The remediations are implemented as AWS Systems Manager automation documents. The solution includes remediations for issues such as unused access keys, open security groups, weak account password policies, VPC flow logging configurations, and public S3 buckets. Remediations can also be configured to trigger automatically when findings appear in AWS Security Hub.
The solution includes the playbook remediations for some of the security controls defined as part of the following standards:
A Playbook called Security Control is included that allows operation with AWS Security Hub's Consolidated Control Findings feature.
Note: To deploy the solution without building from the source code, use the CloudFormation templates linked from the Solution Landing Page.

This section provides a technical walkthrough for either (1) adding new remediations to the solution's existing playbooks, or (2) adding a new playbook for a Security Standard not yet implemented in the solution.
Note: If you choose to continue, please be aware that reading and adjusting the source code will be necessary.
Building from GitHub source will allow you to modify the solution to suit your specific needs. The process consists of downloading the source from GitHub, creating buckets to be used for deployment, building the solution, and uploading the artifacts needed for deployment.
Clone or download the repository to a local directory on your linux client. Note: if you intend to modify the solution you may wish to create your own fork of the GitHub repo and work from that. This allows you to check in any changes you make to your private copy of the solution.
Git Clone example:
git clone https://github.com/aws-solutions/automated-security-response-on-aws.git
Download Zip example:
wget https://github.com/aws-solutions/automated-security-response-on-aws/archive/main.zip
In summary the following files in the ASR repo will be modified/added. In this example a new remediation for ElastiCache.2 was added to the SC & AFSBP playbooks.
Note that all new remediations should be added to the SC playbook, since it consolidates all remediations available in ASR. If you intend to deploy only a specific set of playbooks (e.g., AFSBP), then you can either: (1) add the remediation to only your intended playbook(s), or (2) add the remediation to all playbooks for which it exists in the corresponding Security Hub Standard, in addition to the SC playbook. The second option is recommended for flexibility.
In this example, ElastiCache.2 is included in the following Security Hub Standards: - AFSBP - NIST.800-53.r5 SI-2 - NIST.800-53.r5 SI-2(2) - NIST.800-53.r5 SI-2(4) - NIST.800-53.r5 SI-2(5) - PCI DSS v4.0.1/6.3.3.
Since, by default, ASR only implements playbooks for AFSBP & NIST.800-53, we will add this new remediation to those playbooks in addition to SC.
Modify - source/lib/remediation-runbook-stack.ts - source/playbooks/AFSBP/lib/afsbp_remediations.ts - source/playbooks/NIST80053/lib/control_runbooks-construct.ts - source/playbooks/NIST80053/lib/nist80053_remediations.ts - source/playbooks/SC/lib/control_runbooks-construct.ts - source/playbooks/SC/lib/sc_remediations.ts - source/test/regex_registry.ts
Add - source/playbooks/SC/ssmdocs/SC_ElastiCache.2.ts - source/playbooks/SC/ssmdocs/descriptions/ElastiCache.2.md - source/remediation_runbooks/EnableElastiCacheVersionUpgrades.yaml
ℹ️ NOTE: The name chosen for the runbook can be any string, as long as it is consistent with the rest of the changes made. - source/playbooks/NIST80053/ssmdocs/NIST80053_ElastiCache.2.ts - source/playbooks/AFSBP/ssmdocs/AFSBP_ElastiCache.2.yaml
This is the SSM document used to remediate resources. It must include the AutomationAssumeRole parameter,
which is the IAM role with permissions to execute the remediation. View the existing file source/remediation_runbooks/EnableElastiCacheVersionUpgrades.yaml as a reference to create new remediation runbooks.
All new runbooks should be added in the source/remediation_runbooks/ directory.
A control runbook is a playbook-specific runbook that parses the finding data from the given standard and executes the correct Remediation Runbook. Since we will be adding the ElastiCache.2 remediation to SC, AFSBP, and NIST80053 playbooks, we must create a new control runbook for each. The following files are created: - source/playbooks/SC/ssmdocs/SC_ElastiCache.2.ts - source/playbooks/NIST80053/ssmdocs/NIST80053_ElastiCache.2.ts - source/playbooks/AFSBP/ssmdocs/AFSBP_ElastiCache.2.yaml
ℹ️ NOTE: The naming of these files is important and must follow the format <PLAYBOOK_NAME>_<CONTROL.ID>.ts/yaml
Some playbooks in ASR support IaC control runbooks in typescript, while others must be written in raw YAML. Reference the existing remediations in the given playbook as examples of each. In this example, we will cover the SC playbook which uses IaC.
In the SC playbook, your new control runbook will export a new class that extends ControlRunbookDocument and matches the name you chose for your remediation runbook.
Take a look at the example below:
export class EnableElastiCacheVersionUpgrades extends ControlRunbookDocument {
constructor(scope: Construct, id: string, props: ControlRunbookProps) {
super(scope, id, {
...props,
securityControlId: 'ElastiCache.2',
remediationName: 'EnableElastiCacheVersionUpgrades',
scope: RemediationScope.REGIONAL,
resourceIdRegex: String.raw`^arn:(?:aws|aws-cn|aws-us-gov):elasticache:(?:[a-z]{2}(?:-gov)?-[a-z]+-\d):(?:\d{12}):cluster:([a-zA-Z](?:(?!--)[a-zA-Z0-9-]){0,48}[a-zA-Z0-9]$|[a-zA-Z]$)`,
resourceIdName: 'ClusterId',
updateDescription: new StringFormat('Automatic minor version upgrades enabled for cluster %s.', [
StringVariable.of(`ParseInput.ClusterId`),
]),
});
}
}
securityControlId is the control ID for the remediation that you are adding, as it is defined in the consolidated controls view in Security Hub. remediationName is the name you have chosen for your remediation runbook.scope is the scope of the resource you are remediating, indicating whether it exists globally or in a specific region.resourceIdRegex is the regex used to capture the resource ID that you would like to pass to the remediation runbook as a parameter. Only one group should be captured, all other groups should be non-capturing. If you would like to pass the entire ARN, omit this field.resourceIdName is the name you would like to set for the resource ID captured using resourceIdRegex, this should match the resource ID parameter name in your remediation runbook.updateDescription is the string you would like to assign to the "notes" section of the finding in Security Hub once the remediation succeeds.You must also export a function called createControlRunbook which returns a new instance of your class. For ElastiCache.2, this looks like:
export function createControlRunbook(scope: Construct, id: string, props: PlaybookProps): ControlRunbookDocument {
return new EnableElastiCacheVersionUpgrades(scope, id, { ...props, controlId: 'ElastiCache.2' });
}
where controlId is the control ID as defined in the Security Standard associated with the playbook under which you are operating.
If the Security Hub control has parameters that you would like to pass to your remediation runbook, you can pass them by adding overrides to the following methods:
- getExtraSteps: defines default values for each parameter implemented for the control in Security Hub
ℹ️ NOTE: Each parameter from Security Hub must be given a default value -
getInputParamsStepOutput: defines the outputs for the GetInputParams step of the control runbook - Each output has aname,outputType, andselector. Theselectorshould be the same selector used in thegetExtraStepsmethod override. -getRemediationParams: defines the parameters passed to the remediation runbook, fetched from the GetInputParams step outputs.
To view an example, navigate to the source/playbooks/SC/ssmdocs/SC_DynamoDB.1.ts file.
For each control runbook you created in the previous step, you must now integrate with the infrastructure definitions in the associated playbook. For each control runbook you created, follow the steps below.
⚠️ IMPORTANT: If you created the control runbook using raw YAML instead of typescript IaC, skip to the next section.
In /_<playbook_name>_/control_runbooks-construct.ts
Import your newly created control runbook file like:
import * as elasticache_2 from '../ssmdocs/SC_ElastiCache.2';
Next, go to the array for
const controlRunbooksRecord: Record<string, any>
And add a new entry mapping the control ID (playbook-specific) to the createControlRunbook method you've created:
'ElastiCache.2': elasticache_2.createControlRunbook,
Add the playbook-specific control ID to the list of remediations in _<playbook_name>_\_remediations.ts like below:
{ control: 'ElastiCache.2', versionAdded: '2.3.0' },
The versionAdded field should be the latest version of the solution. If adding the remediation breaches the template size limit, increase the versionAdded. You can adjust the number of remediations included in each playbook member stack in solution_env.sh.
In order for the solution to build, you must create a markdown file that describes the remediation runbook you've created. The name of the markdown file must match the control ID in the SC playbook; for example, ElastiCache.2.md is created in the path source/playbooks/SC/ssmdocs/descriptions/ElastiCache.2.md. This markdown file describes what the runbook does, the input and output parameters, and links to the Security Hub documentation.
⚠️ IMPORTANT: You must create this file following the described naming convention in order to successfully build the solution.
Each remediation has its own IAM role with custom permissions required to execute the remediation runbook. In addition, the RunbookFactory.createRemediationRunbook method needs to be invoked to add the remediation runbook you created in Step 1 to the solution's CloudFormation templates.
In the remediation-runook-stack.ts, each remediation has its own code block in the RemediationRunbookStack class. The following code block shows the creation of a new IAM role and remediation runbook integration for the ElastiCache.2 remediation:
``
//-----------------------
// EnableElastiCacheVersionUpgrades
//
{
const remediationName = 'EnableElastiCacheVersionUpgrades'; // should match the name of your remediation runbook
const inlinePolicy = new Policy(props.roleStack,ASR-Remediation-Policy-${remediationName}`);
const remediationPolicy = new PolicyStatement();
remediationPolicy.addActions('elasticache:ModifyCacheCluster');
remediationPolicy.effect = Effect.ALLOW;
remediationPolicy.addResources(`arn:${this.partition}:elasticache:*:${this.account}:cluster:*`);
inlinePolicy.addStatements(remediationPolicy);
new SsmRole(props.roleStack, 'RemediationRole ' + remediationName, { // creates the remediation IAM role
solutionId: props.solutionId,
ssmDocName: remediationName,
remediationPolicy: inlinePolicy,
remediationRoleName: `${remediationRoleNameBase}${remediationName}`,
});
RunbookFactory.createRemediationRunbook(this, 'ASR ' + reme
$ claude mcp add automated-security-response-on-aws \
-- python -m otcore.mcp_server <graph>