From bbe295a3f1720d850d9f35f457acf610e1d99263 Mon Sep 17 00:00:00 2001 From: Dalton Hubble Date: Fri, 12 Jan 2018 06:56:08 -0800 Subject: [PATCH] Add Terraform v0.11.x support and migration docs * Add explicit "providers" section to modules for Terraform v0.11.x * Retain support for Terraform v0.10.4+ * Add migration guide from Terraform v0.10.x to v0.11.x for those managing existing clusters (action required!) --- CHANGES.md | 4 ++ README.md | 8 ++++ docs/aws.md | 37 +++++++++++++++++-- docs/bare-metal.md | 33 +++++++++++++++-- docs/digital-ocean.md | 36 ++++++++++++++++-- docs/google-cloud.md | 37 +++++++++++++++++-- docs/index.md | 8 ++++ docs/topics/maintenance.md | 75 ++++++++++++++++++++++++++++++++++++++ 8 files changed, 226 insertions(+), 12 deletions(-) diff --git a/CHANGES.md b/CHANGES.md index 1d426cc6..a9677039 100644 --- a/CHANGES.md +++ b/CHANGES.md @@ -4,6 +4,10 @@ Notable changes between versions. ## Latest +* Add Terraform v0.11.x support + * Add explicit "providers" section to modules for Terraform v0.11.x + * Retain support for Terraform v0.10.4+ +* Add [migration guide](https://github.com/poseidon/typhoon/blob/master/docs/topics/maintenance.md) from Terraform v0.10.x to v0.11.x (action required!) * Update etcd from 3.2.13 to 3.2.14 * Update kube-dns from v1.14.7 to v1.14.8 * Use separate service account for kube-dns diff --git a/README.md b/README.md index 4c8f8f99..e0b0f75c 100644 --- a/README.md +++ b/README.md @@ -44,6 +44,14 @@ Define a Kubernetes cluster by using the Terraform module for your chosen platfo ```tf module "google-cloud-yavin" { source = "git::https://github.com/poseidon/typhoon//google-cloud/container-linux/kubernetes" + + providers = { + google = "google.default" + local = "local.default" + null = "null.default" + template = "template.default" + tls = "tls.default" + } # Google Cloud region = "us-central1" diff --git a/docs/aws.md b/docs/aws.md index 42396901..332d757c 100644 --- a/docs/aws.md +++ b/docs/aws.md @@ -10,15 +10,15 @@ Controllers and workers are provisioned to run a `kubelet`. A one-time [bootkube * AWS Account and IAM credentials * AWS Route53 DNS Zone (registered Domain Name or delegated subdomain) -* Terraform v0.10.x and [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) installed locally +* Terraform v0.11.x and [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) installed locally ## Terraform Setup -Install [Terraform](https://www.terraform.io/downloads.html) v0.10.x on your system. +Install [Terraform](https://www.terraform.io/downloads.html) v0.11.x on your system. ```sh $ terraform version -Terraform v0.10.7 +Terraform v0.11.1 ``` Add the [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) plugin binary for your system. @@ -57,9 +57,32 @@ Configure the AWS provider to use your access key credentials in a `providers.tf ```tf provider "aws" { + version = "~> 1.5.0" + alias = "default" + region = "eu-central-1" shared_credentials_file = "/home/user/.config/aws/credentials" } + +provider "local" { + version = "~> 1.0" + alias = "default" +} + +provider "null" { + version = "~> 1.0" + alias = "default" +} + +provider "template" { + version = "~> 1.0" + alias = "default" +} + +provider "tls" { + version = "~> 1.0" + alias = "default" +} ``` Additional configuration options are described in the `aws` provider [docs](https://www.terraform.io/docs/providers/aws/). @@ -75,6 +98,14 @@ Define a Kubernetes cluster using the module `aws/container-linux/kubernetes`. module "aws-tempest" { source = "git::https://github.com/poseidon/typhoon//aws/container-linux/kubernetes" + providers = { + aws = "aws.default" + local = "local.default" + null = "null.default" + template = "template.default" + tls = "tls.default" + } + cluster_name = "tempest" # AWS diff --git a/docs/bare-metal.md b/docs/bare-metal.md index 17f8e3d2..d2c4d5bb 100644 --- a/docs/bare-metal.md +++ b/docs/bare-metal.md @@ -12,7 +12,7 @@ Controllers are provisioned as etcd peers and run `etcd-member` (etcd3) and `kub * PXE-enabled [network boot](https://coreos.com/matchbox/docs/latest/network-setup.html) environment * Matchbox v0.6+ deployment with API enabled * Matchbox credentials `client.crt`, `client.key`, `ca.crt` -* Terraform v0.10.x and [terraform-provider-matchbox](https://github.com/coreos/terraform-provider-matchbox) installed locally +* Terraform v0.11.x and [terraform-provider-matchbox](https://github.com/coreos/terraform-provider-matchbox) installed locally ## Machines @@ -109,11 +109,11 @@ Read about the [many ways](https://coreos.com/matchbox/docs/latest/network-setup ## Terraform Setup -Install [Terraform](https://www.terraform.io/downloads.html) v0.10.x on your system. +Install [Terraform](https://www.terraform.io/downloads.html) v0.11.x on your system. ```sh $ terraform version -Terraform v0.10.7 +Terraform v0.11.1 ``` Add the [terraform-provider-matchbox](https://github.com/coreos/terraform-provider-matchbox) plugin binary for your system. @@ -149,6 +149,26 @@ provider "matchbox" { client_key = "${file("~/.config/matchbox/client.key")}" ca = "${file("~/.config/matchbox/ca.crt")}" } + +provider "local" { + version = "~> 1.0" + alias = "default" +} + +provider "null" { + version = "~> 1.0" + alias = "default" +} + +provider "template" { + version = "~> 1.0" + alias = "default" +} + +provider "tls" { + version = "~> 1.0" + alias = "default" +} ``` ## Cluster @@ -159,6 +179,13 @@ Define a Kubernetes cluster using the module `bare-metal/container-linux/kuberne module "bare-metal-mercury" { source = "git::https://github.com/poseidon/typhoon//bare-metal/container-linux/kubernetes" + providers = { + local = "local.default" + null = "null.default" + template = "template.default" + tls = "tls.default" + } + # install matchbox_http_endpoint = "http://matchbox.example.com" container_linux_channel = "stable" diff --git a/docs/digital-ocean.md b/docs/digital-ocean.md index cdf47a7e..be70d206 100644 --- a/docs/digital-ocean.md +++ b/docs/digital-ocean.md @@ -10,15 +10,15 @@ Controllers and workers are provisioned to run a `kubelet`. A one-time [bootkube * Digital Ocean Account and Token * Digital Ocean Domain (registered Domain Name or delegated subdomain) -* Terraform v0.10.x and [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) installed locally +* Terraform v0.11.x and [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) installed locally ## Terraform Setup -Install [Terraform](https://www.terraform.io/downloads.html) v0.10.x on your system. +Install [Terraform](https://www.terraform.io/downloads.html) v0.11.x on your system. ```sh $ terraform version -Terraform v0.10.7 +Terraform v0.11.1 ``` Add the [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) plugin binary for your system. @@ -58,7 +58,29 @@ Configure the DigitalOcean provider to use your token in a `providers.tf` file. ```tf provider "digitalocean" { + version = "0.1.2" token = "${chomp(file("~/.config/digital-ocean/token"))}" + alias = "default" +} + +provider "local" { + version = "~> 1.0" + alias = "default" +} + +provider "null" { + version = "~> 1.0" + alias = "default" +} + +provider "template" { + version = "~> 1.0" + alias = "default" +} + +provider "tls" { + version = "~> 1.0" + alias = "default" } ``` @@ -69,6 +91,14 @@ Define a Kubernetes cluster using the module `digital-ocean/container-linux/kube ```tf module "digital-ocean-nemo" { source = "git::https://github.com/poseidon/typhoon//digital-ocean/container-linux/kubernetes" + + providers = { + digitalocean = "digitalocean.default" + local = "local.default" + null = "null.default" + template = "template.default" + tls = "tls.default" + } region = "nyc3" dns_zone = "digital-ocean.example.com" diff --git a/docs/google-cloud.md b/docs/google-cloud.md index dae35a22..26505728 100644 --- a/docs/google-cloud.md +++ b/docs/google-cloud.md @@ -10,15 +10,15 @@ Controllers and workers are provisioned to run a `kubelet`. A one-time [bootkube * Google Cloud Account and Service Account * Google Cloud DNS Zone (registered Domain Name or delegated subdomain) -* Terraform v0.10.x and [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) installed locally +* Terraform v0.11.x and [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) installed locally ## Terraform Setup -Install [Terraform](https://www.terraform.io/downloads.html) v0.10.x on your system. +Install [Terraform](https://www.terraform.io/downloads.html) v0.11.x on your system. ```sh $ terraform version -Terraform v0.10.7 +Terraform v0.11.1 ``` Add the [terraform-provider-ct](https://github.com/coreos/terraform-provider-ct) plugin binary for your system. @@ -57,10 +57,33 @@ Configure the Google Cloud provider to use your service account key, project-id, ```tf provider "google" { + version = "1.2" + alias = "default" + credentials = "${file("~/.config/google-cloud/terraform.json")}" project = "project-id" region = "us-central1" } + +provider "local" { + version = "~> 1.0" + alias = "default" +} + +provider "null" { + version = "~> 1.0" + alias = "default" +} + +provider "template" { + version = "~> 1.0" + alias = "default" +} + +provider "tls" { + version = "~> 1.0" + alias = "default" +} ``` Additional configuration options are described in the `google` provider [docs](https://www.terraform.io/docs/providers/google/index.html). @@ -75,6 +98,14 @@ Define a Kubernetes cluster using the module `google-cloud/container-linux/kuber ```tf module "google-cloud-yavin" { source = "git::https://github.com/poseidon/typhoon//google-cloud/container-linux/kubernetes" + + providers = { + google = "google.default" + local = "local.default" + null = "null.default" + template = "template.default" + tls = "tls.default" + } # Google Cloud region = "us-central1" diff --git a/docs/index.md b/docs/index.md index 095f00ff..fbf61d59 100644 --- a/docs/index.md +++ b/docs/index.md @@ -44,6 +44,14 @@ Define a Kubernetes cluster by using the Terraform module for your chosen platfo ```tf module "google-cloud-yavin" { source = "git::https://github.com/poseidon/typhoon//google-cloud/container-linux/kubernetes" + + providers = { + google = "google.default" + local = "local.default" + null = "null.default" + template = "template.default" + tls = "tls.default" + } # Google Cloud region = "us-central1" diff --git a/docs/topics/maintenance.md b/docs/topics/maintenance.md index c164df93..387f1796 100644 --- a/docs/topics/maintenance.md +++ b/docs/topics/maintenance.md @@ -127,3 +127,78 @@ Typhoon supports multi-controller clusters, so it is possible to upgrade a clust !!! warning Typhoon does not support or document node replacement as an upgrade strategy. It limits Typhoon's ability to make infrastructure and architectural changes between tagged releases. +## Terraform v0.11.x + +Terraform v0.10.x to v0.11.x introduced breaking changes in the provider and module inheritance relationship that you MUST be aware of when upgrading to the v0.11.x `terraform` binary. Terraform now allows multiple named (i.e. aliased) copies of a provider to exist (e.g `aws.default`, `aws.somename`). Terraform now also requires providers be explicitly passed to modules in order to satisfy module version contraints (which Typhoon modules define). Full details can be found in [typhoon#77](https://github.com/poseidon/typhoon/issues/77) and [hashicorp#16824](https://github.com/hashicorp/terraform/issues/16824). + +In particular, after upgrading to the v0.11.x `terraform` binary, you'll notice: + +* `terraform plan` does not succeed and prompts for variables when it didn't before +* `terraform plan` does not succeed and mentions "provider configuration block is required for all operations" +* `terraform apply` fails when you comment or remove a module usage in order to delete a cluster + +### New users + +New users can start with Terraform v0.11.x and follow the Typhoon docs without issue. + +### Existing + +Users who used modules to create clusters with Terraform v0.10.x and still manage those clusters via Terraform must explicitly add each provider used in `provider.tf`: + +``` +provider "local" { + version = "~> 1.0" + alias = "default" +} + +provider "null" { + version = "~> 1.0" + alias = "default" +} + +provider "template" { + version = "~> 1.0" + alias = "default" +} + +provider "tls" { + version = "~> 1.0" + alias = "default" +} +``` + +Modify the `google`, `aws`, or `digitalocean` provider section to specify an explicit `alias` name. + +``` +provider "digitalocean" { + version = "0.1.2" + token = "${chomp(file("~/.config/digital-ocean/token"))}" + alias = "default" +} +``` + +!!! note + In these examples, we've chosen to name each provider "default", though the point of the Terraform changes is that other possibilities are possible. + +Edit each instance (i.e. usage) of a module and explicitly pass the providers. + +``` +module "aws-cluster" { + source = "git::https://github.com/poseidon/typhoon//aws/container-linux/kubernetes" + + providers = { + aws = "aws.default" + local = "local.default" + null = "null.default" + template = "template.default" + tls = "tls.default" + } + + cluster_name = "somename" +``` + +Re-run `terraform plan`. Plan will claim there are no changes to apply. Run `terraform apply` anyway as this will update Terraform state to be aware of the explicit provider versions. + +### Verify + +You should now be able to run `terraform plan` without errors. When you choose, you may comment or delete a module from Terraform configs and `terraform apply` should destroy the cluster correctly.