Using Terrascan for Static Code Analysis of Your Infrastructure Code (part 1)
You’ve been working hard on a project trying to get it to production as soon as possible. Maybe, even spent some nights and weekends working extra hard on your terraform code to automatically provision your infrastructure and deploy your app.
Once you finally get it to prod, you feel accomplished and relieved. You feel like nothing can go wrong now. It’s Friday night and you’re ready to go home after a long week. And just when you’re about to leave, your security team calls you.
They found that one of your S3 buckets is leaking sensitive data to the public internet.
You freak out!
Quickly looking through the code to determine what went wrong, you find that one of your buckets has a public-read-write Access Control List (ACL).
You quickly change that to “private”, commit, and “terraform apply”. Luckily the security team informed you that after looking at the logs it seems like no one accessed the files in the bucket other than them.
You still feel terrible, and frustrated that you didn’t catch this before. What can you do to prevent these accidents from happening in the future?
Here’s some help
Infrastructure as code allows you to manage and provision infrastructure using the same development practices as application development. Scanning code for security weaknesses as soon as it’s written has been a long held best practice for secure software development.
To help avoid introducing security weaknesses when provisioning infrastructure, you should scan infrastructure code when using tools such as Terraform, CloudFormation, Pulumy, or the AWS Cloud Development Kit (CDK). Ideally, static code analysis happens on your desktop as soon as the code is written so that you receive immediate feedback and avoid checking in vulnerable code. It should also be integrated into your continuous integration pipeline to avoid provisioning infrastructure with security weaknesses.
One of my favorite tools to scan terraform HCL code for potential security weaknesses is terrascan. (Yes, I’m biased)
Terrascan is a python utility that has a number of security checks for misconfigurations in HCL (the configuration language used by terraform) including: public exposure, encryption, misconfigured security groups, and logging/monitoring misconfigurations.
Since you want to receive early feedback on security issues before they get committed into your version control repository, terrascan can be configured as a pre-commit hook.
Wait, what are pre-commit hooks?
Git hooks are scripts that run on your desktop to automatically verify your code before it’s committed to version control. A popular framework used to manage these is pre-commit.
You’ll need Python installed in your system in order to use both pre-commit and terrascan. The optimal way to install Python is using pyenv which can be installed using the pyenv-installer like this:
Once pyenv is installed the script will output the commands you need to add to your ~/.bashrc in order to load it automatically. Enter these into your current shell. Here’s an example:
Lets install python 3.7.5 and set it as our default globally.
Now you can install pre-commit
Ok, that was easy. Now how do I install terrascan?
First, lets create a directory and repository for the project that will contain your terraform code.
The infrastructure files are going to be in a directory called “infra”.
You’ll need a file called “.pre-commit-config.yaml” that will define the pre-commit hooks used by the project. Add the following into your file:
Now install the terrascan pre-commit
Does this really work?
Let’s add a file called “infra/s3.tf” with some dummy terraform test everything is correctly setup.
Now try to commit the file
You should get an output like this:
As you can see in the output, terrascan is raising an error due to the aws_s3_bucket resource containing a “public-read-write” ACL. Lets fix the issue by changing the “acl” parameter in line #3 to "private" and try again.
Update the “infra/s3.tf” file as follows:
Then…
Your output should look like this:
Wow this is great!
Indeed it is! Using terrascan and pre-commits you’re able to detect issues as soon as the code is written. Relieving you from potential pain once vulnerable code is introduced into your environment.
What if someone on my team doesn’t have terrascan installed?
In the next post I’ll teach you how to configure terrascan as part of your CI/CD pipeline using GitHub Actions.
Do you use pre-commit? What are other pre-commit hooks you use when developing for AWS?