Set up the Teleport Terraform Provider
This guide demonstrates how to set up the Terraform provider for Teleport on Linux and macOS.
Terraform is intended to be used with Machine ID, Teleport's feature for providing identities to machines and services, rather than users. This tutorial will show you how to use a local Machine ID bot to try it out.
For instructions on managing users and roles via Terraform, read the "Managing users and roles with IaC" guide.
For instructions on managing the Teleport dynamic resources as code using GitOps, read the guide to using the Teleport Terraform provider with Spacelift and Machine ID.
Prerequisites
-
A running Teleport cluster version 15.4.22 or above. If you want to get started with Teleport, sign up for a free trial or set up a demo environment.
-
The
tctl
admin tool andtsh
client tool.On Teleport Enterprise, you must use the Enterprise version of
tctl
, which you can download from your Teleport account workspace. Otherwise, visit Installation for instructions on downloadingtctl
andtsh
for Teleport Community Edition.
-
$ terraform version
# Terraform v1.0.0To import existing Teleport resources as Terraform resources, you must have Terraform version
v1.5.0
or above. -
To check that you can connect to your Teleport cluster, sign in with
tsh login
, then verify that you can runtctl
commands using your current credentials.tctl
is supported on macOS and Linux machines.For example:
$ tsh login --proxy=teleport.example.com [email protected]
$ tctl status
# Cluster teleport.example.com
# Version 15.4.22
# CA pin sha256:abdc1245efgh5678abdc1245efgh5678abdc1245efgh5678abdc1245efgh5678If you can connect to the cluster and run the
tctl status
command, you can use your current credentials to run subsequenttctl
commands from your workstation. If you host your own Teleport cluster, you can also runtctl
commands on the computer that hosts the Teleport Auth Service for full permissions.
Step 1/4. Create Teleport credentials for Terraform
Terraform needs a signed identity file from the Teleport cluster certificate authority to manage resources in the cluster. To prepare credentials using a local Teleport bot:
-
Create a folder called
teleport-terraform
to hold temporary files:$ mkdir -p teleport-terraform
$ cd teleport-terraform -
Terraform needs a Teleport role that gives it permission to manage your cluster's resources. The bot creates identity documents that have this role. Configure the necessary role by pasting the following content into a
terraform_role.yaml
file:kind: role
metadata:
name: terraform
spec:
allow:
db_labels:
'*': '*'
app_labels:
'*': '*'
node_labels:
'*': '*'
rules:
- resources:
- app
- cluster_auth_preference
- cluster_networking_config
- db
- device
- github
- login_rule
- oidc
- okta_import_rule
- role
- saml
- session_recording_config
- token
- trusted_cluster
- user
- access_list
- node
- installer
verbs: ['list','create','read','update','delete']
version: v7These settings configure a role named
terraform
with the permissions required to manage resources in your Teleport cluster. -
Create the
terraform
role by running the following command:$ tctl create terraform_role.yaml
role 'terraform' has been created -
Create two scripts that let you quickly and repeatably create and destroy our local Terraform bot. First, create a new file called
create_and_run_terraform_bot.sh
, open it in an editor, and paste in the following content:#! /usr/bin/env bash
TOKEN=$(tctl bots add terraform-test --roles=terraform --format=json | jq -r '.token_id')
tbot start \
--destination-dir=./terraform-identity \
--token="$TOKEN" \
--data-dir=./tbot-data \
--join-method=token \
--auth-server=tele.example.com:443
# Replace with the host and port of your Teleport Auth Service
# or Teleport Proxy ServiceWhen run, this creates a new bot with the token retrieved from the JSON output. That token is piped into the start command. For security reasons, we don't allow bot join tokens to be created in any way other than adding a bot, so for local development work, you must manually manage the bot and its token.
The bot manages its state data in a folder called
tbot-data
in the current working directory. -
Edit
create_and_run_terraform_bot.sh
to replacetele.example.com:443
with the domain name and port of the Teleport Proxy Service in your cluster. -
Create another file called
remove_terraform_bot.sh
, open it in an editor, and paste in the following content:#! /usr/bin/env bash
tctl bots rm terraform-test
rm -rfv ./terraform-identity
rm -rfv ./tbot-dataThis script will be used later to clean up our bot in between runs and when we're done.
-
In a new terminal window, run the
create_and_run_terraform_bot.sh
script to create the new bot and start it:$ chmod +x create_and_run_terraform_bot.sh
$ ./create_and_run_terraform_bot.sh
Step 2/4. Prepare a Terraform configuration file
To prepare a Terraform configuration file:
-
Create a new file called
provider.tf
and open it in an editor. -
Use the Teleport Terraform provider and connect it to your Teleport cluster by pasting the following content into the
provider.tf
file:- Cloud-Hosted
- Self-Hosted
terraform {
required_providers {
teleport = {
source = "terraform.releases.teleport.dev/gravitational/teleport"
version = "~> 15.0"
}
}
}
provider "teleport" {
# Update addr to point to your Teleport Cloud tenant URL's host:port
addr = "mytenant.teleport.sh:443"
identity_file_path = "terraform-identity/identity"
}
# creates a test role, if we don't declare resources, Terraform won't try to
# connect to Teleport and we won't be able to validate the setup.
resource "teleport_role" "test" {
version = "v7"
metadata = {
name = "test"
description = "Dummy role to validate Terraform Provider setup"
labels = {
test = "yes"
}
}
spec = {
}
}terraform {
required_providers {
teleport = {
source = "terraform.releases.teleport.dev/gravitational/teleport"
version = "~> 15.0"
}
}
}
provider "teleport" {
# Update addr to point to Teleport Auth/Proxy
# addr = "auth.example.com:3025"
addr = "proxy.example.com:443"
identity_file_path = "terraform-identity/identity"
}
# creates a test role, if we don't declare resources, Terraform won't try to
# connect to Teleport and we won't be able to validate the setup.
resource "teleport_role" "test" {
version = "v7"
metadata = {
name = "test"
description = "Dummy role to validate Terraform Provider setup"
labels = {
test = "yes"
}
}
spec = {
}
}
Step 3/4. Validate the configuration
To apply the configuration:
-
Check the contents of the
teleport-terraform
folder:$ ls
# provider.tf terraform-identity/ create_and_run_terraform_bot.sh remove_terraform_bot.sh terraform_role.yaml -
Initialize the working directory that contains Terraform configuration files by running the following command:
$ terraform init
-
Execute the Terraform plan defined in the configuration file by running the following command:
$ terraform apply
-
When you're done, use Ctrl-C to stop the Terraform bot. Then run the
remove_terraform_bot.sh
script to remove the bot and clean up theterraform-identity
folder:$ chmod +x remove_terraform_bot.sh
$ ./remove_terraform_bot.shIf you need to start the bot back up, you can run the two bot scripts as many times as necessary.
Step 4/4. [Optional] Import existing resources
This section shows you how to import existing dynamic Teleport resources as Terraform resources.
If you already created Teleport resources using another client tool like tctl
or the Kubernetes Operator, and want to manage all Teleport resources using your
Terraform configuration, follow these steps to generate a .tf
file that
contains resource
blocks that represent your existing Teleport resources.
By defining all Teleport resources in one place, you can help ensure that your cluster configuration matches your expectations.
Add an import
block
-
On your workstation, navigate to your root Teleport Terraform module.
-
Open a file in your text editor to configure Terraform imports. To keep your configuration tidy, open a new file called
imports.tf
. -
Add an
import
block toimports.tf
. Use theto
field to indicate the name of the resource you want to generate configuration for in Terraform. The following example imports a Teleport role calledmyrole
:import {
to = teleport_role.myrole
}
Retrieve the ID of your resource
-
Retrieve the ID of the resource. The method to use depends on the resource type. Use the following rules to do so:
If the resource is
teleport_provision_token
, the ID is themetadata.id
of the resource.If the resource can only have one instance, use the name of the resource type without the
teleport
prefix. For example:Resource ID teleport_cluster_maintenance_config
cluster_maintenance_config
teleport_cluster_networking_config
cluster_networking_config
For all other resources, the ID is always the
metadata.name
of the resource.For example, the
teleport_role
resource uses the role'smetadata.name
field for its ID. To find all possible role IDs, run the following command:$ tctl get roles --format json | jq '.[].metadata.name'
-
In the
import
block, assign theid
field to the resource ID you retrieved earlier. For example, to import a Teleport role with ametadata.name
ofmyrole
, add the following:import {
to = teleport_role.myrole
+ id = "myrole"
}
Generate a configuration file
-
Generate a resource configuration
$ terraform plan -generate-config-out=imported-resources.tf
-
Inspect the resulting file,
imported-resources.tf
. If the newresource
block looks correct, you can check the file into source control.
Next steps
- Follow the user and role IaC guide to use the Terraform Provider to create Teleport users and grant them roles.
- Explore the full list of supported Terraform provider resources.
- See how to use Machine ID with Terraform in production.