Managing Your Github Org with Terraform

Using Terraforms Github provider to manager your Github organization..

Object Partners

With the increasing prevalence of highly distributed systems, it’s becoming very important to automate and template everything possible so your teams don’t get bogged down with mundane tasks. With so many moving parts between teams, projects, and infrastructure, manual tasks for each become error-prone and a source of bottlenecks. Hashicorp’s Terraform is a great tool that allows you to template and manage your infrastructure across all your different providers, and with it’s 0.6.14 release, you can now also manage your Github organizations.

Why Manage a Github Organization

Anyone that has been part of an organization with many moving teams, members, and projects knows that managing it can become frustrating. Anyone that gets stuck as the gatekeeper has to spend a fair amount of time clicking around in Github and you end up with teams and users that have keys to most of the kingdom because you don’t want to deal with such fine-grained control while you’re trying to get your interesting work done. Using Terraform’s Github provider and pull requests as the approval process greatly alleviates these issues.

Tutorial

This tutorial assumes you have installed and have basic knowledge of Terraform (both very easy using the getting started guide).

We’ll start by setting up the Github provider and a simple organization that will use all available resources. If you are following along you will have to create a Github organization, test user, and repository.

###
## <1> The two properties that need to be set are `token` and `organization`. You can hardcode them right in
##     this provider block (very unrecommended) but the better option is to set the `GITHUB_TOKEN`
##     and `GITHUB_ORGANIZATION` environment variables. Terraform will see those and configure the provider with them.
###
provider "github" { }

###
## <2> This assigns a user to the organization. the `username` property should be their string username.
###
resource "github_membership" "test_user_membership" {
    username = "TestUser"
    role = "member"
}

###
## <3> This will create and manage a new team within the organization.
###
resource "github_team" "test_team" {
    name = "test-team"
    description = "A new team created with Terraform."
}

###
## <4> Assigns a user to a team. You can interpolate the team's id with the syntax below.
##     For the `username` you again use the actual string username for the user.
###
resource "github_team_membership" "test_user_test_team" {
    team_id = "${github_team.test_team.id}"
    username = "TestUser"
    role = "member"
}

###
## <5> Assigns an existing Github repository to the created team. For `repository`, use the actual string name
##     of the repository.
###
resource "github_team_repository" "test_team_test_repo" {
    team_id = "${github_team.test_team.id}"
    repository = "existing-repo-name"
    permission = "pull"
}

After setting the GITHUBTOKEN and GITHUBORGANIZATION environment variables and plugging in your own user and repository, execute:

terraform plan

If the execution plan output doesn’t have any issues, you are ready to make these changes to your Github organization. execute:

terraform apply

If you go to Github, it should mirror your github.tf file. From now on adding/removing users, teams, users to those teams, repositories to those teams, or changing permissions is as easy as editing the file and applying.

Suggested Usage

If a single person is tasked with maintaining this file for each organizational change, this won’t be much of an improvement. Committing your Terraform files to Github and allowing a fork/pull model will allow everyone in the organization to own their own changes, but still give a select few the chance to quickly review them and approve just by clicking “merge”. This strikes a nice balance between offloading organizational maintenance work while not surrendering control.

NOTE:This setup is most effective with a build server that applies the Terraform changes after successful build, but that’s a post for another time.

Share this Post

Related Blog Posts

Devops

Using Ansible (Part II)

September 18th, 2015

Continuing where we left off in the previous post, let’s look at how we can start to organize the project a bit more and do some things like add configuration files. To see where we end up checkout the part-ii branch of the companion resources. Since…

Aaron Hanson
Devops

Using Ansible (Part I)

September 16th, 2015

This is going to be a series of using Ansible to help with automating your infrastructure.

Aaron Hanson
Devops

AWS Tricks: Updating Route53 DNS for AutoScalingGroup using Lambda

July 7th, 2015

Utilize Lambda functions to execute automate infrastructure management like DNS record updates during automatic scaling events.

Object Partners

About the author