-
-
Notifications
You must be signed in to change notification settings - Fork 1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Remove need for "backend" block in Terraform modules. #230
Comments
@josh-padnick Glad you created an issue for this, as I am running into it while creating some example configurations for #169. The discussion came up in that thread in this comment, where @brikis98 suggested exposing variables that you can use to change the configuration of the S3 backend. However, to make sure I follow your suggestion, you're saying that the larger problem is that Can you explain more your idea to "auto-generate a boilerplate Terraform template that calls the original module"? Here are my thoughts on a potential solution (not sure if it is the same as your idea or not). Basically, I think that because the root live/terraform.tfvars: terragrunt = {
terraform {
# The root terraform.tfvars file configures the backend, which should
# be used as the default for all child environments and modules
remote_state {
backend = "s3"
config {
bucket = "terragrunt-examples-remote-state"
key = "${path_relative_to_include()}/terraform.tfstate"
region = "us-east-1"
encrypt = true
lock_table = "terragrunt-examples-lock-table"
}
}
}
} live/staging/my-module/terraform.tfvars: terragrunt = {
# Load the root terraform.tfvars file to get the default backend configuration
include {
path = "${find_in_parent_folders()}"
}
terraform {
# The environment terraform.tfvars file tell Terragrunt
# where to load the Terraform source.
source = "/my-module/"
# If we defined a remote_state here, it would override the default
# configuration defined in the root terraform.tfvars. For example,
# we could switch backends entirely and have this module use
# Consul instead of S3 for some reason, but it would still execute
# the same exact Terraform module code.
}
}
key1 = val1
key2 = val2 /my-module/main.tf: # The actual Terraform module does not define a backend in its
# .tf files. This means that by default, it will use the local backend.
variable "key1" {}
variable "key2" {}
... /var/.../terragrunt-download/.../backend.tf: # Terragrunt could use the configuration that the user has already defined
# in the root terraform.tfvars file to generate this backend.tf file in the
# temporary directory in which Terraform actually runs.
# Notice that Terragrunt has already resolved the interpolation
# syntax and this file only contains final raw values.
# Terraform would concat this file with all other *.tf files in the directory
# during its run and use whichever backend was defined in this backend.tf file.
terraform {
backend "s3" {
bucket = "terragrunt-examples-remote-state"
key = "staging/my-module/terraform.tfvars"
region = "us-east-1"
encrypt = true
lock_table = "terragrunt-examples-lock-table"
}
} Currently, it looks like Terragrunt passes all of backend configuration via the CLI when calling Terraform. Thoughts on instead generating a |
If this issue is solved, then I think it would also resolve #212 |
@conorgil I think your understanding is spot on. I think it's a reasonable approach, with two reservations:
Thoughts? |
@brikis98 Great questions. I'll think on this more. Initial questions/responses below:
|
Yep. This was actually the "normal" way of using Terragrunt for most of its life! The support for downloading source code into a temporary folder was only added part of the way through :)
My hunch is that what we're seeing now of the |
Always interesting learning about a project after it has gone through some iterations. I did not realize that was the "normal" way of using Terragrunt historically. Though, now that I stopped to think and remembered that remote state locking was one of (if not the) primary feature for Terragrunt, it does kinda make sense that it could have been used inline for that. My initial thought is that the automatically generated file still seems like a good solution. It would be very easy to debug what Terragrunt is doing under the hood by inspecting that file. For users using remote source, they won't run into problems because of the temp directory. For users using local source, they would have to add it to their gitignore. This would be a pain for those users, but we could make the filename consistent to make it less painful. Also, given that Terraform now natively supports remote state locking and Terragrunt has correspondingly removed support for remote state locking (delegating to Terraform), do you think that using Terragrunt with local source is still a popular use-case? The "best practice" concepts outlined in #169 all favor a directory hierarchy that uses remote source as far as I can tell. Do you think that it is a reasonable stance to just say that as the tool has grown over time, remote source has emerged as the recommended best practice, so that we don't have to worry about legacy use-cases in this circumstance? Given, we'd need to provide a reasonable transition period for those types of things normally, but because there is an easy alternative (update .gitignore) it hopefully wouldn't be too painful in this case.
I agree that the backend will likely undergo lots of changes since it is new and Terraform seems pretty comfortable with breaking changes as long as they are documented well and users have a clear transition path. However, what I am not following is why the CLI and A good example of this happening just recently is actually hashicorp/terraform#14949, where they updated the S3 backend to replace the Thoughts? |
Yes, it is. Since Terraform's
Yes, but Terragrunt currently blindly copies all the keys in the |
Thanks for the background. Makes sense.
That makes sense. The file solution should be agnostic in the same way. It would just copy over the keys from the If a user already has defined a |
It's a bit more complicated. First, we'd have to check if the code already has a |
Fair point on the potential for multiple terraform {
required_version = "> 0.9.0"
}
terraform {
backend "s3" {
bucket = "some-other-bucket"
key = "some-other-key"
}
} yields an error:
So, that would seem to rule out the simple solution of just generating a However, I think that the CLI approach will require scanning the Terraform code as well. The following terraform { } and then running the command:
works without error, but does not write anything to However, the following terraform {
backend "s3" {
bucket = "some-bucket"
key = "some-key"
}
} and then running the command:
works without error and writes the following "backend": {
"type": "s3",
"config": {
"bucket": "some-command-line-bucket",
"key": "some-command-line-key",
"region": "us-east-1"
}
} Therefore, I believe that Terraform requires a Implementing a solution for this issue is definitely trickier than I initially thought. Glad we're talking it through and getting ideas and details written down to figure out the best solution (which I am unsure of at this point)! |
Ah, good to know.
Yes, it does, and it's in our documentation that you have to define a
Indeed. The CLI solution isn't great, but it's workable for now. My vote is to wait and see how the |
Sounds good |
As of #302, Terragrunt now checks if a |
One of the most common issues that Terragrunt users experience is that the "topmost" module that is called from your
terraform.tfvars
file is expected to have abackend
block:terraform.tfvars:
/my-module/main.tf:
In theory, a module should be unopinionated about which backend it implements and the calling code should express this opinion. In practice, Terragrunt works by copying the module to a temp directory and filling in the vars automatically, so it needs a
backend
block to "hook into".An alternative way to implement this is to auto-generate a boilerplate Terraform template that calls the original module, but @brikis98 had a concern that we'd be forever playing catch-up to frequently changing Terraform code.
I don't currently agree with that argument, but it's still non-trivial to update Terragrunt to auto-generate new code, so for now, I just wanted to record the issue and let users know this is just about the most common issue we encounter with users.
The text was updated successfully, but these errors were encountered: