Running a security check against infrastructure as code (IaC) before deployment is a best practice that has been gaining adoption over the last few years as part of the shift-left movement in security. Shift-left entails moving security considerations earlier in the software development lifecycle (SDLC). As it relates to IaC, shifting left means making sure the infrastructure is free of misconfigurations before it is deployed.
You can use Steampipe’s Terraform plugin to do that. The Steampipe Terraform AWS Compliance mod scans your Terraform code for known misconfigurations, and helps you identify and resolve security issues before they become a finding in your CSPM – and more critically, risk in your environment. With CodePipeline, you can easily integrate that scan into your Terraform deployment process, to help ensure that your infrastructure is secure from the start..
In this post, we will set up a CodePipeline that will take your Terraform code, scan it with the Terraform AWS Compliance mod, and push the findings to Steampipe Cloud. CodePipeline will then notify the user of any security issues before deploying the misconfigurations into your cloud environment. By gating the deployment like this, developers are made aware of the security violations they may be about to deploy and can reduce the number of misconfigurations that make it to production.
How it works
When you push to a monitored GitHub repo, you trigger the CodePipeline. The solution uses AWS’s CodeStar Connections to manage the integration between GitHub and CodePipeline.
CodePipeline then runs two CodeBuild jobs - one to generate the Terraform plan, the other to scan the Terraform against the best practices embodied in the Steampipe Terraform AWS Compliance mod. When these are both completed, the workflow notifies the administrator to review the changes. The notification includes links to the terraform plan
output and the Steampipe Cloud Snapshot.
Once the plan and snapshot have been reviewed, the administrator can approve each and the CodePipeline will execute a CodeBuild job to run terraform apply
.
Overall, the pipeline looks like this:
Configuring CodePipeline
The CodePipeline itself, each of the CodeBuild projects that executes Steampipe and Terraform, and the necessary IAM Roles are deployed by this CloudFormation Template. You must specify the GitHub Repo, Branch, and the email address of the person who is notified when a manual approval step occurs.
Configuring CodeStar
To start you must configure the CodeStar Connection into your GitHub organization. The ARN of that CodeStar Connection is required by CodePipeline to start each workflow. If your connection is for GitHub, you’ll be prompted to install the connector in a specific GitHub Organization and then select the Repositories the connector will have access to.
As an aside: CodeStar Connections are so under-the-radar I can’t even find a product page to link to. Just some API docs and the above blog post. However CodeStar is a much better solution than previous methods that required overly-privileged GitHub Personal Access Tokens to be uploaded into shared AWS Accounts. With CodeStar Connections, the integration between GitHub and AWS is based on the organization and repository, not the permissions of the user who established the connection.
Configuring Steampipe
This solution pushes the output of the Terraform AWS Compliance as a snapshot to Steampipe Cloud. Users can review the snapshot without having to log into the AWS Console. In order to authenticate to Steampipe Cloud, you will need to generate an API Token. With that token, you can create an AWS Secrets Manager secret which CodeBuild will import. Also in the secret is the Steampipe Cloud organization and workspace in the WORKSPACE field.
aws secretsmanager create-secret --name steampipe-cloud --secret-string \'{"STEAMPIPE_CLOUD_TOKEN":"spt_PUTYOURTOKENHERE","WORKSPACE":"fooli/memefactory"}'
Deploying the CloudFormation
To deploy the cloudformation template you’ll need the following parameters:
- GitHub Repository to trigger from. This should be in the form of
org/repo
. - Branch
- Notification Email
- CodeStar Connection Arn you created above
- Steampipe Secret Name you created above
Configuring your Terraform Repository
In order for CodePipeline and CodeBuild to scan and deploy your Terraform, you must add three buildspec files to your repository’s root directory. They are:
Buildspec.steampipe.yaml
- the commands to download, install and configure steampipe, and to run the scan and upload the results to Steampipe cloudBuildspec-tf-plan.yaml
- the commands to download terraform, and run the terraform-planBuildspec-tf-apply.yaml
- the commands to download terraform, and run the terraform-apply
These files can be found here in the steampipe-samples repository.
Using this solution
When you push a commit to the specified branch the pipeline will automatically kick off. It will download the source code, Steampipe, the plugin, and the mod. The scan results will be pushed to Steampipe Cloud and the user will get an email that looks like this:
Clicking on the "Content to review" link in the mail takes you directly to the report in Steampipe Cloud.
At this point you would ideally fix the issues identified and push a new commit. However, if this is an emergency fix or the business is ok accepting the risk, you can approve the pipeline to proceed. The Terraform plan also generates an email for you to review and the plan file is in the logs of the CodeBuild execution.
Once you approve both the Steampipe report and the Terraform plan output, another CodeBuild execution will spin up to run terraform apply
.
Shift Left with Steampipe
When you scan your Terraform code with Steampipe, you reduce the risk of security incidents and data breaches, and help protect your critical infrastructure and applications. With easy integration and a user-friendly interface, you can quickly get started scanning your Terraform code. So why wait? Start using Steampipe today to secure your Terraform code with confidence!