Continuous Integration for Terraform Modules with GitHub Actions

Collaborating on infrastructure projects using code can introduce challenges such as testing, configuring continuous integration, and deployment pipelines. These things help to ensure that the software is stable, and enables faster releases. These challenges extend to things like Terraform modules that help you share Terraform configuration in your organization. In this post, we’ll take a look at how you can configure a continuous integration pipeline to help test and collaborate on Terraform modules using Github Actions.

GitHub Actions

GitHub Actions gives users the ability to configure actions based on events such as pull requests and merges to their repositories. This feature can be used for Terraform modules managed in GitHub, without having to rely on external tooling.

GitHub Actions relies on a YAML workflow file to specify the steps to execute. A typical workflow for a Terraform module includes terraform init and terraform validate commands. The init command initializes the module and downloads any needed providers. The validate command helps validate the configuration files in the module and is useful for general verification.

Now, let’s take a look at how to construct this workflow with a GitHub Actions workflow file. Create a new workflow file at /.github/workflows/workflow.yaml in the root of the GitHub repository. The content of the workflow file should be as follows:

“`yaml
name: Terraform CI

on:
pull_request:
branches:
– master

jobs:
validate:
name: Validate
runs-on: ubuntu-latest
steps:
– name: Check out code
uses: actions/[email protected]

- name: Run a Terraform init  
  uses: docker://hashicorp/terraform:0.12.11
  with:
    entrypoint: terraform
    args: init

- name: Run a Terraform validate    
  uses: docker://hashicorp/terraform:0.12.11
  with:
    entrypoint: terraform
    args: validate

“`
First, we name the workflow “Terraform CI”. Next, we specify that this workflow should be triggered on a pull request event opened against the master branch.

Then, we define each step to be run during this workflow. In the example, we use the predefined checkout action to retrieve the code contained in the repository. After retrieving the contents of the repository, we specify steps to execute terraform init and terraform validate commands using the Terraform container from Docker Hub.

By using these steps, we can initialize and validate the syntax of Terraform modules in Github without setting up additional tooling. Teams can collaborate on modules and push to the repository with a continuous integration workflow.

Continuous Testing

In addition to validating Terraform code, we can extend this workflow to incorporate automated testing of modules. This is especially important when multiple developers are collaborating on a module, and helps continuously verify that it executes as expected.

We now update our example with the addition of a step to execute unit tests implemented with Terratest, a Golang library for running tests against Terraform.

“`yaml
name: Terraform CI

on:
pull_request:
branches:
– master

jobs:
validate:
name: Validate
runs-on: ubuntu-latest
steps:

Steps omitted for clarity

  • name: Set up Go 1.13
    uses: actions/[email protected]
    with:
    go-version: 1.13
    id: go

    • name: Get dependencies
      run: |
      if [ -f Gopkg.toml ]; then
      curl https://raw.githubusercontent.com/golang/dep/master/install.sh | sh
      dep ensure
      else
      go get -v -t -d ./…
      fi
    • name: Test
      working-directory: /home/runner/work/terratest-demo/terratest-demo/test
      run: go test

      Similar to the previous section, we use the
      setup-goaction to bootstrap a Golang environment to stage the unit tests. Next, we pull down the dependencies for the test code in order to executego test. Before running the tests, we change to the directory containing the test files, located in/home/runner/work/{repository-name}/{repository-name}`

GitHub Status Checks

To ensure a potentially disruptive configuration does not affect a stable Terraform module, we protect the master branch from merging a pull request with failing checks. We go to the “Settings” tab on the GitHub repository and select the “Branches” section.

We select “Require status checks to pass before merging” and choose the status checks created by the GitHub actions workflow. Finally, we click “Create” to save the branch protection rule. This will ensure that pull requests can’t be completed until the checks have passed.

Conclusion

In this post, we covered how GitHub Actions enables a flexible, native continuous integration pipeline for Terraform modules without the need to depend on external tooling. Github Actions enables us to validate syntax, test resources, and maintain the quality of our Terraform modules as we integrate changes to their configurations. To learn more about GitHub Actions, refer to the official documentation.

Originally posted on Hashicorp Blog
Author: Xander Grzywinski

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *