-
Notifications
You must be signed in to change notification settings - Fork 9.5k
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
Sort should retain length of list #31035
Comments
Hi @Nuru, Thanks for filing the request! It seems possible to update Given the example shown however, I would not use |
Considering the use case of sorting subnet IDs to avoid them churning over time, is it true that AWS guarantees that any new subnet ID issued will always be lexically greater than any previous one issued, or is it possible that a newly-added subnet ID might sort earlier than a preexisting one and thus end up creating the same problem here? Typically we'd advise dealing with this situation by assigning each subnet a locally-defined name specific to the configuration in addition to the ID assigned by the remote system, and then have Terraform track the instances by the local name instead of the remote name. The typical way to represent that would be for the input variable to be a mapping from local names to remote IDs: variable "subnet_ids" {
type = map(string)
}
resource "aws_route_table_association" "public" {
for_each = var.subnet_ids
subnet_id = each.value
# ...
} In this pattern the idea is for the caller of the module to name the subnets after something that makes sense in this context that is chosen statically in the configuration. A typical answer I've seen is to name them after availability zones, in the common case where there's a single subnet per availability zone. Another variant is to name them with compound strings like I suppose what you are doing here is effectively the same except you are setting the "local names" to instead be numeric indices representing the position of the subnets in a lexically-sorted list. That works as long as new items are always lexically greater than all that existed before, but that isn't true for all systems. (I don't know if it's true for AWS EC2.) I feel a bit torn here because on the surface it does seem reasonable to make Could the situation you have in mind potentially be handled using a map like I've shown above? |
Since I proposed opening this issue in a comment elsewhere, I want to be clear with others who might read this what exactly I was imagining we'd consider here. Imagine a value named tolist([
"subnet-abc123",
(known after apply),
"subnet-def456",
(known after apply),
(known after apply),
]) Today My proposition is that although we don't know what value each index in the resulting list will have, we do know how many indices there will be, which is a different way to say we know how long the result will be: it'll be the same length as the input list. So given that, would it be reasonable for tolist([ # (of string)
(known after apply),
(known after apply),
(known after apply),
(known after apply),
(known after apply),
]) Now At first blush this seems backward compatible to me because we've typically considered it okay for something previously unknown to start being known in a newer version, as long as it starts being known in a manner consistent with our usual rules about what known values are allowed to substitute for an unknown value placeholder. However, I've not considered it in detail yet, so I may be missing some edge cases that make this concerning. One thing that would be worth exploring is how this would behave if |
@apparentlymart wrote:
No, of course new subnet IDs likely will not fall lexicographically after existing ones, but that is not my concern. I want to address situations where the set of items remains stable but the order of items in the list does not. For example, AFAIK, given data "aws_subnets" "private" {
tags = {
"subnetType" = "private"
}
} the value (order of subnet IDs in the list) of { for i, v in data.aws_subnets.private.ids : i => v } which only solves the problem if I establish some order on the IDs. The easy way would be to sort them. Any other solution requires adding additional data to the solution, and such data is not always easily available. @jbardin said (paraphrasing)
Why is that? Why cannot |
@Nuru Sorry, I agree with the assessment here that a list of |
I'm going to lock this issue because it has been closed for 30 days ⏳. This helps our maintainers find and focus on the active issues. |
Current Terraform Version
Use-cases
Given a list of items, e.g. subnet IDs, I want to create a corresponding list of resources, e.g. route tables. Since the subnet IDs will not be known at plan time, this will not work:
OK, I understand, the key values are unknown, so then I switch to
which works, but now every time the order of the list of subnets changes (which may be generated by an API beyond my control), all the route table associations change. I want to keep the associations consistent as long as the set of subnet IDs remains the same (which is what I was attempting with
for_each
), so I try sorting the list:Unfortunately, this breaks, too.
Proposal
It appears that at present,
sort
returns a list of unknown length. It should return a list of known length of unknown values.References
#30937 (comment)
The text was updated successfully, but these errors were encountered: