editor php Youzi mengajar anda cara menggunakan skrip Golang untuk mengubah suai nilai dalam fail Terraform (format HCL). Terraform ialah alat infrastruktur sebagai kod yang membantu kami mengurus dan mengautomasikan infrastruktur awan. Walau bagaimanapun, jika kita perlu kerap mengubah suai nilai tertentu dalam fail Terraform, operasi manual akan menjadi sangat membosankan. Oleh itu, menggunakan skrip Golang untuk mengubah suai nilai dalam fail Terraform akan menjadi kaedah yang lebih cekap. Dalam artikel ini, saya akan menunjukkan kepada anda cara menulis skrip menggunakan Golang untuk mencapai ini, supaya anda boleh mengubah suai nilai dengan mudah dalam fail Terraform.
Saya cuba melakukan sedikit automasi pada fail terraform yang saya ada yang mentakrifkan kumpulan keselamatan rangkaian biru. Pada asasnya, saya mempunyai laman web dan akses ssh, saya hanya mahu membenarkan alamat ip awam saya, yang boleh saya akses daripada nilai icanhazip.com
获取该地址。我希望使用 golang 脚本将我的 ip 写入 .tf 文件的相关部分(本质上是设置 security_rule.source_address_prefixes
).
Saya cuba menggunakan hclsimple
库,并尝试了 gohcl
、hclwrite
dan lain-lain dalam golang tetapi pada asasnya saya tidak membuat sebarang kemajuan dalam menukar fail hcl kepada struktur golang.
Fail terraform saya (dalam format hcl saya percaya) kelihatan seperti ini:
resource "azurerm_network_security_group" "my_nsg" { name = "my_nsg" location = "loc" resource_group_name = "rgname" security_rule = [ { access = "deny" description = "desc" destination_address_prefix = "*" destination_address_prefixes = [] destination_application_security_group_ids = [] destination_port_range = "" destination_port_ranges = [ "123", "456", "789", "1001", ] direction = "inbound" name = "allowinboundthing" priority = 100 protocol = "*" source_address_prefix = "*" source_address_prefixes = [ # obtain from icanhazip.com "1.2.3.4" ] source_application_security_group_ids = [] source_port_range = "*" source_port_ranges = [] }, { access = "allow" description = "grant acccess to app" destination_address_prefix = "*" destination_address_prefixes = [] destination_application_security_group_ids = [] destination_port_range = "" destination_port_ranges = [ "443", "80", ] direction = "inbound" name = "allowipinbound" priority = 200 protocol = "*" source_address_prefix = "" source_address_prefixes = [ # obtain from icanhazip.com "1.2.3.4" ] source_application_security_group_ids = [] source_port_range = "*" source_port_ranges = [] } ] }
Inilah yang saya dapat dengan skrip golang saya yang cuba mewakili data di atas sebagai struktur dan kemudian menyahkod fail .tf itu sendiri (saya menyalin beberapa kaedah secara setempat daripada hclsimple
agar ia menyahkod .tf seperti yang dicadangkan dalam dokumentasinya Dokumen
package main import ( "fmt" "io" "io/ioutil" "log" "os" "path/filepath" "strings" "github.com/hashicorp/hcl/v2" "github.com/hashicorp/hcl/v2/gohcl" "github.com/hashicorp/hcl/v2/hclsimple" "github.com/hashicorp/hcl/v2/hclsyntax" "github.com/hashicorp/hcl/v2/json" ) type config struct { networksecuritygroup []networksecuritygroup `hcl:"resource,block"` } type networksecuritygroup struct { type string `hcl:"azurerm_network_security_group,label"` name string `hcl:"mick-linux3-nsg,label"` nameattr string `hcl:"name"` location string `hcl:"location"` resourcegroupname string `hcl:"resource_group_name"` securityrule []securityrule `hcl:"security_rule,block"` } type securityrule struct { access string `hcl:"access"` description string `hcl:"description"` destinationaddressprefix string `hcl:"destination_address_prefix"` destinationaddressprefixes []string `hcl:"destination_address_prefixes"` destinationapplicationsecuritygroupids []string `hcl:"destination_application_security_group_ids"` destinationportrange string `hcl:"destination_port_range"` destinationportranges []string `hcl:"destination_port_ranges"` direction string `hcl:"direction"` name string `hcl:"name"` priority int `hcl:"priority"` protocol string `hcl:"protocol"` sourceaddressprefix string `hcl:"source_address_prefix"` sourceaddressprefixes []string `hcl:"source_address_prefixes"` sourceapplicationsecuritygroupids []string `hcl:"source_application_security_group_ids"` sourceportrange string `hcl:"source_port_range"` sourceportranges []string `hcl:"source_port_ranges"` } func main() { // lets pass this in as a param? configfilepath := "nsg.tf" // create new config struct var config config // this decodes the tf file into the config struct, and hydrates the values err := mydecodefile(configfilepath, nil, &config) if err != nil { log.fatalf("failed to load configuration: %s", err) } log.printf("configuration is %#v", config) // let's read in the file contents file, err := os.open(configfilepath) if err != nil { fmt.printf("failed to read file: %v\n", err) return } defer file.close() // read the file and output as a []bytes bytes, err := io.readall(file) if err != nil { fmt.println("error reading file:", err) return } // parse, decode and evaluate the config of the .tf file hclsimple.decode(configfilepath, bytes, nil, &config) // iterate through the rules until we find one with // description = "grant acccess to flask app" // code go here for _, nsg := range config.networksecuritygroup { fmt.printf("security rule: %s", nsg.securityrule) } } // basically copied from here https://github.com/hashicorp/hcl/blob/v2.16.2/hclsimple/hclsimple.go#l59 // but modified to handle .tf files too func mydecode(filename string, src []byte, ctx *hcl.evalcontext, target interface{}) error { var file *hcl.file var diags hcl.diagnostics switch suffix := strings.tolower(filepath.ext(filename)); suffix { case ".tf": file, diags = hclsyntax.parseconfig(src, filename, hcl.pos{line: 1, column: 1}) case ".hcl": file, diags = hclsyntax.parseconfig(src, filename, hcl.pos{line: 1, column: 1}) case ".json": file, diags = json.parse(src, filename) default: diags = diags.append(&hcl.diagnostic{ severity: hcl.diagerror, summary: "unsupported file format", detail: fmt.sprintf("cannot read from %s: unrecognized file format suffix %q.", filename, suffix), }) return diags } if diags.haserrors() { return diags } diags = gohcl.decodebody(file.body, ctx, target) if diags.haserrors() { return diags } return nil } // taken from here https://github.com/hashicorp/hcl/blob/v2.16.2/hclsimple/hclsimple.go#l89 func mydecodefile(filename string, ctx *hcl.evalcontext, target interface{}) error { src, err := ioutil.readfile(filename) if err != nil { if os.isnotexist(err) { return hcl.diagnostics{ { severity: hcl.diagerror, summary: "configuration file not found", detail: fmt.sprintf("the configuration file %s does not exist.", filename), }, } } return hcl.diagnostics{ { severity: hcl.diagerror, summary: "failed to read configuration", detail: fmt.sprintf("can't read %s: %s.", filename, err), }, } } return mydecode(filename, src, ctx, target) }
Apabila saya menjalankan kod, pada asasnya saya cuba mentakrifkan networksecuritygroup.securityrule, dan menerima ralat berikut menggunakan kod di atas:
2023/05/24 11:42:11 Failed to load configuration: nsg.tf:6,3-16: Unsupported argument; An argument named "security_rule" is not expected here. Did you mean to define a block of type "security_rule"? exit status 1
Sebarang cadangan amat kami hargai
Oleh itu, buat masa ini https://www.php.cn/link/f56de5ef149cf0aedcc8f4797031e229 tidak boleh dilakukan (lihat di sini/9fc5f https://www.php cc8f4797031e229/ isu/50 - Cadangan ini sendiri perlu diubah untuk kemudahan)hclwrite
Saya mencipta fail
yang mengandungi pembolehubah tempatan, yang kemudian saya rujuk dalam peraturan keselamatan nsg: locals.tf
locals { my_ip = "1.2.3.4" }
my_ip=$(curl -s -4 icanhazip.com) sed -i "s|my_ip = \".*\"|my_ip = \"$my_ip\"|" locals.tf
Atas ialah kandungan terperinci Bagaimanakah saya boleh meminta skrip Golang mengubah suai nilai dalam fail Terraform (format HCL)?. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!