Closed rhoriguchi closed 9 months ago
We have the prefix and hash to avoid ID conflicts within a cdktf stack. Within a construct scope all IDs need to unique (a construct requirement), even if the type differs. For terraform there can not be the same resource name for the same resource type in the entire stack (they would just overwrite one another). This means the requirement for cdktf is to have these both combined, leading to the hashing and prefixing we do. With the current solution there are no ways to mess up, the default is easy.
I can see this being a problem with refactoring constructs into stacks, for this we propose using move blocks to change the resource addresses within terraform to the new name.
Another alternative would be to use overrideLogicalId
to set the name on the resources manually, this could even be done by extending the class, e.g.
class FixedNameS3Bucket extends S3Bucket {
constructor(scope: Construct, name: string, options: S3BucketOptions) {
super(scope, name, options);
this.overrideLogicalId(name);
}
}
Yet another alternative if you want to go all in with this would be to extend TerraformStack
and provide your own allocateLogicalId
function. It should work if you are in Typescript, but you are definitely leaving the supported area of use.
I think adding this override will make it more likely for users to run into issues that the current solution solves quite nicely. It is unlikely we will support the option out of the box.
I was nerd-sniped by Daniels answer and initially wanted to try whether an Aspect could also be used here (tl;dr: it can't be used).
However, overriding Stack#getLogicalId
seemed to be the simplest solution:
class MyStack extends TerraformStack {
getLogicalId(tfElement: TerraformElement): string {
return tfElement.node.id;
}
constructor(scope: Construct, id: string) {
super(scope, id);
new RandomProvider(this, "random", {});
new TerraformOutput(this, "global-output", {
value: "global-output",
});
new Pet(this, "global-pet", {});
new NestedConstruct(this, "nested-construct");
}
}
Note: As Daniel alluded to, constructs need unique ids, so this requires globally unique names for the Terraform resources and does not support having two resources with a different type share the same name (which Terraform supports).
Thank you for the solutions. I've also tried to solve it with aspects but that sadly does not work. The solution from @ansgarm works greate in our case. This issue can be closed, if this is not planed to be implemented. But maybe document it somewhere, so users know this is a possible solution to get "raw" ids.
That's great to hear, @rhoriguchi! Closing this issue then 👍
Given it's not an officially supported workflow, I don't think we would put it in our docs at this point in time. However, this issue will hopefully turn up for folks that are encountering this problem in the future!
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. If you've found a problem that seems similar to this, please open a new issue and complete the issue template so we can capture all the details necessary to investigate further.
Description
A global setting to enable static terraform resource IDs for all constructs and sub constructs in a stack, using the explicitly set ID in the constructor with no hash and not prefixing it with the parrent constructs ID.
Without this feature it's practically impossible to refactor CDK code down the road specialy when adding nested constructs.
In contrast to #329 a feature that does this for all sub constructs and not only on stack level and for direct subconstructs would be usefull.
References
329
Help Wanted
Community Note