Apply\Destory Terraform modules via a simple REST API endpoint.
Apply\Destory Terraform modules via a simple REST API endpoint.
Github actions CI unit tests & auto dockerhub push status:
terraform apply
terraform destroy
terraform plan
terraform apply
or terraform destroy
command)terraform apply
command via the request body to scale services up\down as neededRunning Terraformize is as simple as running a docker container
docker run -d -p 80:80 -v /path/to/my/terraform/module/dir:/www/terraform_modules/ naorlivne/terraformize
Feel free to skip to the end of the document for a working example that will explain how to use Terraformize
Terraformize uses sane defaults but they can all be easily changed:
value | envvar | default value | notes |
---|---|---|---|
basic_auth_user | BASIC_AUTH_USER | None | Basic auth username to use |
basic_auth_password | BASIC_AUTH_PASSWORD | None | Basic auth password to use |
auth_token | AUTH_TOKEN | None | bearer token to use |
terraform_binary_path | TERRAFORM_BINARY_PATH | None | The path to the terraform binary, if None will use the default OS PATH to find it |
terraform_modules_path | TERRAFORM_MODULES_PATH | /www/terraform_modules | The path to the parent directory where all terraform module directories will be stored at as subdirs |
parallelism | PARALLELISM | 10 | The number of parallel resource operations |
rabbit_url_connection_string | RABBIT_URL_CONNECTION_STRING | None | The URL paramters string to connect to RabbitMQ with, if unset RabbitMQ will not be used and only API will be possible |
rabbit_read_queue | RABBIT_READ_QUEUE | terraformize_read_queue | Name of the queue to read messages from |
rabbit_reply_queue | RABBIT_REPLY_QUEUE | terraformize_reply_queue | Name of the queue to respond with the run result to |
CONFIG_DIR | /www/config | The path to the directory where configuration files are stored at | |
HOST | 0.0.0.0 | The IP for gunicorn to bind to | |
PORT | 80 | The port for gunicorn to bind to | |
WORKER_CLASS | sync | The gunicorn class to use | |
WORKERS | 1 | Number of gunicorn workers | |
THREADS | 1 | Number of gunicorn threads | |
PRELOAD | False | If gunicorn should preload the code | |
LOG_LEVEL | error | The log level for gunicorn | |
TIMEOUT | 600 | The timeout for gunicorn, if your terraform run takes longer you will need to increase it |
The easiest way to change a default value is to pass the envvar key\value to the docker container with the -e
cli arg but if you want you can also create a configuration file with the settings you wish (in whatever of the standard format you desire) & place it in the /www/config folder inside the container.
Most providers also allow setting their configuration access_keys\etc via envvars use -e
cli args to configure them is ideal as well but should you wish to configure a file you can also easily mount\copy it into the container as well.
Terraformize supports 3 authentication methods:
Authorization Basic your_user_pass_base64_combo
header with your_user_pass_base64_combo being the same as basic_auth_user
& basic_auth_password
configured in Terraformize Authorization Bearer your_token
header with your_token being the same as the auth_token
configured in Terraformizeterraform apply
for youterraform apply
as a JSON in the body of the message in the format of {"var_key1": "var_value1", "var_key2": "var_value2"}
terraform apply
ran but failed to make all needed modifications{"init_stdout": "...", "init_stderr": "...", "stderr": "...", "stdout": "..."}
with the stderr & stdout of the terraform apply
& terraform init
runwebhook
URL paramter with the address of the webhook terraformize will return a 202
HTTP code with a body of {{'request_uuid': 'ec743bc4-0724-4f44-9ad3-5814071faddx'}}
to the request then work behind the scene to run terraform in a non blocking way, to result of the terraform run will be sent to the webhook address you configured along with the UUID of the request for you to know which request said result related toterraform destroy
for youterraform destroy
as a JSON in the body of the message in the format of {"var_key1": "var_value1", "var_key2": "var_value2"}
terraform destroy
ran but failed to make all needed modifications{"init_stdout": "...", "init_stderr": "...", "stderr": "...", "stdout": "..."}
with the stderr & stdout of the terraform destroy
& terraform init
runwebhook
URL paramter with the address of the webhook terraformize will return a 202
HTTP code with a body of {{'request_uuid': 'ec743bc4-0724-4f44-9ad3-5814071faddx'}}
to the request then work behind the scene to run terraform in a non blocking way, to result of the terraform run will be sent to the webhook address you configured along with the UUID of the request for you to know which request said result related toterraform plan
for youterraform apply
as a JSON in the body of the message in the format of {"var_key1": "var_value1", "var_key2": "var_value2"}
terraform apply
ran but failed to plan all needed modifications{"init_stdout": "...", "init_stderr": "...", "stderr": "...", "stdout": "...", "exit_code": "0""}
with the stderr & stdout of the terraform apply
& terraform init
runwebhook
URL paramter with the address of the webhook terraformize will return a 202
HTTP code with a body of {{'request_uuid': 'ec743bc4-0724-4f44-9ad3-5814071faddx'}}
to the request then work behind the scene to run terraform in a non blocking way, to result of the terraform run will be sent to the webhook address you configured along with the UUID of the request for you to know which request said result related toif you prefer using RabbitMQ instead of the API then you’ll need to configure the rabbit_url_connection_string
(examples can be seen at https://pika.readthedocs.io/en/stable/examples/using_urlparameters.html#using-urlparameters), Terrafromize will then use 2 Queues on rabbit (defined at the rabbit_read_queue
& rabbit_reply_queue
params), you don’t have to create the queues manually, if need be they will be created.
Now all you need to do in order to have a terraform run is to publish a message to the rabbit_read_queue
with the following format:
{
"module_folder": "module_folder_name",
"workspace": "workspace_name",
"uuid": "unique_uuid_you_created_to_identify_the_request",
"run_type": "apply/destroy/plan",
"run_variables": {
"var_to_pass_to_terraform_key": "var_to_pass_to_terraform_value",
"another_var_to_pass_to_terraform_key": "another_var_to_pass_to_terraform_value"
}
}
Terraformize will then run terraform for you and will return the result of the terraform run to the rabbit_reply_queue
queue in the following format:
{
"uuid": "unique_uuid_you_created_to_identify_the_request",
"init_stdout": "...",
"init_stderr": "...",
"stderr": "...",
"stdout": "...",
"exit_code": 0
}
It’s up to you to ensure the uuid
you pass is indeed unique.
shell script
mkdir terraformize_test
cd
into the folder as we will be mounting it into the container from the parent folder in a couple of stepsNow we need a valid terraform configuration in it, if it works in terraform it will work with terraformize but for this example we will keep it simple with a single terraformize_test/test.tf
file:
resource "null_resource" "test" {
count = 1
}
variable "test_var" {
description = "an example variable"
default = "my_variable_default_value"
}
output "test" {
value = var.test_var
}
docker run -d -p 80:80 -v `pwd`:/www/terraform_modules naorlivne/terraformize
terraform apply
for us (notice how we are passing variables in the body):}’
"test_var": "hello-world"
}’
"test_var": "hello-world"
terrafrom destroy
for us):}’
"test_var": "hello-world"
}’
"test_var": "hello-world"