Skip to content

smartatransit/cloud-config

Repository files navigation

cloud-config

This repository (and its integration with the free Terraform Cloud service) allows smartatransit team members to deploy Docker resources to our cloud host. In the future it could be used to deploy other cloud infrastructure outside of the host at well.

Creating a plan

To deploy a service, clone the repository (or pull the master branch if it's already cloned) and create a new branch for your work. Create a new file like my_service_name.tf, where you'll place your Terraform configuration. Below is a sample of what that might look like.

When you're done, push your branch and open a pull request against the master branch. This should automatically start a terraform plan job in Terraform Cloud, which you should be able to view if you're a member of the smartatransit organization. Just click the link in the newly created status check on your pull request. When the plan job finishes, it'll show you a summary of the changes that your pull request will make.

Understanding the plan

If drift or manual intervention has changed the state from what master said it should be, this may include more changes than you intended, as Terraform attempts to bring things back into line. One common example you may see is that a Docker service in production is pinned to the latest image under a given tag, Terraform may want to update the service to a new release. These changes are generally OK, but if you see something in the Terraform plan that you don't understand, consider reaching out to another team member familiar with the affected area before proceeding.

Applying a plan

When you're confident that the Terraform plan describes what you want it to, you're ready to merge your pull request to master. Merging will trigger another plan which you can find in the Terraform Cloud workspace. This time, at the bottom of the page you'll find the option to confirm and apply the changes. If all goes well, your changes will be successfully deployed to the host.

Example

variable "myservice_postgres_password" {
  type = string
}

resource "docker_secret" "myservice_postgres_password" {
  name = "myservice_postgres_password"
  data = base64encode(var.myservice_postgres_password)
}

resource "docker_network" "myservice" {
  name   = "myservice"
  driver = "overlay"
}

resource "docker_volume" "postgres_data" {
  name = "myservice"
}

resource "postgresql_role" "myservice" {
  name     = "myservice"
  login    = true
  password = var.myservice_postgres_password
}

resource "postgresql_database" "myservice" {
  name  = "myservice"
  owner = postgresql_role.smartadata.name
}

resource "docker_service" "myservice" {
  name = "myservice"

  task_spec {
    container_spec {
      image = "smartatransit/myservice:production"

      env = {
        DEBUG         = "true"
        POSTGRES_HOST = var.postgres_host
      }

      mounts {
        target = "/myservice-data-dir"
        source = docker_volume.myservice.name
        type   = "volume"
      }

      secrets {
        secret_id   = docker_secret.myservice_postgres_password.id
        secret_name = docker_secret.myservice_postgres_password.name
        file_name   = "/run/secrets/myservice_postgres_password"
      }
    }

    networks = [docker_network.myservice.id]
  }
}

The variable blocks are used to declare names for values that are going to be passed in from outside the configuration. This is useful for sensitive values like passwords which we don't want checked into this repository. You can then add the value directly in the Terraform Cloud web UI by selecting the "Variables" tab. If your variable is a sensitive value like a password, make sure to check the "Sensitive" box so Terraform knows to censor this value in the log output.

The resource blocks each create and manage a resource either from the Docker provider or the Postgresql provider. Documentation for those can be found here and here.

Notice that this example references the variable var.postgres_host, which is not defined here. You can reference variables in other files to create links among the services. Terraform will build a graph to determine the correct order in which to create or update resources, but it will break if there are circular references.

For more information on Terraform and HCL (the configuration language it relies on) see the documentation or reach out to your fellow team members for help!

About

terraforming docker swarm services

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages