resource-generator: SubParams → nested SingleNestedAttribute/ListNestedAttribute + bump 5.0.73
This commit is contained in:
@@ -190,3 +190,131 @@ func PlanModifierExpr(p types.Param) string {
|
||||
return "stringplanmodifier.RequiresReplace()"
|
||||
}
|
||||
}
|
||||
|
||||
// ─── Nested (map-fixed) helpers ──────────────────────────────────────────────
|
||||
|
||||
// IsNested возвращает true для параметров с SubParams (map-fixed/array-map-fixed).
|
||||
func IsNested(p types.Param) bool {
|
||||
return p.IsNested
|
||||
}
|
||||
|
||||
// IsNestedList возвращает true для array-map-fixed (список объектов).
|
||||
func IsNestedList(p types.Param) bool {
|
||||
return p.IsNested && strings.Contains(strings.ToLower(p.Type), "array")
|
||||
}
|
||||
|
||||
// NestedModelName возвращает имя вложенного Go-struct для ресурса и параметра.
|
||||
// Например: NestedModelName("postgres", "cluster_configuration") → "PostgresClusterConfigurationModel"
|
||||
func NestedModelName(resourceName, paramCode string) string {
|
||||
return ToCamel(resourceName) + ToCamel(paramCode) + "Model"
|
||||
}
|
||||
|
||||
// NestedTfType возвращает Go-тип для вложенного поля в Model:
|
||||
// *PostgresClusterConfigurationModel (SingleNestedAttribute) или
|
||||
// []PostgresClusterConfigurationModel (ListNestedAttribute — array-map-fixed).
|
||||
func NestedTfType(p types.Param, resourceName string) string {
|
||||
name := NestedModelName(resourceName, p.Code)
|
||||
if IsNestedList(p) {
|
||||
return "[]" + name
|
||||
}
|
||||
return "*" + name
|
||||
}
|
||||
|
||||
// NestedSchemaType возвращает тип схемы для nested параметра:
|
||||
// "SingleNested" (map-fixed) или "ListNested" (array-map-fixed).
|
||||
func NestedSchemaType(p types.Param) string {
|
||||
if IsNestedList(p) {
|
||||
return "ListNested"
|
||||
}
|
||||
return "SingleNested"
|
||||
}
|
||||
|
||||
// NestedSchemaBlock генерирует открывающую строку для nested-атрибута в Schema.
|
||||
func NestedSchemaBlock(p types.Param) string {
|
||||
t := NestedSchemaType(p)
|
||||
switch t {
|
||||
case "ListNested":
|
||||
return fmt.Sprintf("schema.%sAttribute{Optional: true,\n\t\t\tNestedObject: schema.NestedAttributeObject{Attributes: map[string]schema.Attribute{", t)
|
||||
default:
|
||||
req := "Required: true"
|
||||
if p.Default != "" {
|
||||
req = "Optional: true, Computed: true"
|
||||
}
|
||||
return fmt.Sprintf("schema.%sAttribute{%s,\n\t\t\tAttributes: map[string]schema.Attribute{", t, req)
|
||||
}
|
||||
}
|
||||
|
||||
// NestedSchemaEnd возвращает закрывающую строку для nested-атрибута.
|
||||
func NestedSchemaEnd(p types.Param) string {
|
||||
t := NestedSchemaType(p)
|
||||
if t == "ListNested" {
|
||||
return "}},"
|
||||
}
|
||||
return "},"
|
||||
}
|
||||
|
||||
// SubSchemaType возвращает тип схемы для подпараметра.
|
||||
func SubSchemaType(p types.Param) string {
|
||||
switch strings.ToLower(p.Type) {
|
||||
case "bool":
|
||||
return "Bool"
|
||||
case "int64", "int", "number":
|
||||
return "Int64"
|
||||
default:
|
||||
return "String"
|
||||
}
|
||||
}
|
||||
|
||||
// SubDefaultExpr возвращает выражение default для подпараметра.
|
||||
// ⚠️ Только Optional+Computed (Required несовместим с Default во фреймворке).
|
||||
func SubDefaultExpr(p types.Param) string {
|
||||
if p.Default == "" {
|
||||
return ""
|
||||
}
|
||||
switch strings.ToLower(p.Type) {
|
||||
case "bool":
|
||||
return fmt.Sprintf("booldefault.StaticBool(%s)", strings.ToLower(p.Default))
|
||||
case "int64", "int", "number":
|
||||
return fmt.Sprintf("int64default.StaticInt64(%s)", p.Default)
|
||||
default:
|
||||
return fmt.Sprintf("stringdefault.StaticString(%q)", p.Default)
|
||||
}
|
||||
}
|
||||
|
||||
// SubParamFormat возвращает JSON-ключ:значение для форматирования подпараметра.
|
||||
func SubParamFormat(p types.Param, varPrefix string) string {
|
||||
varName := varPrefix + "." + ToCamel(p.Code)
|
||||
switch strings.ToLower(p.Type) {
|
||||
case "bool":
|
||||
return fmt.Sprintf(`"%s": `+varName+`.ValueBool()`, p.Code)
|
||||
case "int64", "int", "number":
|
||||
return fmt.Sprintf(`"%s": %s `+varName+`.ValueInt64()`, p.Code, "%s")
|
||||
default:
|
||||
return fmt.Sprintf(`"%s": `+varName+`.ValueString()`, p.Code)
|
||||
}
|
||||
}
|
||||
|
||||
// NestedJSONExpr возвращает выражение для сборки JSON из nested struct через resources_core.BuildJSON.
|
||||
// BuildJSON принимает map[string]string где ключи — имена полей,
|
||||
// значения — уже отформатированные строки (числа без кавычек, строки с кавычками).
|
||||
// Пример: resources_core.BuildJSON(map[string]string{"cpu": "500", "name": "\"hello\""}) → {"cpu":500,"name":"hello"}
|
||||
func NestedJSONExpr(p types.Param, varName string) string {
|
||||
pairs := make([]string, 0, len(p.SubParams))
|
||||
for _, sp := range p.SubParams {
|
||||
field := varName + "." + ToCamel(sp.Code)
|
||||
var valExpr string
|
||||
switch strings.ToLower(sp.Type) {
|
||||
case "bool":
|
||||
// BuildJSON ожидает "true"/"false" (без кавычек)
|
||||
valExpr = fmt.Sprintf(`fmt.Sprintf("%%v", %s.ValueBool())`, field)
|
||||
case "int64", "int", "number":
|
||||
// BuildJSON ожидает "500" (без кавычек)
|
||||
valExpr = fmt.Sprintf(`fmt.Sprintf("%%d", %s.ValueInt64())`, field)
|
||||
default:
|
||||
// BuildJSON ожидает "\"hello\"" (с кавычками)
|
||||
valExpr = fmt.Sprintf(`fmt.Sprintf("\"%%s\"", %s.ValueString())`, field)
|
||||
}
|
||||
pairs = append(pairs, fmt.Sprintf(`"%s": %s`, sp.Code, valExpr))
|
||||
}
|
||||
return fmt.Sprintf("resources_core.BuildJSON(map[string]string{%s})", strings.Join(pairs, ", "))
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user