gpt4 book ai didi

go - 无法将 terraform variables.tf 文件读入可能进入程序

转载 作者:行者123 更新时间:2023-12-05 08:48:01 26 4
gpt4 key购买 nike

我正在尝试编写一个 go 程序,该程序读取 terraform variables.tf 并填充一个结构供以后操作。但是,我在尝试“解析”文件时遇到错误。我希望有人能告诉我我做错了什么:

代码:

package main

import (
"fmt"
"io/ioutil"
"log"
"os"

"github.com/hashicorp/hcl/v2"
"github.com/hashicorp/hcl/v2/gohcl"
"github.com/hashicorp/hcl/v2/hclsyntax"
)

type Config struct {
Upstreams []*TfVariable `hcl:"variable,block"`
}

type TfVariable struct {
Name string `hcl:",label"`
// Default string `hcl:"default,optional"`
Type string `hcl:"type"`
Description string `hcl:"description,attr"`
// validation block
Sensitive bool `hcl:"sensitive,optional"`
}

func main() {
readHCLFile("examples/string.tf")
}

// Exits program by sending error message to standard error and specified error code.
func abort(errorMessage string, exitcode int) {
fmt.Fprintln(os.Stderr, errorMessage)
os.Exit(exitcode)
}

func readHCLFile(filePath string) {
content, err := ioutil.ReadFile(filePath)
if err != nil {
log.Fatal(err)
}

fmt.Printf("File contents: %s", content) // TODO: Remove me

file, diags := hclsyntax.ParseConfig(content, filePath, hcl.Pos{Line: 1, Column: 1})
if diags.HasErrors() {
log.Fatal(fmt.Errorf("ParseConfig: %w", diags))
}

c := &Config{}
diags = gohcl.DecodeBody(file.Body, nil, c)
if diags.HasErrors() {
log.Fatal(fmt.Errorf("DecodeBody: %w", diags))
}

fmt.Println(c) // TODO: Remove me
}

错误

File contents: variable "image_id" {
type = string
description = "The id of the machine image (AMI) to use for the server."
sensitive = false
}

variable "other_id" {
type = string
description = "The id of the machine image (AMI) to use for the server."
sensitive = true
}
2021/03/13 19:55:49 DecodeBody: examples/string.tf:2,17-23: Variables not allowed; Variables may not be used here., and 3 other diagnostic(s)
exit status 1

堆栈驱动程序 question可悲的是 hcl1

Blog post我在引用。

最佳答案

它看起来像是库的错误/功能,因为一旦您将 string 更改为 "string",例如,

variable "image_id" {
type = string
...

variable "image_id" {
type = "string"
...

gohcl.DecodeBody 成功。

---更新---

所以,他们确实在 Terraform 中使用了这个包,但是他们 custom-parse configs ,即,他们不使用 gohcl.DecodeBody。他们还custom-treat type 属性,使用 hcl.ExprAsKeyword(comparedescription)。正如您假设的那样,他们确实使用了 custom type对于 type,但通过自定义解析您不必这样做。

下面是一个工作示例:

package main

import (
"fmt"
"log"
"os"

"github.com/hashicorp/hcl/v2"
"github.com/hashicorp/hcl/v2/gohcl"
"github.com/hashicorp/hcl/v2/hclsyntax"
)

var (
configFileSchema = &hcl.BodySchema{
Blocks: []hcl.BlockHeaderSchema{
{
Type: "variable",
LabelNames: []string{"name"},
},
},
}

variableBlockSchema = &hcl.BodySchema{
Attributes: []hcl.AttributeSchema{
{
Name: "description",
},
{
Name: "type",
},
{
Name: "sensitive",
},
},
}
)

type Config struct {
Variables []*Variable
}

type Variable struct {
Name string
Description string
Type string
Sensitive bool
}

func main() {
config := configFromFile("examples/string.tf")
for _, v := range config.Variables {
fmt.Printf("%+v\n", v)
}
}

func configFromFile(filePath string) *Config {
content, err := os.ReadFile(filePath) // go 1.16
if err != nil {
log.Fatal(err)
}

file, diags := hclsyntax.ParseConfig(content, filePath, hcl.Pos{Line: 1, Column: 1})
if diags.HasErrors() {
log.Fatal("ParseConfig", diags)
}

bodyCont, diags := file.Body.Content(configFileSchema)
if diags.HasErrors() {
log.Fatal("file content", diags)
}

res := &Config{}

for _, block := range bodyCont.Blocks {
v := &Variable{
Name: block.Labels[0],
}

blockCont, diags := block.Body.Content(variableBlockSchema)
if diags.HasErrors() {
log.Fatal("block content", diags)
}

if attr, exists := blockCont.Attributes["description"]; exists {
diags := gohcl.DecodeExpression(attr.Expr, nil, &v.Description)
if diags.HasErrors() {
log.Fatal("description attr", diags)
}
}

if attr, exists := blockCont.Attributes["sensitive"]; exists {
diags := gohcl.DecodeExpression(attr.Expr, nil, &v.Sensitive)
if diags.HasErrors() {
log.Fatal("sensitive attr", diags)
}
}

if attr, exists := blockCont.Attributes["type"]; exists {
v.Type = hcl.ExprAsKeyword(attr.Expr)
if v.Type == "" {
log.Fatal("type attr", "invalid value")
}
}

res.Variables = append(res.Variables, v)
}
return res
}

为完整性添加,example/string.tf:

variable "image_id" {
type = string
description = "The id of the machine image (AMI) to use for the server."
sensitive = false
}

variable "other_id" {
type = string
description = "The id of the machine image (AMI) to use for the server."
sensitive = true
}

关于go - 无法将 terraform variables.tf 文件读入可能进入程序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66620096/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com