Hey Team,
I was working on writing terraform provider for one of our products. I was thinking of using codegen (tfplugingen-framwork). I did explore about it.
I wanted to check with you on best practices/suggestion.
We have two approaches here to think on, which is regarding the file/folder structure and go package.
So, Is it better to maintain a single package for all schema and Model struct generated (for all the resources) using tfplugingen-framework generate resources, and other package for the resources files generated using tfplugingen-framework scaffold resource?
OR
Other option would be to make a single package for the particular resource and than generate both resource file and schema file in the same package, but the issue/concern here is that, we have nearly 300 resources/endpoints, which can expand as well, So, this creates a lot of folders and packages to maintain.
Can you suggest us here on what is the best way?
Hey there @rohit-myali
,
Generally speaking, we (the TF DevEx team) currently donβt have a broad recommendation for how to structure code generation projects for terraform providers, as itβs still in tech preview and weβre actively researching how to build further on it, which may influence that recommendation.
More specifically, to the two approaches you provided, I would lean towards a project structure like option 1, which separates βgenerated codeβ (generate
command) from βmanually writtenβ (initially created with scaffold
command) code. That could be one generated package for all resources, or multiple generated packages for each resource, but the general rule of thumb there would be a package should either be entirely managed by a code generation process, or the package should be manually developed/managed (aided with the scaffold
command).
Our current default for code generation package structure creates one package per resource/data source, and the primary reason for that is naming conflicts. There are a lot of exported schema/types that may have similar names across resources, so itβs currently easiest for us to generate the resource schema/types in itβs own package vs. trying to understand the entire context and avoid naming conflicts in a βsmarterβ way.
If you combine that default with option 1, you could have one package that is βmanuallyβ maintained (containing resource files created via scaffold
) and then multiple packages (all under /internal/generated
) that are maintained by the code generation process:
.
βββ internal/
β βββ generated/
β β βββ resource_order/
β β β βββ order_resource_gen.go
β β βββ resource_pet/
β β βββ pet_resource_gen.go
β βββ order_resource.go (CRUD logic, consumes 'resource_order' package)
β βββ pet_resource.go (CRUD logic, consumes 'resource_pet' package)
β βββ provider.go (provider logic)
βββ generator_config.yml
βββ go.mod
βββ go.sum
βββ main.go
βββ openapi.json
βββ provider-code-spec.json
As we expand on the tech preview, there may be more opportunities to move logic from the manually maintained internal
package, to the internal/generated
packages. (like say, CRUD functionality implemented from a user-defined .gotmpl
file)
1 Like