From fde275e5a671f414e87049214575c72bbff6026e Mon Sep 17 00:00:00 2001 From: Ivan Diachenko Date: Mon, 23 Dec 2024 16:53:05 +0300 Subject: [PATCH 1/3] feat(scaffold): add template path arg to scaffold resources command --- internal/cmd/scaffold_resource.go | 5 ++++- internal/scaffold/resource.go | 16 ++++++++++++++-- 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/internal/cmd/scaffold_resource.go b/internal/cmd/scaffold_resource.go index a8f8d3be..95e07e25 100644 --- a/internal/cmd/scaffold_resource.go +++ b/internal/cmd/scaffold_resource.go @@ -26,6 +26,7 @@ type ScaffoldResourceCommand struct { flagOutputFile string flagPackageName string flagForceOverwrite bool + flagTemplatePath string } func (cmd *ScaffoldResourceCommand) Flags() *flag.FlagSet { @@ -36,6 +37,8 @@ func (cmd *ScaffoldResourceCommand) Flags() *flag.FlagSet { fs.StringVar(&cmd.flagOutputDir, "output-dir", ".", "directory path to output scaffolded code file") fs.StringVar(&cmd.flagOutputFile, "output-file", "", "file name and extension to write scaffolded code to, default will use the --name flag with '_resource.go' suffix") fs.StringVar(&cmd.flagPackageName, "package", "provider", "name of Go package for scaffolded code file") + fs.StringVar(&cmd.flagTemplatePath, "template", "", "path to template file for scaffolded code file") + return fs } @@ -110,7 +113,7 @@ func (cmd *ScaffoldResourceCommand) runInternal(_ context.Context) error { return fmt.Errorf("'%s' is not a valid Terraform resource identifier", cmd.flagResourceNameSnake) } - goBytes, err := scaffold.ResourceBytes(resourceIdentifier, cmd.flagPackageName) + goBytes, err := scaffold.ResourceBytes(resourceIdentifier, cmd.flagPackageName, cmd.flagTemplatePath) if err != nil { return fmt.Errorf("error creating scaffolding resource Go code: %w", err) } diff --git a/internal/scaffold/resource.go b/internal/scaffold/resource.go index 2b478da8..580a7575 100644 --- a/internal/scaffold/resource.go +++ b/internal/scaffold/resource.go @@ -5,14 +5,26 @@ package scaffold import ( "bytes" + "os" "text/template" "github.com/hashicorp/terraform-plugin-codegen-framework/internal/schema" ) // ResourceBytes will create scaffolding Go code bytes for a Terraform Plugin Framework resource -func ResourceBytes(resourceIdentifier schema.FrameworkIdentifier, packageName string) ([]byte, error) { - t, err := template.New("resource_scaffold").Parse(resourceScaffoldGoTemplate) +func ResourceBytes(resourceIdentifier schema.FrameworkIdentifier, packageName, templatePath string) ([]byte, error) { + templateStr := resourceScaffoldGoTemplate + + if templatePath != "" { + file, err := os.ReadFile(templatePath) + if err != nil { + return nil, err + } + + templateStr = string(file) + } + + t, err := template.New("resource_scaffold").Parse(templateStr) if err != nil { return nil, err } From e6331749cb84f79796ef3d77fce03d7e5ef16a0f Mon Sep 17 00:00:00 2001 From: Ivan Diachenko Date: Thu, 26 Dec 2024 19:04:21 +0300 Subject: [PATCH 2/3] feat(scaffold): add template path arg to scaffold resources command --- internal/cmd/generate_resources.go | 2 +- internal/cmd/scaffold_resource.go | 2 +- internal/scaffold/resource.go | 2 ++ internal/schema/framework_identifier.go | 7 +++++++ 4 files changed, 11 insertions(+), 2 deletions(-) diff --git a/internal/cmd/generate_resources.go b/internal/cmd/generate_resources.go index 4630ecad..1bad05d9 100644 --- a/internal/cmd/generate_resources.go +++ b/internal/cmd/generate_resources.go @@ -78,7 +78,7 @@ func (cmd *GenerateResourcesCommand) Help() string { return strBuilder.String() } -func (a *GenerateResourcesCommand) Synopsis() string { +func (cmd *GenerateResourcesCommand) Synopsis() string { return "Generate code for resources from an Intermediate Representation (IR) JSON file." } diff --git a/internal/cmd/scaffold_resource.go b/internal/cmd/scaffold_resource.go index 95e07e25..0938d09b 100644 --- a/internal/cmd/scaffold_resource.go +++ b/internal/cmd/scaffold_resource.go @@ -80,7 +80,7 @@ func (cmd *ScaffoldResourceCommand) Help() string { return strBuilder.String() } -func (a *ScaffoldResourceCommand) Synopsis() string { +func (cmd *ScaffoldResourceCommand) Synopsis() string { return "Create scaffolding code for a Terraform Plugin Framework resource." } diff --git a/internal/scaffold/resource.go b/internal/scaffold/resource.go index 580a7575..957c0ffb 100644 --- a/internal/scaffold/resource.go +++ b/internal/scaffold/resource.go @@ -36,11 +36,13 @@ func ResourceBytes(resourceIdentifier schema.FrameworkIdentifier, packageName, t NameSnake string NameCamel string NamePascal string + NameKebab string }{ PackageName: packageName, NameSnake: string(resourceIdentifier), NameCamel: resourceIdentifier.ToCamelCase(), NamePascal: resourceIdentifier.ToPascalCase(), + NameKebab: resourceIdentifier.ToKebabCase(), } err = t.Execute(&buf, templateData) diff --git a/internal/schema/framework_identifier.go b/internal/schema/framework_identifier.go index 7488c1f4..4a88dd08 100644 --- a/internal/schema/framework_identifier.go +++ b/internal/schema/framework_identifier.go @@ -91,6 +91,13 @@ func (identifier FrameworkIdentifier) ToPrefixPascalCase(prefix string) string { return pascalCase } +// ToKebabCase will return kebab case formatted string of the identifier. +// Example: +// - example_resource_thing -> example-resource-thing +func (identifier FrameworkIdentifier) ToKebabCase() string { + return strings.ReplaceAll(identifier.ToString(), "_", "-") +} + // ToString returns the FrameworkIdentifier as a string without any formatting. // Example: // - example_resource_thing -> example_resource_thing From 3631701693d7428b88d507d5d88fc3aceccd7819 Mon Sep 17 00:00:00 2001 From: Ivan Diachenko Date: Sat, 28 Dec 2024 12:25:28 +0300 Subject: [PATCH 3/3] feat(scaffold): add template path arg to scaffold data-source command --- internal/cmd/scaffold_data_source.go | 7 +++++-- internal/scaffold/data_source.go | 16 ++++++++++++++-- 2 files changed, 19 insertions(+), 4 deletions(-) diff --git a/internal/cmd/scaffold_data_source.go b/internal/cmd/scaffold_data_source.go index f652ec72..770d53e0 100644 --- a/internal/cmd/scaffold_data_source.go +++ b/internal/cmd/scaffold_data_source.go @@ -26,6 +26,7 @@ type ScaffoldDataSourceCommand struct { flagOutputFile string flagPackageName string flagForceOverwrite bool + flagTemplatePath string } func (cmd *ScaffoldDataSourceCommand) Flags() *flag.FlagSet { @@ -36,6 +37,8 @@ func (cmd *ScaffoldDataSourceCommand) Flags() *flag.FlagSet { fs.StringVar(&cmd.flagOutputDir, "output-dir", ".", "directory path to output scaffolded code file") fs.StringVar(&cmd.flagOutputFile, "output-file", "", "file name and extension to write scaffolded code to, default will use the --name flag with '_data_source.go' suffix") fs.StringVar(&cmd.flagPackageName, "package", "provider", "name of Go package for scaffolded code file") + fs.StringVar(&cmd.flagTemplatePath, "template", "", "path to template file for scaffolded code file") + return fs } @@ -77,7 +80,7 @@ func (cmd *ScaffoldDataSourceCommand) Help() string { return strBuilder.String() } -func (a *ScaffoldDataSourceCommand) Synopsis() string { +func (cmd *ScaffoldDataSourceCommand) Synopsis() string { return "Create scaffolding code for a Terraform Plugin Framework data source." } @@ -110,7 +113,7 @@ func (cmd *ScaffoldDataSourceCommand) runInternal(_ context.Context) error { return fmt.Errorf("'%s' is not a valid Terraform data source identifier", cmd.flagDataSourceNameSnake) } - goBytes, err := scaffold.DataSourceBytes(dataSourceIdentifier, cmd.flagPackageName) + goBytes, err := scaffold.DataSourceBytes(dataSourceIdentifier, cmd.flagPackageName, cmd.flagTemplatePath) if err != nil { return fmt.Errorf("error creating scaffolding data source Go code: %w", err) } diff --git a/internal/scaffold/data_source.go b/internal/scaffold/data_source.go index b4c67435..d88b7076 100644 --- a/internal/scaffold/data_source.go +++ b/internal/scaffold/data_source.go @@ -5,14 +5,26 @@ package scaffold import ( "bytes" + "os" "text/template" "github.com/hashicorp/terraform-plugin-codegen-framework/internal/schema" ) // DataSourceBytes will create scaffolding Go code bytes for a Terraform Plugin Framework data source -func DataSourceBytes(dataSourceIdentifier schema.FrameworkIdentifier, packageName string) ([]byte, error) { - t, err := template.New("data_source_scaffold").Parse(dataSourceScaffoldGoTemplate) +func DataSourceBytes(dataSourceIdentifier schema.FrameworkIdentifier, packageName, templatePath string) ([]byte, error) { + templateStr := dataSourceScaffoldGoTemplate + + if templatePath != "" { + file, err := os.ReadFile(templatePath) + if err != nil { + return nil, err + } + + templateStr = string(file) + } + + t, err := template.New("data_source_scaffold").Parse(templateStr) if err != nil { return nil, err }