diff --git a/README.md b/README.md index db2df8e0..79fefaa3 100755 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ Terraform VKCS Provider Requirements ------------ -- [Terraform](https://www.terraform.io/downloads.html) 1.0.x +- [Terraform](https://www.terraform.io/downloads.html) 1.1.5 and later - [Go](https://golang.org/doc/install) 1.18 (to build the provider plugin) Using The Provider diff --git a/go.mod b/go.mod index f0871b30..233deca1 100644 --- a/go.mod +++ b/go.mod @@ -8,7 +8,11 @@ require ( github.com/gophercloud/gophercloud v0.24.0 github.com/gophercloud/utils v0.0.0-20220307143606-8e7800759d16 github.com/hashicorp/go-cty v1.4.1-0.20200414143053-d3edf31b6320 - github.com/hashicorp/terraform-plugin-sdk/v2 v2.24.0 + github.com/hashicorp/terraform-plugin-framework v1.2.0 + github.com/hashicorp/terraform-plugin-go v0.15.0 + github.com/hashicorp/terraform-plugin-mux v0.10.0 + github.com/hashicorp/terraform-plugin-sdk/v2 v2.26.1 + github.com/hashicorp/terraform-plugin-testing v1.2.0 github.com/mitchellh/go-homedir v1.1.0 github.com/mitchellh/mapstructure v1.5.0 github.com/satori/go.uuid v1.2.0 @@ -17,7 +21,6 @@ require ( require ( github.com/agext/levenshtein v1.2.3 // indirect - github.com/apparentlymart/go-cidr v1.1.0 // indirect github.com/apparentlymart/go-textseg/v13 v13.0.0 // indirect github.com/davecgh/go-spew v1.1.1 // indirect github.com/fatih/color v1.13.0 // indirect @@ -25,9 +28,9 @@ require ( github.com/hashicorp/errwrap v1.1.0 // indirect github.com/hashicorp/go-checkpoint v0.5.0 // indirect github.com/hashicorp/go-cleanhttp v0.5.2 // indirect - github.com/hashicorp/go-hclog v1.4.0 // indirect + github.com/hashicorp/go-hclog v1.5.0 // indirect github.com/hashicorp/go-multierror v1.1.1 // indirect - github.com/hashicorp/go-plugin v1.4.8 // indirect + github.com/hashicorp/go-plugin v1.4.9 // indirect github.com/hashicorp/go-uuid v1.0.3 // indirect github.com/hashicorp/go-version v1.6.0 // indirect github.com/hashicorp/hc-install v0.5.0 // indirect @@ -35,10 +38,9 @@ require ( github.com/hashicorp/logutils v1.0.0 // indirect github.com/hashicorp/terraform-exec v0.18.1 // indirect github.com/hashicorp/terraform-json v0.16.0 // indirect - github.com/hashicorp/terraform-plugin-go v0.14.3 // indirect github.com/hashicorp/terraform-plugin-log v0.8.0 // indirect - github.com/hashicorp/terraform-registry-address v0.1.0 // indirect - github.com/hashicorp/terraform-svchost v0.0.0-20200729002733-f050f53b9734 // indirect + github.com/hashicorp/terraform-registry-address v0.2.0 // indirect + github.com/hashicorp/terraform-svchost v0.0.1 // indirect github.com/hashicorp/yamux v0.0.0-20211028200310-0bc27b27de87 // indirect github.com/mattn/go-colorable v0.1.12 // indirect github.com/mattn/go-isatty v0.0.14 // indirect @@ -50,8 +52,8 @@ require ( github.com/pmezard/go-difflib v1.0.0 // indirect github.com/stretchr/objx v0.4.0 // indirect github.com/vmihailenco/msgpack v4.0.4+incompatible // indirect - github.com/vmihailenco/msgpack/v4 v4.3.12 // indirect - github.com/vmihailenco/tagparser v0.1.2 // indirect + github.com/vmihailenco/msgpack/v5 v5.3.5 // indirect + github.com/vmihailenco/tagparser/v2 v2.0.0 // indirect github.com/zclconf/go-cty v1.13.1 // indirect golang.org/x/crypto v0.7.0 // indirect golang.org/x/mod v0.8.0 // indirect @@ -59,9 +61,9 @@ require ( golang.org/x/sys v0.6.0 // indirect golang.org/x/text v0.8.0 // indirect google.golang.org/appengine v1.6.7 // indirect - google.golang.org/genproto v0.0.0-20220525015930-6ca3db687a9d // indirect - google.golang.org/grpc v1.51.0 // indirect - google.golang.org/protobuf v1.28.1 // indirect + google.golang.org/genproto v0.0.0-20230110181048-76db0878b65f // indirect + google.golang.org/grpc v1.54.0 // indirect + google.golang.org/protobuf v1.30.0 // indirect gopkg.in/yaml.v2 v2.4.0 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect ) diff --git a/go.sum b/go.sum index 00889733..27707f68 100644 --- a/go.sum +++ b/go.sum @@ -1,6 +1,3 @@ -cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= -cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= -github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= github.com/Masterminds/goutils v1.1.1/go.mod h1:8cTjp+g8YejhMuvIA5y2vz3BpJxksy863GQaJW2MFNU= github.com/Masterminds/semver/v3 v3.1.1/go.mod h1:VPu/7SZ7ePZ3QOrcuXROw5FAcLl4a0cBrbBpGY/8hQs= github.com/Masterminds/sprig/v3 v3.2.1/go.mod h1:UoaO7Yp8KlPnJIYWTFkMaqPUYKTfGFPhxNuwnnxkKlk= @@ -14,43 +11,22 @@ github.com/acomagu/bufpipe v1.0.3/go.mod h1:mxdxdup/WdsKVreO5GpW4+M/1CE2sMG4jeGJ github.com/agext/levenshtein v1.2.3 h1:YB2fHEn0UJagG8T1rrWknE3ZQzWM06O8AMAatNn7lmo= github.com/agext/levenshtein v1.2.3/go.mod h1:JEDfjyjHDjOF/1e4FlBE/PkbqA9OfWu2ki2W0IB5558= github.com/anmitsu/go-shlex v0.0.0-20161002113705-648efa622239/go.mod h1:2FmKhYUyUczH0OGQWaF5ceTx0UBShxjsH6f8oGKYe2c= -github.com/antihax/optional v1.0.0/go.mod h1:uupD/76wgC+ih3iEmQUL+0Ugr19nfwCT1kdvxnR2qWY= -github.com/apparentlymart/go-cidr v1.1.0 h1:2mAhrMoF+nhXqxTzSZMUzDHkLjmIHC+Zzn4tdgBZjnU= -github.com/apparentlymart/go-cidr v1.1.0/go.mod h1:EBcsNrHc3zQeuaeCeCtQruQm+n9/YjEn/vI25Lg7Gwc= -github.com/apparentlymart/go-dump v0.0.0-20190214190832-042adf3cf4a0 h1:MzVXffFUye+ZcSR6opIgz9Co7WcDx6ZcY+RjfFHoA0I= -github.com/apparentlymart/go-textseg v1.0.0/go.mod h1:z96Txxhf3xSFMPmb5X/1W05FF/Nj9VFpLOpjS5yuumk= github.com/apparentlymart/go-textseg/v12 v12.0.0/go.mod h1:S/4uRK2UtaQttw1GenVJEynmyUenKwP++x/+DdGV/Ec= github.com/apparentlymart/go-textseg/v13 v13.0.0 h1:Y+KvPE1NYz0xl601PVImeQfFyEy6iT90AvPUL1NNfNw= github.com/apparentlymart/go-textseg/v13 v13.0.0/go.mod h1:ZK2fH7c4NqDTLtiYLvIkEghdlcqw7yxLeM89kiTRPUo= github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8= github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5/go.mod h1:wHh0iHkYZB8zMSxRWpUBQtwG5a7fFgvEO+odwuTv2gs= github.com/bgentry/speakeasy v0.1.0/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs= -github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= -github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= -github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw= -github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= -github.com/cncf/udpa/go v0.0.0-20201120205902-5459f2c99403/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk= -github.com/cncf/udpa/go v0.0.0-20210930031921-04548b0d99d4/go.mod h1:6pvJx4me5XPnfI9Z40ddWsdw2W/uZgQLFXToKeRcDiI= -github.com/cncf/xds/go v0.0.0-20210922020428-25de7278fc84/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= -github.com/cncf/xds/go v0.0.0-20211001041855-01bcc9b48dfe/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= -github.com/cncf/xds/go v0.0.0-20211011173535-cb28da3451f1/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/emirpasic/gods v1.12.0 h1:QAUIPSaCu4G+POclxeqb3F+WPpdKqFGlw36+yOzGlrg= github.com/emirpasic/gods v1.12.0/go.mod h1:YfzfFFoVP/catgzJb4IKIqXjX78Ha8FMSDh3ymbK86o= -github.com/envoyproxy/go-control-plane v0.9.0/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= -github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= -github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1mIlRU8Am5FuJP05cCM98= -github.com/envoyproxy/go-control-plane v0.9.9-0.20201210154907-fd9021fe5dad/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk= -github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1/go.mod h1:KJwIaB5Mv44NWtYuAOFCVOjcI94vtpEz2JU/D2v6IjE= -github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= github.com/fatih/color v1.13.0 h1:8LOYc1KYPPmyKMuN8QV2DNRWNbLo6LZ0iLs8+mlH53w= github.com/fatih/color v1.13.0/go.mod h1:kLAiJbzzSOZDVNGyDpeOxJ47H46qBXwg5ILebYFFOfk= github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc= -github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= github.com/gliderlabs/ssh v0.2.2/go.mod h1:U7qILu1NlMHj9FlMhZLlkCdDnU1DBEAqr0aevW3Awn0= github.com/go-git/gcfg v1.5.0 h1:Q5ViNfGF8zFgyJWPqYwA7qGFoMTEiBmdlkcfRmpIMa4= github.com/go-git/gcfg v1.5.0/go.mod h1:5m20vg6GwYabIxaOonVkTdrILxQMpEShl1xiMF4ua+E= @@ -63,32 +39,14 @@ github.com/go-git/go-git/v5 v5.4.2/go.mod h1:gQ1kArt6d+n+BGd+/B/I74HwRTLhth2+zti github.com/go-test/deep v1.0.3 h1:ZrJSEWsXzPOxaZnFteGEfooLba+ju3FYIbOrS+rQd68= github.com/gofrs/flock v0.8.1 h1:+gYjHKf32LDeiEEFhQaotPbLuUXjY5ZqxKgXy7n59aw= github.com/gofrs/flock v0.8.1/go.mod h1:F1TvTiK9OcQqauNUHlbJvyl9Qa1QvF/gOUDKA14jxHU= -github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q= -github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A= github.com/golang/protobuf v1.1.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= -github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= github.com/golang/protobuf v1.3.1/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= -github.com/golang/protobuf v1.3.2/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U= -github.com/golang/protobuf v1.3.3/go.mod h1:vzj43D7+SQXF/4pzW/hwtAqwc6iTitCiVSaWz5lYuqw= -github.com/golang/protobuf v1.3.4/go.mod h1:vzj43D7+SQXF/4pzW/hwtAqwc6iTitCiVSaWz5lYuqw= -github.com/golang/protobuf v1.4.0-rc.1/go.mod h1:ceaxUfeHdC40wWswd/P6IGgMaK3YpKi5j83Wpe3EHw8= -github.com/golang/protobuf v1.4.0-rc.1.0.20200221234624-67d41d38c208/go.mod h1:xKAWHe0F5eneWXFV3EuXVDTCmh+JuBKY0li0aMyXATA= -github.com/golang/protobuf v1.4.0-rc.2/go.mod h1:LlEzMj4AhA7rCAGe4KMBDvJI+AwstrUpVNzEA03Pprs= -github.com/golang/protobuf v1.4.0-rc.4.0.20200313231945-b860323f09d0/go.mod h1:WU3c8KckQ9AFe+yFwt9sWVRKCVIyN9cPHBJSNnbL67w= -github.com/golang/protobuf v1.4.0/go.mod h1:jodUvKwWbYaEsadDk5Fwe5c77LiNKVO9IDvqG2KuDX0= -github.com/golang/protobuf v1.4.1/go.mod h1:U8fpvMrcmy5pZrNK1lt4xCsGvpyWQ/VVv6QDs8UjoX8= -github.com/golang/protobuf v1.4.2/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= -github.com/golang/protobuf v1.4.3/go.mod h1:oDoupMAO8OvCJWAcko0GGGIgR6R6ocIYbsSw735rRwI= github.com/golang/protobuf v1.5.0/go.mod h1:FsONVRAS9T7sI+LIUmWTfcYkHO4aIWwzhcaSAoJOfIk= github.com/golang/protobuf v1.5.2 h1:ROPKBNFfQgOUMifHyP+KYbvpjbdoFNs+aK7DXlji0Tw= github.com/golang/protobuf v1.5.2/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY= -github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M= github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= -github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/go-cmp v0.5.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38= github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= @@ -98,30 +56,27 @@ github.com/gophercloud/gophercloud v0.24.0 h1:jDsIMGJ1KZpAjYfQgGI2coNQj5Q83oPzui github.com/gophercloud/gophercloud v0.24.0/go.mod h1:Q8fZtyi5zZxPS/j9aj3sSxtvj41AdQMDwyo1myduD5c= github.com/gophercloud/utils v0.0.0-20220307143606-8e7800759d16 h1:slt/exMiitZNY+5OrKJ6ZvSogqN+SyzeYzAtyI6db9A= github.com/gophercloud/utils v0.0.0-20220307143606-8e7800759d16/go.mod h1:qOGlfG6OIJ193/c3Xt/XjOfHataNZdQcVgiu93LxBUM= -github.com/grpc-ecosystem/grpc-gateway v1.16.0/go.mod h1:BDjrQk3hbvj6Nolgz8mAMFbcEtjT1g+wF4CSlocrBnw= github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= github.com/hashicorp/errwrap v1.1.0 h1:OxrOeh75EUXMY8TBjag2fzXGZ40LB6IKw45YeGUDY2I= github.com/hashicorp/errwrap v1.1.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= github.com/hashicorp/go-checkpoint v0.5.0 h1:MFYpPZCnQqQTE18jFwSII6eUQrD/oxMFp3mlgcqk5mU= github.com/hashicorp/go-checkpoint v0.5.0/go.mod h1:7nfLNL10NsxqO4iWuW6tWW0HjZuDrwkBuEQsVcpCOgg= github.com/hashicorp/go-cleanhttp v0.5.0/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= -github.com/hashicorp/go-cleanhttp v0.5.1/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80= github.com/hashicorp/go-cleanhttp v0.5.2 h1:035FKYIWjmULyFRBKPs8TBQoi0x6d9G4xc9neXJWAZQ= github.com/hashicorp/go-cleanhttp v0.5.2/go.mod h1:kO/YDlP8L1346E6Sodw+PrpBSV4/SoxCXGY6BqNFT48= github.com/hashicorp/go-cty v1.4.1-0.20200414143053-d3edf31b6320 h1:1/D3zfFHttUKaCaGKZ/dR2roBXv0vKbSCnssIldfQdI= github.com/hashicorp/go-cty v1.4.1-0.20200414143053-d3edf31b6320/go.mod h1:EiZBMaudVLy8fmjf9Npq1dq9RalhveqZG5w/yz3mHWs= -github.com/hashicorp/go-hclog v1.4.0 h1:ctuWFGrhFha8BnnzxqeRGidlEcQkDyL5u8J8t5eA11I= -github.com/hashicorp/go-hclog v1.4.0/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M= +github.com/hashicorp/go-hclog v1.5.0 h1:bI2ocEMgcVlz55Oj1xZNBsVi900c7II+fWDyV9o+13c= +github.com/hashicorp/go-hclog v1.5.0/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M= github.com/hashicorp/go-multierror v1.0.0/go.mod h1:dHtQlpGsu+cZNNAkkCN/P3hoUDHhCYQXV3UM06sGGrk= github.com/hashicorp/go-multierror v1.1.1 h1:H5DkEtf6CXdFp0N0Em5UCwQpXMWke8IA0+lD48awMYo= github.com/hashicorp/go-multierror v1.1.1/go.mod h1:iw975J/qwKPdAO1clOe2L8331t/9/fmwbPZ6JB6eMoM= -github.com/hashicorp/go-plugin v1.4.8 h1:CHGwpxYDOttQOY7HOWgETU9dyVjOXzniXDqJcYJE1zM= -github.com/hashicorp/go-plugin v1.4.8/go.mod h1:viDMjcLJuDui6pXb8U4HVfb8AamCWhHGUjr2IrTF67s= +github.com/hashicorp/go-plugin v1.4.9 h1:ESiK220/qE0aGxWdzKIvRH69iLiuN/PjoLTm69RoWtU= +github.com/hashicorp/go-plugin v1.4.9/go.mod h1:viDMjcLJuDui6pXb8U4HVfb8AamCWhHGUjr2IrTF67s= github.com/hashicorp/go-uuid v1.0.0/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= github.com/hashicorp/go-uuid v1.0.2/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8= github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro= -github.com/hashicorp/go-version v1.2.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= github.com/hashicorp/go-version v1.6.0 h1:feTTfFNnjP967rlCxM/I9g701jU+RN74YKx2mOkIeek= github.com/hashicorp/go-version v1.6.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= github.com/hashicorp/hc-install v0.5.0 h1:D9bl4KayIYKEeJ4vUDe9L5huqxZXczKaykSRcmQ0xY0= @@ -134,16 +89,22 @@ github.com/hashicorp/terraform-exec v0.18.1 h1:LAbfDvNQU1l0NOQlTuudjczVhHj061fNX github.com/hashicorp/terraform-exec v0.18.1/go.mod h1:58wg4IeuAJ6LVsLUeD2DWZZoc/bYi6dzhLHzxM41980= github.com/hashicorp/terraform-json v0.16.0 h1:UKkeWRWb23do5LNAFlh/K3N0ymn1qTOO8c+85Albo3s= github.com/hashicorp/terraform-json v0.16.0/go.mod h1:v0Ufk9jJnk6tcIZvScHvetlKfiNTC+WS21mnXIlc0B0= -github.com/hashicorp/terraform-plugin-go v0.14.3 h1:nlnJ1GXKdMwsC8g1Nh05tK2wsC3+3BL/DBBxFEki+j0= -github.com/hashicorp/terraform-plugin-go v0.14.3/go.mod h1:7ees7DMZ263q8wQ6E4RdIdR6nHHJtrdt4ogX5lPkX1A= +github.com/hashicorp/terraform-plugin-framework v1.2.0 h1:MZjFFfULnFq8fh04FqrKPcJ/nGpHOvX4buIygT3MSNY= +github.com/hashicorp/terraform-plugin-framework v1.2.0/go.mod h1:nToI62JylqXDq84weLJ/U3umUsBhZAaTmU0HXIVUOcw= +github.com/hashicorp/terraform-plugin-go v0.15.0 h1:1BJNSUFs09DS8h/XNyJNJaeusQuWc/T9V99ylU9Zwp0= +github.com/hashicorp/terraform-plugin-go v0.15.0/go.mod h1:tk9E3/Zx4RlF/9FdGAhwxHExqIHHldqiQGt20G6g+nQ= github.com/hashicorp/terraform-plugin-log v0.8.0 h1:pX2VQ/TGKu+UU1rCay0OlzosNKe4Nz1pepLXj95oyy0= github.com/hashicorp/terraform-plugin-log v0.8.0/go.mod h1:1myFrhVsBLeylQzYYEV17VVjtG8oYPRFdaZs7xdW2xs= -github.com/hashicorp/terraform-plugin-sdk/v2 v2.24.0 h1:FtCLTiTcykdsURXPt/ku7fYXm3y19nbzbZcUxHx9RbI= -github.com/hashicorp/terraform-plugin-sdk/v2 v2.24.0/go.mod h1:80wf5oad1tW+oLnbXS4UTYmDCrl7BuN1Q+IA91X1a4Y= -github.com/hashicorp/terraform-registry-address v0.1.0 h1:W6JkV9wbum+m516rCl5/NjKxCyTVaaUBbzYcMzBDO3U= -github.com/hashicorp/terraform-registry-address v0.1.0/go.mod h1:EnyO2jYO6j29DTHbJcm00E5nQTFeTtyZH3H5ycydQ5A= -github.com/hashicorp/terraform-svchost v0.0.0-20200729002733-f050f53b9734 h1:HKLsbzeOsfXmKNpr3GiT18XAblV0BjCbzL8KQAMZGa0= -github.com/hashicorp/terraform-svchost v0.0.0-20200729002733-f050f53b9734/go.mod h1:kNDNcF7sN4DocDLBkQYz73HGKwN1ANB1blq4lIYLYvg= +github.com/hashicorp/terraform-plugin-mux v0.10.0 h1:VejY1BffxGy2iYOaa8DDHavY4k9jbvAE8F3lhruspKY= +github.com/hashicorp/terraform-plugin-mux v0.10.0/go.mod h1:9sdnpmY20xIsl4ItsfODZYE+MgpSy/osXpSf+RwaZCY= +github.com/hashicorp/terraform-plugin-sdk/v2 v2.26.1 h1:G9WAfb8LHeCxu7Ae8nc1agZlQOSCUWsb610iAogBhCs= +github.com/hashicorp/terraform-plugin-sdk/v2 v2.26.1/go.mod h1:xcOSYlRVdPLmDUoqPhO9fiO/YCN/l6MGYeTzGt5jgkQ= +github.com/hashicorp/terraform-plugin-testing v1.2.0 h1:pASRAe6BOZFO4xSGQr9WzitXit0nrQAYDk8ziuRfn9E= +github.com/hashicorp/terraform-plugin-testing v1.2.0/go.mod h1:+8bp3O7xUb1UtBcdknrGdVRIuTw4b62TYSIgXHqlyew= +github.com/hashicorp/terraform-registry-address v0.2.0 h1:92LUg03NhfgZv44zpNTLBGIbiyTokQCDcdH5BhVHT3s= +github.com/hashicorp/terraform-registry-address v0.2.0/go.mod h1:478wuzJPzdmqT6OGbB/iH82EDcI8VFM4yujknh/1nIs= +github.com/hashicorp/terraform-svchost v0.0.1 h1:Zj6fR5wnpOHnJUmLyWozjMeDaVuE+cstMPj41/eKmSQ= +github.com/hashicorp/terraform-svchost v0.0.1/go.mod h1:ut8JaH0vumgdCfJaihdcZULqkAwHdQNwNH7taIDdsZM= github.com/hashicorp/yamux v0.0.0-20211028200310-0bc27b27de87 h1:xixZ2bWeofWV68J+x6AzmKuVM/JWCQwkWm6GW/MUR6I= github.com/hashicorp/yamux v0.0.0-20211028200310-0bc27b27de87/go.mod h1:CtWFDAQgb7dxtzFs4tWbplKIe2jSi3+5vKbgIO0SLnQ= github.com/huandu/xstrings v1.3.1/go.mod h1:y5/lhBue+AyNmUVz9RLU9xbLR0o4KIIExikq4ovT0aE= @@ -165,7 +126,6 @@ github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= -github.com/kylelemons/godebug v0.0.0-20170820004349-d65d576e9348/go.mod h1:B69LEHPfb2qLo0BaaOLcbitczOKLWTsrBG9LczfCD4k= github.com/kylelemons/godebug v1.1.0 h1:RPNrshWIDI6G2gRW9EHilWtl7Z6Sb1BR0xunSBf0SNc= github.com/matryer/is v1.2.0/go.mod h1:2fLPjFQM9rhQ15aVEtbuwhJinnOqrmgXPNdZsdwlWXA= github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU= @@ -199,8 +159,6 @@ github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINE github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI= -github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= -github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6LYCDYWNEvQ= github.com/satori/go.uuid v1.2.0 h1:0uYX9dsZ2yD7q2RtLRtPSdGDWzjeM3TbMJP9utgA0ww= github.com/satori/go.uuid v1.2.0/go.mod h1:dA0hQrYB0VpLJoorglMZABFdXlWrHn1NEOzdhQKdks0= github.com/sergi/go-diff v1.1.0/go.mod h1:STckp+ISIX8hZLjrqAeVduY0gWCT9IjLuqbuNXdaHfM= @@ -223,22 +181,18 @@ github.com/stretchr/testify v1.7.2/go.mod h1:R6va5+xMeoiuVRoj+gSkQ7d3FALtqAAGI1F github.com/vmihailenco/msgpack v3.3.3+incompatible/go.mod h1:fy3FlTQTDXWkZ7Bh6AcGMlsjHatGryHQYUTf1ShIgkk= github.com/vmihailenco/msgpack v4.0.4+incompatible h1:dSLoQfGFAo3F6OoNhwUmLwVgaUXK79GlxNBwueZn0xI= github.com/vmihailenco/msgpack v4.0.4+incompatible/go.mod h1:fy3FlTQTDXWkZ7Bh6AcGMlsjHatGryHQYUTf1ShIgkk= -github.com/vmihailenco/msgpack/v4 v4.3.12 h1:07s4sz9IReOgdikxLTKNbBdqDMLsjPKXwvCazn8G65U= -github.com/vmihailenco/msgpack/v4 v4.3.12/go.mod h1:gborTTJjAo/GWTqqRjrLCn9pgNN+NXzzngzBKDPIqw4= -github.com/vmihailenco/tagparser v0.1.1/go.mod h1:OeAg3pn3UbLjkWt+rN9oFYB6u/cQgqMEUPoW2WPyhdI= -github.com/vmihailenco/tagparser v0.1.2 h1:gnjoVuB/kljJ5wICEEOpx98oXMWPLj22G67Vbd1qPqc= -github.com/vmihailenco/tagparser v0.1.2/go.mod h1:OeAg3pn3UbLjkWt+rN9oFYB6u/cQgqMEUPoW2WPyhdI= +github.com/vmihailenco/msgpack/v5 v5.3.5 h1:5gO0H1iULLWGhs2H5tbAHIZTV8/cYafcFOr9znI5mJU= +github.com/vmihailenco/msgpack/v5 v5.3.5/go.mod h1:7xyJ9e+0+9SaZT0Wt1RGleJXzli6Q/V5KbhBonMG9jc= +github.com/vmihailenco/tagparser/v2 v2.0.0 h1:y09buUbR+b5aycVFQs/g70pqKVZNBmxwAhO7/IwNM9g= +github.com/vmihailenco/tagparser/v2 v2.0.0/go.mod h1:Wri+At7QHww0WTrCBeu4J6bNtoV6mEfg5OIWRZA9qds= github.com/xanzy/ssh-agent v0.3.0 h1:wUMzuKtKilRgBAD1sUb8gOwwRr2FGoBVumcjoOACClI= github.com/xanzy/ssh-agent v0.3.0/go.mod h1:3s9xbODqPuuhK9JV1R321M/FlMZSBvE5aY6eAcqrDh0= github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY= -github.com/zclconf/go-cty v1.1.0/go.mod h1:xnAOWiHeOqg2nWS62VtQ7pbOu17FtxJNW8RLEih+O3s= github.com/zclconf/go-cty v1.13.1 h1:0a6bRwuiSHtAmqCqNOE+c2oHgepv0ctoxU4FUe43kwc= github.com/zclconf/go-cty v1.13.1/go.mod h1:YKQzy/7pZ7iq2jNFzy5go57xdxdWoLLpaEp4u238AE0= -go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI= golang.org/x/crypto v0.0.0-20190219172222-a4c6cb3142f2/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= golang.org/x/crypto v0.0.0-20200414173820-0848c9571904/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= -golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20200820211705-5c72a883971a/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= golang.org/x/crypto v0.0.0-20201221181555-eec23a3978ad/go.mod h1:jdWPYTVW3xRLrWPugEBEK3UY2ZEsg3UU495nc5E+M+I= golang.org/x/crypto v0.0.0-20210322153248-0c34fe9e7dc2/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4= @@ -248,45 +202,23 @@ golang.org/x/crypto v0.0.0-20211202192323-5770296d904e/go.mod h1:IxCIyHEi3zRg3s0 golang.org/x/crypto v0.5.0/go.mod h1:NK/OQwhpMQP3MwtdjgLlYHnH9ebylxKWv3e0fK+mkQU= golang.org/x/crypto v0.7.0 h1:AvwMYaRytfdeVt3u6mLaxYtErKYjxA2OXjJ1HHq6t3A= golang.org/x/crypto v0.7.0/go.mod h1:pYwdfH91IfpZVANVyUOhSIPZaFoJGxTFbZhFTx+dXZU= -golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= -golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= -golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU= -golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= golang.org/x/mod v0.7.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/mod v0.8.0 h1:LUYupSeNrTNCGzR/hVBk2NHZO4hXcVaW1k4Qx7rjPx8= golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= -golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20180811021610-c39426892332/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20190213061140-3a22650c66bd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= -golang.org/x/net v0.0.0-20190311183353-d8887717615a/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= golang.org/x/net v0.0.0-20190603091049-60506f45cf65/go.mod h1:HSz+uSET+XFnRR8LxR5pz3Of3rY3CfYBVs4xY44aLks= golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20191009170851-d66e71096ffb/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20200301022130-244492dfa37a/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20200822124328-c89045814202/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA= -golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= -golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210326060303-6b1517762897/go.mod h1:uSPa2vr4CLtc/ILN5odXGNXS6mhrKVzTaCXzk9m6W3k= -golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM= golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= golang.org/x/net v0.5.0/go.mod h1:DivGGAXEgPSlEBzxGzZI+ZLohi+xUj054jfeKui00ws= golang.org/x/net v0.8.0 h1:Zrh2ngAOFYneWTAIAPethzeaQLuHwhuBkuV6ZiRnUaQ= golang.org/x/net v0.8.0/go.mod h1:QVkue5JL9kW//ek3r6jTKnTFis1tRmNAW2P1shuFdJc= -golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= -golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= -golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -296,16 +228,11 @@ golang.org/x/sys v0.0.0-20191026070338-33540a1f6037/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20200116001909-b77594299b42/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200223170610-d5e6a3e2c0ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200302150141-5c8b2ff67527/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200323222414-85ca7c5b95cd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210119212857-b64e53b001e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210320140829-1e4c9ba3b0c4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210324051608-47abb6519492/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210502180810-71e4cd670f79/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= @@ -323,57 +250,27 @@ golang.org/x/term v0.6.0 h1:clScbb1cHjoCkyRbWwBEUZ5H/tIFu5TAXIqaZD0Gcjw= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= golang.org/x/text v0.6.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= golang.org/x/text v0.8.0 h1:57P1ETyNKtuIjB4SRd15iJxuhj8Gc416Y78H3qgMh68= golang.org/x/text v0.8.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= -golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= -golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY= -golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= -golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= -golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= -google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= -google.golang.org/appengine v1.6.5/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= google.golang.org/appengine v1.6.7 h1:FZR1q0exgwxzPzp/aF+VccGrSfxfPpkBqjIIEq3ru6c= google.golang.org/appengine v1.6.7/go.mod h1:8WjMMxjGQR8xUklV/ARdw2HLXBOI7O7uCIDZVag1xfc= -google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc= -google.golang.org/genproto v0.0.0-20190819201941-24fa4b261c55/go.mod h1:DMBHOl98Agz4BDEuKkezgsaosCRResVns1a3J2ZsMNc= -google.golang.org/genproto v0.0.0-20200513103714-09dca8ec2884/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= -google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013/go.mod h1:NbSheEEYHJ7i3ixzK3sjbqSGDJWnxyFXZblF3eUsNvo= -google.golang.org/genproto v0.0.0-20220525015930-6ca3db687a9d h1:8BnRR08DxAQ+e2pFx64Q3Ltg/AkrrxyG1LLa1WpomyA= -google.golang.org/genproto v0.0.0-20220525015930-6ca3db687a9d/go.mod h1:yKyY4AMRwFiC8yMMNaMi+RkCnjZJt9LoWuvhXjMs+To= -google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= -google.golang.org/grpc v1.23.0/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg= -google.golang.org/grpc v1.25.1/go.mod h1:c3i+UQWmh7LiEpx4sFZnkU36qjEYZ0imhYfXVyQciAY= -google.golang.org/grpc v1.27.0/go.mod h1:qbnxyOmOxrQa7FizSgH+ReBfzJrCY1pSN7KXBS8abTk= -google.golang.org/grpc v1.33.1/go.mod h1:fr5YgcSWrqhRRxogOsw7RzIpsmvOZ6IcH4kBYTpR3n0= -google.golang.org/grpc v1.36.0/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU= -google.golang.org/grpc v1.46.2/go.mod h1:vN9eftEi1UMyUsIF80+uQXhHjbXYbm0uXoFCACuMGWk= -google.golang.org/grpc v1.51.0 h1:E1eGv1FTqoLIdnBCZufiSHgKjlqG6fKFf6pPWtMTh8U= -google.golang.org/grpc v1.51.0/go.mod h1:wgNDFcnuBGmxLKI/qn4T+m5BtEBYXJPvibbUPsAIPww= -google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= -google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= -google.golang.org/protobuf v0.0.0-20200228230310-ab0ca4ff8a60/go.mod h1:cfTl7dwQJ+fmap5saPgwCLgHXTUD7jkjRqWcaiX5VyM= -google.golang.org/protobuf v1.20.1-0.20200309200217-e05f789c0967/go.mod h1:A+miEFZTKqfCUM6K7xSMQL9OKL/b6hQv+e19PK+JZNE= -google.golang.org/protobuf v1.21.0/go.mod h1:47Nbq4nVaFHyn7ilMalzfO3qCViNmqZ2kzikPIcrTAo= -google.golang.org/protobuf v1.22.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= -google.golang.org/protobuf v1.23.0/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= -google.golang.org/protobuf v1.23.1-0.20200526195155-81db48ad09cc/go.mod h1:EGpADcykh3NcUnDUJcl1+ZksZNG86OlYog2l/sGQquU= -google.golang.org/protobuf v1.25.0/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlbajtzgsN7c= +google.golang.org/genproto v0.0.0-20230110181048-76db0878b65f h1:BWUVssLB0HVOSY78gIdvk1dTVYtT1y8SBWtPYuTJ/6w= +google.golang.org/genproto v0.0.0-20230110181048-76db0878b65f/go.mod h1:RGgjbofJ8xD9Sq1VVhDM1Vok1vRONV+rg+CjzG4SZKM= +google.golang.org/grpc v1.54.0 h1:EhTqbhiYeixwWQtAEZAxmV9MGqcjEU2mFx52xCzNyag= +google.golang.org/grpc v1.54.0/go.mod h1:PUSEXI6iWghWaB6lXM4knEgpJNu2qUcKfDtNci3EC2g= google.golang.org/protobuf v1.26.0-rc.1/go.mod h1:jlhhOSvTdKEhbULTjvd4ARK9grFBp09yW+WbY/TyQbw= google.golang.org/protobuf v1.26.0/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= -google.golang.org/protobuf v1.27.1/go.mod h1:9q0QmTI4eRPtz6boOQmLYwt+qCgq0jsYwAQnmE0givc= -google.golang.org/protobuf v1.28.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= -google.golang.org/protobuf v1.28.1 h1:d0NfwRgPtno5B1Wa6L2DAG+KivqkdutMf1UhdNx175w= -google.golang.org/protobuf v1.28.1/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= +google.golang.org/protobuf v1.30.0 h1:kPPoIgf3TsEvrm0PFe15JQ+570QVxYzEvvHqChK+cng= +google.golang.org/protobuf v1.30.0/go.mod h1:HV8QOd/L58Z+nl8r43ehVNZIU/HEI6OcFqwMG9pJV4I= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= @@ -383,7 +280,6 @@ gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EV gopkg.in/warnings.v0 v0.1.2 h1:wFXVbFY8DY5/xOe1ECiWdKCzZlxgshcYVNkBHstARME= gopkg.in/warnings.v0 v0.1.2/go.mod h1:jksf8JmL6Qr/oQM2OXTHunEvvTAsrWBLb6OOjuVWRNI= gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= -gopkg.in/yaml.v2 v2.2.3/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= @@ -392,5 +288,3 @@ gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= -honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4= diff --git a/helpers/providerjson/helpers.go b/helpers/providerjson/helpers.go deleted file mode 100644 index 3024c1cf..00000000 --- a/helpers/providerjson/helpers.go +++ /dev/null @@ -1,26 +0,0 @@ -package providerjson - -import ( - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" -) - -func (p *ProviderJSON) DataSources() []terraform.DataSource { - s := schema.Provider(*p) - return s.DataSources() -} - -func (p *ProviderJSON) Resources() []terraform.ResourceType { - s := schema.Provider(*p) - return s.Resources() -} - -func NodeIsBlock(input SchemaJSON) bool { - if input.Type == SchemaTypeList || input.Type == SchemaTypeSet { - if _, ok := input.Elem.(ResourceJSON); ok { - return true - } - } - - return false -} diff --git a/helpers/providerjson/read.go b/helpers/providerjson/json/read.go similarity index 53% rename from helpers/providerjson/read.go rename to helpers/providerjson/json/read.go index f863c849..86cbbce4 100644 --- a/helpers/providerjson/read.go +++ b/helpers/providerjson/json/read.go @@ -1,18 +1,20 @@ -package providerjson +package json import ( "encoding/json" "os" + + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" ) -func ReadWithWrapper(filename string) (*ProviderWrapper, error) { +func ReadWithWrapper(filename string) (*schema.ProviderWrapper, error) { f, err := os.Open(filename) if err != nil { return nil, err } defer f.Close() - var pw ProviderWrapper + var pw schema.ProviderWrapper err = json.NewDecoder(f).Decode(&pw) if err != nil { return nil, err diff --git a/helpers/providerjson/json/write.go b/helpers/providerjson/json/write.go new file mode 100644 index 00000000..0f530794 --- /dev/null +++ b/helpers/providerjson/json/write.go @@ -0,0 +1,33 @@ +package json + +import ( + "encoding/json" + "os" + + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" +) + +func DumpWithWrapper(wrapper *schema.ProviderWrapper) error { + if err := json.NewEncoder(os.Stdout).Encode(wrapper); err != nil { + return err + } + + return nil +} + +func WriteWithWrapper(wrapper *schema.ProviderWrapper, filename string) error { + f, err := os.Create(filename) + if err != nil { + return err + } + defer f.Close() + + encoder := json.NewEncoder(f) + encoder.SetIndent("", " ") + + if err := encoder.Encode(wrapper); err != nil { + return err + } + + return nil +} diff --git a/helpers/providerjson/schema/helpers.go b/helpers/providerjson/schema/helpers.go new file mode 100644 index 00000000..fa54a666 --- /dev/null +++ b/helpers/providerjson/schema/helpers.go @@ -0,0 +1,70 @@ +package schema + +import ( + "context" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + ds_schema "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-framework/provider" + "github.com/hashicorp/terraform-plugin-framework/resource" + rs_schema "github.com/hashicorp/terraform-plugin-framework/resource/schema" + sdkschema "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" +) + +func (p *ProviderJSON) SDKSchema() map[string]*sdkschema.Schema { + return p.SDKProvider.Schema +} + +func (p *ProviderJSON) SDKDataSourcesMap() map[string]*sdkschema.Resource { + return p.SDKProvider.DataSourcesMap +} + +func (p *ProviderJSON) SDKResourcesMap() map[string]*sdkschema.Resource { + return p.SDKProvider.ResourcesMap +} + +func (p *ProviderJSON) ResourcesMap() map[string]*rs_schema.Schema { + resourcesMap := make(map[string]*rs_schema.Schema) + ctx := context.Background() + providerMeta := provider.MetadataResponse{} + p.Provider.Metadata(ctx, provider.MetadataRequest{}, &providerMeta) + + for _, f := range p.Provider.Resources(ctx) { + rs := f() + rsMeta := resource.MetadataResponse{} + rs.Metadata(ctx, resource.MetadataRequest{ProviderTypeName: providerMeta.TypeName}, &rsMeta) + rsSchema := resource.SchemaResponse{} + rs.Schema(ctx, resource.SchemaRequest{}, &rsSchema) + resourcesMap[rsMeta.TypeName] = &rsSchema.Schema + } + + return resourcesMap +} + +func (p *ProviderJSON) DataSourcesMap() map[string]*ds_schema.Schema { + dataSourcesMap := make(map[string]*ds_schema.Schema) + ctx := context.Background() + providerMeta := provider.MetadataResponse{} + p.Provider.Metadata(ctx, provider.MetadataRequest{}, &providerMeta) + + for _, f := range p.Provider.DataSources(ctx) { + ds := f() + dsMeta := datasource.MetadataResponse{} + ds.Metadata(ctx, datasource.MetadataRequest{ProviderTypeName: providerMeta.TypeName}, &dsMeta) + dsSchema := datasource.SchemaResponse{} + ds.Schema(ctx, datasource.SchemaRequest{}, &dsSchema) + dataSourcesMap[dsMeta.TypeName] = &dsSchema.Schema + } + + return dataSourcesMap +} + +func NodeIsBlock(input SchemaJSON) bool { + if input.Type == SchemaTypeList || input.Type == SchemaTypeSet { + if _, ok := input.Elem.(ResourceJSON); ok { + return true + } + } + + return false +} diff --git a/helpers/providerjson/json.go b/helpers/providerjson/schema/schema.go similarity index 80% rename from helpers/providerjson/json.go rename to helpers/providerjson/schema/schema.go index 9cd68e12..d951599f 100644 --- a/helpers/providerjson/json.go +++ b/helpers/providerjson/schema/schema.go @@ -1,21 +1,28 @@ -package providerjson +package schema import ( "encoding/json" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" + "github.com/hashicorp/terraform-plugin-framework/provider" + sdkschema "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" ) const ( SchemaTypeSet = "TypeSet" SchemaTypeList = "TypeList" + SchemaTypeMap = "TypeMap" SchemaTypeInt = "TypeInt" - SchemaTypeString = "String" - SchemaTypeBool = "Bool" - SchemaTypeFloat = "Float" + SchemaTypeString = "TypeString" + SchemaTypeBool = "TypeBool" + SchemaTypeFloat = "TypeFloat" + SchemaTypeNumber = "TypeNumber" + SchemaTypeObject = "TypeObject" ) -type ProviderJSON schema.Provider +type ProviderJSON struct { + SDKProvider *sdkschema.Provider + Provider provider.Provider +} type SchemaJSON struct { Type string `json:"type,omitempty"` @@ -108,7 +115,8 @@ type ProviderSchemaJSON struct { } type ProviderWrapper struct { - ProviderName string `json:"provider_name"` - SchemaVersion string `json:"schema_version"` - ProviderSchema *ProviderSchemaJSON `json:"provider_schema,omitempty"` + ProviderName string `json:"provider_name"` + ProviderVersion string `json:"provider_version"` + SchemaVersion string `json:"schema_version"` + ProviderSchema *ProviderSchemaJSON `json:"provider_schema,omitempty"` } diff --git a/helpers/providerjson/transform.go b/helpers/providerjson/transform.go deleted file mode 100644 index 2fa0b51f..00000000 --- a/helpers/providerjson/transform.go +++ /dev/null @@ -1,272 +0,0 @@ -package providerjson - -import ( - "fmt" - - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" -) - -func ResourceFromRaw(input *schema.Resource) (*ResourceJSON, error) { - if input == nil { - return nil, fmt.Errorf("resource not found") - } - - result := &ResourceJSON{ - Description: input.Description, - Deprecated: input.DeprecationMessage, - } - translatedSchema := make(map[string]SchemaJSON) - - for k, s := range input.Schema { - translatedSchema[k] = SchemaFromRaw(s) - } - result.Schema = translatedSchema - - if input.Timeouts != nil { - timeouts := &ResourceTimeoutJSON{} - if t := input.Timeouts; t != nil { - if t.Create != nil { - timeouts.Create = int(t.Create.Minutes()) - } - if t.Read != nil { - timeouts.Read = int(t.Read.Minutes()) - } - if t.Delete != nil { - timeouts.Delete = int(t.Delete.Minutes()) - } - if t.Update != nil { - timeouts.Update = int(t.Update.Minutes()) - } - } - result.Timeouts = timeouts - } - - return result, nil -} - -func SchemaFromRaw(input *schema.Schema) SchemaJSON { - return SchemaJSON{ - Type: input.Type.String(), - ConfigMode: decodeConfigMode(input.ConfigMode), - Optional: input.Optional, - Required: input.Required, - Default: input.Default, - Description: input.Description, - Computed: input.Computed, - ForceNew: input.ForceNew, - Elem: decodeElem(input.Elem), - MaxItems: input.MaxItems, - MinItems: input.MinItems, - Deprecated: input.Deprecated, - } -} - -func SchemaFromMap(input map[string]interface{}) SchemaJSON { - result := SchemaJSON{} - if t, ok := input["type"]; ok { - result.Type = t.(string) - } - - if t, ok := input["config_mode"]; ok { - result.ConfigMode = t.(string) - } - - if t, ok := input["optional"]; ok { - result.Optional = t.(bool) - } - - if t, ok := input["required"]; ok { - result.Required = t.(bool) - } - - if t, ok := input["default"]; ok { - result.Default = t - } - - if t, ok := input["description"]; ok { - result.Description = t.(string) - } - - if t, ok := input["computed"]; ok { - result.Computed = t.(bool) - } - - if t, ok := input["force_new"]; ok { - result.ForceNew = t.(bool) - } - - if t, ok := input["elem"]; ok { - result.Elem = decodeElem(t) - } - - if t, ok := input["min_items"]; ok { - result.MinItems = int(t.(float64)) - } - - if t, ok := input["max_items"]; ok { - result.MaxItems = int(t.(float64)) - } - - if t, ok := input["new_since"]; ok { - result.NewSince = t.(string) - } - - if t, ok := input["deprecated"]; ok { - result.Deprecated = t.(string) - } - - return result -} - -func ResourceFromMap(input map[string]interface{}) ResourceJSON { - result := ResourceJSON{ - Schema: make(map[string]SchemaJSON, 0), - } - for k, v := range input { - result.Schema[k] = SchemaFromMap(v.(map[string]interface{})) - } - return result -} - -func addNewSinceToResource(base, current *ResourceJSON, curVersion string) { - if base == nil { - current.NewSince = curVersion - return - } - - current.NewSince = base.NewSince - if current.NewSince != "" { - return - } - - for k, curS := range current.Schema { - var baseS *SchemaJSON - if b, ok := base.Schema[k]; ok { - baseS = &b - } - addNewSinceToSchema(baseS, &curS, curVersion) - current.Schema[k] = curS - } -} - -func addNewSinceToSchema(base, current *SchemaJSON, curVersion string) { - if base == nil { - current.NewSince = curVersion - return - } - - current.NewSince = base.NewSince - if current.NewSince != "" { - return - } - - switch el := current.Elem.(type) { - case *SchemaJSON: - if baseEl, ok := base.Elem.(SchemaJSON); ok { - addNewSinceToSchema(&baseEl, el, curVersion) - } - case *ResourceJSON: - if baseEl, ok := base.Elem.(ResourceJSON); ok { - addNewSinceToResource(&baseEl, el, curVersion) - } - } -} - -func decodeConfigMode(input schema.SchemaConfigMode) (out string) { - switch input { - case 1: - out = "Auto" - case 2: - out = "Block" - case 4: - out = "Attribute" - } - return -} - -func decodeElem(input interface{}) interface{} { - switch t := input.(type) { - case bool: - return t - case string: - return t - case int: - return t - case float32, float64: - return t - case *schema.Schema: - return SchemaFromRaw(t) - case *schema.Resource: - r, _ := ResourceFromRaw(t) - return r - } - return nil -} - -func ProviderFromRaw(input *ProviderJSON) (*ProviderSchemaJSON, error) { - if input == nil { - return nil, fmt.Errorf("provider was nil converting from raw") - } - - result := &ProviderSchemaJSON{} - - providerSchema := make(map[string]SchemaJSON) - resourceSchemas := make(map[string]ResourceJSON) - dataSourceSchemas := make(map[string]ResourceJSON) - - for k, v := range input.Schema { - providerSchema[k] = SchemaFromRaw(v) - } - - for k, v := range input.ResourcesMap { - resource, err := ResourceFromRaw(v) - if err != nil { - return nil, err - } - resourceSchemas[k] = *resource - } - - for k, v := range input.DataSourcesMap { - dataSource, err := ResourceFromRaw(v) - if err != nil { - return nil, err - } - dataSourceSchemas[k] = *dataSource - } - - result.Schema = providerSchema - result.ResourcesMap = resourceSchemas - result.DataSourcesMap = dataSourceSchemas - return result, nil -} - -func addNewSince(base, current *ProviderSchemaJSON, curVersion string) { - for k, r := range current.ResourcesMap { - var baseR *ResourceJSON - if b, ok := base.ResourcesMap[k]; ok { - baseR = &b - } - addNewSinceToResource(baseR, &r, curVersion) - current.ResourcesMap[k] = r - } - - for k, r := range current.DataSourcesMap { - var baseR *ResourceJSON - if b, ok := base.DataSourcesMap[k]; ok { - baseR = &b - } - addNewSinceToResource(baseR, &r, curVersion) - current.DataSourcesMap[k] = r - } -} - -func WrappedProvider(input *ProviderJSON, wrapper *ProviderWrapper) (*ProviderWrapper, error) { - schema, err := ProviderFromRaw(input) - if err != nil { - return nil, err - } - - wrapper.ProviderSchema = schema - - return wrapper, nil -} diff --git a/helpers/providerjson/transform/datasource/transform.go b/helpers/providerjson/transform/datasource/transform.go new file mode 100644 index 00000000..fc40e51d --- /dev/null +++ b/helpers/providerjson/transform/datasource/transform.go @@ -0,0 +1,156 @@ +package datasource + +import ( + "context" + "fmt" + + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/transform" +) + +func ResourceFromRaw(input *schema.Schema) (*jsonschema.ResourceJSON, error) { + if input == nil { + return nil, fmt.Errorf("data source not found") + } + + result := &jsonschema.ResourceJSON{ + Description: input.Description, + Deprecated: input.DeprecationMessage, + } + translatedSchema := make(map[string]jsonschema.SchemaJSON) + for k, a := range input.Attributes { + translatedSchema[k] = SchemaFromAttribute(a) + } + for k, b := range input.Blocks { + translatedSchema[k] = SchemaFromBlock(b) + } + result.Schema = translatedSchema + + return result, nil +} + +func SchemaFromAttribute(input schema.Attribute) jsonschema.SchemaJSON { + return jsonschema.SchemaJSON{ + Type: decodeAttrType(input), + Optional: input.IsOptional(), + Required: input.IsRequired(), + Description: input.GetDescription(), + Computed: input.IsComputed(), + Deprecated: input.GetDeprecationMessage(), + Elem: decodeAttrElem(input), + } +} + +func SchemaFromBlock(input schema.Block) jsonschema.SchemaJSON { + var maxItems int + if _, ok := input.(schema.SingleNestedBlock); ok { + maxItems = 1 + } + + return jsonschema.SchemaJSON{ + Type: decodeBlockType(input), + Description: input.GetDescription(), + Deprecated: input.GetDeprecationMessage(), + Elem: decodeBlockElem(input), + MaxItems: maxItems, + } +} + +func decodeAttrType(input schema.Attribute) string { + switch input.(type) { + case schema.BoolAttribute: + return jsonschema.SchemaTypeBool + case schema.StringAttribute: + return jsonschema.SchemaTypeString + case schema.Int64Attribute: + return jsonschema.SchemaTypeInt + case schema.Float64Attribute: + return jsonschema.SchemaTypeFloat + case schema.ListAttribute: + return jsonschema.SchemaTypeList + case schema.ListNestedAttribute: + return jsonschema.SchemaTypeList + case schema.SetAttribute: + return jsonschema.SchemaTypeSet + case schema.SetNestedAttribute: + return jsonschema.SchemaTypeSet + case schema.MapAttribute: + return jsonschema.SchemaTypeMap + case schema.MapNestedAttribute: + return jsonschema.SchemaTypeMap + } + + return "" +} + +func decodeBlockType(input schema.Block) string { + switch input.(type) { + case schema.SingleNestedBlock: + return jsonschema.SchemaTypeList + case schema.ListNestedBlock: + return jsonschema.SchemaTypeList + case schema.SetNestedBlock: + return jsonschema.SchemaTypeSet + } + + return "" +} + +func decodeAttrElem(input schema.Attribute) interface{} { + switch t := input.(type) { + case schema.ListAttribute: + return &jsonschema.SchemaJSON{Type: transform.DecodeValueType(t.ElementType.ValueType(context.Background()))} + case schema.SetAttribute: + return &jsonschema.SchemaJSON{Type: transform.DecodeValueType(t.ElementType.ValueType(context.Background()))} + case schema.MapAttribute: + return &jsonschema.SchemaJSON{Type: transform.DecodeValueType(t.ElementType.ValueType(context.Background()))} + case schema.ListNestedAttribute: + return decodeNestedAttributeObject(t.NestedObject) + case schema.SetNestedAttribute: + return decodeNestedAttributeObject(t.NestedObject) + case schema.MapNestedAttribute: + return decodeNestedAttributeObject(t.NestedObject) + } + + return nil +} + +func decodeBlockElem(input schema.Block) *jsonschema.ResourceJSON { + switch t := input.(type) { + case schema.SingleNestedBlock: + m := make(map[string]jsonschema.SchemaJSON) + for k, a := range t.Attributes { + m[k] = SchemaFromAttribute(a) + } + for k, b := range t.Blocks { + m[k] = SchemaFromBlock(b) + } + return &jsonschema.ResourceJSON{Schema: m} + case schema.ListNestedBlock: + return decodeNestedBlockObject(t.NestedObject) + case schema.SetNestedBlock: + return decodeNestedBlockObject(t.NestedObject) + } + + return nil +} + +func decodeNestedAttributeObject(input schema.NestedAttributeObject) *jsonschema.ResourceJSON { + m := make(map[string]jsonschema.SchemaJSON) + for k, a := range input.Attributes { + m[k] = SchemaFromAttribute(a) + } + return &jsonschema.ResourceJSON{Schema: m} +} + +func decodeNestedBlockObject(input schema.NestedBlockObject) *jsonschema.ResourceJSON { + m := make(map[string]jsonschema.SchemaJSON) + for k, a := range input.Attributes { + m[k] = SchemaFromAttribute(a) + } + for k, b := range input.Blocks { + m[k] = SchemaFromBlock(b) + } + return &jsonschema.ResourceJSON{Schema: m} +} diff --git a/helpers/providerjson/transform/provider/new_since.go b/helpers/providerjson/transform/provider/new_since.go new file mode 100644 index 00000000..1b18bc2e --- /dev/null +++ b/helpers/providerjson/transform/provider/new_since.go @@ -0,0 +1,66 @@ +package provider + +import ( + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" +) + +func addNewSince(base, current *schema.ProviderSchemaJSON, curVersion string) { + for k, r := range current.ResourcesMap { + var baseR *schema.ResourceJSON + if b, ok := base.ResourcesMap[k]; ok { + baseR = &b + } + addNewSinceToResource(baseR, &r, curVersion) + current.ResourcesMap[k] = r + } + + for k, r := range current.DataSourcesMap { + var baseR *schema.ResourceJSON + if b, ok := base.DataSourcesMap[k]; ok { + baseR = &b + } + addNewSinceToResource(baseR, &r, curVersion) + current.DataSourcesMap[k] = r + } +} + +func addNewSinceToResource(base, current *schema.ResourceJSON, curVersion string) { + if base == nil { + current.NewSince = curVersion + return + } + + current.NewSince = base.NewSince + + for k, curS := range current.Schema { + if k == "id" { + continue + } + var baseS *schema.SchemaJSON + if b, ok := base.Schema[k]; ok { + baseS = &b + } + addNewSinceToSchema(baseS, &curS, curVersion) + current.Schema[k] = curS + } +} + +func addNewSinceToSchema(base, current *schema.SchemaJSON, curVersion string) { + if base == nil { + current.NewSince = curVersion + return + } + + current.NewSince = base.NewSince + + switch el := current.Elem.(type) { + case *schema.SchemaJSON: + if baseEl, ok := base.Elem.(schema.SchemaJSON); ok { + addNewSinceToSchema(&baseEl, el, curVersion) + } + case *schema.ResourceJSON: + if baseEl, ok := base.Elem.(schema.ResourceJSON); ok { + addNewSinceToResource(&baseEl, el, curVersion) + } + } +} diff --git a/helpers/providerjson/transform/provider/transform.go b/helpers/providerjson/transform/provider/transform.go new file mode 100644 index 00000000..68a5a4f3 --- /dev/null +++ b/helpers/providerjson/transform/provider/transform.go @@ -0,0 +1,78 @@ +package provider + +import ( + "fmt" + + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/transform/datasource" + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/transform/resource" + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/transform/sdk" +) + +func WrappedProviderFromRaw(input *jsonschema.ProviderJSON, base, wrapper *jsonschema.ProviderWrapper) (*jsonschema.ProviderWrapper, error) { + schema, err := ProviderFromRaw(input) + if err != nil { + return nil, err + } + + if base != nil { + addNewSince(base.ProviderSchema, schema, wrapper.ProviderVersion) + } + + wrapper.ProviderSchema = schema + + return wrapper, nil +} + +func ProviderFromRaw(input *jsonschema.ProviderJSON) (*jsonschema.ProviderSchemaJSON, error) { + if input == nil { + return nil, fmt.Errorf("provider was nil converting from raw") + } + + result := &jsonschema.ProviderSchemaJSON{} + + providerSchema := make(map[string]jsonschema.SchemaJSON) + resourceSchemas := make(map[string]jsonschema.ResourceJSON) + dataSourceSchemas := make(map[string]jsonschema.ResourceJSON) + + for k, v := range input.SDKSchema() { + providerSchema[k] = sdk.SchemaFromRaw(v) + } + + for k, v := range input.SDKResourcesMap() { + resource, err := sdk.ResourceFromRaw(v) + if err != nil { + return nil, err + } + resourceSchemas[k] = *resource + } + + for k, v := range input.SDKDataSourcesMap() { + dataSource, err := sdk.ResourceFromRaw(v) + if err != nil { + return nil, err + } + dataSourceSchemas[k] = *dataSource + } + + for k, v := range input.ResourcesMap() { + resource, err := resource.ResourceFromRaw(v) + if err != nil { + return nil, err + } + resourceSchemas[k] = *resource + } + + for k, v := range input.DataSourcesMap() { + dataSource, err := datasource.ResourceFromRaw(v) + if err != nil { + return nil, err + } + dataSourceSchemas[k] = *dataSource + } + + result.Schema = providerSchema + result.ResourcesMap = resourceSchemas + result.DataSourcesMap = dataSourceSchemas + return result, nil +} diff --git a/helpers/providerjson/transform/resource/transform.go b/helpers/providerjson/transform/resource/transform.go new file mode 100644 index 00000000..d128bc9e --- /dev/null +++ b/helpers/providerjson/transform/resource/transform.go @@ -0,0 +1,156 @@ +package resource + +import ( + "context" + "fmt" + + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/transform" +) + +func ResourceFromRaw(input *schema.Schema) (*jsonschema.ResourceJSON, error) { + if input == nil { + return nil, fmt.Errorf("resource not found") + } + + result := &jsonschema.ResourceJSON{ + Description: input.Description, + Deprecated: input.DeprecationMessage, + } + translatedSchema := make(map[string]jsonschema.SchemaJSON) + for k, a := range input.Attributes { + translatedSchema[k] = SchemaFromAttribute(a) + } + for k, b := range input.Blocks { + translatedSchema[k] = SchemaFromBlock(b) + } + result.Schema = translatedSchema + + return result, nil +} + +func SchemaFromAttribute(input schema.Attribute) jsonschema.SchemaJSON { + return jsonschema.SchemaJSON{ + Type: decodeAttrType(input), + Optional: input.IsOptional(), + Required: input.IsRequired(), + Description: input.GetDescription(), + Computed: input.IsComputed(), + Deprecated: input.GetDeprecationMessage(), + Elem: decodeAttrElem(input), + } +} + +func SchemaFromBlock(input schema.Block) jsonschema.SchemaJSON { + var maxItems int + if _, ok := input.(schema.SingleNestedBlock); ok { + maxItems = 1 + } + + return jsonschema.SchemaJSON{ + Type: decodeBlockType(input), + Description: input.GetDescription(), + Deprecated: input.GetDeprecationMessage(), + Elem: decodeBlockElem(input), + MaxItems: maxItems, + } +} + +func decodeAttrType(input schema.Attribute) string { + switch input.(type) { + case schema.BoolAttribute: + return jsonschema.SchemaTypeBool + case schema.StringAttribute: + return jsonschema.SchemaTypeString + case schema.Int64Attribute: + return jsonschema.SchemaTypeInt + case schema.Float64Attribute: + return jsonschema.SchemaTypeFloat + case schema.ListAttribute: + return jsonschema.SchemaTypeList + case schema.ListNestedAttribute: + return jsonschema.SchemaTypeList + case schema.SetAttribute: + return jsonschema.SchemaTypeSet + case schema.SetNestedAttribute: + return jsonschema.SchemaTypeSet + case schema.MapAttribute: + return jsonschema.SchemaTypeMap + case schema.MapNestedAttribute: + return jsonschema.SchemaTypeMap + } + + return "" +} + +func decodeBlockType(input schema.Block) string { + switch input.(type) { + case schema.SingleNestedBlock: + return jsonschema.SchemaTypeList + case schema.ListNestedBlock: + return jsonschema.SchemaTypeList + case schema.SetNestedBlock: + return jsonschema.SchemaTypeSet + } + + return "" +} + +func decodeAttrElem(input schema.Attribute) interface{} { + switch t := input.(type) { + case schema.ListAttribute: + return &jsonschema.SchemaJSON{Type: transform.DecodeValueType(t.ElementType.ValueType(context.Background()))} + case schema.SetAttribute: + return &jsonschema.SchemaJSON{Type: transform.DecodeValueType(t.ElementType.ValueType(context.Background()))} + case schema.MapAttribute: + return &jsonschema.SchemaJSON{Type: transform.DecodeValueType(t.ElementType.ValueType(context.Background()))} + case schema.ListNestedAttribute: + return decodeNestedAttributeObject(t.NestedObject) + case schema.SetNestedAttribute: + return decodeNestedAttributeObject(t.NestedObject) + case schema.MapNestedAttribute: + return decodeNestedAttributeObject(t.NestedObject) + } + + return nil +} + +func decodeBlockElem(input schema.Block) *jsonschema.ResourceJSON { + switch t := input.(type) { + case schema.SingleNestedBlock: + m := make(map[string]jsonschema.SchemaJSON) + for k, a := range t.Attributes { + m[k] = SchemaFromAttribute(a) + } + for k, b := range t.Blocks { + m[k] = SchemaFromBlock(b) + } + return &jsonschema.ResourceJSON{Schema: m} + case schema.ListNestedBlock: + return decodeNestedBlockObject(t.NestedObject) + case schema.SetNestedBlock: + return decodeNestedBlockObject(t.NestedObject) + } + + return nil +} + +func decodeNestedAttributeObject(input schema.NestedAttributeObject) *jsonschema.ResourceJSON { + m := make(map[string]jsonschema.SchemaJSON) + for k, a := range input.Attributes { + m[k] = SchemaFromAttribute(a) + } + return &jsonschema.ResourceJSON{Schema: m} +} + +func decodeNestedBlockObject(input schema.NestedBlockObject) *jsonschema.ResourceJSON { + m := make(map[string]jsonschema.SchemaJSON) + for k, a := range input.Attributes { + m[k] = SchemaFromAttribute(a) + } + for k, b := range input.Blocks { + m[k] = SchemaFromBlock(b) + } + return &jsonschema.ResourceJSON{Schema: m} +} diff --git a/helpers/providerjson/transform/sdk/transform.go b/helpers/providerjson/transform/sdk/transform.go new file mode 100644 index 00000000..5b9b231a --- /dev/null +++ b/helpers/providerjson/transform/sdk/transform.go @@ -0,0 +1,94 @@ +package sdk + +import ( + "fmt" + + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" +) + +func ResourceFromRaw(input *schema.Resource) (*jsonschema.ResourceJSON, error) { + if input == nil { + return nil, fmt.Errorf("resource not found") + } + + result := &jsonschema.ResourceJSON{ + Description: input.Description, + Deprecated: input.DeprecationMessage, + } + translatedSchema := make(map[string]jsonschema.SchemaJSON) + + for k, s := range input.Schema { + translatedSchema[k] = SchemaFromRaw(s) + } + result.Schema = translatedSchema + + if input.Timeouts != nil { + timeouts := &jsonschema.ResourceTimeoutJSON{} + if t := input.Timeouts; t != nil { + if t.Create != nil { + timeouts.Create = int(t.Create.Minutes()) + } + if t.Read != nil { + timeouts.Read = int(t.Read.Minutes()) + } + if t.Delete != nil { + timeouts.Delete = int(t.Delete.Minutes()) + } + if t.Update != nil { + timeouts.Update = int(t.Update.Minutes()) + } + } + result.Timeouts = timeouts + } + + return result, nil +} + +func SchemaFromRaw(input *schema.Schema) jsonschema.SchemaJSON { + return jsonschema.SchemaJSON{ + Type: input.Type.String(), + ConfigMode: decodeConfigMode(input.ConfigMode), + Optional: input.Optional, + Required: input.Required, + Default: input.Default, + Description: input.Description, + Computed: input.Computed, + ForceNew: input.ForceNew, + Elem: decodeElem(input.Elem), + MaxItems: input.MaxItems, + MinItems: input.MinItems, + Deprecated: input.Deprecated, + } +} + +func decodeConfigMode(input schema.SchemaConfigMode) (out string) { + switch input { + case 1: + out = "Auto" + case 2: + out = "Block" + case 4: + out = "Attribute" + } + return +} + +func decodeElem(input interface{}) interface{} { + switch t := input.(type) { + case bool: + return t + case string: + return t + case int: + return t + case float32, float64: + return t + case *schema.Schema: + return SchemaFromRaw(t) + case *schema.Resource: + r, _ := ResourceFromRaw(t) + return r + } + return nil +} diff --git a/helpers/providerjson/transform/util.go b/helpers/providerjson/transform/util.go new file mode 100644 index 00000000..e8f7f457 --- /dev/null +++ b/helpers/providerjson/transform/util.go @@ -0,0 +1,31 @@ +package transform + +import ( + "github.com/hashicorp/terraform-plugin-framework/attr" + "github.com/hashicorp/terraform-plugin-framework/types" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" +) + +func DecodeValueType(input attr.Value) string { + switch input.(type) { + case types.Bool: + return jsonschema.SchemaTypeBool + case types.Float64: + return jsonschema.SchemaTypeFloat + case types.Int64: + return jsonschema.SchemaTypeInt + case types.List: + return jsonschema.SchemaTypeList + case types.Map: + return jsonschema.SchemaTypeMap + case types.Number: + return jsonschema.SchemaTypeNumber + case types.Object: + return jsonschema.SchemaTypeObject + case types.Set: + return jsonschema.SchemaTypeSet + case types.String: + return jsonschema.SchemaTypeString + } + return "" +} diff --git a/helpers/providerjson/write.go b/helpers/providerjson/write.go deleted file mode 100644 index 227bf170..00000000 --- a/helpers/providerjson/write.go +++ /dev/null @@ -1,46 +0,0 @@ -package providerjson - -import ( - "encoding/json" - "os" -) - -func DumpWithWrapper(wrapper *ProviderWrapper, data *ProviderJSON) error { - if s, err := ProviderFromRaw(data); err != nil { - return err - } else { - wrapper.ProviderSchema = s - } - - if err := json.NewEncoder(os.Stdout).Encode(wrapper); err != nil { - return err - } - - return nil -} - -func WriteWithWrapper(base, wrapper *ProviderWrapper, data *ProviderJSON, filename, providerVersion string) error { - if s, err := ProviderFromRaw(data); err != nil { - return err - } else { - if base != nil { - addNewSince(base.ProviderSchema, s, providerVersion) - } - wrapper.ProviderSchema = s - } - - f, err := os.Create(filename) - if err != nil { - return err - } - defer f.Close() - - encoder := json.NewEncoder(f) - encoder.SetIndent("", " ") - - if err := encoder.Encode(wrapper); err != nil { - return err - } - - return nil -} diff --git a/helpers/schema-api/main.go b/helpers/schema-api/main.go index c12dbbdb..734dc6c6 100644 --- a/helpers/schema-api/main.go +++ b/helpers/schema-api/main.go @@ -2,12 +2,14 @@ package main import ( "flag" - "fmt" "log" "os" "github.com/vk-cs/terraform-provider-vkcs/helpers/changelog" - "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson" + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/json" + "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" + transform "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/transform/provider" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/provider" ) @@ -19,31 +21,37 @@ func main() { changelogPath := f.String("changelog", "CHANGELOG.md", "path to changelog file") if err := f.Parse(os.Args[1:]); err != nil { - fmt.Printf("error parsing args: %+v", err) - os.Exit(1) + log.Fatalf("error parsing args: %+v", err) } data := loadData() if exportSchema != nil { log.Printf("dumping schema for '%s'", *providerName) - wrappedProvider := &providerjson.ProviderWrapper{ - ProviderName: *providerName, - SchemaVersion: "1", - } + cl, err := changelog.NewChangelogFromFile(*changelogPath) if err != nil { - panic(err) + log.Fatalf("error parsing changelog: %+v", err) + } + + baseProvider, _ := json.ReadWithWrapper(*exportSchema) + wrappedProvider := &schema.ProviderWrapper{ + ProviderName: *providerName, + ProviderVersion: cl.Versions[0].Version, + SchemaVersion: "1", } - curVersion := cl.Versions[0].Version - baseProvider, _ := providerjson.ReadWithWrapper(*exportSchema) - if err := providerjson.WriteWithWrapper(baseProvider, wrappedProvider, data, *exportSchema, curVersion); err != nil { + + wrappedProvider, err = transform.WrappedProviderFromRaw(data, baseProvider, wrappedProvider) + if err != nil { + log.Fatalf("error transforming provider into json schema: %+v", err) + } + + if err := json.WriteWithWrapper(wrappedProvider, *exportSchema); err != nil { log.Fatalf("error writing provider schema for %q to %q: %+v", *providerName, *exportSchema, err) } } } -func loadData() *providerjson.ProviderJSON { - p := provider.ProviderBase() - return (*providerjson.ProviderJSON)(p) +func loadData() *schema.ProviderJSON { + return &schema.ProviderJSON{SDKProvider: provider.SDKProviderBase(), Provider: provider.ProviderBase()} } diff --git a/main.go b/main.go index e0cd6116..2b2cddd0 100755 --- a/main.go +++ b/main.go @@ -1,11 +1,56 @@ package main import ( - "github.com/hashicorp/terraform-plugin-sdk/v2/plugin" + "context" + "flag" + "log" + + "github.com/hashicorp/terraform-plugin-framework/providerserver" + "github.com/hashicorp/terraform-plugin-go/tfprotov6" + "github.com/hashicorp/terraform-plugin-go/tfprotov6/tf6server" + "github.com/hashicorp/terraform-plugin-mux/tf5to6server" + "github.com/hashicorp/terraform-plugin-mux/tf6muxserver" "github.com/vk-cs/terraform-provider-vkcs/vkcs/provider" ) func main() { - plugin.Serve(&plugin.ServeOpts{ - ProviderFunc: provider.Provider}) + debugFlag := flag.Bool("debug", false, "Start provider in debug mode.") + flag.Parse() + + ctx := context.Background() + + upgradedSdkServer, err := tf5to6server.UpgradeServer( + ctx, + provider.SDKProvider().GRPCProvider, + ) + if err != nil { + log.Fatal(err) + } + + providers := []func() tfprotov6.ProviderServer{ + providerserver.NewProtocol6(provider.Provider()), + func() tfprotov6.ProviderServer { + return upgradedSdkServer + }, + } + + muxServer, err := tf6muxserver.NewMuxServer(ctx, providers...) + if err != nil { + log.Fatal(err) + } + + var serveOpts []tf6server.ServeOpt + + if *debugFlag { + serveOpts = append(serveOpts, tf6server.WithManagedDebug()) + } + + err = tf6server.Serve( + "vk-cs/vkcs", + muxServer.ProviderServer, + serveOpts..., + ) + if err != nil { + log.Fatal(err) + } } diff --git a/templates/index.md.tmpl b/templates/index.md.tmpl index 137a9229..c464a103 100644 --- a/templates/index.md.tmpl +++ b/templates/index.md.tmpl @@ -14,7 +14,7 @@ Use the navigation to the left to read about the available resources. ## Example Usage -Terraform 1.0 and later: +Terraform 1.1.5 and later: ```terraform # Configure the vkcs provider diff --git a/vkcs/blockstorage/blockstorage_snapshot.go b/vkcs/blockstorage/blockstorage_snapshot.go index 8e3aa2ef..a35598d5 100644 --- a/vkcs/blockstorage/blockstorage_snapshot.go +++ b/vkcs/blockstorage/blockstorage_snapshot.go @@ -6,10 +6,10 @@ import ( "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/blockstorage/v3/snapshots" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) -func blockStorageSnapshotStateRefreshFunc(client *gophercloud.ServiceClient, volumeSnapshotID string) resource.StateRefreshFunc { +func blockStorageSnapshotStateRefreshFunc(client *gophercloud.ServiceClient, volumeSnapshotID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { v, err := snapshots.Get(client, volumeSnapshotID).Extract() if err != nil { diff --git a/vkcs/blockstorage/blockstorage_volume.go b/vkcs/blockstorage/blockstorage_volume.go index 7ec19c6a..a18a56af 100644 --- a/vkcs/blockstorage/blockstorage_volume.go +++ b/vkcs/blockstorage/blockstorage_volume.go @@ -6,7 +6,7 @@ import ( "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/blockstorage/extensions/volumeactions" "github.com/gophercloud/gophercloud/openstack/blockstorage/v3/volumes" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" ) @@ -19,7 +19,7 @@ func (opts volumeChangeTypeOpts) ToVolumeChangeTypeMap() (map[string]interface{} return util.BuildRequest(opts, "os-retype") } -func blockStorageVolumeStateRefreshFunc(client *gophercloud.ServiceClient, volumeID string) resource.StateRefreshFunc { +func blockStorageVolumeStateRefreshFunc(client *gophercloud.ServiceClient, volumeID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { v, err := volumes.Get(client, volumeID).Extract() if err != nil { diff --git a/vkcs/blockstorage/data_source_vkcs_blockstorage_snapshot_test.go b/vkcs/blockstorage/data_source_vkcs_blockstorage_snapshot_test.go index 8ddf3758..8af53fae 100644 --- a/vkcs/blockstorage/data_source_vkcs_blockstorage_snapshot_test.go +++ b/vkcs/blockstorage/data_source_vkcs_blockstorage_snapshot_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/blockstorage/data_source_vkcs_blockstorage_volume_test.go b/vkcs/blockstorage/data_source_vkcs_blockstorage_volume_test.go index 1b822177..30eaccdd 100644 --- a/vkcs/blockstorage/data_source_vkcs_blockstorage_volume_test.go +++ b/vkcs/blockstorage/data_source_vkcs_blockstorage_volume_test.go @@ -3,7 +3,7 @@ package blockstorage_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/blockstorage/import_vkcs_blockstorage_snapshot_test.go b/vkcs/blockstorage/import_vkcs_blockstorage_snapshot_test.go index a065951a..8fe6aea8 100644 --- a/vkcs/blockstorage/import_vkcs_blockstorage_snapshot_test.go +++ b/vkcs/blockstorage/import_vkcs_blockstorage_snapshot_test.go @@ -3,7 +3,7 @@ package blockstorage_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/blockstorage/import_vkcs_blockstorage_volume_test.go b/vkcs/blockstorage/import_vkcs_blockstorage_volume_test.go index bca8057d..3a2a80ac 100644 --- a/vkcs/blockstorage/import_vkcs_blockstorage_volume_test.go +++ b/vkcs/blockstorage/import_vkcs_blockstorage_volume_test.go @@ -3,7 +3,7 @@ package blockstorage_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/blockstorage/resource_vkcs_blockstorage_volume.go b/vkcs/blockstorage/resource_vkcs_blockstorage_volume.go index 6bb12a21..863a3412 100644 --- a/vkcs/blockstorage/resource_vkcs_blockstorage_volume.go +++ b/vkcs/blockstorage/resource_vkcs_blockstorage_volume.go @@ -8,7 +8,7 @@ import ( "github.com/gophercloud/gophercloud/openstack/blockstorage/extensions/volumeactions" "github.com/gophercloud/gophercloud/openstack/blockstorage/v3/volumes" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -155,7 +155,7 @@ func resourceBlockStorageVolumeCreate(ctx context.Context, d *schema.ResourceDat return diag.Errorf("error creating vkcs_blockstorage_volume: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{bsVolumeStatusBuild, bsVolumeStatusDownloading}, Target: []string{bsVolumeStatusActive}, Refresh: blockStorageVolumeStateRefreshFunc(blockStorageClient, v.ID), @@ -236,7 +236,7 @@ func resourceBlockStorageVolumeUpdate(ctx context.Context, d *schema.ResourceDat return diag.Errorf("error extending vkcs_blockstorage_volume %s size: %s", d.Id(), err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{bsVolumeStatusBuild, bsVolumeStatusDownloading}, Target: []string{bsVolumeStatusActive, bsVolumeStatusInUse}, Refresh: blockStorageVolumeStateRefreshFunc(blockStorageClient, d.Id()), @@ -265,7 +265,7 @@ func resourceBlockStorageVolumeUpdate(ctx context.Context, d *schema.ResourceDat if err != nil { return diag.Errorf("error changing type of vkcs_blockstorage_volume %s", d.Id()) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{bsVolumeStatusBuild, bsVolumeStatusRetype}, Target: []string{bsVolumeStatusActive, bsVolumeStatusInUse}, Refresh: blockStorageVolumeStateRefreshFunc(blockStorageClient, d.Id()), @@ -294,7 +294,7 @@ func resourceBlockStorageVolumeDelete(ctx context.Context, d *schema.ResourceDat return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_blockstorage_volume")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{bsVolumeStatusActive, bsVolumeStatusShutdown, bsVolumeStatusInUse}, Target: []string{bsVolumeStatusDeleted}, Refresh: blockStorageVolumeStateRefreshFunc(blockStorageClient, d.Id()), diff --git a/vkcs/blockstorage/resource_vkcs_blockstorage_volume_snapshot.go b/vkcs/blockstorage/resource_vkcs_blockstorage_volume_snapshot.go index d4b046e5..6198cc8c 100644 --- a/vkcs/blockstorage/resource_vkcs_blockstorage_volume_snapshot.go +++ b/vkcs/blockstorage/resource_vkcs_blockstorage_volume_snapshot.go @@ -7,7 +7,7 @@ import ( "github.com/gophercloud/gophercloud/openstack/blockstorage/v3/snapshots" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -116,7 +116,7 @@ func resourceBlockStorageSnapshotCreate(ctx context.Context, d *schema.ResourceD // Wait for the volume snapshot to become available. log.Printf("[DEBUG] Waiting for vkcs_blockstorage_volume_snapshot %s to become available", snapshot.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{bsSnapshotStatusBuild}, Target: []string{bsSnapshotStatusActive}, Refresh: blockStorageSnapshotStateRefreshFunc(blockStorageClient, snapshot.ID), @@ -176,7 +176,7 @@ func resourceBlockStorageSnapshotUpdate(ctx context.Context, d *schema.ResourceD if err != nil { return diag.Errorf("error updating vkcs_blockstorage_snapshot") } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{bsSnapshotStatusBuild}, Target: []string{bsSnapshotStatusActive}, Refresh: blockStorageSnapshotStateRefreshFunc(blockStorageClient, d.Id()), @@ -199,7 +199,7 @@ func resourceBlockStorageSnapshotUpdate(ctx context.Context, d *schema.ResourceD if err != nil { return diag.Errorf("error updating vkcs_blockstorage_snapshot metadata") } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{bsSnapshotStatusBuild}, Target: []string{bsSnapshotStatusActive}, Refresh: blockStorageSnapshotStateRefreshFunc(blockStorageClient, d.Id()), @@ -227,7 +227,7 @@ func resourceBlockStorageSnapshotDelete(ctx context.Context, d *schema.ResourceD return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_blockstorage_snapshot")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{bsSnapshotStatusActive, bsSnapshotStatusShutdown}, Target: []string{bsSnapshotStatusDeleted}, Refresh: blockStorageVolumeStateRefreshFunc(blockStorageClient, d.Id()), diff --git a/vkcs/blockstorage/resource_vkcs_blockstorage_volume_snapshot_test.go b/vkcs/blockstorage/resource_vkcs_blockstorage_volume_snapshot_test.go index b4df1cc1..55757af2 100644 --- a/vkcs/blockstorage/resource_vkcs_blockstorage_volume_snapshot_test.go +++ b/vkcs/blockstorage/resource_vkcs_blockstorage_volume_snapshot_test.go @@ -5,8 +5,8 @@ import ( "testing" "github.com/gophercloud/gophercloud/openstack/blockstorage/v3/snapshots" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" ) diff --git a/vkcs/blockstorage/resource_vkcs_blockstorage_volume_test.go b/vkcs/blockstorage/resource_vkcs_blockstorage_volume_test.go index 3c3d6a87..bda7bdb4 100644 --- a/vkcs/blockstorage/resource_vkcs_blockstorage_volume_test.go +++ b/vkcs/blockstorage/resource_vkcs_blockstorage_volume_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/compute/compute_floatingip_associate.go b/vkcs/compute/compute_floatingip_associate.go index 0e9070a1..fae22189 100644 --- a/vkcs/compute/compute_floatingip_associate.go +++ b/vkcs/compute/compute_floatingip_associate.go @@ -4,12 +4,11 @@ import ( "fmt" "strings" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/compute/v2/extensions/floatingips" "github.com/gophercloud/gophercloud/openstack/compute/v2/servers" nfloatingips "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/layer3/floatingips" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) func ParseComputeFloatingIPAssociateID(id string) (string, string, string, error) { @@ -72,7 +71,7 @@ func computeFloatingIPAssociateComputeExists(computeClient *gophercloud.ServiceC } func computeFloatingIPAssociateCheckAssociation( - computeClient *gophercloud.ServiceClient, instanceID, floatingIP string) resource.StateRefreshFunc { + computeClient *gophercloud.ServiceClient, instanceID, floatingIP string) retry.StateRefreshFunc { return func() (interface{}, string, error) { instance, err := servers.Get(computeClient, instanceID).Extract() if err != nil { diff --git a/vkcs/compute/compute_interface_attach.go b/vkcs/compute/compute_interface_attach.go index 16d216e3..fd3117e2 100644 --- a/vkcs/compute/compute_interface_attach.go +++ b/vkcs/compute/compute_interface_attach.go @@ -5,14 +5,13 @@ import ( "log" "strings" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/compute/v2/extensions/attachinterfaces" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) func computeInterfaceAttachAttachFunc( - computeClient *gophercloud.ServiceClient, instanceID, attachmentID string) resource.StateRefreshFunc { + computeClient *gophercloud.ServiceClient, instanceID, attachmentID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { va, err := attachinterfaces.Get(computeClient, instanceID, attachmentID).Extract() if err != nil { @@ -27,7 +26,7 @@ func computeInterfaceAttachAttachFunc( } func computeInterfaceAttachDetachFunc( - computeClient *gophercloud.ServiceClient, instanceID, attachmentID string) resource.StateRefreshFunc { + computeClient *gophercloud.ServiceClient, instanceID, attachmentID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { log.Printf("[DEBUG] Attempting to detach vkcs_compute_interface_attach %s from instance %s", attachmentID, instanceID) diff --git a/vkcs/compute/compute_volume_attach.go b/vkcs/compute/compute_volume_attach.go index 1effb3ec..b0bc4633 100644 --- a/vkcs/compute/compute_volume_attach.go +++ b/vkcs/compute/compute_volume_attach.go @@ -5,11 +5,10 @@ import ( "log" "strings" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/blockstorage/v3/volumes" "github.com/gophercloud/gophercloud/openstack/compute/v2/extensions/volumeattach" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) func ComputeVolumeAttachParseID(id string) (string, string, error) { @@ -24,7 +23,7 @@ func ComputeVolumeAttachParseID(id string) (string, string, error) { return instanceID, attachmentID, nil } -func computeVolumeAttachAttachFunc(computeClient *gophercloud.ServiceClient, blockStorageClient *gophercloud.ServiceClient, instanceID, attachmentID string, volumeID string) resource.StateRefreshFunc { +func computeVolumeAttachAttachFunc(computeClient *gophercloud.ServiceClient, blockStorageClient *gophercloud.ServiceClient, instanceID, attachmentID string, volumeID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { va, err := volumeattach.Get(computeClient, instanceID, attachmentID).Extract() if err != nil { @@ -49,7 +48,7 @@ func computeVolumeAttachAttachFunc(computeClient *gophercloud.ServiceClient, blo } } -func computeVolumeAttachDetachFunc(computeClient *gophercloud.ServiceClient, instanceID, attachmentID string) resource.StateRefreshFunc { +func computeVolumeAttachDetachFunc(computeClient *gophercloud.ServiceClient, instanceID, attachmentID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { log.Printf("[DEBUG] vkcs_compute_volume_attach attempting to detach VKCS volume %s from instance %s", attachmentID, instanceID) diff --git a/vkcs/compute/data_source_vkcs_compute_availability_zones_test.go b/vkcs/compute/data_source_vkcs_compute_availability_zones_test.go index 9b9ac720..de523b16 100644 --- a/vkcs/compute/data_source_vkcs_compute_availability_zones_test.go +++ b/vkcs/compute/data_source_vkcs_compute_availability_zones_test.go @@ -4,7 +4,7 @@ import ( "regexp" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/data_source_vkcs_compute_flavor_test.go b/vkcs/compute/data_source_vkcs_compute_flavor_test.go index 60054d56..eb6e6ca3 100644 --- a/vkcs/compute/data_source_vkcs_compute_flavor_test.go +++ b/vkcs/compute/data_source_vkcs_compute_flavor_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/data_source_vkcs_compute_instance_test.go b/vkcs/compute/data_source_vkcs_compute_instance_test.go index 0fc67d39..b63f9e42 100644 --- a/vkcs/compute/data_source_vkcs_compute_instance_test.go +++ b/vkcs/compute/data_source_vkcs_compute_instance_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/data_source_vkcs_compute_keypair_test.go b/vkcs/compute/data_source_vkcs_compute_keypair_test.go index e0efdc4c..a72ce057 100644 --- a/vkcs/compute/data_source_vkcs_compute_keypair_test.go +++ b/vkcs/compute/data_source_vkcs_compute_keypair_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/data_source_vkcs_compute_quotaset_test.go b/vkcs/compute/data_source_vkcs_compute_quotaset_test.go index 824a954f..6d94bba1 100644 --- a/vkcs/compute/data_source_vkcs_compute_quotaset_test.go +++ b/vkcs/compute/data_source_vkcs_compute_quotaset_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/import_vkcs_compute_floatingip_associate_test.go b/vkcs/compute/import_vkcs_compute_floatingip_associate_test.go index 6e49ad65..92fb9da0 100644 --- a/vkcs/compute/import_vkcs_compute_floatingip_associate_test.go +++ b/vkcs/compute/import_vkcs_compute_floatingip_associate_test.go @@ -3,7 +3,7 @@ package compute_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/import_vkcs_compute_instance_test.go b/vkcs/compute/import_vkcs_compute_instance_test.go index 13b011c3..543fd1eb 100644 --- a/vkcs/compute/import_vkcs_compute_instance_test.go +++ b/vkcs/compute/import_vkcs_compute_instance_test.go @@ -3,7 +3,7 @@ package compute_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/import_vkcs_compute_interface_attach_test.go b/vkcs/compute/import_vkcs_compute_interface_attach_test.go index 262e697f..80b723a3 100644 --- a/vkcs/compute/import_vkcs_compute_interface_attach_test.go +++ b/vkcs/compute/import_vkcs_compute_interface_attach_test.go @@ -3,7 +3,7 @@ package compute_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/import_vkcs_compute_keypair_test.go b/vkcs/compute/import_vkcs_compute_keypair_test.go index 71cb6932..4a487f99 100644 --- a/vkcs/compute/import_vkcs_compute_keypair_test.go +++ b/vkcs/compute/import_vkcs_compute_keypair_test.go @@ -3,7 +3,7 @@ package compute_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/import_vkcs_compute_servergroup_test.go b/vkcs/compute/import_vkcs_compute_servergroup_test.go index 3b95d08d..9948f5c4 100644 --- a/vkcs/compute/import_vkcs_compute_servergroup_test.go +++ b/vkcs/compute/import_vkcs_compute_servergroup_test.go @@ -3,7 +3,7 @@ package compute_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/import_vkcs_compute_volume_attach_test.go b/vkcs/compute/import_vkcs_compute_volume_attach_test.go index d7f4363c..029358f0 100644 --- a/vkcs/compute/import_vkcs_compute_volume_attach_test.go +++ b/vkcs/compute/import_vkcs_compute_volume_attach_test.go @@ -3,7 +3,7 @@ package compute_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/compute/resource_vkcs_compute_floatingip_associate.go b/vkcs/compute/resource_vkcs_compute_floatingip_associate.go index bf1cc08a..2a0e9b5b 100644 --- a/vkcs/compute/resource_vkcs_compute_floatingip_associate.go +++ b/vkcs/compute/resource_vkcs_compute_floatingip_associate.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" @@ -104,7 +104,7 @@ func resourceComputeFloatingIPAssociateCreate(ctx context.Context, d *schema.Res } if waitUntilAssociated { - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"NOT_ASSOCIATED"}, Target: []string{"ASSOCIATED"}, Refresh: computeFloatingIPAssociateCheckAssociation(computeClient, instanceID, floatingIP), diff --git a/vkcs/compute/resource_vkcs_compute_floatingip_associate_test.go b/vkcs/compute/resource_vkcs_compute_floatingip_associate_test.go index 15b399a6..2e366090 100644 --- a/vkcs/compute/resource_vkcs_compute_floatingip_associate_test.go +++ b/vkcs/compute/resource_vkcs_compute_floatingip_associate_test.go @@ -7,8 +7,8 @@ import ( "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/compute/v2/servers" "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/layer3/floatingips" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/compute" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/compute/resource_vkcs_compute_instance.go b/vkcs/compute/resource_vkcs_compute_instance.go index 4d23c027..090f0fb0 100755 --- a/vkcs/compute/resource_vkcs_compute_instance.go +++ b/vkcs/compute/resource_vkcs_compute_instance.go @@ -28,7 +28,7 @@ import ( imagesutils "github.com/gophercloud/utils/openstack/imageservice/v2/images" "github.com/gophercloud/utils/terraform/hashcode" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -532,7 +532,7 @@ func resourceComputeInstanceCreate(ctx context.Context, d *schema.ResourceData, "[DEBUG] Waiting for instance (%s) to become running", server.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"BUILD"}, Target: []string{"ACTIVE"}, Refresh: ServerStateRefreshFunc(computeClient, server.ID), @@ -541,7 +541,7 @@ func resourceComputeInstanceCreate(ctx context.Context, d *schema.ResourceData, MinTimeout: 3 * time.Second, } - err = resource.RetryContext(ctx, stateConf.Timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, stateConf.Timeout, func() *retry.RetryError { _, err = stateConf.WaitForStateContext(ctx) if err != nil { log.Printf("[DEBUG] Retrying after error: %s", err) @@ -562,7 +562,7 @@ func resourceComputeInstanceCreate(ctx context.Context, d *schema.ResourceData, if err != nil { return diag.Errorf("Error stopping VKCS instance: %s", err) } - stopStateConf := &resource.StateChangeConf{ + stopStateConf := &retry.StateChangeConf{ //Pending: []string{"ACTIVE"}, Target: []string{"SHUTOFF"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -722,7 +722,7 @@ func resourceComputeInstanceUpdate(ctx context.Context, d *schema.ResourceData, if err != nil { return diag.Errorf("Error shelve VKCS instance: %s", err) } - shelveStateConf := &resource.StateChangeConf{ + shelveStateConf := &retry.StateChangeConf{ //Pending: []string{"ACTIVE"}, Target: []string{"SHELVED_OFFLOADED"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -742,7 +742,7 @@ func resourceComputeInstanceUpdate(ctx context.Context, d *schema.ResourceData, if err != nil { return diag.Errorf("Error stopping VKCS instance: %s", err) } - stopStateConf := &resource.StateChangeConf{ + stopStateConf := &retry.StateChangeConf{ //Pending: []string{"ACTIVE"}, Target: []string{"SHUTOFF"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -772,7 +772,7 @@ func resourceComputeInstanceUpdate(ctx context.Context, d *schema.ResourceData, return diag.Errorf("Error starting VKCS instance: %s", err) } } - startStateConf := &resource.StateChangeConf{ + startStateConf := &retry.StateChangeConf{ //Pending: []string{"SHUTOFF"}, Target: []string{"ACTIVE"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -903,7 +903,7 @@ func resourceComputeInstanceUpdate(ctx context.Context, d *schema.ResourceData, // Resize instance without confirmation if specified by user. if ignoreResizeConfirmation { - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"RESIZE", "VERIFY_RESIZE"}, Target: []string{"ACTIVE", "SHUTOFF"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -917,7 +917,7 @@ func resourceComputeInstanceUpdate(ctx context.Context, d *schema.ResourceData, return diag.Errorf("Error waiting for instance (%s) to resize: %s", d.Id(), err) } } else { - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"RESIZE"}, Target: []string{"VERIFY_RESIZE"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -938,7 +938,7 @@ func resourceComputeInstanceUpdate(ctx context.Context, d *schema.ResourceData, return diag.Errorf("Error confirming resize of VKCS server: %s", err) } - stateConf = &resource.StateChangeConf{ + stateConf = &retry.StateChangeConf{ Pending: []string{"VERIFY_RESIZE"}, Target: []string{"ACTIVE", "SHUTOFF"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -981,7 +981,7 @@ func resourceComputeInstanceDelete(ctx context.Context, d *schema.ResourceData, if err != nil { log.Printf("[WARN] Error stopping vkcs_compute_instance: %s", err) } else { - stopStateConf := &resource.StateChangeConf{ + stopStateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"SHUTOFF"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -1009,7 +1009,7 @@ func resourceComputeInstanceDelete(ctx context.Context, d *schema.ResourceData, } else { for _, network := range allInstanceNetworks { if network.Port != "" { - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{""}, Target: []string{"DETACHED"}, Refresh: computeInterfaceAttachDetachFunc(computeClient, d.Id(), network.Port), @@ -1046,7 +1046,7 @@ func resourceComputeInstanceDelete(ctx context.Context, d *schema.ResourceData, // Wait for the instance to delete before moving on. log.Printf("[DEBUG] Waiting for instance (%s) to delete", d.Id()) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE", "SHUTOFF"}, Target: []string{"DELETED", "SOFT_DELETED"}, Refresh: ServerStateRefreshFunc(computeClient, d.Id()), @@ -1147,9 +1147,9 @@ func resourceComputeInstanceImportState(ctx context.Context, d *schema.ResourceD return results, nil } -// ServerStateRefreshFunc returns a resource.StateRefreshFunc that is used to watch +// ServerStateRefreshFunc returns a retry.StateRefreshFunc that is used to watch // an VKCS instance. -func ServerStateRefreshFunc(client *gophercloud.ServiceClient, instanceID string) resource.StateRefreshFunc { +func ServerStateRefreshFunc(client *gophercloud.ServiceClient, instanceID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { s, err := servers.Get(client, instanceID).Extract() if err != nil { diff --git a/vkcs/compute/resource_vkcs_compute_instance_test.go b/vkcs/compute/resource_vkcs_compute_instance_test.go index 4071390e..705cb40e 100755 --- a/vkcs/compute/resource_vkcs_compute_instance_test.go +++ b/vkcs/compute/resource_vkcs_compute_instance_test.go @@ -11,14 +11,15 @@ import ( "github.com/google/go-cmp/cmp" "github.com/gophercloud/gophercloud/openstack/compute/v2/extensions/bootfromvolume" "github.com/gophercloud/gophercloud/openstack/compute/v2/extensions/volumeattach" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" + "github.com/gophercloud/gophercloud/openstack/compute/v2/servers" "github.com/gophercloud/gophercloud/pagination" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/compute" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" ) func TestAccComputeInstance_basic(t *testing.T) { diff --git a/vkcs/compute/resource_vkcs_compute_interface_attach.go b/vkcs/compute/resource_vkcs_compute_interface_attach.go index 20b78831..7d4462ca 100644 --- a/vkcs/compute/resource_vkcs_compute_interface_attach.go +++ b/vkcs/compute/resource_vkcs_compute_interface_attach.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -118,7 +118,7 @@ func resourceComputeInterfaceAttachCreate(ctx context.Context, d *schema.Resourc return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ATTACHING"}, Target: []string{"ATTACHED"}, Refresh: computeInterfaceAttachAttachFunc(computeClient, instanceID, attachment.PortID), @@ -184,7 +184,7 @@ func resourceComputeInterfaceAttachDelete(ctx context.Context, d *schema.Resourc return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{""}, Target: []string{"DETACHED"}, Refresh: computeInterfaceAttachDetachFunc(computeClient, instanceID, attachmentID), diff --git a/vkcs/compute/resource_vkcs_compute_interface_attach_test.go b/vkcs/compute/resource_vkcs_compute_interface_attach_test.go index 3ff920ec..f512247c 100644 --- a/vkcs/compute/resource_vkcs_compute_interface_attach_test.go +++ b/vkcs/compute/resource_vkcs_compute_interface_attach_test.go @@ -5,8 +5,8 @@ import ( "testing" "github.com/gophercloud/gophercloud/openstack/compute/v2/extensions/attachinterfaces" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/compute" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/compute/resource_vkcs_compute_keypair_test.go b/vkcs/compute/resource_vkcs_compute_keypair_test.go index c8818bd4..17582101 100644 --- a/vkcs/compute/resource_vkcs_compute_keypair_test.go +++ b/vkcs/compute/resource_vkcs_compute_keypair_test.go @@ -5,8 +5,8 @@ import ( "regexp" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/compute/resource_vkcs_compute_servergroup_test.go b/vkcs/compute/resource_vkcs_compute_servergroup_test.go index 28e64b06..9471a70c 100644 --- a/vkcs/compute/resource_vkcs_compute_servergroup_test.go +++ b/vkcs/compute/resource_vkcs_compute_servergroup_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/compute/resource_vkcs_compute_volume_attach.go b/vkcs/compute/resource_vkcs_compute_volume_attach.go index 488a66ac..bdb94e02 100644 --- a/vkcs/compute/resource_vkcs_compute_volume_attach.go +++ b/vkcs/compute/resource_vkcs_compute_volume_attach.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -84,14 +84,14 @@ func resourceComputeVolumeAttachCreate(ctx context.Context, d *schema.ResourceDa var attachment *volumeattach.VolumeAttachment timeout := d.Timeout(schema.TimeoutCreate) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { attachment, err = volumeattach.Create(computeClient, instanceID, attachOpts).Extract() if err != nil { if _, ok := err.(gophercloud.ErrDefault400); ok { - return resource.RetryableError(err) + return retry.RetryableError(err) } - return resource.NonRetryableError(err) + return retry.NonRetryableError(err) } return nil @@ -101,7 +101,7 @@ func resourceComputeVolumeAttachCreate(ctx context.Context, d *schema.ResourceDa return diag.Errorf("Error creating vkcs_compute_volume_attach %s: %s", instanceID, err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ATTACHING"}, Target: []string{"ATTACHED"}, Refresh: computeVolumeAttachAttachFunc(computeClient, blockStorageClient, instanceID, attachment.ID, volumeID), @@ -161,7 +161,7 @@ func resourceComputeVolumeAttachDelete(ctx context.Context, d *schema.ResourceDa return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{""}, Target: []string{"DETACHED"}, Refresh: computeVolumeAttachDetachFunc(computeClient, instanceID, attachmentID), diff --git a/vkcs/compute/resource_vkcs_compute_volume_attach_test.go b/vkcs/compute/resource_vkcs_compute_volume_attach_test.go index 58cbf859..283baa0f 100644 --- a/vkcs/compute/resource_vkcs_compute_volume_attach_test.go +++ b/vkcs/compute/resource_vkcs_compute_volume_attach_test.go @@ -5,8 +5,8 @@ import ( "testing" "github.com/gophercloud/gophercloud/openstack/compute/v2/extensions/volumeattach" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/compute" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/db/data_source_vkcs_db_backup_test.go b/vkcs/db/data_source_vkcs_db_backup_test.go index 8436dcee..428c6730 100644 --- a/vkcs/db/data_source_vkcs_db_backup_test.go +++ b/vkcs/db/data_source_vkcs_db_backup_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/data_source_vkcs_db_config_group_test.go b/vkcs/db/data_source_vkcs_db_config_group_test.go index 5500840a..7e7bbd2b 100644 --- a/vkcs/db/data_source_vkcs_db_config_group_test.go +++ b/vkcs/db/data_source_vkcs_db_config_group_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/data_source_vkcs_db_database_test.go b/vkcs/db/data_source_vkcs_db_database_test.go index 623e3649..99336e0d 100755 --- a/vkcs/db/data_source_vkcs_db_database_test.go +++ b/vkcs/db/data_source_vkcs_db_database_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/data_source_vkcs_db_datastore_capabilities.go b/vkcs/db/data_source_vkcs_db_datastore_capabilities.go index 8dc87564..898e3173 100644 --- a/vkcs/db/data_source_vkcs_db_datastore_capabilities.go +++ b/vkcs/db/data_source_vkcs_db_datastore_capabilities.go @@ -5,131 +5,162 @@ import ( "fmt" "strconv" - "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + "github.com/hashicorp/terraform-plugin-framework/diag" + "github.com/hashicorp/terraform-plugin-framework/types" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/datastores" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" ) -func DataSourceDatabaseDatastoreCapabilities() *schema.Resource { - return &schema.Resource{ - ReadContext: dataSourceDatabaseDatastoreCapabilitiesRead, - Schema: map[string]*schema.Schema{ - "region": { - Type: schema.TypeString, +// Ensure the implementation satisfies the desired interfaces. +var _ datasource.DataSource = &DatastoreCapabilitiesDataSource{} + +func NewDatastoreCapabilitiesDataSource() datasource.DataSource { + return &DatastoreCapabilitiesDataSource{} +} + +type DatastoreCapabilitiesDataSource struct { + config clients.Config +} + +type DatastoreCapabilitiesDataSourceModel struct { + ID types.String `tfsdk:"id"` + DatastoreName types.String `tfsdk:"datastore_name"` + DatastoreVersionID types.String `tfsdk:"datastore_version_id"` + Capabilities []DatastoreCapabilityItemModel `tfsdk:"capabilities"` + Region types.String `tfsdk:"region"` +} + +type DatastoreCapabilityItemModel struct { + Name types.String `tfsdk:"name"` + Description types.String `tfsdk:"description"` + Params []DatastoreCapabilityParamsModel `tfsdk:"params"` + ShouldBeOnMaster types.Bool `tfsdk:"should_be_on_master"` + AllowMajorUpgrade types.Bool `tfsdk:"allow_major_upgrade"` + AllowUpgradeFromBackup types.Bool `tfsdk:"allow_upgrade_from_backup"` +} + +type DatastoreCapabilityParamsModel struct { + Name types.String `tfsdk:"name"` + Required types.Bool `tfsdk:"required"` + Type types.String `tfsdk:"type"` + ElementType types.String `tfsdk:"element_type"` + EnumValues types.List `tfsdk:"enum_values"` + DefaultValue types.String `tfsdk:"default_value"` + Min types.Float64 `tfsdk:"min"` + Max types.Float64 `tfsdk:"max"` + Regex types.String `tfsdk:"regex"` + Masked types.Bool `tfsdk:"masked"` +} + +func (d *DatastoreCapabilitiesDataSource) Metadata(ctx context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + resp.TypeName = "vkcs_db_datastore_capabilities" +} + +func (d *DatastoreCapabilitiesDataSource) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + resp.Schema = schema.Schema{ + Attributes: map[string]schema.Attribute{ + "id": schema.StringAttribute{ + Computed: true, + Description: "ID of the resource", + }, + + "region": schema.StringAttribute{ Computed: true, Optional: true, Description: "The `region` to fetch availability zones from, defaults to the provider's `region`.", }, - "datastore_name": { - Type: schema.TypeString, + "datastore_name": schema.StringAttribute{ Required: true, Description: "Name of the data store.", }, - "datastore_version_id": { - Type: schema.TypeString, + "datastore_version_id": schema.StringAttribute{ Required: true, Description: "ID of the version of the data store.", }, - "capabilities": { - Type: schema.TypeList, + "capabilities": schema.ListNestedAttribute{ Computed: true, - Elem: &schema.Resource{ - Schema: map[string]*schema.Schema{ - "name": { - Type: schema.TypeString, + NestedObject: schema.NestedAttributeObject{ + Attributes: map[string]schema.Attribute{ + "name": schema.StringAttribute{ Computed: true, Description: "Name of data store capability.", }, - "description": { - Type: schema.TypeString, + "description": schema.StringAttribute{ Computed: true, Description: "Description of data store capability.", }, - "params": { - Type: schema.TypeList, - Computed: true, - Elem: dataSourceDatabaseDatastoreCapabilitiesParam(), + "params": schema.ListNestedAttribute{ + Computed: true, + NestedObject: DatastoreCapabilitiesParamSchema(), }, - "should_be_on_master": { - Type: schema.TypeBool, + "should_be_on_master": schema.BoolAttribute{ Computed: true, Description: "This attribute indicates whether a capability applies only to the master node.", }, - "allow_major_upgrade": { - Type: schema.TypeBool, + "allow_major_upgrade": schema.BoolAttribute{ Computed: true, Description: "This attribute indicates whether a capability can be applied in the next major version of data store.", }, - "allow_upgrade_from_backup": { - Type: schema.TypeBool, + "allow_upgrade_from_backup": schema.BoolAttribute{ Computed: true, Description: "This attribute indicates whether a capability can be applied to upgrade from backup.", }, }, }, - Description: "Versions of the datastore.", + Description: "Capabilities of the datastore.", }, }, Description: "Use this data source to get capabilities supported for a VKCS datastore.", } } -func dataSourceDatabaseDatastoreCapabilitiesParam() *schema.Resource { - return &schema.Resource{ - Schema: map[string]*schema.Schema{ - "name": { - Type: schema.TypeString, +func DatastoreCapabilitiesParamSchema() schema.NestedAttributeObject { + return schema.NestedAttributeObject{ + Attributes: map[string]schema.Attribute{ + "name": schema.StringAttribute{ Computed: true, Description: "Name of a parameter.", }, - "required": { - Type: schema.TypeBool, + "required": schema.BoolAttribute{ Computed: true, Description: "Required indicates whether a parameter value must be set.", }, - "type": { - Type: schema.TypeString, + "type": schema.StringAttribute{ Computed: true, Description: "Type of value for a parameter.", }, - "element_type": { - Type: schema.TypeString, + "element_type": schema.StringAttribute{ Computed: true, Description: "Type of element value for a parameter of `list` type.", }, - "enum_values": { - Type: schema.TypeList, + "enum_values": schema.ListAttribute{ Computed: true, - Elem: &schema.Schema{Type: schema.TypeString}, + ElementType: types.StringType, Description: "Supported values for a parameter.", }, - "default_value": { - Type: schema.TypeString, + "default_value": schema.StringAttribute{ Computed: true, Description: "Default value for a parameter.", }, - "min": { - Type: schema.TypeFloat, + "min": schema.Float64Attribute{ Computed: true, Description: "Minimum value for a parameter.", }, - "max": { - Type: schema.TypeFloat, + "max": schema.Float64Attribute{ Computed: true, Description: "Maximum value for a parameter.", }, - "regex": { - Type: schema.TypeString, + "regex": schema.StringAttribute{ Computed: true, Description: "Regular expression that a parameter value must match.", }, - "masked": { - Type: schema.TypeBool, + "masked": schema.BoolAttribute{ Computed: true, Description: "Masked indicates whether a parameter value must be a boolean mask.", }, @@ -137,45 +168,75 @@ func dataSourceDatabaseDatastoreCapabilitiesParam() *schema.Resource { } } -func dataSourceDatabaseDatastoreCapabilitiesRead(ctx context.Context, d *schema.ResourceData, meta interface{}) diag.Diagnostics { - config := meta.(clients.Config) - region := util.GetRegion(d, config) - dbClient, err := config.DatabaseV1Client(region) - if err != nil { - return diag.Errorf("Error creating VKCS database client: %s", err) +func (d *DatastoreCapabilitiesDataSource) Configure(ctx context.Context, req datasource.ConfigureRequest, resp *datasource.ConfigureResponse) { + if req.ProviderData == nil { + return } + d.config = req.ProviderData.(clients.Config) +} - dsName := d.Get("datastore_name").(string) - dsVersionID := d.Get("datastore_version_id").(string) +func (d *DatastoreCapabilitiesDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + var data DatastoreCapabilitiesDataSourceModel - capabilities, err := datastores.ListCapabilities(dbClient, dsName, dsVersionID).Extract() + // Read Terraform configuration data into the model + resp.Diagnostics.Append(req.Config.Get(ctx, &data)...) + if resp.Diagnostics.HasError() { + return + } + + dsName := data.DatastoreName.ValueString() + dsVersionID := data.DatastoreVersionID.ValueString() + region := data.Region.ValueString() + if region == "" { + region = d.config.GetRegion() + } + + dbClient, err := d.config.DatabaseV1Client(region) if err != nil { - return diag.FromErr(util.CheckDeleted(d, err, "Error retrieving vkcs_db_backup")) + resp.Diagnostics.AddError("Error creating VKCS database client", err.Error()) + return } - flattenedCapabilities := flattenDatabaseDatastoreCapabilities(capabilities) + capabilities, err := datastores.ListCapabilities(dbClient, dsName, dsVersionID).Extract() + if err != nil { + resp.Diagnostics.AddError("Error retrieving vkcs_db_datastore_capabilities", + util.CheckDeletedDatasource(ctx, resp, err).Error()) + return + } + flattenedCapabilities, diags := flattenDatastoreCapabilities(ctx, capabilities) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return + } + data.Capabilities = flattenedCapabilities - d.SetId(fmt.Sprintf("%s/%s/capabilities", dsName, dsVersionID)) - d.Set("capabilities", flattenedCapabilities) + data.ID = types.StringValue(fmt.Sprintf("%s/%s/capabilities", dsName, dsVersionID)) + data.Region = types.StringValue(region) - return nil + // Save data into Terraform state + resp.Diagnostics.Append(resp.State.Set(ctx, &data)...) } -func flattenDatabaseDatastoreCapabilities(capabilities []datastores.Capability) (r []map[string]interface{}) { +func flattenDatastoreCapabilities(ctx context.Context, capabilities []datastores.Capability) (r []DatastoreCapabilityItemModel, diags diag.Diagnostics) { for _, c := range capabilities { - r = append(r, map[string]interface{}{ - "name": c.Name, - "description": c.Description, - "params": flattenDatabaseDatastoreCapabilityParams(c.Params), - "should_be_on_master": c.ShouldBeOnMaster, - "allow_major_upgrade": c.AllowMajorUpgrade, - "allow_upgrade_from_backup": c.AllowUpgradeFromBackup, + params, diags := flattenDatastoreCapabilityParams(ctx, c.Params) + if diags.HasError() { + return nil, diags + } + + r = append(r, DatastoreCapabilityItemModel{ + Name: types.StringValue(c.Name), + Description: types.StringValue(c.Description), + Params: params, + ShouldBeOnMaster: types.BoolValue(c.ShouldBeOnMaster), + AllowMajorUpgrade: types.BoolValue(c.AllowMajorUpgrade), + AllowUpgradeFromBackup: types.BoolValue(c.AllowUpgradeFromBackup), }) } return } -func flattenDatabaseDatastoreCapabilityParams(params map[string]*datastores.CapabilityParam) (r []map[string]interface{}) { +func flattenDatastoreCapabilityParams(ctx context.Context, params map[string]*datastores.CapabilityParam) (r []DatastoreCapabilityParamsModel, diags diag.Diagnostics) { for name, p := range params { var defaultValue string switch v := p.DefaultValue.(type) { @@ -184,17 +245,23 @@ func flattenDatabaseDatastoreCapabilityParams(params map[string]*datastores.Capa case float64: defaultValue = strconv.FormatFloat(p.DefaultValue.(float64), 'f', -1, 64) } - r = append(r, map[string]interface{}{ - "name": name, - "required": p.Required, - "type": p.Type, - "element_type": p.ElementType, - "enum_values": p.EnumValues, - "default_value": defaultValue, - "min": p.MinValue, - "max": p.MaxValue, - "regex": p.Regex, - "masked": p.Masked, + + enumValues, diags := types.ListValueFrom(ctx, types.StringType, p.EnumValues) + if diags.HasError() { + return nil, diags + } + + r = append(r, DatastoreCapabilityParamsModel{ + Name: types.StringValue(name), + Required: types.BoolValue(p.Required), + Type: types.StringValue(p.Type), + ElementType: types.StringValue(p.ElementType), + EnumValues: enumValues, + DefaultValue: types.StringValue(defaultValue), + Min: types.Float64Value(p.MinValue), + Max: types.Float64Value(p.MaxValue), + Regex: types.StringValue(p.Regex), + Masked: types.BoolValue(p.Masked), }) } return diff --git a/vkcs/db/data_source_vkcs_db_datastore_capabilities_test.go b/vkcs/db/data_source_vkcs_db_datastore_capabilities_test.go index e5956d94..7a520fce 100644 --- a/vkcs/db/data_source_vkcs_db_datastore_capabilities_test.go +++ b/vkcs/db/data_source_vkcs_db_datastore_capabilities_test.go @@ -3,21 +3,46 @@ package db_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) func TestAccDatabaseDatastoreCapabilitiesDataSource_basic(t *testing.T) { resource.Test(t, resource.TestCase{ - PreCheck: func() { acctest.AccTestPreCheck(t) }, - ProviderFactories: acctest.AccTestProviders, + PreCheck: func() { acctest.AccTestPreCheck(t) }, Steps: []resource.TestStep{ { + ProtoV6ProviderFactories: acctest.AccTestProtoV6ProviderFactories, + Config: testAccDatabaseDatastoreCapabilitiesDataSourceBasic, + Check: resource.ComposeTestCheckFunc( + resource.TestCheckResourceAttr("data.vkcs_db_datastore_capabilities.capabilities", "datastore_name", "mysql"), + ), + }, + }, + }) +} + +func TestAccDatabaseDatastoreCapabilitiesDataSource_migrateToFramework(t *testing.T) { + resource.Test(t, resource.TestCase{ + PreCheck: func() { acctest.AccTestPreCheck(t) }, + Steps: []resource.TestStep{ + { + ExternalProviders: map[string]resource.ExternalProvider{ + "vkcs": { + VersionConstraint: "0.2.2", + Source: "vk-cs/vkcs", + }, + }, Config: testAccDatabaseDatastoreCapabilitiesDataSourceBasic, Check: resource.ComposeTestCheckFunc( resource.TestCheckResourceAttr("data.vkcs_db_datastore_capabilities.capabilities", "datastore_name", "mysql"), ), }, + { + ProtoV6ProviderFactories: acctest.AccTestProtoV6ProviderFactories, + Config: testAccDatabaseDatastoreCapabilitiesDataSourceBasic, + PlanOnly: true, + }, }, }) } diff --git a/vkcs/db/data_source_vkcs_db_datastore_parameters_test.go b/vkcs/db/data_source_vkcs_db_datastore_parameters_test.go index a0c12938..803c6804 100644 --- a/vkcs/db/data_source_vkcs_db_datastore_parameters_test.go +++ b/vkcs/db/data_source_vkcs_db_datastore_parameters_test.go @@ -3,7 +3,7 @@ package db_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/data_source_vkcs_db_datastore_test.go b/vkcs/db/data_source_vkcs_db_datastore_test.go index f04a6a30..a80bb671 100644 --- a/vkcs/db/data_source_vkcs_db_datastore_test.go +++ b/vkcs/db/data_source_vkcs_db_datastore_test.go @@ -4,7 +4,7 @@ import ( "regexp" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/data_source_vkcs_db_datastores_test.go b/vkcs/db/data_source_vkcs_db_datastores_test.go index 2a21234f..4e7145a0 100644 --- a/vkcs/db/data_source_vkcs_db_datastores_test.go +++ b/vkcs/db/data_source_vkcs_db_datastores_test.go @@ -4,7 +4,7 @@ import ( "regexp" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/data_source_vkcs_db_instance_test.go b/vkcs/db/data_source_vkcs_db_instance_test.go index 8dc10d0a..71ccf06e 100755 --- a/vkcs/db/data_source_vkcs_db_instance_test.go +++ b/vkcs/db/data_source_vkcs_db_instance_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/data_source_vkcs_db_user_test.go b/vkcs/db/data_source_vkcs_db_user_test.go index 5e155a57..84119722 100755 --- a/vkcs/db/data_source_vkcs_db_user_test.go +++ b/vkcs/db/data_source_vkcs_db_user_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/db_backup.go b/vkcs/db/db_backup.go index 3ccce620..5532b23b 100644 --- a/vkcs/db/db_backup.go +++ b/vkcs/db/db_backup.go @@ -4,11 +4,11 @@ import ( "fmt" "github.com/gophercloud/gophercloud" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/backups" ) -func databaseBackupStateRefreshFunc(client *gophercloud.ServiceClient, backupID string) resource.StateRefreshFunc { +func databaseBackupStateRefreshFunc(client *gophercloud.ServiceClient, backupID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { b, err := backups.Get(client, backupID).Extract() if err != nil { diff --git a/vkcs/db/db_cluster.go b/vkcs/db/db_cluster.go index ae72051f..a3c007d5 100755 --- a/vkcs/db/db_cluster.go +++ b/vkcs/db/db_cluster.go @@ -7,7 +7,7 @@ import ( "log" "github.com/gophercloud/gophercloud" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/clusters" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/instances" @@ -190,7 +190,7 @@ type dbResourceUpdateContext struct { Ctx context.Context Client *gophercloud.ServiceClient D *schema.ResourceData - StateConf *resource.StateChangeConf + StateConf *retry.StateChangeConf } func (uCtx *dbResourceUpdateContext) WaitForStateContext() error { @@ -623,7 +623,7 @@ func getClusterStatus(c *clusters.ClusterResp) string { return c.Task.Name } -func databaseClusterStateRefreshFunc(client *gophercloud.ServiceClient, clusterID string, capabilitiesOpts *[]instances.CapabilityOpts) resource.StateRefreshFunc { +func databaseClusterStateRefreshFunc(client *gophercloud.ServiceClient, clusterID string, capabilitiesOpts *[]instances.CapabilityOpts) retry.StateRefreshFunc { return func() (interface{}, string, error) { c, err := clusters.Get(client, clusterID).Extract() if err != nil { diff --git a/vkcs/db/db_database.go b/vkcs/db/db_database.go index e65946dd..16098a93 100755 --- a/vkcs/db/db_database.go +++ b/vkcs/db/db_database.go @@ -4,11 +4,11 @@ import ( "fmt" "github.com/gophercloud/gophercloud" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/databases" ) -func databaseDatabaseStateRefreshFunc(client *gophercloud.ServiceClient, dbmsID string, databaseName string, dbmsType string) resource.StateRefreshFunc { +func databaseDatabaseStateRefreshFunc(client *gophercloud.ServiceClient, dbmsID string, databaseName string, dbmsType string) retry.StateRefreshFunc { return func() (interface{}, string, error) { pages, err := databases.List(client, dbmsID, dbmsType).AllPages() if err != nil { diff --git a/vkcs/db/db_instance.go b/vkcs/db/db_instance.go index f77b3789..ff02137f 100755 --- a/vkcs/db/db_instance.go +++ b/vkcs/db/db_instance.go @@ -10,7 +10,7 @@ import ( "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/instances" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" ) @@ -166,7 +166,7 @@ func flattenDatabaseBackupSchedule(b instances.BackupSchedule) []map[string]inte return backupschedule } -func databaseInstanceStateRefreshFunc(client *gophercloud.ServiceClient, instanceID string, capabilitiesOpts *[]instances.CapabilityOpts) resource.StateRefreshFunc { +func databaseInstanceStateRefreshFunc(client *gophercloud.ServiceClient, instanceID string, capabilitiesOpts *[]instances.CapabilityOpts) retry.StateRefreshFunc { return func() (interface{}, string, error) { i, err := instances.Get(client, instanceID).Extract() if err != nil { diff --git a/vkcs/db/db_user.go b/vkcs/db/db_user.go index 1e297e5f..e9f5a701 100755 --- a/vkcs/db/db_user.go +++ b/vkcs/db/db_user.go @@ -4,7 +4,7 @@ import ( "fmt" "github.com/gophercloud/gophercloud" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" db "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/databases" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/users" ) @@ -27,7 +27,7 @@ func flattenDatabaseUserDatabases(v []db.Database) []interface{} { return databases } -func databaseUserStateRefreshFunc(client *gophercloud.ServiceClient, dbmsID string, userName string, dbmsType string) resource.StateRefreshFunc { +func databaseUserStateRefreshFunc(client *gophercloud.ServiceClient, dbmsID string, userName string, dbmsType string) retry.StateRefreshFunc { return func() (interface{}, string, error) { pages, err := users.List(client, dbmsID, dbmsType).AllPages() if err != nil { diff --git a/vkcs/db/import_vkcs_db_cluster_test.go b/vkcs/db/import_vkcs_db_cluster_test.go index a6783382..15fdb39e 100644 --- a/vkcs/db/import_vkcs_db_cluster_test.go +++ b/vkcs/db/import_vkcs_db_cluster_test.go @@ -3,7 +3,7 @@ package db_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/import_vkcs_db_cluster_with_shards_test.go b/vkcs/db/import_vkcs_db_cluster_with_shards_test.go index 3c828181..e9329c4a 100644 --- a/vkcs/db/import_vkcs_db_cluster_with_shards_test.go +++ b/vkcs/db/import_vkcs_db_cluster_with_shards_test.go @@ -3,7 +3,7 @@ package db_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/import_vkcs_db_config_group_test.go b/vkcs/db/import_vkcs_db_config_group_test.go index ad04c889..0ecc9dce 100644 --- a/vkcs/db/import_vkcs_db_config_group_test.go +++ b/vkcs/db/import_vkcs_db_config_group_test.go @@ -3,7 +3,7 @@ package db_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/import_vkcs_db_database_test.go b/vkcs/db/import_vkcs_db_database_test.go index 368c1ce6..1610a44b 100644 --- a/vkcs/db/import_vkcs_db_database_test.go +++ b/vkcs/db/import_vkcs_db_database_test.go @@ -3,7 +3,7 @@ package db_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/import_vkcs_db_instance_test.go b/vkcs/db/import_vkcs_db_instance_test.go index 13437c57..58b91631 100644 --- a/vkcs/db/import_vkcs_db_instance_test.go +++ b/vkcs/db/import_vkcs_db_instance_test.go @@ -3,7 +3,7 @@ package db_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/import_vkcs_db_user_test.go b/vkcs/db/import_vkcs_db_user_test.go index 0fdbc606..c47c5a7b 100644 --- a/vkcs/db/import_vkcs_db_user_test.go +++ b/vkcs/db/import_vkcs_db_user_test.go @@ -3,7 +3,7 @@ package db_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/db/resource_vkcs_db_backup.go b/vkcs/db/resource_vkcs_db_backup.go index 9979b0bb..da644e50 100644 --- a/vkcs/db/resource_vkcs_db_backup.go +++ b/vkcs/db/resource_vkcs_db_backup.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db" @@ -199,7 +199,7 @@ func resourceDatabaseBackupCreate(ctx context.Context, d *schema.ResourceData, m // Wait for the backup to become available. log.Printf("[DEBUG] Waiting for vkcs_db_backup %s to become available", backup.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbBackupStatusNew), string(dbBackupStatusBuild)}, Target: []string{string(dbBackupStatusActive)}, Refresh: databaseBackupStateRefreshFunc(DatabaseV1Client, backup.ID), @@ -265,7 +265,7 @@ func resourceDatabaseBackupDelete(ctx context.Context, d *schema.ResourceData, m return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_db_backup")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbBackupStatusActive), string(dbBackupStatusToDelete)}, Target: []string{string(dbBackupStatusDeleted)}, Refresh: databaseBackupStateRefreshFunc(DatabaseV1Client, d.Id()), diff --git a/vkcs/db/resource_vkcs_db_backup_test.go b/vkcs/db/resource_vkcs_db_backup_test.go index f198127c..a5ef06a3 100644 --- a/vkcs/db/resource_vkcs_db_backup_test.go +++ b/vkcs/db/resource_vkcs_db_backup_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/backups" diff --git a/vkcs/db/resource_vkcs_db_cluster.go b/vkcs/db/resource_vkcs_db_cluster.go index 57b7ff3c..53fbe3c2 100755 --- a/vkcs/db/resource_vkcs_db_cluster.go +++ b/vkcs/db/resource_vkcs_db_cluster.go @@ -9,7 +9,7 @@ import ( "github.com/hashicorp/go-cty/cty" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -566,7 +566,7 @@ func resourceDatabaseClusterCreate(ctx context.Context, d *schema.ResourceData, // Wait for the cluster to become available. log.Printf("[DEBUG] Waiting for vkcs_db_cluster %s to become available", cluster.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbClusterStatusBuild), string(dbClusterStatusBackup)}, Target: []string{string(dbClusterStatusActive)}, Refresh: databaseClusterStateRefreshFunc(DatabaseV1Client, cluster.ID, checkCapabilities), @@ -667,7 +667,7 @@ func resourceDatabaseClusterUpdate(ctx context.Context, d *schema.ResourceData, } clusterID := d.Id() - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbClusterStatusBuild)}, Target: []string{string(dbClusterStatusActive)}, Refresh: databaseClusterStateRefreshFunc(dbClient, d.Id(), nil), @@ -787,7 +787,7 @@ func resourceDatabaseClusterDelete(ctx context.Context, d *schema.ResourceData, return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_db_cluster")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbClusterStatusActive), string(dbClusterStatusDeleting)}, Target: []string{string(dbClusterStatusDeleted)}, Refresh: databaseClusterStateRefreshFunc(DatabaseV1Client, d.Id(), nil), diff --git a/vkcs/db/resource_vkcs_db_cluster_test.go b/vkcs/db/resource_vkcs_db_cluster_test.go index 916fbd65..999f2fbd 100755 --- a/vkcs/db/resource_vkcs_db_cluster_test.go +++ b/vkcs/db/resource_vkcs_db_cluster_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/db" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/db/resource_vkcs_db_cluster_with_shards.go b/vkcs/db/resource_vkcs_db_cluster_with_shards.go index 078f96fa..718dc68b 100755 --- a/vkcs/db/resource_vkcs_db_cluster_with_shards.go +++ b/vkcs/db/resource_vkcs_db_cluster_with_shards.go @@ -10,7 +10,7 @@ import ( "github.com/hashicorp/go-cty/cty" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/clusters" @@ -531,7 +531,7 @@ func resourceDatabaseClusterWithShardsCreate(ctx context.Context, d *schema.Reso // Wait for the cluster to become available. log.Printf("[DEBUG] Waiting for vkcs_db_cluster_with_shards %s to become available", cluster.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbClusterStatusBuild)}, Target: []string{string(dbClusterStatusActive)}, Refresh: databaseClusterStateRefreshFunc(DatabaseV1Client, cluster.ID, checkCapabilities), @@ -657,7 +657,7 @@ func resourceDatabaseClusterWithShardsUpdate(ctx context.Context, d *schema.Reso } clusterID := d.Id() - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbClusterStatusBuild)}, Target: []string{string(dbClusterStatusActive)}, Refresh: databaseClusterStateRefreshFunc(dbClient, clusterID, nil), @@ -762,7 +762,7 @@ func resourceDatabaseClusterWithShardsDelete(ctx context.Context, d *schema.Reso return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_db_cluster_with_shards")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbClusterStatusActive), string(dbClusterStatusDeleting)}, Target: []string{string(dbClusterStatusDeleted)}, Refresh: databaseClusterStateRefreshFunc(DatabaseV1Client, d.Id(), nil), diff --git a/vkcs/db/resource_vkcs_db_cluster_with_shards_test.go b/vkcs/db/resource_vkcs_db_cluster_with_shards_test.go index a9709508..2e07ff2e 100755 --- a/vkcs/db/resource_vkcs_db_cluster_with_shards_test.go +++ b/vkcs/db/resource_vkcs_db_cluster_with_shards_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/clusters" diff --git a/vkcs/db/resource_vkcs_db_config_group_test.go b/vkcs/db/resource_vkcs_db_config_group_test.go index 0db83ff5..71beb116 100644 --- a/vkcs/db/resource_vkcs_db_config_group_test.go +++ b/vkcs/db/resource_vkcs_db_config_group_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" cg "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/config_groups" diff --git a/vkcs/db/resource_vkcs_db_database.go b/vkcs/db/resource_vkcs_db_database.go index 128189ec..a8c7954f 100755 --- a/vkcs/db/resource_vkcs_db_database.go +++ b/vkcs/db/resource_vkcs_db_database.go @@ -6,7 +6,7 @@ import ( "strings" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db" @@ -113,7 +113,7 @@ func resourceDatabaseDatabaseCreate(ctx context.Context, d *schema.ResourceData, return diag.Errorf("error creating vkcs_db_database: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"BUILD"}, Target: []string{"ACTIVE"}, Refresh: databaseDatabaseStateRefreshFunc(DatabaseV1Client, dbmsID, databaseName, dbmsType), diff --git a/vkcs/db/resource_vkcs_db_database_test.go b/vkcs/db/resource_vkcs_db_database_test.go index 3c51dcc9..b763ae3a 100755 --- a/vkcs/db/resource_vkcs_db_database_test.go +++ b/vkcs/db/resource_vkcs_db_database_test.go @@ -5,8 +5,8 @@ import ( "strings" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/databases" diff --git a/vkcs/db/resource_vkcs_db_instance.go b/vkcs/db/resource_vkcs_db_instance.go index 44618070..5ea1b76a 100755 --- a/vkcs/db/resource_vkcs_db_instance.go +++ b/vkcs/db/resource_vkcs_db_instance.go @@ -8,7 +8,7 @@ import ( "github.com/hashicorp/go-cty/cty" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/instances" @@ -597,7 +597,7 @@ func resourceDatabaseInstanceCreate(ctx context.Context, d *schema.ResourceData, // Wait for the instance to become available. log.Printf("[DEBUG] Waiting for vkcs_db_instance %s to become available", instance.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbInstanceStatusBuild), string(dbInstanceStatusBackup)}, Target: []string{string(dbInstanceStatusActive)}, Refresh: databaseInstanceStateRefreshFunc(DatabaseV1Client, instance.ID, checkCapabilities), @@ -735,7 +735,7 @@ func resourceDatabaseInstanceUpdate(ctx context.Context, d *schema.ResourceData, return diag.Errorf("Error creating VKCS database client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbInstanceStatusBuild)}, Target: []string{string(dbInstanceStatusActive)}, Refresh: databaseInstanceStateRefreshFunc(DatabaseV1Client, d.Id(), nil), @@ -955,7 +955,7 @@ func resourceDatabaseInstanceUpdate(ctx context.Context, d *schema.ResourceData, return diag.Errorf("error applying capability to vkcs_db_instance %s: %s", d.Id(), err) } - applyCapabilityInstanceConf := &resource.StateChangeConf{ + applyCapabilityInstanceConf := &retry.StateChangeConf{ Pending: []string{string(dbInstanceStatusCapabilityApplying), string(dbInstanceStatusBuild)}, Target: []string{string(dbInstanceStatusActive)}, Refresh: databaseInstanceStateRefreshFunc(DatabaseV1Client, d.Id(), &newCapabilitiesOpts), @@ -1019,7 +1019,7 @@ func resourceDatabaseInstanceDelete(ctx context.Context, d *schema.ResourceData, return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_db_instance")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(dbInstanceStatusActive), string(dbInstanceStatusBackup), string(dbInstanceStatusShutdown)}, Target: []string{string(dbInstanceStatusDeleted)}, diff --git a/vkcs/db/resource_vkcs_db_instance_test.go b/vkcs/db/resource_vkcs_db_instance_test.go index 4de27dda..5a4737a5 100755 --- a/vkcs/db/resource_vkcs_db_instance_test.go +++ b/vkcs/db/resource_vkcs_db_instance_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/instances" diff --git a/vkcs/db/resource_vkcs_db_user.go b/vkcs/db/resource_vkcs_db_user.go index 3aec3758..0937bb25 100755 --- a/vkcs/db/resource_vkcs_db_user.go +++ b/vkcs/db/resource_vkcs_db_user.go @@ -6,7 +6,7 @@ import ( "strings" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db" @@ -132,7 +132,7 @@ func resourceDatabaseUserCreate(ctx context.Context, d *schema.ResourceData, met return diag.Errorf("error creating vkcs_db_user: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"BUILD"}, Target: []string{"ACTIVE"}, Refresh: databaseUserStateRefreshFunc(DatabaseV1Client, dbmsID, userName, dbmsType), @@ -220,7 +220,7 @@ func resourceDatabaseUserUpdate(ctx context.Context, d *schema.ResourceData, met dbmsType := d.Get("dbms_type").(string) if d.HasChange("databases") { - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"BUILD"}, Target: []string{"ACTIVE"}, Refresh: databaseUserStateRefreshFunc(DatabaseV1Client, dbmsID, userName, dbmsType), diff --git a/vkcs/db/resource_vkcs_db_user_test.go b/vkcs/db/resource_vkcs_db_user_test.go index 22039f1d..b5f26af1 100755 --- a/vkcs/db/resource_vkcs_db_user_test.go +++ b/vkcs/db/resource_vkcs_db_user_test.go @@ -5,8 +5,8 @@ import ( "strings" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/db/v1/instances" diff --git a/vkcs/firewall/data_source_vkcs_networking_secgroup_test.go b/vkcs/firewall/data_source_vkcs_networking_secgroup_test.go index b42a153c..f8ff25b1 100644 --- a/vkcs/firewall/data_source_vkcs_networking_secgroup_test.go +++ b/vkcs/firewall/data_source_vkcs_networking_secgroup_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/firewall/import_vkcs_networking_secgroup_rule_test.go b/vkcs/firewall/import_vkcs_networking_secgroup_rule_test.go index 0626a9d3..7127a14b 100644 --- a/vkcs/firewall/import_vkcs_networking_secgroup_rule_test.go +++ b/vkcs/firewall/import_vkcs_networking_secgroup_rule_test.go @@ -3,7 +3,7 @@ package firewall_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/firewall/import_vkcs_networking_secgroup_test.go b/vkcs/firewall/import_vkcs_networking_secgroup_test.go index ef9bced1..3101268b 100644 --- a/vkcs/firewall/import_vkcs_networking_secgroup_test.go +++ b/vkcs/firewall/import_vkcs_networking_secgroup_test.go @@ -3,7 +3,7 @@ package firewall_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/firewall/networking_secgroup.go b/vkcs/firewall/networking_secgroup.go index 0b85fdfd..fae552af 100644 --- a/vkcs/firewall/networking_secgroup.go +++ b/vkcs/firewall/networking_secgroup.go @@ -3,14 +3,13 @@ package firewall import ( "log" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/security/groups" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) -// networkingSecgroupStateRefreshFuncDelete returns a special case resource.StateRefreshFunc to try to delete a secgroup. -func networkingSecgroupStateRefreshFuncDelete(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +// networkingSecgroupStateRefreshFuncDelete returns a special case retry.StateRefreshFunc to try to delete a secgroup. +func networkingSecgroupStateRefreshFuncDelete(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { log.Printf("[DEBUG] Attempting to delete vkcs_networking_secgroup %s", id) diff --git a/vkcs/firewall/networking_secgroup_rule.go b/vkcs/firewall/networking_secgroup_rule.go index fc4dbcde..deea2810 100644 --- a/vkcs/firewall/networking_secgroup_rule.go +++ b/vkcs/firewall/networking_secgroup_rule.go @@ -4,13 +4,12 @@ import ( "fmt" "strconv" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/security/rules" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) -func resourceNetworkingSecGroupRuleStateRefreshFunc(client *gophercloud.ServiceClient, sgRuleID string) resource.StateRefreshFunc { +func resourceNetworkingSecGroupRuleStateRefreshFunc(client *gophercloud.ServiceClient, sgRuleID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { sgRule, err := rules.Get(client, sgRuleID).Extract() if err != nil { diff --git a/vkcs/firewall/resource_vkcs_networking_secgroup.go b/vkcs/firewall/resource_vkcs_networking_secgroup.go index b2c5e3c8..7ece161f 100644 --- a/vkcs/firewall/resource_vkcs_networking_secgroup.go +++ b/vkcs/firewall/resource_vkcs_networking_secgroup.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -211,7 +211,7 @@ func resourceNetworkingSecGroupDelete(ctx context.Context, d *schema.ResourceDat return diag.Errorf("Error creating VKCS networking client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: networkingSecgroupStateRefreshFuncDelete(networkingClient, d.Id()), diff --git a/vkcs/firewall/resource_vkcs_networking_secgroup_rule.go b/vkcs/firewall/resource_vkcs_networking_secgroup_rule.go index 18531a3f..e0a46061 100644 --- a/vkcs/firewall/resource_vkcs_networking_secgroup_rule.go +++ b/vkcs/firewall/resource_vkcs_networking_secgroup_rule.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -257,7 +257,7 @@ func resourceNetworkingSecGroupRuleDelete(ctx context.Context, d *schema.Resourc return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_networking_secgroup_rule")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: resourceNetworkingSecGroupRuleStateRefreshFunc(networkingClient, d.Id()), diff --git a/vkcs/firewall/resource_vkcs_networking_secgroup_rule_test.go b/vkcs/firewall/resource_vkcs_networking_secgroup_rule_test.go index 0e36acb1..846fd371 100644 --- a/vkcs/firewall/resource_vkcs_networking_secgroup_rule_test.go +++ b/vkcs/firewall/resource_vkcs_networking_secgroup_rule_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/firewall/resource_vkcs_networking_secgroup_test.go b/vkcs/firewall/resource_vkcs_networking_secgroup_test.go index 9734689a..53db1fa1 100644 --- a/vkcs/firewall/resource_vkcs_networking_secgroup_test.go +++ b/vkcs/firewall/resource_vkcs_networking_secgroup_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/images/data_source_vkcs_images_image_test.go b/vkcs/images/data_source_vkcs_images_image_test.go index ef0428b4..3406ea2b 100644 --- a/vkcs/images/data_source_vkcs_images_image_test.go +++ b/vkcs/images/data_source_vkcs_images_image_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/images/images_image.go b/vkcs/images/images_image.go index 77c9073f..06408a13 100644 --- a/vkcs/images/images_image.go +++ b/vkcs/images/images_image.go @@ -15,9 +15,10 @@ import ( "strings" "github.com/gofrs/flock" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" + "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/imageservice/v2/images" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" ) @@ -154,7 +155,7 @@ func resourceImagesImageFile(client *gophercloud.ServiceClient, d *schema.Resour } } -func resourceImagesImageRefreshFunc(client *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func resourceImagesImageRefreshFunc(client *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { img, err := images.Get(client, id).Extract() if err != nil { diff --git a/vkcs/images/import_vkcs_images_image_test.go b/vkcs/images/import_vkcs_images_image_test.go index 9a048ab7..3f80bfb7 100644 --- a/vkcs/images/import_vkcs_images_image_test.go +++ b/vkcs/images/import_vkcs_images_image_test.go @@ -3,7 +3,7 @@ package images_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/images/resource_vkcs_images_image.go b/vkcs/images/resource_vkcs_images_image.go index 2efa50f8..7bd5d165 100644 --- a/vkcs/images/resource_vkcs_images_image.go +++ b/vkcs/images/resource_vkcs_images_image.go @@ -9,7 +9,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -299,7 +299,7 @@ func resourceImagesImageCreate(ctx context.Context, d *schema.ResourceData, meta } // wait for active - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(images.ImageStatusQueued), string(images.ImageStatusSaving), string(images.ImageStatusImporting)}, Target: []string{string(images.ImageStatusActive)}, Refresh: resourceImagesImageRefreshFunc(imageClient, d.Id()), diff --git a/vkcs/images/resource_vkcs_images_image_test.go b/vkcs/images/resource_vkcs_images_image_test.go index 9c80b27c..4caeca1b 100644 --- a/vkcs/images/resource_vkcs_images_image_test.go +++ b/vkcs/images/resource_vkcs_images_image_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/internal/acctest/acctest.go b/vkcs/internal/acctest/acctest.go index 33439849..fff1449c 100644 --- a/vkcs/internal/acctest/acctest.go +++ b/vkcs/internal/acctest/acctest.go @@ -2,12 +2,18 @@ package acctest import ( "bytes" + "context" "fmt" "os" "testing" "text/template" + "github.com/hashicorp/terraform-plugin-framework/providerserver" + "github.com/hashicorp/terraform-plugin-go/tfprotov6" + "github.com/hashicorp/terraform-plugin-mux/tf5to6server" + "github.com/hashicorp/terraform-plugin-mux/tf6muxserver" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" "github.com/vk-cs/terraform-provider-vkcs/vkcs/provider" ) @@ -47,14 +53,37 @@ var AccTestValues map[string]string = map[string]string{ var AccTestProviders map[string]func() (*schema.Provider, error) var AccTestProvider *schema.Provider +var AccTestProtoV6ProviderFactories map[string]func() (tfprotov6.ProviderServer, error) func init() { - AccTestProvider = provider.Provider() + AccTestProvider = provider.SDKProvider() AccTestProviders = map[string]func() (*schema.Provider, error){ "vkcs": func() (*schema.Provider, error) { return AccTestProvider, nil }, } + AccTestProtoV6ProviderFactories = map[string]func() (tfprotov6.ProviderServer, error){ + "vkcs": func() (tfprotov6.ProviderServer, error) { + ctx := context.Background() + providers := []func() tfprotov6.ProviderServer{ + providerserver.NewProtocol6(provider.Provider()), + func() tfprotov6.ProviderServer { + server, _ := tf5to6server.UpgradeServer( + ctx, + provider.SDKProvider().GRPCProvider, + ) + return server + }, + } + + muxServer, err := tf6muxserver.NewMuxServer(ctx, providers...) + if err != nil { + return nil, err + } + + return muxServer, nil + }, + } } func AccTestPreCheck(t *testing.T) { @@ -164,3 +193,19 @@ func AccTestRenderConfig(testConfig string, values ...map[string]string) string return buf.String() } + +func AccTestGetStepsWithMigrationCases(steps []resource.TestStep) (migrationSteps []resource.TestStep) { + for _, step := range steps { + migrationSteps = append(migrationSteps, resource.TestStep{ + Config: step.Config, + Check: step.Check, + ExternalProviders: map[string]resource.ExternalProvider{ + "vkcs": { + VersionConstraint: "0.2.1", + Source: "vk-cs/vkcs", + }, + }, + }) + } + return append(migrationSteps, steps...) +} diff --git a/vkcs/internal/clients/config.go b/vkcs/internal/clients/config.go index bf338af3..5abba41a 100644 --- a/vkcs/internal/clients/config.go +++ b/vkcs/internal/clients/config.go @@ -4,12 +4,16 @@ import ( "context" "fmt" "net/http" + "os" "time" "github.com/gophercloud/gophercloud" "github.com/gophercloud/utils/terraform/auth" "github.com/gophercloud/utils/terraform/mutexkv" - "github.com/hashicorp/terraform-plugin-sdk/v2/diag" + "github.com/hashicorp/terraform-plugin-framework/diag" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-framework/provider" + sdkdiag "github.com/hashicorp/terraform-plugin-sdk/v2/diag" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/meta" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" @@ -45,23 +49,42 @@ type configer struct { ContainerInfraV1MicroVersion string } -func ConfigureProvider(d *schema.ResourceData, terraformVersion string) (Config, diag.Diagnostics) { +func getConfigParam(d *schema.ResourceData, key string, envKey string, defaultVal string) (param string) { + tfAttr := d.Get(key) + if tfAttr != nil { + param = tfAttr.(string) + } + if param == "" { + param = os.Getenv(envKey) + } + if param == "" { + param = defaultVal + } + return param +} + +func ConfigureSdkProvider(d *schema.ResourceData, terraformVersion string) (Config, sdkdiag.Diagnostics) { + containerInfraV1MicroVersion := d.Get("cloud_containers_api_version").(string) + if containerInfraV1MicroVersion == "" { + containerInfraV1MicroVersion = CloudContainersAPIVersion + } + config := &configer{ auth.Config{ - Username: d.Get("username").(string), - Password: d.Get("password").(string), - TenantID: d.Get("project_id").(string), - Region: d.Get("region").(string), - IdentityEndpoint: d.Get("auth_url").(string), - UserDomainID: d.Get("user_domain_id").(string), - UserDomainName: d.Get("user_domain_name").(string), + Username: getConfigParam(d, "username", "OS_USERNAME", ""), + Password: getConfigParam(d, "password", "OS_PASSWORD", ""), + TenantID: getConfigParam(d, "project_id", "OS_PROJECT_ID", ""), + Region: getConfigParam(d, "region", "OS_REGION_NAME", DefaultRegionName), + IdentityEndpoint: getConfigParam(d, "auth_url", "OS_AUTH_URL", DefaultIdentityEndpoint), + UserDomainID: getConfigParam(d, "user_domain_id", "OS_USER_DOMAIN_ID", ""), + UserDomainName: getConfigParam(d, "user_domain_name", "OS_USER_DOMAIN_NAME", DefaultUserDomainName), AllowReauth: true, MaxRetries: maxRetriesCount, TerraformVersion: terraformVersion, SDKVersion: meta.SDKVersionString(), MutexKV: mutexkv.NewMutexKV(), }, - d.Get("cloud_containers_api_version").(string), + containerInfraV1MicroVersion, } if config.UserDomainID != "" { @@ -69,7 +92,7 @@ func ConfigureProvider(d *schema.ResourceData, terraformVersion string) (Config, } if err := config.LoadAndValidate(); err != nil { - return nil, diag.FromErr(err) + return nil, sdkdiag.FromErr(err) } return config, nil } @@ -165,3 +188,77 @@ func (c *configer) LoadBalancerV2Client(region string) (*gophercloud.ServiceClie func (c *configer) GetMutex() *mutexkv.MutexKV { return c.Config.MutexKV } + +func (c *configer) updateWithEnv() { + if c.Username == "" { + c.Username = os.Getenv("OS_USERNAME") + } + if c.Password == "" { + c.Password = os.Getenv("OS_PASSWORD") + } + if c.TenantID == "" { + c.TenantID = os.Getenv("OS_PROJECT_ID") + } + if c.Region == "" { + c.Region = os.Getenv("OS_REGION_NAME") + } + if c.IdentityEndpoint == "" { + c.IdentityEndpoint = os.Getenv("OS_AUTH_URL") + } + if c.UserDomainID == "" { + c.UserDomainID = os.Getenv("OS_USER_DOMAIN_ID") + } + if c.UserDomainName == "" { + c.UserDomainName = os.Getenv("OS_USER_DOMAIN_NAME") + } +} + +func ConfigureProvider(ctx context.Context, req provider.ConfigureRequest) (Config, diag.Diagnostics) { + var diags diag.Diagnostics + config := configer{} + + req.Config.GetAttribute(ctx, path.Root("auth_url"), &config.IdentityEndpoint) + req.Config.GetAttribute(ctx, path.Root("username"), &config.Username) + req.Config.GetAttribute(ctx, path.Root("password"), &config.Password) + req.Config.GetAttribute(ctx, path.Root("project_id"), &config.TenantID) + req.Config.GetAttribute(ctx, path.Root("user_domain_id"), &config.UserDomainID) + req.Config.GetAttribute(ctx, path.Root("user_domain_name"), &config.UserDomainName) + req.Config.GetAttribute(ctx, path.Root("region"), &config.Region) + req.Config.GetAttribute(ctx, path.Root("cloud_containers_api_version"), &config.ContainerInfraV1MicroVersion) + config.updateWithEnv() + + if config.UserDomainID != "" { + config.UserDomainName = "" + } + + terraformVersion := req.TerraformVersion + if terraformVersion == "" { + // Terraform 0.12 introduced this field to the protocol + // We can therefore assume that if it's missing it's 0.10 or 0.11 + terraformVersion = "0.11+compatible" + } + config.TerraformVersion = terraformVersion + + if config.ContainerInfraV1MicroVersion == "" { + config.ContainerInfraV1MicroVersion = CloudContainersAPIVersion + } + if config.Region == "" { + config.Region = DefaultRegionName + } + if config.IdentityEndpoint == "" { + config.IdentityEndpoint = DefaultIdentityEndpoint + } + if config.UserDomainName == "" { + config.UserDomainName = DefaultUserDomainName + } + + config.AllowReauth = true + config.MaxRetries = maxRetriesCount + config.MutexKV = mutexkv.NewMutexKV() + + if err := config.LoadAndValidate(); err != nil { + diags.AddError("Config validation error", err.Error()) + } + + return &config, diags +} diff --git a/vkcs/internal/clients/defaults.go b/vkcs/internal/clients/defaults.go index 81fb9280..c59d4f5f 100644 --- a/vkcs/internal/clients/defaults.go +++ b/vkcs/internal/clients/defaults.go @@ -1,7 +1,8 @@ package clients const ( - DefaultIdentityEndpoint = "https://infra.mail.ru/identity/v3/" - DefaultUserDomainName = "users" - DefaultRegionName = "RegionOne" + DefaultIdentityEndpoint = "https://infra.mail.ru/identity/v3/" + DefaultUserDomainName = "users" + DefaultRegionName = "RegionOne" + CloudContainersAPIVersion = "1.28" ) diff --git a/vkcs/internal/generate/providerschema/main.go b/vkcs/internal/generate/providerschema/main.go index a8f675a6..39fefeab 100644 --- a/vkcs/internal/generate/providerschema/main.go +++ b/vkcs/internal/generate/providerschema/main.go @@ -65,7 +65,7 @@ func (g ProviderSchemaJSONGenerator) codeForSchema() string { pSchema := strings.ReplaceAll(compactSchemaJSON.String(), "`", "`+\"`\"+`") - return fmt.Sprintf("const providerSchemaBase = `%s`", pSchema) + return fmt.Sprintf("const ProviderSchemaJSON = `%s`", pSchema) } func goFmtAndWriteToFile(filePath, fileContents string) error { diff --git a/vkcs/internal/providerwrapper/framework/datasource/customschema/custom.go b/vkcs/internal/providerwrapper/framework/datasource/customschema/custom.go new file mode 100644 index 00000000..5e0291e4 --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/datasource/customschema/custom.go @@ -0,0 +1,173 @@ +package customschema + +import ( + "fmt" + "strings" + + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" +) + +func CustomizeSchema(sJSON jsonschema.ResourceJSON, s schema.Schema) schema.Schema { + if s.DeprecationMessage != "" && !strings.Contains(strings.ToLower(s.Description), "deprecated") { + s.Description += fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(s.DeprecationMessage, ".")) + } + + if s.DeprecationMessage == "" && sJSON.NewSince != "" { + s.Description += fmt.Sprintf(" **New since %s**.", sJSON.NewSince) + } + + for name, attr := range s.Attributes { + attrJSON := sJSON.Schema[name] + s.Attributes[name] = customizeAttribute(attrJSON, attr, name) + } + + for name, block := range s.Blocks { + blockJSON := sJSON.Schema[name] + customizeBlock(blockJSON, block, name) + } + + return s +} + +func customizeBlock(blockJSON jsonschema.SchemaJSON, block schema.Block, name string) schema.Block { + switch b := block.(type) { + case schema.SingleNestedBlock: + b.Description = addNewSinceToBlock(b, blockJSON) + b.Description = addDeprecatedToBlock(b) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(blockJSON) { + nestedAttrsJSONs = blockJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range b.Attributes { + b.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + return b + case schema.ListNestedBlock: + b.Description = addNewSinceToBlock(b, blockJSON) + b.Description = addDeprecatedToBlock(b) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(blockJSON) { + nestedAttrsJSONs = blockJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range b.NestedObject.Attributes { + b.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + for nestedName, nestedBlock := range b.NestedObject.Blocks { + b.NestedObject.Blocks[nestedName] = customizeBlock(nestedAttrsJSONs[nestedName], nestedBlock, nestedName) + } + + return b + case schema.SetNestedBlock: + b.Description = addNewSinceToBlock(b, blockJSON) + b.Description = addDeprecatedToBlock(b) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(blockJSON) { + nestedAttrsJSONs = blockJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range b.NestedObject.Attributes { + b.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + for nestedName, nestedBlock := range b.NestedObject.Blocks { + b.NestedObject.Blocks[nestedName] = customizeBlock(nestedAttrsJSONs[nestedName], nestedBlock, nestedName) + } + + return b + } + + return block +} + +func customizeAttribute(attrJSON jsonschema.SchemaJSON, attr schema.Attribute, name string) schema.Attribute { + switch a := attr.(type) { + case schema.BoolAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.Float64Attribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.Int64Attribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.ListAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.MapAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.NumberAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.ObjectAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.SetAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.StringAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.ListNestedAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(attrJSON) { + nestedAttrsJSONs = attrJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range a.NestedObject.Attributes { + a.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + return a + case schema.SetNestedAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(attrJSON) { + nestedAttrsJSONs = attrJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range a.NestedObject.Attributes { + a.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + return a + case schema.MapNestedAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(attrJSON) { + nestedAttrsJSONs = attrJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range a.NestedObject.Attributes { + a.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + return a + } + + return attr +} diff --git a/vkcs/internal/providerwrapper/framework/datasource/customschema/deprecated.go b/vkcs/internal/providerwrapper/framework/datasource/customschema/deprecated.go new file mode 100644 index 00000000..83683229 --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/datasource/customschema/deprecated.go @@ -0,0 +1,22 @@ +package customschema + +import ( + "fmt" + "strings" + + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" +) + +func addDeprecatedToAttr(attr schema.Attribute) string { + if attr.GetDeprecationMessage() != "" && !strings.Contains(strings.ToLower(attr.GetDescription()), "deprecated") { + return attr.GetDescription() + fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(attr.GetDeprecationMessage(), ".")) + } + return attr.GetDescription() +} + +func addDeprecatedToBlock(block schema.Block) string { + if block.GetDeprecationMessage() != "" && !strings.Contains(strings.ToLower(block.GetDescription()), "deprecated") { + return block.GetDescription() + fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(block.GetDeprecationMessage(), ".")) + } + return block.GetDescription() +} diff --git a/vkcs/internal/providerwrapper/framework/datasource/customschema/new_since.go b/vkcs/internal/providerwrapper/framework/datasource/customschema/new_since.go new file mode 100644 index 00000000..03d312b5 --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/datasource/customschema/new_since.go @@ -0,0 +1,22 @@ +package customschema + +import ( + "fmt" + + "github.com/hashicorp/terraform-plugin-framework/datasource/schema" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" +) + +func addNewSinceToAttr(attr schema.Attribute, attrJSON jsonschema.SchemaJSON) string { + if attr.GetDeprecationMessage() == "" && attrJSON.NewSince != "" { + return attr.GetDescription() + fmt.Sprintf(" **New since %s**.", attrJSON.NewSince) + } + return attr.GetDescription() +} + +func addNewSinceToBlock(block schema.Block, blockJSON jsonschema.SchemaJSON) string { + if block.GetDeprecationMessage() == "" && blockJSON.NewSince != "" { + return block.GetDescription() + fmt.Sprintf(" **New since %s**.", blockJSON.NewSince) + } + return block.GetDescription() +} diff --git a/vkcs/internal/providerwrapper/framework/datasource/wrapper_data_source.go b/vkcs/internal/providerwrapper/framework/datasource/wrapper_data_source.go new file mode 100644 index 00000000..3f6d21ad --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/datasource/wrapper_data_source.go @@ -0,0 +1,57 @@ +package frameworkwrapper + +import ( + "context" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/providerwrapper/framework/datasource/customschema" +) + +var ( + _ datasource.DataSource = &DataSourceWrapper{} +) + +func NewDataSourceWrapper(dataSource datasource.DataSource, dataSourceJSON jsonschema.ResourceJSON) *DataSourceWrapper { + return &DataSourceWrapper{ + dataSource: dataSource, + dataSourceJSON: dataSourceJSON, + } +} + +type DataSourceWrapper struct { + dataSource datasource.DataSource + dataSourceJSON jsonschema.ResourceJSON +} + +func (dw *DataSourceWrapper) Metadata(ctx context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) { + dw.dataSource.Metadata(ctx, req, resp) +} + +func (dw *DataSourceWrapper) Schema(ctx context.Context, req datasource.SchemaRequest, resp *datasource.SchemaResponse) { + dw.dataSource.Schema(ctx, req, resp) + resp.Schema = customschema.CustomizeSchema(dw.dataSourceJSON, resp.Schema) +} + +func (dw *DataSourceWrapper) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { + dw.dataSource.Read(ctx, req, resp) +} + +func (dw *DataSourceWrapper) Configure(ctx context.Context, req datasource.ConfigureRequest, resp *datasource.ConfigureResponse) { + if ds, ok := dw.dataSource.(datasource.DataSourceWithConfigure); ok { + ds.Configure(ctx, req, resp) + } +} + +func (dw *DataSourceWrapper) ConfigValidators(ctx context.Context) []datasource.ConfigValidator { + if ds, ok := dw.dataSource.(datasource.DataSourceWithConfigValidators); ok { + return ds.ConfigValidators(ctx) + } + return nil +} + +func (dw *DataSourceWrapper) ValidateConfig(ctx context.Context, req datasource.ValidateConfigRequest, resp *datasource.ValidateConfigResponse) { + if ds, ok := dw.dataSource.(datasource.DataSourceWithValidateConfig); ok { + ds.ValidateConfig(ctx, req, resp) + } +} diff --git a/vkcs/internal/providerwrapper/framework/resource/customschema/custom.go b/vkcs/internal/providerwrapper/framework/resource/customschema/custom.go new file mode 100644 index 00000000..e9e93482 --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/resource/customschema/custom.go @@ -0,0 +1,173 @@ +package customschema + +import ( + "fmt" + "strings" + + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" +) + +func CustomizeSchema(sJSON jsonschema.ResourceJSON, s schema.Schema) schema.Schema { + if s.DeprecationMessage != "" && !strings.Contains(strings.ToLower(s.Description), "deprecated") { + s.Description += fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(s.DeprecationMessage, ".")) + } + + if s.DeprecationMessage == "" && sJSON.NewSince != "" { + s.Description += fmt.Sprintf(" **New since %s**.", sJSON.NewSince) + } + + for name, attr := range s.Attributes { + attrJSON := sJSON.Schema[name] + s.Attributes[name] = customizeAttribute(attrJSON, attr, name) + } + + for name, block := range s.Blocks { + blockJSON := sJSON.Schema[name] + customizeBlock(blockJSON, block, name) + } + + return s +} + +func customizeBlock(blockJSON jsonschema.SchemaJSON, block schema.Block, name string) schema.Block { + switch b := block.(type) { + case schema.SingleNestedBlock: + b.Description = addNewSinceToBlock(b, blockJSON) + b.Description = addDeprecatedToBlock(b) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(blockJSON) { + nestedAttrsJSONs = blockJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range b.Attributes { + b.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + return b + case schema.ListNestedBlock: + b.Description = addNewSinceToBlock(b, blockJSON) + b.Description = addDeprecatedToBlock(b) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(blockJSON) { + nestedAttrsJSONs = blockJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range b.NestedObject.Attributes { + b.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + for nestedName, nestedBlock := range b.NestedObject.Blocks { + b.NestedObject.Blocks[nestedName] = customizeBlock(nestedAttrsJSONs[nestedName], nestedBlock, nestedName) + } + + return b + case schema.SetNestedBlock: + b.Description = addNewSinceToBlock(b, blockJSON) + b.Description = addDeprecatedToBlock(b) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(blockJSON) { + nestedAttrsJSONs = blockJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range b.NestedObject.Attributes { + b.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + for nestedName, nestedBlock := range b.NestedObject.Blocks { + b.NestedObject.Blocks[nestedName] = customizeBlock(nestedAttrsJSONs[nestedName], nestedBlock, nestedName) + } + + return b + } + + return block +} + +func customizeAttribute(attrJSON jsonschema.SchemaJSON, attr schema.Attribute, name string) schema.Attribute { + switch a := attr.(type) { + case schema.BoolAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.Float64Attribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.Int64Attribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.ListAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.MapAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.NumberAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.ObjectAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.SetAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.StringAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + return a + case schema.ListNestedAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(attrJSON) { + nestedAttrsJSONs = attrJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range a.NestedObject.Attributes { + a.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + return a + case schema.SetNestedAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(attrJSON) { + nestedAttrsJSONs = attrJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range a.NestedObject.Attributes { + a.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + return a + case schema.MapNestedAttribute: + a.Description = addNewSinceToAttr(a, attrJSON) + a.Description = addDeprecatedToAttr(a) + + var nestedAttrsJSONs map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(attrJSON) { + nestedAttrsJSONs = attrJSON.Elem.(jsonschema.ResourceJSON).Schema + } + + for nestedName, nestedAttr := range a.NestedObject.Attributes { + a.NestedObject.Attributes[nestedName] = customizeAttribute(nestedAttrsJSONs[nestedName], nestedAttr, nestedName) + } + + return a + } + + return attr +} diff --git a/vkcs/internal/providerwrapper/framework/resource/customschema/deprecated.go b/vkcs/internal/providerwrapper/framework/resource/customschema/deprecated.go new file mode 100644 index 00000000..07e9ef79 --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/resource/customschema/deprecated.go @@ -0,0 +1,22 @@ +package customschema + +import ( + "fmt" + "strings" + + "github.com/hashicorp/terraform-plugin-framework/resource/schema" +) + +func addDeprecatedToAttr(attr schema.Attribute) string { + if attr.GetDeprecationMessage() != "" && !strings.Contains(strings.ToLower(attr.GetDescription()), "deprecated") { + return attr.GetDescription() + fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(attr.GetDeprecationMessage(), ".")) + } + return attr.GetDescription() +} + +func addDeprecatedToBlock(block schema.Block) string { + if block.GetDeprecationMessage() != "" && !strings.Contains(strings.ToLower(block.GetDescription()), "deprecated") { + return block.GetDescription() + fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(block.GetDeprecationMessage(), ".")) + } + return block.GetDescription() +} diff --git a/vkcs/internal/providerwrapper/framework/resource/customschema/new_since.go b/vkcs/internal/providerwrapper/framework/resource/customschema/new_since.go new file mode 100644 index 00000000..c74f56a2 --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/resource/customschema/new_since.go @@ -0,0 +1,22 @@ +package customschema + +import ( + "fmt" + + "github.com/hashicorp/terraform-plugin-framework/resource/schema" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" +) + +func addNewSinceToAttr(attr schema.Attribute, attrJSON jsonschema.SchemaJSON) string { + if attr.GetDeprecationMessage() == "" && attrJSON.NewSince != "" { + return attr.GetDescription() + fmt.Sprintf(" **New since %s**.", attrJSON.NewSince) + } + return attr.GetDescription() +} + +func addNewSinceToBlock(block schema.Block, blockJSON jsonschema.SchemaJSON) string { + if block.GetDeprecationMessage() == "" && blockJSON.NewSince != "" { + return block.GetDescription() + fmt.Sprintf(" **New since %s**.", blockJSON.NewSince) + } + return block.GetDescription() +} diff --git a/vkcs/internal/providerwrapper/framework/resource/wrapper_resource.go b/vkcs/internal/providerwrapper/framework/resource/wrapper_resource.go new file mode 100644 index 00000000..ebb687ca --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/resource/wrapper_resource.go @@ -0,0 +1,87 @@ +package frameworkwrapper + +import ( + "context" + + "github.com/hashicorp/terraform-plugin-framework/resource" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/providerwrapper/framework/resource/customschema" +) + +var ( + _ resource.Resource = &ResourceWrapper{} +) + +func NewResourceWrapper(resource resource.Resource, resourceJSON jsonschema.ResourceJSON) *ResourceWrapper { + return &ResourceWrapper{ + resource: resource, + resourceJSON: resourceJSON, + } +} + +type ResourceWrapper struct { + resource resource.Resource + resourceJSON jsonschema.ResourceJSON +} + +func (rw *ResourceWrapper) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) { + rw.resource.Metadata(ctx, req, resp) +} + +func (rw *ResourceWrapper) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) { + rw.resource.Schema(ctx, req, resp) + resp.Schema = customschema.CustomizeSchema(rw.resourceJSON, resp.Schema) +} + +func (rw *ResourceWrapper) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) { + rw.resource.Create(ctx, req, resp) +} + +func (rw *ResourceWrapper) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) { + rw.resource.Read(ctx, req, resp) +} + +func (rw *ResourceWrapper) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) { + rw.resource.Update(ctx, req, resp) +} + +func (rw *ResourceWrapper) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) { + rw.resource.Delete(ctx, req, resp) +} + +func (rw *ResourceWrapper) Configure(ctx context.Context, req resource.ConfigureRequest, resp *resource.ConfigureResponse) { + if rs, ok := rw.resource.(resource.ResourceWithConfigure); ok { + rs.Configure(ctx, req, resp) + } +} + +func (rw *ResourceWrapper) ConfigValidators(ctx context.Context) []resource.ConfigValidator { + if rs, ok := rw.resource.(resource.ResourceWithConfigValidators); ok { + return rs.ConfigValidators(ctx) + } + return nil +} + +func (rw *ResourceWrapper) ImportState(ctx context.Context, req resource.ImportStateRequest, resp *resource.ImportStateResponse) { + if rs, ok := rw.resource.(resource.ResourceWithImportState); ok { + rs.ImportState(ctx, req, resp) + } else { + resp.Diagnostics.AddError( + "Resource Import Not Implemented", + "This resource does not support import.", + ) + } +} + +func (rw *ResourceWrapper) ModifyPlan(ctx context.Context, req resource.ModifyPlanRequest, resp *resource.ModifyPlanResponse) { + if rs, ok := rw.resource.(resource.ResourceWithModifyPlan); ok { + rs.ModifyPlan(ctx, req, resp) + } +} + +func (rw *ResourceWrapper) UpgradeState(ctx context.Context) map[int64]resource.StateUpgrader { + if rs, ok := rw.resource.(resource.ResourceWithUpgradeState); ok { + return rs.UpgradeState(ctx) + } + return make(map[int64]resource.StateUpgrader, 0) +} diff --git a/vkcs/internal/providerwrapper/framework/wrapper_provider.go b/vkcs/internal/providerwrapper/framework/wrapper_provider.go new file mode 100644 index 00000000..12ad3794 --- /dev/null +++ b/vkcs/internal/providerwrapper/framework/wrapper_provider.go @@ -0,0 +1,90 @@ +package frameworkwrapper + +import ( + "context" + "encoding/json" + + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/provider" + "github.com/hashicorp/terraform-plugin-framework/resource" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/providerwrapper" + dswrapper "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/providerwrapper/framework/datasource" + rswrapper "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/providerwrapper/framework/resource" +) + +var ( + _ provider.Provider = &ProviderWrapper{} +) + +func NewProviderWrapper(provider provider.Provider) *ProviderWrapper { + var wrapperSchemaJSON jsonschema.ProviderWrapper + err := json.Unmarshal([]byte(providerwrapper.ProviderSchemaJSON), &wrapperSchemaJSON) + if err != nil { + panic(err) + } + + return &ProviderWrapper{ + provider: provider, + providerSchemaJSON: wrapperSchemaJSON.ProviderSchema, + } +} + +type ProviderWrapper struct { + provider provider.Provider + providerSchemaJSON *jsonschema.ProviderSchemaJSON +} + +func (pw *ProviderWrapper) Metadata(ctx context.Context, req provider.MetadataRequest, resp *provider.MetadataResponse) { + pw.provider.Metadata(ctx, req, resp) +} + +// Schema defines the provider-level schema for configuration data. +func (pw *ProviderWrapper) Schema(ctx context.Context, req provider.SchemaRequest, resp *provider.SchemaResponse) { + pw.provider.Schema(ctx, req, resp) +} + +// Configure prepares a HashiCups API client for data sources and resources. +func (pw *ProviderWrapper) Configure(ctx context.Context, req provider.ConfigureRequest, resp *provider.ConfigureResponse) { + pw.provider.Configure(ctx, req, resp) +} + +// DataSources defines the data sources implemented in the provider. +func (pw *ProviderWrapper) DataSources(ctx context.Context) []func() datasource.DataSource { + dataSourcesFactories := pw.provider.DataSources(ctx) + wrappedDataSourcesFactories := make([]func() datasource.DataSource, len(dataSourcesFactories)) + for i, f := range dataSourcesFactories { + wrappedDataSourcesFactories[i] = pw.dataSourceWrapperFactory(ctx, f) + } + return wrappedDataSourcesFactories +} + +// Resources defines the resources implemented in the provider. +func (pw ProviderWrapper) Resources(ctx context.Context) []func() resource.Resource { + resourcesFactories := pw.provider.Resources(ctx) + wrappedResourcesFactories := make([]func() resource.Resource, len(resourcesFactories)) + for i, f := range resourcesFactories { + wrappedResourcesFactories[i] = pw.resourceWrapperFactory(ctx, f) + } + return wrappedResourcesFactories +} + +func (pw *ProviderWrapper) dataSourceWrapperFactory(ctx context.Context, f func() datasource.DataSource) func() datasource.DataSource { + return func() datasource.DataSource { + d := f() + dMeta := datasource.MetadataResponse{} + d.Metadata(ctx, datasource.MetadataRequest{}, &dMeta) + dsSchemaJSON := pw.providerSchemaJSON.DataSourcesMap[dMeta.TypeName] + return dswrapper.NewDataSourceWrapper(d, dsSchemaJSON) + } +} + +func (pw *ProviderWrapper) resourceWrapperFactory(ctx context.Context, f func() resource.Resource) func() resource.Resource { + return func() resource.Resource { + r := f() + rMeta := resource.MetadataResponse{} + r.Metadata(ctx, resource.MetadataRequest{}, &rMeta) + rsSchemaJSON := pw.providerSchemaJSON.ResourcesMap[rMeta.TypeName] + return rswrapper.NewResourceWrapper(r, rsSchemaJSON) + } +} diff --git a/vkcs/provider/schema_base.go b/vkcs/internal/providerwrapper/schema_base.go similarity index 99% rename from vkcs/provider/schema_base.go rename to vkcs/internal/providerwrapper/schema_base.go index 44effce7..d1ad1e29 100644 --- a/vkcs/provider/schema_base.go +++ b/vkcs/internal/providerwrapper/schema_base.go @@ -1,5 +1,5 @@ -package provider +package providerwrapper // NOTE: this file is generated via 'go:generate' - manual changes will be overwritten -const providerSchemaBase = `{"provider_name":"vkcs","schema_version":"1","provider_schema":{"schema":{"auth_url":{"type":"TypeString","optional":true,"description":"The Identity authentication URL."},"cloud_containers_api_version":{"type":"TypeString","optional":true,"default":"1.28","description":"Cloud Containers API version to use.\n_NOTE_ Only for custom VKCS deployments."},"password":{"type":"TypeString","required":true,"description":"Password to login with."},"project_id":{"type":"TypeString","required":true,"description":"The ID of Project to login with."},"region":{"type":"TypeString","optional":true,"description":"A region to use."},"user_domain_id":{"type":"TypeString","optional":true,"description":"The id of the domain where the user resides."},"user_domain_name":{"type":"TypeString","optional":true,"description":"The name of the domain where the user resides."},"username":{"type":"TypeString","required":true,"description":"User name to login with."}},"resources":{"vkcs_blockstorage_snapshot":{"schema":{"description":{"type":"TypeString","optional":true,"description":"The description of the volume."},"force":{"type":"TypeBool","optional":true,"description":"Allows or disallows snapshot of a volume when the volume is attached to an instance."},"metadata":{"type":"TypeMap","optional":true,"description":"Map of key-value metadata of the volume.","elem":{"type":"TypeString"}},"name":{"type":"TypeString","optional":true,"description":"The name of the snapshot."},"region":{"type":"TypeString","optional":true,"computed":true,"force_new":true},"volume_id":{"type":"TypeString","required":true,"description":"ID of the volume to create snapshot for. Changing this creates a new snapshot.","force_new":true}},"timeouts":{"create":30},"description":"Provides a blockstorage snapshot resource. This can be used to create, modify and delete blockstorage snapshot."},"vkcs_blockstorage_volume":{"schema":{"availability_zone":{"type":"TypeString","required":true,"description":"The name of the availability zone of the volume."},"description":{"type":"TypeString","optional":true,"description":"The description of the volume."},"image_id":{"type":"TypeString","optional":true,"description":"ID of the image to create volume with. Changing this creates a new volume. Only one of snapshot_id, source_volume_id, image_id fields may be set.","force_new":true},"metadata":{"type":"TypeMap","optional":true,"description":"Map of key-value metadata of the volume.","computed":true,"elem":{"type":"TypeString"}},"name":{"type":"TypeString","optional":true,"description":"The name of the volume."},"region":{"type":"TypeString","optional":true,"description":"Region to create resource in.","computed":true,"force_new":true},"size":{"type":"TypeInt","required":true,"description":"The size of the volume."},"snapshot_id":{"type":"TypeString","optional":true,"description":"ID of the snapshot of volume. Changing this creates a new volume. Only one of snapshot_id, source_volume_id, image_id fields may be set.","force_new":true},"source_vol_id":{"type":"TypeString","optional":true,"description":"ID of the source volume. Changing this creates a new volume. Only one of snapshot_id, source_volume_id, image_id fields may be set.","force_new":true},"volume_type":{"type":"TypeString","required":true,"description":"The type of the volume."}},"timeouts":{"create":30},"description":"Provides a blockstorage volume resource. This can be used to create, modify and delete blockstorage volume."},"vkcs_compute_floatingip_associate":{"schema":{"fixed_ip":{"type":"TypeString","optional":true,"description":"The specific IP address to direct traffic to.","force_new":true},"floating_ip":{"type":"TypeString","required":true,"description":"The floating IP to associate.","force_new":true},"instance_id":{"type":"TypeString","required":true,"description":"The instance to associate the floating IP with.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V2 Compute client. Keypairs are associated with accounts, but a Compute client is needed to create one. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new floatingip_associate.","computed":true,"force_new":true},"wait_until_associated":{"type":"TypeBool","optional":true,"description":"In cases where the VKCS environment does not automatically wait until the association has finished, set this option to have Terraform poll the instance until the floating IP has been associated. Defaults to false.","force_new":true}},"timeouts":{"create":10},"description":"Associate a floating IP to an instance."},"vkcs_compute_instance":{"schema":{"access_ip_v4":{"type":"TypeString","optional":true,"description":"The first detected Fixed IPv4 address.","computed":true},"admin_pass":{"type":"TypeString","optional":true,"description":"The administrative password to assign to the server. Changing this changes the root password on the existing server."},"all_metadata":{"type":"TypeMap","description":"Contains all instance metadata, even metadata not set by Terraform.","computed":true},"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the instance, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"availability_zone":{"type":"TypeString","optional":true,"description":"The availability zone in which to create the server. Conflicts with ` + "`" + `availability_zone_hints` + "`" + `. Changing this creates a new server.","computed":true,"force_new":true},"block_device":{"type":"TypeList","optional":true,"description":"Configuration of block devices. The block_device structure is documented below. Changing this creates a new server. You can specify multiple block devices which will create an instance with multiple disks. This configuration is very flexible, so please see the following [reference](https://docs.openstack.org/nova/latest/user/block-device-mapping.html) for more information.","elem":{"schema":{"boot_index":{"type":"TypeInt","optional":true,"default":-1,"description":"The boot index of the volume. It defaults to -1. Changing this creates a new server. _note_ You must set the boot index to 0 for one of the block devices if more than one is defined.","force_new":true},"delete_on_termination":{"type":"TypeBool","optional":true,"default":false,"description":"Delete the volume / block device upon termination of the instance. Defaults to false. Changing this creates a new server.","force_new":true},"destination_type":{"type":"TypeString","optional":true,"description":"The type that gets created. Possible values are \"volume\" and \"local\". Changing this creates a new server.","force_new":true},"device_type":{"type":"TypeString","optional":true,"description":"The low-level device type that will be used. Most common thing is to leave this empty. Changing this creates a new server.","force_new":true},"disk_bus":{"type":"TypeString","optional":true,"description":"The low-level disk bus that will be used. Most common thing is to leave this empty. Changing this creates a new server.","force_new":true},"guest_format":{"type":"TypeString","optional":true,"description":"Specifies the guest server disk file system format, such as ` + "`" + `ext2` + "`" + `, ` + "`" + `ext3` + "`" + `, ` + "`" + `ext4` + "`" + `, ` + "`" + `xfs` + "`" + ` or ` + "`" + `swap` + "`" + `. Swap block device mappings have the following restrictions: source_type must be blank and destination_type must be local and only one swap disk per server and the size of the swap disk must be less than or equal to the swap size of the flavor. Changing this creates a new server.","force_new":true},"source_type":{"type":"TypeString","required":true,"description":"The source type of the device. Must be one of \"blank\", \"image\", \"volume\", or \"snapshot\". Changing this creates a new server.","force_new":true},"uuid":{"type":"TypeString","optional":true,"description":"(Optional if ` + "`" + `source_type` + "`" + ` is set to ` + "`" + `\"blank\"` + "`" + ` ) The UUID of the image, volume, or snapshot. Changing this creates a new server.","force_new":true},"volume_size":{"type":"TypeInt","optional":true,"description":"The size of the volume to create (in gigabytes). Required in the following combinations: source=image and destination=volume, source=blank and destination=local, and source=blank and destination=volume. Changing this creates a new server.","force_new":true},"volume_type":{"type":"TypeString","optional":true,"description":"The volume type that will be used. Changing this creates a new server.","force_new":true}}}},"config_drive":{"type":"TypeBool","optional":true,"description":"Whether to use the config_drive feature to configure the instance. Changing this creates a new server.","force_new":true},"flavor_id":{"type":"TypeString","optional":true,"description":"(Required if ` + "`" + `flavor_name` + "`" + ` is empty) The flavor ID of the desired flavor for the server. Changing this resizes the existing server.","computed":true},"flavor_name":{"type":"TypeString","optional":true,"description":"(Required if ` + "`" + `flavor_id` + "`" + ` is empty) The name of the desired flavor for the server. Changing this resizes the existing server.","computed":true},"force_delete":{"type":"TypeBool","optional":true,"default":false,"description":"Whether to force the compute instance to be forcefully deleted. This is useful for environments that have reclaim / soft deletion enabled."},"image_id":{"type":"TypeString","optional":true,"description":"(Required if ` + "`" + `image_name` + "`" + ` is empty and not booting from a volume. Do not specify if booting from a volume.) The image ID of the desired image for the server. Changing this creates a new server.","computed":true,"force_new":true},"image_name":{"type":"TypeString","optional":true,"description":"(Required if ` + "`" + `image_id` + "`" + ` is empty and not booting from a volume. Do not specify if booting from a volume.) The name of the desired image for the server. Changing this creates a new server.","computed":true,"force_new":true},"key_pair":{"type":"TypeString","optional":true,"description":"The name of a key pair to put on the server. The key pair must already be created and associated with the tenant's account. Changing this creates a new server.","force_new":true},"metadata":{"type":"TypeMap","optional":true,"description":"Metadata key/value pairs to make available from within the instance. Changing this updates the existing server metadata."},"name":{"type":"TypeString","required":true,"description":"A unique name for the resource."},"network":{"type":"TypeList","optional":true,"description":"An array of one or more networks to attach to the instance. The network object structure is documented below. Changing this creates a new server.","computed":true,"force_new":true,"elem":{"schema":{"access_network":{"type":"TypeBool","optional":true,"default":false,"description":"Specifies if this network should be used for provisioning access. Accepts true or false. Defaults to false."},"fixed_ip_v4":{"type":"TypeString","optional":true,"description":"Specifies a fixed IPv4 address to be used on this network. Changing this creates a new server.","computed":true,"force_new":true},"mac":{"type":"TypeString","description":"The MAC address of the NIC on that network.","computed":true},"name":{"type":"TypeString","optional":true,"description":"(Optional if ` + "`" + `uuid` + "`" + ` or ` + "`" + `port` + "`" + ` is provided) The human-readable name of the network. Changing this creates a new server.","computed":true,"force_new":true},"port":{"type":"TypeString","optional":true,"description":"(Optional if ` + "`" + `uuid` + "`" + ` or ` + "`" + `name` + "`" + ` is provided) The port UUID of a network to attach to the server. Changing this creates a new server.","computed":true,"force_new":true},"uuid":{"type":"TypeString","optional":true,"description":"(Optional if ` + "`" + `port` + "`" + ` or ` + "`" + `name` + "`" + ` is provided) The network UUID to attach to the server. Changing this creates a new server.","computed":true,"force_new":true}}}},"network_mode":{"type":"TypeString","optional":true,"description":"Special string for ` + "`" + `network` + "`" + ` option to create the server. ` + "`" + `network_mode` + "`" + ` can be ` + "`" + `\"auto\"` + "`" + ` or ` + "`" + `\"none\"` + "`" + `. Please see the following [reference](https://docs.openstack.org/api-ref/compute/?expanded=create-server-detail#id11) for more information. Conflicts with ` + "`" + `network` + "`" + `.","force_new":true},"personality":{"type":"TypeSet","optional":true,"description":"Customize the personality of an instance by defining one or more files and their contents. The personality structure is described below.","force_new":true,"elem":{"schema":{"content":{"type":"TypeString","required":true,"description":"The contents of the file. Limited to 255 bytes."},"file":{"type":"TypeString","required":true,"description":"The absolute path of the destination file."}}}},"power_state":{"type":"TypeString","optional":true,"default":"active","description":"Provide the VM state. Only 'active' and 'shutoff' are supported values. *Note*: If the initial power_state is the shutoff the VM will be stopped immediately after build and the provisioners like remote-exec or files are not supported."},"region":{"type":"TypeString","optional":true,"description":"The region in which to create the server instance. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new server.","computed":true,"force_new":true},"scheduler_hints":{"type":"TypeSet","optional":true,"description":"Provide the Nova scheduler with hints on how the instance should be launched. The available hints are described below.","elem":{"schema":{"group":{"type":"TypeString","optional":true,"description":"A UUID of a Server Group. The instance will be placed into that group.","force_new":true}}}},"security_groups":{"type":"TypeSet","optional":true,"description":"An array of one or more security group names to associate with the server. Changing this results in adding/removing security groups from the existing server. *Note*: When attaching the instance to networks using Ports, place the security groups on the Port and not the instance. *Note*: Names should be used and not ids, as ids trigger unnecessary updates.","computed":true,"elem":{"type":"TypeString"}},"stop_before_destroy":{"type":"TypeBool","optional":true,"default":false,"description":"Whether to try stop instance gracefully before destroying it, thus giving chance for guest OS daemons to stop correctly. If instance doesn't stop within timeout, it will be destroyed anyway."},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the instance. Changing this updates the existing instance tags.","elem":{"type":"TypeString"}},"user_data":{"type":"TypeString","optional":true,"description":"The user data to provide when launching the instance.\tChanging this creates a new server.","force_new":true},"vendor_options":{"type":"TypeSet","optional":true,"description":"Map of additional vendor-specific options. Supported options are described below.","elem":{"schema":{"detach_ports_before_destroy":{"type":"TypeBool","optional":true,"default":false,"description":"Whether to try to detach all attached ports to the vm before destroying it to make sure the port state is correct after the vm destruction. This is helpful when the port is not deleted."},"ignore_resize_confirmation":{"type":"TypeBool","optional":true,"default":false,"description":"Boolean to control whether to ignore manual confirmation of the instance resizing."}}},"max_items":1,"min_items":1}},"timeouts":{"create":30,"delete":30,"update":30},"description":"Manages a compute VM instance resource.\n\n~\u003e **Note:** All arguments including the instance admin password will be stored in the raw state as plain-text. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_compute_interface_attach":{"schema":{"fixed_ip":{"type":"TypeString","optional":true,"description":"An IP address to assosciate with the port.\n_NOTE_: This option cannot be used with port_id. You must specify a network_id. The IP address must lie in a range on the supplied network.","computed":true,"force_new":true},"instance_id":{"type":"TypeString","required":true,"description":"The ID of the Instance to attach the Port or Network to.","force_new":true},"network_id":{"type":"TypeString","optional":true,"description":"The ID of the Network to attach to an Instance. A port will be created automatically.\n_NOTE_: This option and ` + "`" + `port_id` + "`" + ` are mutually exclusive.","computed":true,"force_new":true},"port_id":{"type":"TypeString","optional":true,"description":"The ID of the Port to attach to an Instance.\n_NOTE_: This option and ` + "`" + `network_id` + "`" + ` are mutually exclusive.","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to create the interface attachment. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new attachment.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Attaches a Network Interface (a Port) to an Instance using the VKCS Compute API."},"vkcs_compute_keypair":{"schema":{"fingerprint":{"type":"TypeString","description":"The fingerprint of the public key.","computed":true},"name":{"type":"TypeString","required":true,"description":"A unique name for the keypair. Changing this creates a new keypair.","force_new":true},"private_key":{"type":"TypeString","description":"The generated private key when no public key is specified.","computed":true},"public_key":{"type":"TypeString","optional":true,"description":"A pregenerated OpenSSH-formatted public key. Changing this creates a new keypair. If a public key is not specified, then a public/private key pair will be automatically generated. If a pair is created, then destroying this resource means you will lose access to that keypair forever.","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. Keypairs are associated with accounts, but a Compute client is needed to create one. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new keypair.","computed":true,"force_new":true},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"description":"Manages a keypair resource within VKCS.\n\n~\u003e **Important Security Notice** The private key generated by this resource will be stored *unencrypted* in your Terraform state file. **Use of this resource for production deployments is *not* recommended**. Instead, generate a private key file outside of Terraform and distribute it securely to the system where Terraform will be run."},"vkcs_compute_servergroup":{"schema":{"members":{"type":"TypeList","description":"The instances that are part of this server group.","computed":true,"elem":{"type":"TypeString"}},"name":{"type":"TypeString","required":true,"description":"A unique name for the server group. Changing this creates a new server group.","force_new":true},"policies":{"type":"TypeList","optional":true,"description":"The set of policies for the server group. All policies are mutually exclusive. See the Policies section for more information. Changing this creates a new server group.","force_new":true,"elem":{"type":"TypeString"}},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new server group.","computed":true,"force_new":true},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"description":"Manages a Server Group resource within VKCS."},"vkcs_compute_volume_attach":{"schema":{"instance_id":{"type":"TypeString","required":true,"description":"The ID of the Instance to attach the Volume to.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. A Compute client is needed to create a volume attachment. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new volume attachment.","computed":true,"force_new":true},"volume_id":{"type":"TypeString","required":true,"description":"The ID of the Volume to attach to an Instance.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Attaches a Block Storage Volume to an Instance using the VKCS Compute API."},"vkcs_db_backup":{"schema":{"container_prefix":{"type":"TypeString","optional":true,"description":"Prefix of S3 bucket ([prefix] - [project_id]) to store backup data. Default: databasebackups","force_new":true},"created":{"type":"TypeString","description":"Backup creation timestamp","computed":true},"datastore":{"type":"TypeList","description":"Object that represents datastore of backup","computed":true,"elem":{"schema":{"type":{"type":"TypeString","description":"Version of the datastore. Changing this creates a new instance.","computed":true},"version":{"type":"TypeString","description":"Type of the datastore. Changing this creates a new instance.","computed":true}}}},"dbms_id":{"type":"TypeString","required":true,"description":"ID of the instance or cluster, to create backup of.","force_new":true},"dbms_type":{"type":"TypeString","description":"Type of dbms for the backup, can be \"instance\" or \"cluster\".","computed":true},"description":{"type":"TypeString","optional":true,"description":"The description of the backup","force_new":true},"location_ref":{"type":"TypeString","description":"Location of backup data on backup storage","computed":true},"meta":{"type":"TypeString","description":"Metadata of the backup","computed":true},"name":{"type":"TypeString","required":true,"description":"The name of the backup. Changing this creates a new backup","force_new":true},"size":{"type":"TypeFloat","description":"Backup's volume size","computed":true},"updated":{"type":"TypeString","description":"Timestamp of backup's last update","computed":true},"wal_size":{"type":"TypeFloat","description":"Backup's WAL volume size","computed":true}},"timeouts":{"create":30,"delete":30},"description":"Provides a db backup resource. This can be used to create and delete db backup.","new_since":"v0.1.4"},"vkcs_db_cluster":{"schema":{"availability_zone":{"type":"TypeString","optional":true,"description":"The name of the availability zone of the cluster. Changing this creates a new cluster.","force_new":true},"backup_schedule":{"type":"TypeList","optional":true,"description":"Object that represents configuration of PITR backup. This functionality is available only for postgres datastore.","elem":{"schema":{"interval_hours":{"type":"TypeInt","required":true,"description":"Time interval between backups, specified in hours. Available values: 3, 6, 8, 12, 24."},"keep_count":{"type":"TypeInt","required":true,"description":"Number of backups to be stored."},"name":{"type":"TypeString","required":true,"description":"Name of the schedule."},"start_hours":{"type":"TypeInt","required":true,"description":"Hours part of timestamp of initial backup."},"start_minutes":{"type":"TypeInt","required":true,"description":"Minutes part of timestamp of initial backup."}}},"max_items":1,"new_since":"v0.1.4"},"capabilities":{"type":"TypeList","optional":true,"description":"Object that represents capability applied to cluster. There can be several instances of this object.","elem":{"schema":{"name":{"type":"TypeString","required":true,"description":"The name of the capability to apply."},"settings":{"type":"TypeMap","optional":true,"description":"Map of key-value settings of the capability.","elem":{"type":"TypeString"}}}}},"cloud_monitoring_enabled":{"type":"TypeBool","optional":true,"description":"Enable cloud monitoring for the cluster. Changing this for Redis or MongoDB creates a new instance.","new_since":"v0.2.0"},"cluster_size":{"type":"TypeInt","required":true,"description":"The number of instances in the cluster."},"configuration_id":{"type":"TypeString","optional":true,"description":"The id of the configuration attached to cluster."},"datastore":{"type":"TypeList","required":true,"description":"Object that represents datastore of the cluster. Changing this creates a new cluster.","force_new":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore. Changing this creates a new cluster. Type of the datastore can either be \"galera_mysql\", \"postgresql\" or \"tarantool\".","force_new":true},"version":{"type":"TypeString","required":true,"description":"Version of the datastore. Changing this creates a new cluster.","force_new":true}}},"max_items":1},"disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of the cluster.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for autoresize."}}},"max_items":1},"flavor_id":{"type":"TypeString","required":true,"description":"The ID of flavor for the cluster."},"floating_ip_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether floating ip is created for cluster. Changing this creates a new cluster.","force_new":true},"instances":{"type":"TypeList","description":"Cluster instances info.","computed":true,"elem":{"schema":{"instance_id":{"type":"TypeString","description":"The id of the instance.","computed":true},"ip":{"type":"TypeList","description":"IP address of the instance.","computed":true,"elem":{"type":"TypeString"}},"role":{"type":"TypeString","description":"The role of the instance in cluster.","computed":true}}}},"keypair":{"type":"TypeString","optional":true,"description":"Name of the keypair to be attached to cluster. Changing this creates a new cluster.","force_new":true},"loadbalancer_id":{"type":"TypeString","description":"The id of the loadbalancer attached to the cluster.","computed":true,"new_since":"v0.1.15"},"name":{"type":"TypeString","required":true,"description":"The name of the cluster. Changing this creates a new cluster.","force_new":true},"network":{"type":"TypeList","optional":true,"description":"Object that represents network of the cluster. Changing this creates a new cluster.","force_new":true,"elem":{"schema":{"port":{"type":"TypeString","optional":true,"description":"The port id of the network. Changing this creates a new cluster.","force_new":true,"deprecated":"This argument is deprecated, please do not use it."},"security_groups":{"type":"TypeSet","optional":true,"description":"An array of one or more security group IDs to associate with the cluster instances. Changing this creates a new cluster.","force_new":true,"elem":{"type":"TypeString"},"new_since":"v0.2.0"},"subnet_id":{"type":"TypeString","optional":true,"description":"The id of the subnet. Changing this creates a new cluster.","force_new":true,"new_since":"v0.1.15"},"uuid":{"type":"TypeString","optional":true,"description":"The id of the network. Changing this creates a new cluster.**Note** Although this argument is marked as optional, it is actually required at the moment. Not setting a value for it may cause an error.","force_new":true}}}},"region":{"type":"TypeString","optional":true,"description":"Region to create resource in.","computed":true,"force_new":true},"restore_point":{"type":"TypeList","optional":true,"description":"Object that represents backup to restore cluster from.","force_new":true,"elem":{"schema":{"backup_id":{"type":"TypeString","required":true,"description":"ID of the backup.","force_new":true},"target":{"type":"TypeString","optional":true,"description":"Used only for restoring from PITR backups. Timestamp of needed backup in format \"2021-10-06 01:02:00\". You can specify \"latest\" to use most recent backup.","force_new":true}}},"max_items":1,"new_since":"v0.1.4"},"root_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether root user is enabled for the cluster."},"root_password":{"type":"TypeString","optional":true,"description":"Password for the root user of the cluster.","computed":true},"shrink_options":{"type":"TypeList","optional":true,"description":"Used only for shrinking cluster. List of IDs of instances that should remain after shrink. If no options are supplied, shrink operation will choose first non-leader instance to delete.","elem":{"type":"TypeString"}},"volume_size":{"type":"TypeInt","required":true,"description":"Size of the cluster instance volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the cluster instance volume. Changing this creates a new cluster."},"wal_disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of wal volume of the cluster.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether wal volume autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for wal volume autoresize."}}},"max_items":1},"wal_volume":{"type":"TypeList","optional":true,"description":"Object that represents wal volume of the cluster. Changing this creates a new cluster.","elem":{"schema":{"size":{"type":"TypeInt","required":true,"description":"Size of the instance wal volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the cluster wal volume. Changing this creates a new cluster."}}}}},"timeouts":{"create":30,"delete":30},"description":"Provides a db cluster resource. This can be used to create, modify and delete db cluster for galera_mysql, postgresql, tarantool datastores."},"vkcs_db_cluster_with_shards":{"schema":{"capabilities":{"type":"TypeList","optional":true,"description":"Object that represents capability applied to cluster. There can be several instances of this object.","elem":{"schema":{"name":{"type":"TypeString","required":true,"description":"The name of the capability to apply."},"settings":{"type":"TypeMap","optional":true,"description":"Map of key-value settings of the capability.","elem":{"type":"TypeString"}}}}},"cloud_monitoring_enabled":{"type":"TypeBool","optional":true,"description":"Enable cloud monitoring for the cluster. Changing this for Redis or MongoDB creates a new instance.","new_since":"v0.2.0"},"configuration_id":{"type":"TypeString","optional":true,"description":"The id of the configuration attached to cluster."},"datastore":{"type":"TypeList","required":true,"description":"Object that represents datastore of the cluster. Changing this creates a new cluster.","force_new":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore. Changing this creates a new cluster. Type of the datastore must be \"clickhouse\".","force_new":true},"version":{"type":"TypeString","required":true,"description":"Version of the datastore. Changing this creates a new cluster.","force_new":true}}},"max_items":1},"disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of the cluster.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for autoresize."}}},"max_items":1},"floating_ip_enabled":{"type":"TypeBool","optional":true,"description":"Boolean field that indicates whether floating ip is created for cluster. Changing this creates a new cluster.","force_new":true},"keypair":{"type":"TypeString","optional":true,"description":"Name of the keypair to be attached to cluster. Changing this creates a new cluster.","force_new":true},"name":{"type":"TypeString","required":true,"description":"The name of the cluster. Changing this creates a new cluster.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"Region to create resource in.","computed":true,"force_new":true},"restore_point":{"type":"TypeList","optional":true,"description":"Object that represents backup to restore instance from.","force_new":true,"elem":{"schema":{"backup_id":{"type":"TypeString","required":true,"description":"ID of the backup.","force_new":true}}},"max_items":1,"new_since":"v0.1.4"},"root_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether root user is enabled for the cluster."},"root_password":{"type":"TypeString","optional":true,"description":"Password for the root user of the cluster.","computed":true},"shard":{"type":"TypeList","required":true,"description":"Object that represents cluster shard. There can be several instances of this object.","elem":{"schema":{"availability_zone":{"type":"TypeString","optional":true,"description":"The name of the availability zone of the cluster shard. Changing this creates a new cluster.","force_new":true},"flavor_id":{"type":"TypeString","required":true,"description":"The ID of flavor for the cluster shard."},"instances":{"type":"TypeList","description":"Shard instances info.","computed":true,"elem":{"schema":{"instance_id":{"type":"TypeString","description":"The id of the instance.","computed":true},"ip":{"type":"TypeList","description":"IP address of the instance.","computed":true,"elem":{"type":"TypeString"}}}},"new_since":"v0.1.15"},"network":{"type":"TypeList","optional":true,"force_new":true,"elem":{"schema":{"port":{"type":"TypeString","optional":true,"description":"The port id of the network. Changing this creates a new cluster.","force_new":true,"deprecated":"This argument is deprecated, please do not use it."},"security_groups":{"type":"TypeSet","optional":true,"description":"An array of one or more security group IDs to associate with the shard instances. Changing this creates a new cluster.","force_new":true,"elem":{"type":"TypeString"},"new_since":"v0.2.0"},"subnet_id":{"type":"TypeString","optional":true,"description":"The id of the subnet. Changing this creates a new cluster.","force_new":true,"new_since":"v0.1.15"},"uuid":{"type":"TypeString","optional":true,"description":"The id of the network. Changing this creates a new cluster.**Note** Although this argument is marked as optional, it is actually required at the moment. Not setting a value for it may cause an error.","force_new":true}},"description":"Object that represents network of the cluster shard. Changing this creates a new cluster."}},"shard_id":{"type":"TypeString","required":true,"description":"The ID of the shard. Changing this creates a new cluster.","force_new":true},"shrink_options":{"type":"TypeList","optional":true,"description":"Used only for shrinking cluster. List of IDs of instances that should remain after shrink. If no options are supplied, shrink operation will choose first non-leader instance to delete.","elem":{"type":"TypeString"}},"size":{"type":"TypeInt","required":true,"description":"The number of instances in the cluster shard."},"volume_size":{"type":"TypeInt","required":true,"description":"Size of the cluster shard instance volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the cluster shard instance volume."},"wal_volume":{"type":"TypeList","optional":true,"description":"Object that represents wal volume of the cluster.","elem":{"schema":{"size":{"type":"TypeInt","required":true,"description":"Size of the instance wal volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the cluster wal volume."}}}}}}},"wal_disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of wal volume of the cluster.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether wal volume autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for wal volume autoresize."}}},"max_items":1}},"timeouts":{"create":30,"delete":30},"description":"Provides a db cluster with shards resource. This can be used to create, modify and delete db cluster with shards for clickhouse datastore."},"vkcs_db_config_group":{"schema":{"created":{"type":"TypeString","description":"Timestamp of config group's creation","computed":true},"datastore":{"type":"TypeList","required":true,"description":"Object that represents datastore of the config group. Changing this creates a new config group.","force_new":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore.","force_new":true},"version":{"type":"TypeString","required":true,"description":"Version of the datastore.","force_new":true}}},"max_items":1},"description":{"type":"TypeString","optional":true,"description":"The description of the config group."},"name":{"type":"TypeString","required":true,"description":"The name of the config group."},"updated":{"type":"TypeString","description":"Timestamp of config group's last update","computed":true},"values":{"type":"TypeMap","required":true,"description":"Map of configuration parameters in format \"key\": \"value\".","elem":{"type":"TypeString"}}},"description":"Provides a db config group resource. This can be used to create, update and delete db config group.","new_since":"v0.1.7"},"vkcs_db_database":{"schema":{"charset":{"type":"TypeString","optional":true,"description":"Type of charset used for the database. Changing this creates a new database.","force_new":true},"collate":{"type":"TypeString","optional":true,"description":"Collate option of the database. Changing this creates a new database.","force_new":true},"dbms_id":{"type":"TypeString","required":true,"description":"ID of the instance or cluster that database is created for.","force_new":true},"dbms_type":{"type":"TypeString","description":"Type of dbms for the database, can be \"instance\" or \"cluster\".","computed":true},"name":{"type":"TypeString","required":true,"description":"The name of the database. Changing this creates a new database.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Provides a db database resource. This can be used to create, modify and delete db databases."},"vkcs_db_instance":{"schema":{"availability_zone":{"type":"TypeString","optional":true,"description":"The name of the availability zone of the instance. Changing this creates a new instance.","force_new":true},"backup_schedule":{"type":"TypeList","optional":true,"description":"Object that represents configuration of PITR backup. This functionality is available only for postgres datastore.","elem":{"schema":{"interval_hours":{"type":"TypeInt","required":true,"description":"Time interval between backups, specified in hours. Available values: 3, 6, 8, 12, 24."},"keep_count":{"type":"TypeInt","required":true,"description":"Number of backups to be stored."},"name":{"type":"TypeString","required":true,"description":"Name of the schedule."},"start_hours":{"type":"TypeInt","required":true,"description":"Hours part of timestamp of initial backup."},"start_minutes":{"type":"TypeInt","required":true,"description":"Minutes part of timestamp of initial backup."}}},"max_items":1,"new_since":"v0.1.4"},"capabilities":{"type":"TypeList","optional":true,"description":"Object that represents capability applied to instance. There can be several instances of this object (see example).","elem":{"schema":{"name":{"type":"TypeString","required":true,"description":"The name of the capability to apply."},"settings":{"type":"TypeMap","optional":true,"description":"Map of key-value settings of the capability.","elem":{"type":"TypeString"}}}}},"cloud_monitoring_enabled":{"type":"TypeBool","optional":true,"description":"Enable cloud monitoring for the instance. Changing this for Redis or MongoDB creates a new instance.","new_since":"v0.2.0"},"configuration_id":{"type":"TypeString","optional":true,"description":"The id of the configuration attached to instance."},"datastore":{"type":"TypeList","required":true,"description":"Object that represents datastore of the instance. Changing this creates a new instance.","force_new":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore. Changing this creates a new instance.","force_new":true},"version":{"type":"TypeString","required":true,"description":"Version of the datastore. Changing this creates a new instance.","force_new":true}}},"max_items":1},"disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of the instance.","computed":true,"elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for autoresize."}}},"max_items":1},"flavor_id":{"type":"TypeString","required":true,"description":"The ID of flavor for the instance."},"floating_ip_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether floating ip is created for instance. Changing this creates a new instance.","force_new":true},"ip":{"type":"TypeList","description":"IP address of the instance.","computed":true,"elem":{"type":"TypeString"}},"keypair":{"type":"TypeString","optional":true,"description":"Name of the keypair to be attached to instance. Changing this creates a new instance.","force_new":true},"name":{"type":"TypeString","required":true,"description":"The name of the instance. Changing this creates a new instance","force_new":true},"network":{"type":"TypeList","optional":true,"description":"Object that represents network of the instance. Changing this creates a new instance.","force_new":true,"elem":{"schema":{"fixed_ip_v4":{"type":"TypeString","optional":true,"description":"The IPv4 address. Changing this creates a new instance. **Note** This argument conflicts with \"replica_of\". Setting both at the same time causes \"fixed_ip_v4\" to be ignored.","force_new":true},"port":{"type":"TypeString","optional":true,"description":"The port id of the network. Changing this creates a new instance.","force_new":true,"deprecated":"This argument is deprecated, please do not use it."},"security_groups":{"type":"TypeSet","optional":true,"description":"An array of one or more security group IDs to associate with the instance. Changing this creates a new instance.","force_new":true,"elem":{"type":"TypeString"},"new_since":"v0.2.0"},"subnet_id":{"type":"TypeString","optional":true,"description":"The id of the subnet. Changing this creates a new instance.","force_new":true,"new_since":"v0.1.15"},"uuid":{"type":"TypeString","optional":true,"description":"The id of the network. Changing this creates a new instance.**Note** Although this argument is marked as optional, it is actually required at the moment. Not setting a value for it may cause an error.","force_new":true}}}},"region":{"type":"TypeString","optional":true,"description":"Region to create resource in.","computed":true,"force_new":true},"replica_of":{"type":"TypeString","optional":true,"description":"ID of the instance, that current instance is replica of."},"restore_point":{"type":"TypeList","optional":true,"description":"Object that represents backup to restore instance from.","force_new":true,"elem":{"schema":{"backup_id":{"type":"TypeString","required":true,"description":"ID of the backup.","force_new":true},"target":{"type":"TypeString","optional":true,"description":"Used only for restoring from postgresql PITR backups. Timestamp of needed backup in format \"2021-10-06 01:02:00\". You can specify \"latest\" to use most recent backup.","force_new":true}}},"max_items":1,"new_since":"v0.1.4"},"root_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether root user is enabled for the instance."},"root_password":{"type":"TypeString","optional":true,"description":"Password for the root user of the instance. If this field is empty and root user is enabled, then after creation of the instance this field will contain auto-generated root user password.","computed":true},"size":{"type":"TypeInt","required":true,"description":"Size of the instance volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the instance volume. Changing this creates a new instance.","force_new":true},"wal_disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of the instance wal volume.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether wal volume autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for wal volume autoresize."}}},"max_items":1},"wal_volume":{"type":"TypeList","optional":true,"description":"Object that represents wal volume of the instance. Changing this creates a new instance.","force_new":true,"elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether wal volume autoresize is enabled.","deprecated":"Please, use wal_disk_autoexpand block instead"},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for wal volume autoresize.","deprecated":"Please, use wal_disk_autoexpand block instead"},"size":{"type":"TypeInt","required":true,"description":"Size of the instance wal volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the instance wal volume.","force_new":true}}},"max_items":1}},"timeouts":{"create":30,"delete":30},"description":"Provides a db instance resource. This can be used to create, modify and delete db instance."},"vkcs_db_user":{"schema":{"databases":{"type":"TypeList","optional":true,"description":"List of names of the databases, that user is created for.","computed":true,"elem":{"type":"TypeString"}},"dbms_id":{"type":"TypeString","required":true,"description":"ID of the instance or cluster that user is created for.","force_new":true},"dbms_type":{"type":"TypeString","description":"Type of dbms for the user, can be \"instance\" or \"cluster\".","computed":true},"host":{"type":"TypeString","optional":true,"description":"IP address of the host that user will be accessible from."},"name":{"type":"TypeString","required":true,"description":"The name of the user. Changing this creates a new user."},"password":{"type":"TypeString","required":true,"description":"The password of the user."}},"timeouts":{"create":10,"delete":10},"description":"Provides a db user resource. This can be used to create, modify and delete db user."},"vkcs_images_image":{"schema":{"checksum":{"type":"TypeString","description":"The checksum of the data associated with the image.","computed":true},"container_format":{"type":"TypeString","required":true,"description":"The container format. Must be one of \"bare\".","force_new":true},"created_at":{"type":"TypeString","description":"The date the image was created.","computed":true},"disk_format":{"type":"TypeString","required":true,"description":"The disk format. Must be one of \"raw\", \"iso\".","force_new":true},"file":{"type":"TypeString","description":"The trailing path after the image endpoint that represent the location of the image or the path to retrieve it.","computed":true},"image_cache_path":{"type":"TypeString","optional":true,"default":"/home/panic/.terraform/image_cache","description":"This is the directory where the images will be downloaded. Images will be stored with a filename corresponding to the url's md5 hash. Defaults to \"$HOME/.terraform/image_cache\""},"image_source_password":{"type":"TypeString","optional":true,"description":"The password of basic auth to download ` + "`" + `image_source_url` + "`" + `."},"image_source_url":{"type":"TypeString","optional":true,"description":"This is the url of the raw image. The image will be downloaded in the ` + "`" + `image_cache_path` + "`" + ` before being uploaded to VKCS. Conflicts with ` + "`" + `local_file_path` + "`" + `.","force_new":true},"image_source_username":{"type":"TypeString","optional":true,"description":"The username of basic auth to download ` + "`" + `image_source_url` + "`" + `."},"local_file_path":{"type":"TypeString","optional":true,"description":"This is the filepath of the raw image file that will be uploaded to VKCS. Conflicts with ` + "`" + `image_source_url` + "`" + `","force_new":true},"metadata":{"type":"TypeMap","description":"The metadata associated with the image. Image metadata allow for meaningfully define the image properties and tags. See https://docs.openstack.org/glance/latest/user/metadefs-concepts.html.","computed":true},"min_disk_gb":{"type":"TypeInt","optional":true,"default":0,"description":"Amount of disk space (in GB) required to boot image. Defaults to 0."},"min_ram_mb":{"type":"TypeInt","optional":true,"default":0,"description":"Amount of ram (in MB) required to boot image. Defauts to 0."},"name":{"type":"TypeString","required":true,"description":"The name of the image."},"owner":{"type":"TypeString","description":"The id of the vkcs user who owns the image.","computed":true},"properties":{"type":"TypeMap","optional":true,"description":"A map of key/value pairs to set freeform information about an image. See the \"Notes\" section for further information about properties.","computed":true},"protected":{"type":"TypeBool","optional":true,"default":false,"description":"If true, image will not be deletable. Defaults to false."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Image client. An Image client is needed to create an Image that can be used with a compute instance. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new Image.","computed":true,"force_new":true},"schema":{"type":"TypeString","description":"The path to the JSON-schema that represent the image or image","computed":true},"size_bytes":{"type":"TypeInt","description":"The size in bytes of the data associated with the image.","computed":true},"status":{"type":"TypeString","description":"The status of the image. It can be \"queued\", \"active\" or \"saving\".","computed":true},"tags":{"type":"TypeSet","optional":true,"description":"The tags of the image. It must be a list of strings. At this time, it is not possible to delete all tags of an image.","elem":{"type":"TypeString"}},"updated_at":{"type":"TypeString","description":"The date the image was last updated.","computed":true},"verify_checksum":{"type":"TypeBool","optional":true,"description":"If false, the checksum will not be verified once the image is finished uploading."},"visibility":{"type":"TypeString","optional":true,"default":"private","description":"The visibility of the image. Must be one of \"private\", \"community\", or \"shared\". The ability to set the visibility depends upon the configuration of the VKCS cloud."}},"timeouts":{"create":30},"description":"Manages an Image resource within VKCS.\n\n~\u003e **Note:** All arguments including the source image URL password will be stored in the raw state as plain-text. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_keymanager_container":{"schema":{"acl":{"type":"TypeList","optional":true,"description":"Allows to control an access to a container. Currently only the ` + "`" + `read` + "`" + ` operation is supported. If not specified, the container is accessible project wide. The ` + "`" + `read` + "`" + ` structure is described below.","computed":true,"elem":{"schema":{"read":{"type":"TypeList","optional":true,"description":"Block that describes read operation.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"project_access":{"type":"TypeBool","optional":true,"default":true,"description":"Whether the container is accessible project wide. Defaults to ` + "`" + `true` + "`" + `."},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true},"users":{"type":"TypeSet","optional":true,"description":"The list of user IDs, which are allowed to access the container, when ` + "`" + `project_access` + "`" + ` is set to ` + "`" + `false` + "`" + `.","elem":{"type":"TypeString"}}}},"max_items":1}}},"max_items":1},"consumers":{"type":"TypeList","description":"The list of the container consumers. The structure is described below.","computed":true,"elem":{"schema":{"name":{"type":"TypeString","optional":true,"description":"The name of the consumer."},"url":{"type":"TypeString","optional":true,"description":"The consumer URL."}}}},"container_ref":{"type":"TypeString","description":"The container reference / where to find the container.","computed":true},"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"creator_id":{"type":"TypeString","description":"The creator of the container.","computed":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the Container. Does not have to be unique.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the KeyManager client. A KeyManager client is needed to create a container. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new container.","computed":true,"force_new":true},"secret_refs":{"type":"TypeSet","optional":true,"description":"A set of dictionaries containing references to secrets. The structure is described below.","force_new":true,"elem":{"schema":{"name":{"type":"TypeString","optional":true,"description":"The name of the secret reference. The reference names must correspond the container type, more details are available [here](https://docs.openstack.org/barbican/stein/api/reference/containers.html)."},"secret_ref":{"type":"TypeString","required":true,"description":"The secret reference / where to find the secret, URL."}}}},"status":{"type":"TypeString","description":"The status of the container.","computed":true},"type":{"type":"TypeString","required":true,"description":"Used to indicate the type of container. Must be one of ` + "`" + `generic` + "`" + `, ` + "`" + `rsa` + "`" + ` or ` + "`" + `certificate` + "`" + `.","force_new":true},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true}},"timeouts":{"create":30,"delete":30,"update":30},"description":"Manages a key container resource within VKCS."},"vkcs_keymanager_secret":{"schema":{"acl":{"type":"TypeList","optional":true,"description":"Allows to control an access to a secret. Currently only the ` + "`" + `read` + "`" + ` operation is supported. If not specified, the secret is accessible project wide.","computed":true,"elem":{"schema":{"read":{"type":"TypeList","optional":true,"description":"Block that describes read operation.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"project_access":{"type":"TypeBool","optional":true,"default":true,"description":"Whether the container is accessible project wide. Defaults to ` + "`" + `true` + "`" + `."},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true},"users":{"type":"TypeSet","optional":true,"description":"The list of user IDs, which are allowed to access the container, when ` + "`" + `project_access` + "`" + ` is set to ` + "`" + `false` + "`" + `.","elem":{"type":"TypeString"}}}},"max_items":1}}},"max_items":1},"algorithm":{"type":"TypeString","optional":true,"description":"Metadata provided by a user or system for informational purposes.","computed":true,"force_new":true},"all_metadata":{"type":"TypeMap","description":"The map of metadata, assigned on the secret, which has been explicitly and implicitly added.","computed":true},"bit_length":{"type":"TypeInt","optional":true,"description":"Metadata provided by a user or system for informational purposes.","computed":true,"force_new":true},"content_types":{"type":"TypeMap","description":"The map of the content types, assigned on the secret.","computed":true},"created_at":{"type":"TypeString","description":"The date the secret ACL was created.","computed":true},"creator_id":{"type":"TypeString","description":"The creator of the secret.","computed":true},"expiration":{"type":"TypeString","optional":true,"description":"The expiration time of the secret in the RFC3339 timestamp format (e.g. ` + "`" + `2019-03-09T12:58:49Z` + "`" + `). If omitted, a secret will never expire. Changing this creates a new secret.","force_new":true},"metadata":{"type":"TypeMap","optional":true,"description":"Additional Metadata for the secret."},"mode":{"type":"TypeString","optional":true,"description":"Metadata provided by a user or system for informational purposes.","computed":true,"force_new":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the Secret. Does not have to be unique.","force_new":true},"payload":{"type":"TypeString","optional":true,"description":"The secret's data to be stored. **payload\\_content\\_type** must also be supplied if **payload** is included.","computed":true,"force_new":true},"payload_content_encoding":{"type":"TypeString","optional":true,"description":"(required if **payload** is encoded) The encoding used for the payload to be able to include it in the JSON request. Must be either ` + "`" + `base64` + "`" + ` or ` + "`" + `binary` + "`" + `.","force_new":true},"payload_content_type":{"type":"TypeString","optional":true,"description":"(required if **payload** is included) The media type for the content of the payload. Must be one of ` + "`" + `text/plain` + "`" + `, ` + "`" + `text/plain;charset=utf-8` + "`" + `, ` + "`" + `text/plain; charset=utf-8` + "`" + `, ` + "`" + `application/octet-stream` + "`" + `, ` + "`" + `application/pkcs8` + "`" + `.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the KeyManager client. A KeyManager client is needed to create a secret. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new V1 secret.","computed":true,"force_new":true},"secret_ref":{"type":"TypeString","description":"The secret reference / where to find the secret.","computed":true},"secret_type":{"type":"TypeString","optional":true,"description":"Used to indicate the type of secret being stored. For more information see [Secret types](https://docs.openstack.org/barbican/latest/api/reference/secret_types.html).","computed":true,"force_new":true},"status":{"type":"TypeString","description":"The status of the secret.","computed":true},"updated_at":{"type":"TypeString","description":"The date the secret ACL was last updated.","computed":true}},"timeouts":{"create":30,"delete":30,"update":30},"description":"Manages a key secret resource within VKCS.\n\n~\u003e **Important Security Notice** The payload of this resource will be stored *unencrypted* in your Terraform state file. **Use of this resource for production deployments is *not* recommended**. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_kubernetes_cluster":{"schema":{"api_address":{"type":"TypeString","description":"COE API address.","computed":true,"force_new":true},"api_lb_fip":{"type":"TypeString","optional":true,"description":"API LoadBalancer fip.","computed":true,"force_new":true},"api_lb_vip":{"type":"TypeString","optional":true,"description":"API LoadBalancer vip.","computed":true,"force_new":true},"availability_zone":{"type":"TypeString","required":true,"description":"Availability zone of the cluster.","force_new":true},"cluster_template_id":{"type":"TypeString","required":true,"description":"The UUID of the Kubernetes cluster template. It can be obtained using the cluster_template data source."},"created_at":{"type":"TypeString","description":"The time at which cluster was created.","computed":true},"dns_domain":{"type":"TypeString","optional":true,"description":"Custom DNS cluster domain. Changing this creates a new cluster.","computed":true,"force_new":true},"floating_ip_enabled":{"type":"TypeBool","required":true,"description":"Floating ip is enabled.","force_new":true},"ingress_floating_ip":{"type":"TypeString","optional":true,"description":"Floating IP created for ingress service.","computed":true},"insecure_registries":{"type":"TypeList","optional":true,"description":"Addresses of registries from which you can download images without checking certificates. Changing this creates a new cluster.","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"keypair":{"type":"TypeString","optional":true,"description":"The name of the Compute service SSH keypair. Changing this creates a new cluster.","force_new":true},"labels":{"type":"TypeMap","optional":true,"description":"The list of optional key value pairs representing additional properties of the cluster. Changing this creates a new cluster.\n\n * ` + "`" + `calico_ipv4pool` + "`" + ` to set subnet where pods will be created. Default 10.100.0.0/16.\n * ` + "`" + `clean_volumes` + "`" + ` to remove pvc volumes when deleting a cluster. Default False.\n * ` + "`" + `cloud_monitoring` + "`" + ` to enable cloud monitoring feature.\n * ` + "`" + `docker_registry_enabled=true` + "`" + ` to preinstall Docker Registry.\n * ` + "`" + `etcd_volume_size` + "`" + ` to set etcd volume size. Default 10Gb.\n * ` + "`" + `ingress_controller=\"nginx\"` + "`" + ` to preinstall NGINX Ingress Controller.\n * ` + "`" + `kube_log_level` + "`" + ` to set log level for kubelet in range 0 to 8.\n * ` + "`" + `master_volume_size` + "`" + ` to set master vm volume size. Default 50Gb.\n * ` + "`" + `cluster_node_volume_type` + "`" + ` to set master vm volume type. Default ceph-hdd.\n * ` + "`" + `prometheus_monitoring=true` + "`" + ` to preinstall monitoring system based on Prometheus and Grafana.\n","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"loadbalancer_subnet_id":{"type":"TypeString","optional":true,"description":"The UUID of the load balancer's subnet. Changing this creates new cluster.","computed":true,"force_new":true},"master_addresses":{"type":"TypeList","description":"IP addresses of the master node of the cluster.","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"master_count":{"type":"TypeInt","optional":true,"description":"The number of master nodes for the cluster. Changing this creates a new cluster.","computed":true,"force_new":true},"master_flavor":{"type":"TypeString","optional":true,"description":"The UUID of a flavor for the master nodes. If master_flavor is not present, value from cluster_template will be used.","computed":true},"name":{"type":"TypeString","required":true,"description":"The name of the cluster. Changing this creates a new cluster. Should match the pattern ` + "`" + `^[a-zA-Z][a-zA-Z0-9_.-]*$` + "`" + `.","force_new":true},"network_id":{"type":"TypeString","required":true,"description":"UUID of the cluster's network.","force_new":true},"pods_network_cidr":{"type":"TypeString","optional":true,"description":"Network cidr of k8s virtual network","computed":true,"force_new":true},"project_id":{"type":"TypeString","description":"The project of the cluster.","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"Region to use for the cluster. Default is a region configured for provider.","computed":true,"force_new":true},"registry_auth_password":{"type":"TypeString","optional":true,"description":"Docker registry access password.","computed":true,"force_new":true},"stack_id":{"type":"TypeString","description":"UUID of the Orchestration service stack.","computed":true,"force_new":true},"status":{"type":"TypeString","optional":true,"description":"Current state of a cluster. Changing this to ` + "`" + `RUNNING` + "`" + ` or ` + "`" + `SHUTOFF` + "`" + ` will turn cluster on/off.","computed":true},"subnet_id":{"type":"TypeString","required":true,"description":"UUID of the cluster's subnet.","force_new":true},"updated_at":{"type":"TypeString","description":"The time at which cluster was created.","computed":true},"user_id":{"type":"TypeString","description":"The user of the cluster.","computed":true,"force_new":true}},"timeouts":{"create":60,"delete":30,"update":60},"description":"Provides a kubernetes cluster resource. This can be used to create, modify and delete kubernetes clusters."},"vkcs_kubernetes_node_group":{"schema":{"autoscaling_enabled":{"type":"TypeBool","optional":true,"default":false,"description":"Determines whether the autoscaling is enabled."},"availability_zones":{"type":"TypeList","optional":true,"description":"The list of availability zones of the node group. Zones ` + "`" + `MS1` + "`" + ` and ` + "`" + `GZ1` + "`" + ` are available. By default, node group is being created at cluster's zone.\n**Important:** Receiving default AZ add it manually to your main.tf config to sync it with state to avoid node groups force recreation in the future.","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"cluster_id":{"type":"TypeString","required":true,"description":"The UUID of the existing cluster.","force_new":true},"created_at":{"type":"TypeString","description":"The time at which node group was created.","computed":true},"flavor_id":{"type":"TypeString","optional":true,"description":"The flavor UUID of this node group.","computed":true,"force_new":true},"labels":{"type":"TypeList","optional":true,"description":"The list of objects representing representing additional properties of the node group. Each object should have attribute \"key\". Object may also have optional attribute \"value\".","elem":{"schema":{"key":{"type":"TypeString","required":true},"value":{"type":"TypeString","optional":true}}}},"max_node_unavailable":{"type":"TypeInt","optional":true,"description":"The maximum number of nodes that can fail during an upgrade. The default value is 25 percent.","computed":true},"max_nodes":{"type":"TypeInt","optional":true,"description":"The maximum allowed nodes for this node group.","computed":true},"min_nodes":{"type":"TypeInt","optional":true,"description":"The minimum allowed nodes for this node group. Default to 0 if not set.","computed":true},"name":{"type":"TypeString","required":true,"description":"The name of node group to create. Changing this will force to create a new node group.","force_new":true},"node_count":{"type":"TypeInt","required":true,"description":"The node count for this node group. Should be greater than 0. If ` + "`" + `autoscaling_enabled` + "`" + ` parameter is set, this attribute will be ignored during update."},"state":{"type":"TypeString","description":"Determines current state of node group (RUNNING, SHUTOFF, ERROR).","computed":true},"taints":{"type":"TypeList","optional":true,"description":"The list of objects representing node group taints. Each object should have following attributes: key, value, effect.","elem":{"schema":{"effect":{"type":"TypeString","required":true},"key":{"type":"TypeString","required":true},"value":{"type":"TypeString","required":true}}}},"updated_at":{"type":"TypeString","description":"The time at which node group was created.","computed":true},"uuid":{"type":"TypeString","description":"The UUID of the cluster's node group.","computed":true,"force_new":true},"volume_size":{"type":"TypeInt","optional":true,"description":"The size in GB for volume to load nodes from. Changing this will force to create a new node group.","computed":true,"force_new":true},"volume_type":{"type":"TypeString","optional":true,"description":"The volume type to load nodes from. Changing this will force to create a new node group.","computed":true,"force_new":true}},"timeouts":{"create":60,"delete":30,"update":60},"description":"Provides a cluster node group resource. This can be used to create, modify and delete cluster's node group."},"vkcs_lb_l7policy":{"schema":{"action":{"type":"TypeString","required":true,"description":"The L7 Policy action - can either be REDIRECT\\_TO\\_POOL, REDIRECT\\_TO\\_URL or REJECT."},"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the L7 Policy. A valid value is true (UP) or false (DOWN)."},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the L7 Policy."},"listener_id":{"type":"TypeString","required":true,"description":"The Listener on which the L7 Policy will be associated with. Changing this creates a new L7 Policy.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the L7 Policy. Does not have to be unique."},"position":{"type":"TypeInt","optional":true,"description":"The position of this policy on the listener. Positions start at 1.","computed":true},"redirect_pool_id":{"type":"TypeString","optional":true,"description":"Requests matching this policy will be redirected to the pool with this ID. Only valid if action is REDIRECT\\_TO\\_POOL."},"redirect_url":{"type":"TypeString","optional":true,"description":"Requests matching this policy will be redirected to this URL. Only valid if action is REDIRECT\\_TO\\_URL."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new L7 Policy.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a Load Balancer L7 Policy resource within VKCS."},"vkcs_lb_l7rule":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the L7 Rule. A valid value is true (UP) or false (DOWN)."},"compare_type":{"type":"TypeString","required":true,"description":"The comparison type for the L7 rule - can either be CONTAINS, STARTS\\_WITH, ENDS_WITH, EQUAL_TO or REGEX"},"invert":{"type":"TypeBool","optional":true,"default":false,"description":"When true the logic of the rule is inverted. For example, with invert true, equal to would become not equal to. Default is false."},"key":{"type":"TypeString","optional":true,"description":"The key to use for the comparison. For example, the name of the cookie to evaluate. Valid when ` + "`" + `type` + "`" + ` is set to COOKIE or HEADER."},"l7policy_id":{"type":"TypeString","required":true,"description":"The ID of the L7 Policy to query. Changing this creates a new L7 Rule.","force_new":true},"listener_id":{"type":"TypeString","description":"The ID of the Listener owning this resource.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new L7 Rule.","computed":true,"force_new":true},"type":{"type":"TypeString","required":true,"description":"The L7 Rule type - can either be COOKIE, FILE\\_TYPE, HEADER, HOST\\_NAME or PATH."},"value":{"type":"TypeString","required":true,"description":"The value to use for the comparison. For example, the file type to compare."}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a L7 Rule resource within VKCS."},"vkcs_lb_listener":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the Listener. A valid value is true (UP) or false (DOWN)."},"allowed_cidrs":{"type":"TypeList","optional":true,"description":"A list of CIDR blocks that are permitted to connect to this listener, denying all other source addresses. If not present, defaults to allow all.","elem":{"type":"TypeString"}},"connection_limit":{"type":"TypeInt","optional":true,"description":"The maximum number of connections allowed for the Listener.","computed":true},"default_pool_id":{"type":"TypeString","optional":true,"description":"The ID of the default pool with which the Listener is associated.","computed":true},"default_tls_container_ref":{"type":"TypeString","optional":true,"description":"A reference to a Keymanager Secrets container which stores TLS information. This is required if the protocol is ` + "`" + `TERMINATED_HTTPS` + "`" + `."},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the Listener."},"insert_headers":{"type":"TypeMap","optional":true,"description":"The list of key value pairs representing headers to insert into the request before it is sent to the backend members. Changing this updates the headers of the existing listener."},"loadbalancer_id":{"type":"TypeString","required":true,"description":"The load balancer on which to provision this Listener. Changing this creates a new Listener.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the Listener. Does not have to be unique.","computed":true},"protocol":{"type":"TypeString","required":true,"description":"The protocol - can either be TCP, HTTP, HTTPS, TERMINATED_HTTPS, UDP. Changing this creates a new Listener.","force_new":true},"protocol_port":{"type":"TypeInt","required":true,"description":"The port on which to listen for client traffic. Changing this creates a new Listener.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new Listener.","computed":true,"force_new":true},"sni_container_refs":{"type":"TypeList","optional":true,"description":"A list of references to Keymanager Secrets containers which store SNI information.","elem":{"type":"TypeString"}},"timeout_client_data":{"type":"TypeInt","optional":true,"description":"The client inactivity timeout in milliseconds.","computed":true},"timeout_member_connect":{"type":"TypeInt","optional":true,"description":"The member connection timeout in milliseconds.","computed":true},"timeout_member_data":{"type":"TypeInt","optional":true,"description":"The member inactivity timeout in milliseconds.","computed":true},"timeout_tcp_inspect":{"type":"TypeInt","optional":true,"description":"The time in milliseconds, to wait for additional TCP packets for content inspection.","computed":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a listener resource within VKCS."},"vkcs_lb_loadbalancer":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the Loadbalancer. A valid value is true (UP) or false (DOWN)."},"availability_zone":{"type":"TypeString","optional":true,"description":"The availability zone of the Loadbalancer. Changing this creates a new loadbalancer.","force_new":true},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the Loadbalancer."},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the Loadbalancer. Does not have to be unique."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new LB loadbalancer.","computed":true,"force_new":true},"security_group_ids":{"type":"TypeSet","optional":true,"description":"A list of security group IDs to apply to the loadbalancer. The security groups must be specified by ID and not name (as opposed to how they are configured with the Compute Instance).","computed":true,"elem":{"type":"TypeString"},"deprecated":"This argument is deprecated, please do not use it."},"tags":{"type":"TypeSet","optional":true,"description":"A list of simple strings assigned to the loadbalancer.","elem":{"type":"TypeString"}},"vip_address":{"type":"TypeString","optional":true,"description":"The ip address of the load balancer. Changing this creates a new loadbalancer.","computed":true,"force_new":true},"vip_network_id":{"type":"TypeString","optional":true,"description":"The network on which to allocate the Loadbalancer's address. A tenant can only create Loadbalancers on networks authorized by policy (e.g. networks that belong to them or networks that are shared). Changing this creates a new loadbalancer.","computed":true,"force_new":true},"vip_port_id":{"type":"TypeString","optional":true,"description":"The port UUID that the loadbalancer will use. Changing this creates a new loadbalancer.","computed":true,"force_new":true},"vip_subnet_id":{"type":"TypeString","optional":true,"description":"The subnet on which to allocate the Loadbalancer's address. A tenant can only create Loadbalancers on networks authorized by policy (e.g. networks that belong to them or networks that are shared). Changing this creates a new loadbalancer.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":5,"update":10},"description":"Manages a loadbalancer resource within VKCS."},"vkcs_lb_member":{"schema":{"address":{"type":"TypeString","required":true,"description":"The IP address of the member to receive traffic from the load balancer. Changing this creates a new member.","force_new":true},"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the member. A valid value is true (UP) or false (DOWN). Defaults to true."},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the member."},"pool_id":{"type":"TypeString","required":true,"description":"The id of the pool that this member will be assigned to. Changing this creates a new member.","force_new":true},"protocol_port":{"type":"TypeInt","required":true,"description":"The port on which to listen for client traffic. Changing this creates a new member.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new member.","computed":true,"force_new":true},"subnet_id":{"type":"TypeString","optional":true,"description":"The subnet in which to access the member. Changing this creates a new member.","force_new":true},"weight":{"type":"TypeInt","optional":true,"description":"A positive integer value that indicates the relative portion of traffic that this member should receive from the pool. For example, a member with a weight of 10 receives five times as much traffic as a member with a weight of 2. Defaults to 1.","computed":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a member resource within VKCS."},"vkcs_lb_members":{"schema":{"member":{"type":"TypeSet","optional":true,"description":"A set of dictionaries containing member parameters. The structure is described below.","elem":{"schema":{"address":{"type":"TypeString","required":true,"description":"The IP address of the members to receive traffic from the load balancer."},"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the member. A valid value is true (UP) or false (DOWN). Defaults to true."},"backup":{"type":"TypeBool","optional":true,"description":"A bool that indicates whether the member is backup."},"id":{"type":"TypeString","description":"The unique ID for the member.","computed":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the member."},"protocol_port":{"type":"TypeInt","required":true,"description":"The port on which to listen for client traffic."},"subnet_id":{"type":"TypeString","optional":true,"description":"The subnet in which to access the member."},"weight":{"type":"TypeInt","optional":true,"default":1,"description":"A positive integer value that indicates the relative portion of traffic that this members should receive from the pool. For example, a member with a weight of 10 receives five times as much traffic as a member with a weight of 2. Defaults to 1."}}}},"pool_id":{"type":"TypeString","required":true,"description":"The id of the pool that members will be assigned to. Changing this creates a new members resource.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new members resource.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10,"update":10}},"vkcs_lb_monitor":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the monitor. A valid value is true (UP) or false (DOWN)."},"delay":{"type":"TypeInt","required":true,"description":"The time, in seconds, between sending probes to members."},"expected_codes":{"type":"TypeString","optional":true,"description":"Required for HTTP(S) types. Expected HTTP codes for a passing HTTP(S) monitor. You can either specify a single status like \"200\", or a range like \"200-202\".","computed":true},"http_method":{"type":"TypeString","optional":true,"description":"Required for HTTP(S) types. The HTTP method used for requests by the monitor. If this attribute is not specified, it defaults to \"GET\".","computed":true},"max_retries":{"type":"TypeInt","required":true,"description":"Number of permissible ping failures before changing the member's status to INACTIVE. Must be a number between 1 and 10."},"max_retries_down":{"type":"TypeInt","optional":true,"description":"Number of permissible ping failures befor changing the member's status to ERROR. Must be a number between 1 and 10. Changing this updates the max_retries_down of the existing monitor.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The Name of the Monitor."},"pool_id":{"type":"TypeString","required":true,"description":"The id of the pool that this monitor will be assigned to.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new monitor.","computed":true,"force_new":true},"timeout":{"type":"TypeInt","required":true,"description":"Maximum number of seconds for a monitor to wait for a ping reply before it times out. The value must be less than the delay value."},"type":{"type":"TypeString","required":true,"description":"The type of probe, which is PING, TCP, HTTP, HTTPS, TLS-HELLO or UDP-CONNECT, that is sent by the load balancer to verify the member state. Changing this creates a new monitor.","force_new":true},"url_path":{"type":"TypeString","optional":true,"description":"Required for HTTP(S) types. URI path that will be accessed if monitor type is HTTP or HTTPS.","computed":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a monitor resource within VKCS."},"vkcs_lb_pool":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the pool. A valid value is true (UP) or false (DOWN)."},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the pool."},"lb_method":{"type":"TypeString","required":true,"description":"The load balancing algorithm to distribute traffic to the pool's members. Must be one of ROUND_ROBIN, LEAST_CONNECTIONS, SOURCE_IP, or SOURCE_IP_PORT."},"listener_id":{"type":"TypeString","optional":true,"description":"The Listener on which the members of the pool will be associated with. Changing this creates a new pool. Note: One of LoadbalancerID or ListenerID must be provided.","force_new":true},"loadbalancer_id":{"type":"TypeString","optional":true,"description":"The load balancer on which to provision this pool. Changing this creates a new pool. Note: One of LoadbalancerID or ListenerID must be provided.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the pool."},"persistence":{"type":"TypeList","optional":true,"description":"Omit this field to prevent session persistence. Indicates whether connections in the same session will be processed by the same Pool member or not. Changing this creates a new pool.","computed":true,"force_new":true,"elem":{"schema":{"cookie_name":{"type":"TypeString","optional":true,"description":"The name of the cookie if persistence mode is set appropriately. Required if ` + "`" + `type = APP_COOKIE` + "`" + `.","force_new":true},"type":{"type":"TypeString","required":true,"description":"The type of persistence mode. The current specification supports SOURCE_IP, HTTP_COOKIE, and APP_COOKIE.","force_new":true}}},"max_items":1},"protocol":{"type":"TypeString","required":true,"description":"The protocol - can either be TCP, HTTP, HTTPS, PROXY, or UDP. Changing this creates a new pool.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new pool.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a pool resource within VKCS."},"vkcs_networking_floatingip":{"schema":{"address":{"type":"TypeString","optional":true,"description":"The actual floating IP address itself.","computed":true,"force_new":true},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the floating IP."},"fixed_ip":{"type":"TypeString","optional":true,"description":"Fixed IP of the port to associate with this floating IP. Required if the port has multiple fixed IPs.","computed":true},"pool":{"type":"TypeString","required":true,"description":"The name of the pool from which to obtain the floating IP. Changing this creates a new floating IP.","force_new":true},"port_id":{"type":"TypeString","optional":true,"description":"ID of an existing port with at least one IP address to associate with this floating IP.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a floating IP that can be used with another networking resource, such as a load balancer. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new floating IP (which may or may not have a different address).","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"subnet_id":{"type":"TypeString","optional":true,"description":"The subnet ID of the floating IP pool. Specify this if the floating IP network has multiple subnets.","computed":true},"subnet_ids":{"type":"TypeList","optional":true,"description":"A list of external subnet IDs to try over each to allocate a floating IP address. If a subnet ID in a list has exhausted floating IP pool, the next subnet ID will be tried. This argument is used only during the resource creation. Conflicts with a ` + "`" + `subnet_id` + "`" + ` argument.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a floating IP resource within VKCS that can be used for load balancers."},"vkcs_networking_floatingip_associate":{"schema":{"fixed_ip":{"type":"TypeString","optional":true,"description":"One of the port's IP addresses.","computed":true},"floating_ip":{"type":"TypeString","required":true,"description":"IP Address of an existing floating IP.","force_new":true},"port_id":{"type":"TypeString","required":true,"description":"ID of an existing port with at least one IP address to associate with this floating IP."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a floating IP that can be used with another networking resource, such as a load balancer. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new floating IP (which may or may not have a different address).","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true}},"description":"Associates a floating IP to a port. This is useful for situations where you have a pre-allocated floating IP or are unable to use the ` + "`" + `vkcs_networking_floatingip` + "`" + ` resource to create a floating IP."},"vkcs_networking_network":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the network. Acceptable values are \"true\" and \"false\". Changing this value updates the state of the existing network."},"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the network, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the network. Changing this updates the name of the existing network."},"name":{"type":"TypeString","optional":true,"description":"The name of the network. Changing this updates the name of the existing network."},"port_security_enabled":{"type":"TypeBool","optional":true,"default":true,"description":"Whether to explicitly enable or disable port security on the network. Port Security is usually enabled by default, so omitting this argument will usually result in a value of \"true\". Setting this explicitly to ` + "`" + `false` + "`" + ` will disable port security. Valid values are ` + "`" + `true` + "`" + ` and ` + "`" + `false` + "`" + `."},"private_dns_domain":{"type":"TypeString","optional":true,"description":"Private dns domain name","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a network. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new network.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the network.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true},"vkcs_services_access":{"type":"TypeBool","optional":true,"description":"Whether VKCS services access is enabled. This feature should be enabled globally for your project. Access can be enabled for new or existing networks, but cannot be disabled for existing networks. Valid values are ` + "`" + `true` + "`" + ` and ` + "`" + `false` + "`" + `."}},"timeouts":{"create":10,"delete":10},"description":"Manages a network resource within VKCS."},"vkcs_networking_port":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"Administrative up/down status for the port (must be ` + "`" + `true` + "`" + ` or ` + "`" + `false` + "`" + ` if provided). Changing this updates the ` + "`" + `admin_state_up` + "`" + ` of an existing port."},"all_fixed_ips":{"type":"TypeList","description":"The collection of Fixed IP addresses on the port in the order returned by the Network v2 API.","computed":true,"elem":{"type":"TypeString"}},"all_security_group_ids":{"type":"TypeSet","description":"The collection of Security Group IDs on the port which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the port, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"allowed_address_pairs":{"type":"TypeSet","optional":true,"description":"An IP/MAC Address pair of additional IP addresses that can be active on this port. The structure is described below.","elem":{"schema":{"ip_address":{"type":"TypeString","required":true,"description":"The additional IP address."},"mac_address":{"type":"TypeString","optional":true,"description":"The additional MAC address."}}}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the port. Changing this updates the ` + "`" + `description` + "`" + ` of an existing port."},"device_id":{"type":"TypeString","optional":true,"description":"The ID of the device attached to the port. Changing this creates a new port.","computed":true,"force_new":true},"device_owner":{"type":"TypeString","optional":true,"description":"The device owner of the port. Changing this creates a new port.","computed":true,"force_new":true},"dns_assignment":{"type":"TypeList","description":"The list of maps representing port DNS assignments.","computed":true,"elem":{"type":"TypeMap"}},"dns_name":{"type":"TypeString","optional":true,"description":"The port DNS name.","computed":true},"extra_dhcp_option":{"type":"TypeSet","optional":true,"description":"An extra DHCP option that needs to be configured on the port. The structure is described below. Can be specified multiple times.","elem":{"schema":{"name":{"type":"TypeString","required":true,"description":"Name of the DHCP option."},"value":{"type":"TypeString","required":true,"description":"Value of the DHCP option."}}}},"fixed_ip":{"type":"TypeList","optional":true,"description":"(Conflicts with ` + "`" + `no_fixed_ip` + "`" + `) An array of desired IPs for this port. The structure is described below.","elem":{"schema":{"ip_address":{"type":"TypeString","optional":true,"description":"IP address desired in the subnet for this port. If you don't specify ` + "`" + `ip_address` + "`" + `, an available IP address from the specified subnet will be allocated to this port. This field will not be populated if it is left blank or omitted. To retrieve the assigned IP address, use the ` + "`" + `all_fixed_ips` + "`" + ` attribute."},"subnet_id":{"type":"TypeString","required":true,"description":"Subnet in which to allocate IP address for this port."}}}},"mac_address":{"type":"TypeString","optional":true,"description":"Specify a specific MAC address for the port. Changing this creates a new port.","computed":true,"force_new":true},"name":{"type":"TypeString","optional":true,"description":"A unique name for the port. Changing this updates the ` + "`" + `name` + "`" + ` of an existing port."},"network_id":{"type":"TypeString","required":true,"description":"The ID of the network to attach the port to. Changing this creates a new port.","force_new":true},"no_fixed_ip":{"type":"TypeBool","optional":true,"description":"(Conflicts with ` + "`" + `fixed_ip` + "`" + `) Create a port with no fixed IP address. This will also remove any fixed IPs previously set on a port. ` + "`" + `true` + "`" + ` is the only valid value for this argument."},"no_security_groups":{"type":"TypeBool","optional":true,"description":"(Conflicts with ` + "`" + `security_group_ids` + "`" + `) If set to ` + "`" + `true` + "`" + `, then no security groups are applied to the port. If set to ` + "`" + `false` + "`" + ` and no ` + "`" + `security_group_ids` + "`" + ` are specified, then the port will yield to the default behavior of the Networking service, which is to usually apply the \"default\" security group."},"port_security_enabled":{"type":"TypeBool","optional":true,"default":true,"description":"Whether to explicitly enable or disable port security on the port. Port Security is usually enabled by default, so omitting argument will usually result in a value of ` + "`" + `true` + "`" + `. Setting this explicitly to ` + "`" + `false` + "`" + ` will disable port security. In order to disable port security, the port must not have any security groups. Valid values are ` + "`" + `true` + "`" + ` and ` + "`" + `false` + "`" + `."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a port. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new port.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"security_group_ids":{"type":"TypeSet","optional":true,"description":"(Conflicts with ` + "`" + `no_security_groups` + "`" + `) A list of security group IDs to apply to the port. The security groups must be specified by ID and not name (as opposed to how they are configured with the Compute Instance).","elem":{"type":"TypeString"}},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the port.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a port resource within VKCS."},"vkcs_networking_port_secgroup_associate":{"schema":{"all_security_group_ids":{"type":"TypeSet","description":"The collection of Security Group IDs on the port which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"enforce":{"type":"TypeBool","optional":true,"default":false,"description":"Whether to replace or append the list of security groups, specified in the ` + "`" + `security_group_ids` + "`" + `. Defaults to ` + "`" + `false` + "`" + `."},"port_id":{"type":"TypeString","required":true,"description":"An UUID of the port to apply security groups to.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to manage a port. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new resource.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"security_group_ids":{"type":"TypeSet","required":true,"description":"A list of security group IDs to apply to the port. The security groups must be specified by ID and not name (as opposed to how they are configured with the Compute Instance).","elem":{"type":"TypeString"}}},"description":"Manages a port's security groups within VKCS. Useful, when the port was created not by Terraform. It should not be used, when the port was created directly within Terraform.\n\nWhen the resource is deleted, Terraform doesn't delete the port, but unsets the list of user defined security group IDs. However, if ` + "`" + `enforce` + "`" + ` is set to ` + "`" + `true` + "`" + ` and the resource is deleted, Terraform will remove all assigned security group IDs."},"vkcs_networking_router":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"description":"Administrative up/down status for the router (must be \"true\" or \"false\" if provided). Changing this updates the ` + "`" + `admin_state_up` + "`" + ` of an existing router.","computed":true},"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the router, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the router."},"external_network_id":{"type":"TypeString","optional":true,"description":"The network UUID of an external gateway for the router. A router with an external gateway is required if any compute instances or load balancers will be using floating IPs. Changing this updates the external gateway of the router.","computed":true},"name":{"type":"TypeString","optional":true,"description":"A unique name for the router. Changing this updates the ` + "`" + `name` + "`" + ` of an existing router."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to create a router. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new router.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the router.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional driver-specific options.","force_new":true},"vendor_options":{"type":"TypeSet","optional":true,"description":"Map of additional vendor-specific options. Supported options are described below.","elem":{"schema":{"set_router_gateway_after_create":{"type":"TypeBool","optional":true,"default":false,"description":"Boolean to control whether the Router gateway is assigned during creation or updated after creation."}}},"max_items":1,"min_items":1}},"timeouts":{"create":10,"delete":10},"description":"Manages a router resource within VKCS."},"vkcs_networking_router_interface":{"schema":{"port_id":{"type":"TypeString","optional":true,"description":"ID of the port this interface connects to. Changing this creates a new router interface.","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to create a router. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new router interface.","computed":true,"force_new":true},"router_id":{"type":"TypeString","required":true,"description":"ID of the router this interface belongs to. Changing this creates a new router interface.","force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"subnet_id":{"type":"TypeString","optional":true,"description":"ID of the subnet this interface connects to. Changing this creates a new router interface.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a router interface resource within VKCS."},"vkcs_networking_router_route":{"schema":{"destination_cidr":{"type":"TypeString","required":true,"description":"CIDR block to match on the packet’s destination IP. Changing this creates a new routing entry.","force_new":true},"next_hop":{"type":"TypeString","required":true,"description":"IP address of the next hop gateway. Changing this creates a new routing entry.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to configure a routing entry on a router. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new routing entry.","computed":true,"force_new":true},"router_id":{"type":"TypeString","required":true,"description":"ID of the router this routing entry belongs to. Changing this creates a new routing entry.","force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true}},"description":"Creates a routing entry on a VKCS router."},"vkcs_networking_secgroup":{"schema":{"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the security group, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"delete_default_rules":{"type":"TypeBool","optional":true,"description":"Whether or not to delete the default egress security rules. This is ` + "`" + `false` + "`" + ` by default. See the below note for more information.","force_new":true},"description":{"type":"TypeString","optional":true,"description":"A unique name for the security group.","computed":true},"name":{"type":"TypeString","required":true,"description":"A unique name for the security group."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to create a port. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new security group.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the security group.","elem":{"type":"TypeString"}}},"timeouts":{"delete":10},"description":"Manages a security group resource within VKCS."},"vkcs_networking_secgroup_rule":{"schema":{"description":{"type":"TypeString","optional":true,"description":"A description of the rule. Changing this creates a new security group rule.","force_new":true},"direction":{"type":"TypeString","required":true,"description":"The direction of the rule, valid values are __ingress__ or __egress__. Changing this creates a new security group rule.","force_new":true},"ethertype":{"type":"TypeString","optional":true,"default":"IPv4","description":"The layer 3 protocol type, the only valid value is __IPv4__. Changing this creates a new security group rule.","force_new":true,"deprecated":"Only IPv4 can be used as ethertype. This argument is deprecated, please do not use it."},"port_range_max":{"type":"TypeInt","optional":true,"description":"The higher part of the allowed port range, valid integer value needs to be between 1 and 65535. Changing this creates a new security group rule.","computed":true,"force_new":true},"port_range_min":{"type":"TypeInt","optional":true,"description":"The lower part of the allowed port range, valid integer value needs to be between 1 and 65535. Changing this creates a new security group rule.","computed":true,"force_new":true},"protocol":{"type":"TypeString","optional":true,"description":"The layer 4 protocol type, valid values are following. Changing this creates a new security group rule. This is required if you want to specify a port range.\n * __tcp__\n * __udp__\n * __icmp__\n * __ah__\n * __dccp__\n * __egp__\n * __esp__\n * __gre__\n * __igmp__\n * __ospf__\n * __pgm__\n * __rsvp__\n * __sctp__\n * __udplite__\n * __vrrp__","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to create a port. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new security group rule.","computed":true,"force_new":true},"remote_group_id":{"type":"TypeString","optional":true,"description":"The remote group id, the value needs to be an ID of a security group in the same tenant. Changing this creates a new security group rule. **Note**: Only one of ` + "`" + `remote_group_id` + "`" + ` or ` + "`" + `remote_ip_prefix` + "`" + ` may be set.","computed":true,"force_new":true},"remote_ip_prefix":{"type":"TypeString","optional":true,"description":"The remote CIDR, the value needs to be a valid CIDR (i.e. 192.168.0.0/16). Changing this creates a new security group rule. **Note**: Only one of ` + "`" + `remote_group_id` + "`" + ` or ` + "`" + `remote_ip_prefix` + "`" + ` may be set.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"security_group_id":{"type":"TypeString","required":true,"description":"The security group id the rule should belong to, the value needs to be an ID of a security group in the same tenant. Changing this creates a new security group rule.","force_new":true}},"timeouts":{"delete":10},"description":"Manages a security group rule resource within VKCS."},"vkcs_networking_subnet":{"schema":{"all_tags":{"type":"TypeSet","description":"The collection of ags assigned on the subnet, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"allocation_pool":{"type":"TypeSet","optional":true,"description":"A block declaring the start and end range of the IP addresses available for use with DHCP in this subnet. Multiple ` + "`" + `allocation_pool` + "`" + ` blocks can be declared, providing the subnet with more than one range of IP addresses to use with DHCP. However, each IP range must be from the same CIDR that the subnet is part of. The ` + "`" + `allocation_pool` + "`" + ` block is documented below.","computed":true,"elem":{"schema":{"end":{"type":"TypeString","required":true,"description":"The ending address."},"start":{"type":"TypeString","required":true,"description":"The starting address."}}}},"cidr":{"type":"TypeString","optional":true,"description":"CIDR representing IP range for this subnet, based on IP version. You can omit this option if you are creating a subnet from a subnet pool.","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the subnet. Changing this updates the name of the existing subnet."},"dns_nameservers":{"type":"TypeList","optional":true,"description":"An array of DNS name server names used by hosts in this subnet. Changing this updates the DNS name servers for the existing subnet.","elem":{"type":"TypeString"}},"enable_dhcp":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the network. Acceptable values are \"true\" and \"false\". Changing this value enables or disables the DHCP capabilities of the existing subnet. Defaults to true."},"gateway_ip":{"type":"TypeString","optional":true,"description":"Default gateway used by devices in this subnet. Leaving this blank and not setting ` + "`" + `no_gateway` + "`" + ` will cause a default gateway of ` + "`" + `.1` + "`" + ` to be used. Changing this updates the gateway IP of the existing subnet.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the subnet. Changing this updates the name of the existing subnet."},"network_id":{"type":"TypeString","required":true,"description":"The UUID of the parent network. Changing this creates a new subnet.","force_new":true},"no_gateway":{"type":"TypeBool","optional":true,"default":false,"description":"Do not set a gateway IP on this subnet. Changing this removes or adds a default gateway IP of the existing subnet."},"prefix_length":{"type":"TypeInt","optional":true,"description":"The prefix length to use when creating a subnet from a subnet pool. The default subnet pool prefix length that was defined when creating the subnet pool will be used if not provided. Changing this creates a new subnet.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a subnet. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new subnet.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"subnetpool_id":{"type":"TypeString","optional":true,"description":"The ID of the subnetpool associated with the subnet.","force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the subnet.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a subnet resource within VKCS."},"vkcs_networking_subnet_route":{"schema":{"destination_cidr":{"type":"TypeString","required":true,"description":"CIDR block to match on the packet’s destination IP. Changing this creates a new routing entry.","force_new":true},"next_hop":{"type":"TypeString","required":true,"description":"IP address of the next hop gateway. Changing this creates a new routing entry.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to configure a routing entry on a subnet. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new routing entry.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"subnet_id":{"type":"TypeString","required":true,"description":"ID of the subnet this routing entry belongs to. Changing this creates a new routing entry.","force_new":true}},"description":"Creates a routing entry on a VKCS subnet."},"vkcs_publicdns_record":{"schema":{"content":{"type":"TypeString","optional":true,"description":"The content of the record.","computed":true},"full_name":{"type":"TypeString","description":"The full name of the SRV record.","computed":true},"host":{"type":"TypeString","optional":true,"description":"The domain name of the target host.","computed":true},"ip":{"type":"TypeString","optional":true,"description":"The IP address of the record. It should be IPv4 for record of type \"A\" and IPv6 for record of type \"AAAA\".","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the record.","computed":true},"port":{"type":"TypeInt","optional":true,"description":"The port on the target host of the service.","computed":true},"priority":{"type":"TypeInt","optional":true,"description":"The priority of the record's server.","computed":true},"proto":{"type":"TypeString","optional":true,"description":"The name of the desired protocol."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V2 Public DNS client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new record.","computed":true,"force_new":true},"service":{"type":"TypeString","optional":true,"description":"The name of the desired service."},"ttl":{"type":"TypeInt","optional":true,"description":"The time to live of the record.","computed":true},"type":{"type":"TypeString","required":true,"description":"The type of the record. Must be one of following: \"A\", \"AAAA\", \"CNAME\", \"MX\", \"NS\", \"SRV\", \"TXT\".","force_new":true},"weight":{"type":"TypeInt","optional":true,"description":"The relative weight of the record's server.","computed":true},"zone_id":{"type":"TypeString","required":true,"description":"The ID of the zone to attach the record to.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a public DNS zone record resource within VKCS.\u003cbr\u003e\n**Note:** Although some arguments are marked as optional, it is actually required to set values for them depending on record \\\"type\\\". Use this map to get information about which arguments you have to set:\n\n| Record type | Required arguments |\n| ----------- | ------------------ |\n| A | ip |\n| AAAA | ip |\n| CNAME | name, content |\n| MX | priority, content |\n| NS | content |\n| SRV | service, proto, priority, weight, host, port |\n| TXT | content |\n\n\n","new_since":"v0.2.0"},"vkcs_publicdns_zone":{"schema":{"admin_email":{"type":"TypeString","optional":true,"description":"The admin email of the zone SOA."},"expire":{"type":"TypeInt","optional":true,"description":"The expire time of the zone SOA.","computed":true},"primary_dns":{"type":"TypeString","optional":true,"description":"The primary DNS of the zone SOA.","computed":true},"refresh":{"type":"TypeInt","optional":true,"description":"The refresh time of the zone SOA.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V2 Public DNS client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new zone.","computed":true,"force_new":true},"retry":{"type":"TypeInt","optional":true,"description":"The retry time of the zone SOA.","computed":true},"serial":{"type":"TypeInt","description":"The serial number of the zone SOA.","computed":true},"status":{"type":"TypeString","description":"The status of the zone.","computed":true},"ttl":{"type":"TypeInt","optional":true,"description":"The TTL (time to live) of the zone SOA.","computed":true},"zone":{"type":"TypeString","required":true,"description":"The name of the zone. **Changes this creates a new zone**.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a public DNS record resource within VKCS.","new_since":"v0.2.0"},"vkcs_sharedfilesystem_securityservice":{"schema":{"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the security service. Changing this updates the description of the existing security service."},"dns_ip":{"type":"TypeString","optional":true,"description":"The security service DNS IP address that is used inside the tenant network."},"domain":{"type":"TypeString","optional":true,"description":"The security service domain."},"name":{"type":"TypeString","optional":true,"description":"The name of the security service. Changing this updates the name of the existing security service."},"password":{"type":"TypeString","optional":true,"description":"The user password, if you specify a user."},"project_id":{"type":"TypeString","description":"The owner of the Security Service.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to create a security service. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new security service.","computed":true,"force_new":true},"server":{"type":"TypeString","optional":true,"description":"The security service host name or IP address."},"type":{"type":"TypeString","required":true,"description":"The security service type - can either be active\\_directory, kerberos or ldap. Changing this updates the existing security service."},"user":{"type":"TypeString","optional":true,"description":"The security service user or group name that is used by the tenant."}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Use this resource to configure a security service.\n\n~\u003e **Note:** All arguments including the security service password will be stored in the raw state as plain-text. [Read more about sensitive data in state](/docs/state/sensitive-data.html).\n\nA security service stores configuration information for clients for authentication and authorization (AuthN/AuthZ). For example, a share server will be the client for an existing service such as LDAP, Kerberos, or Microsoft Active Directory."},"vkcs_sharedfilesystem_share":{"schema":{"all_metadata":{"type":"TypeMap","description":"The map of metadata, assigned on the share, which has been explicitly and implicitly added.","computed":true},"availability_zone":{"type":"TypeString","optional":true,"description":"The share availability zone. Changing this creates a new share.","computed":true,"force_new":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the share. Changing this updates the description of the existing share."},"export_location_path":{"type":"TypeString","description":"The export location path of the share.","computed":true,"new_since":"v0.1.15"},"name":{"type":"TypeString","required":true,"description":"The name of the share. Changing this updates the name of the existing share."},"project_id":{"type":"TypeString","description":"The owner of the Share.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to create a share. Changing this creates a new share.","computed":true,"force_new":true},"share_network_id":{"type":"TypeString","required":true,"description":"The UUID of the share network."},"share_proto":{"type":"TypeString","required":true,"description":"The share protocol - can either be NFS, CIFS, CEPHFS, GLUSTERFS, HDFS or MAPRFS. Changing this creates a new share.","force_new":true},"share_server_id":{"type":"TypeString","description":"The UUID of the share server.","computed":true},"share_type":{"type":"TypeString","optional":true,"description":"The share type name. If you omit this parameter, the default share type is used.","computed":true,"force_new":true},"size":{"type":"TypeInt","required":true,"description":"The share size, in GBs. The requested share size cannot be greater than the allowed GB quota. Changing this resizes the existing share."},"snapshot_id":{"type":"TypeString","optional":true,"description":"The UUID of the share's base snapshot. Changing this creates a new share.","force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Use this resource to configure a share."},"vkcs_sharedfilesystem_share_access":{"schema":{"access_level":{"type":"TypeString","required":true,"description":"The access level to the share. Can either be ` + "`" + `rw` + "`" + ` or ` + "`" + `ro` + "`" + `.","force_new":true},"access_to":{"type":"TypeString","required":true,"description":"The value that defines the access. Can either be an IP address or a username verified by configured Security Service of the Share Network.","force_new":true},"access_type":{"type":"TypeString","required":true,"description":"The access rule type. Can either be an ip, user, cert, or cephx.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to create a share access. Changing this creates a new share access.","computed":true,"force_new":true},"share_id":{"type":"TypeString","required":true,"description":"The UUID of the share to which you are granted access.","force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Use this resource to control the share access lists.\n\n~\u003e **Important Security Notice** The access key assigned by this resource will be stored *unencrypted* in your Terraform state file. If you use this resource in production, please make sure your state file is sufficiently protected. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_sharedfilesystem_sharenetwork":{"schema":{"cidr":{"type":"TypeString","description":"The share network CIDR.","computed":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the share network. Changing this updates the description of the existing share network."},"name":{"type":"TypeString","optional":true,"description":"The name for the share network. Changing this updates the name of the existing share network."},"neutron_net_id":{"type":"TypeString","required":true,"description":"The UUID of a neutron network when setting up or updating a share network. Changing this updates the existing share network if it's not used by shares."},"neutron_subnet_id":{"type":"TypeString","required":true,"description":"The UUID of the neutron subnet when setting up or updating a share network. Changing this updates the existing share network if it's not used by shares."},"project_id":{"type":"TypeString","description":"The owner of the Share Network.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to create a share network. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new share network.","computed":true,"force_new":true},"security_service_ids":{"type":"TypeSet","optional":true,"description":"The list of security service IDs to associate with the share network. The security service must be specified by ID and not name.","elem":{"type":"TypeString"}}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Use this resource to configure a share network.\n\nA share network stores network information that share servers can use when shares are created."},"vkcs_vpnaas_endpoint_group":{"schema":{"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the group. Changing this updates the description of the existing group."},"endpoints":{"type":"TypeSet","optional":true,"description":"List of endpoints of the same type, for the endpoint group. The values will depend on the type. Changing this creates a new group.","force_new":true,"elem":{"type":"TypeString"}},"name":{"type":"TypeString","optional":true,"description":"The name of the group. Changing this updates the name of the existing group."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create an endpoint group. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new group.","computed":true,"force_new":true},"type":{"type":"TypeString","optional":true,"description":"The type of the endpoints in the group. A valid value is subnet, cidr, network, router, or vlan. Changing this creates a new group.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages an Endpoint Group resource within VKCS."},"vkcs_vpnaas_ike_policy":{"schema":{"auth_algorithm":{"type":"TypeString","optional":true,"default":"sha1","description":"The authentication hash algorithm. Valid values are sha1, sha256, sha384, sha512. Default is sha1. Changing this updates the algorithm of the existing policy."},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the policy. Changing this updates the description of the existing policy."},"encryption_algorithm":{"type":"TypeString","optional":true,"default":"aes-128","description":"The encryption algorithm. Valid values are 3des, aes-128, aes-192 and so on. The default value is aes-128. Changing this updates the existing policy."},"ike_version":{"type":"TypeString","optional":true,"default":"v1","description":"The IKE mode. A valid value is v1 or v2. Default is v1. Changing this updates the existing policy."},"lifetime":{"type":"TypeSet","optional":true,"description":"The lifetime of the security association. Consists of Unit and Value.","computed":true,"elem":{"schema":{"units":{"type":"TypeString","optional":true,"description":"The units for the lifetime of the security association. Can be either seconds or kilobytes. Default is seconds.","computed":true},"value":{"type":"TypeInt","optional":true,"description":"The value for the lifetime of the security association. Must be a positive integer. Default is 3600.","computed":true}}}},"name":{"type":"TypeString","optional":true,"description":"The name of the policy. Changing this updates the name of the existing policy."},"pfs":{"type":"TypeString","optional":true,"default":"group5","description":"The perfect forward secrecy mode. Valid values are Group2, Group5 and Group14. Default is Group5. Changing this updates the existing policy."},"phase1_negotiation_mode":{"type":"TypeString","optional":true,"default":"main","description":"The IKE mode. A valid value is main, which is the default. Changing this updates the existing policy."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a VPN service. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new service.","computed":true,"force_new":true}},"timeouts":{"create":10},"description":"Manages a IKE policy resource within VKCS."},"vkcs_vpnaas_ipsec_policy":{"schema":{"auth_algorithm":{"type":"TypeString","optional":true,"description":"The authentication hash algorithm. Valid values are sha1, sha256, sha384, sha512. Default is sha1. Changing this updates the algorithm of the existing policy.","computed":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the policy. Changing this updates the description of the existing policy."},"encapsulation_mode":{"type":"TypeString","optional":true,"description":"The encapsulation mode. Valid values are tunnel and transport. Default is tunnel. Changing this updates the existing policy.","computed":true},"encryption_algorithm":{"type":"TypeString","optional":true,"description":"The encryption algorithm. Valid values are 3des, aes-128, aes-192 and so on. The default value is aes-128. Changing this updates the existing policy.","computed":true},"lifetime":{"type":"TypeSet","optional":true,"description":"The lifetime of the security association. Consists of Unit and Value.","computed":true,"elem":{"schema":{"units":{"type":"TypeString","optional":true,"description":"The units for the lifetime of the security association. Can be either seconds or kilobytes. Default is seconds.","computed":true},"value":{"type":"TypeInt","optional":true,"description":"The value for the lifetime of the security association. Must be a positive integer. Default is 3600.","computed":true}}}},"name":{"type":"TypeString","optional":true,"description":"The name of the policy. Changing this updates the name of the existing policy."},"pfs":{"type":"TypeString","optional":true,"description":"The perfect forward secrecy mode. Valid values are Group2, Group5 and Group14. Default is Group5. Changing this updates the existing policy.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create an IPSec policy. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new policy.","computed":true,"force_new":true},"transform_protocol":{"type":"TypeString","optional":true,"description":"The transform protocol. Valid values are ESP, AH and AH-ESP. Changing this updates the existing policy. Default is ESP.","computed":true}},"timeouts":{"create":10},"description":"Manages a IPSec policy resource within VKCS."},"vkcs_vpnaas_service":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the resource. Can either be up(true) or down(false). Changing this updates the administrative state of the existing service."},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the service. Changing this updates the description of the existing service."},"external_v4_ip":{"type":"TypeString","description":"The read-only external (public) IPv4 address that is used for the VPN service.","computed":true},"external_v6_ip":{"type":"TypeString","description":"The read-only external (public) IPv6 address that is used for the VPN service.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the service. Changing this updates the name of the existing service."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a VPN service. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new service.","computed":true,"force_new":true},"router_id":{"type":"TypeString","required":true,"description":"The ID of the router. Changing this creates a new service.","force_new":true},"status":{"type":"TypeString","description":"Indicates whether IPsec VPN service is currently operational. Values are ACTIVE, DOWN, BUILD, ERROR, PENDING_CREATE, PENDING_UPDATE, or PENDING_DELETE.","computed":true},"subnet_id":{"type":"TypeString","optional":true,"description":"SubnetID is the ID of the subnet. Default is null.","force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a VPN service resource within VKCS."},"vkcs_vpnaas_site_connection":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the resource. Can either be up(true) or down(false). Changing this updates the administrative state of the existing connection."},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the connection. Changing this updates the description of the existing connection."},"dpd":{"type":"TypeSet","optional":true,"description":"A dictionary with dead peer detection (DPD) protocol controls.","computed":true,"elem":{"schema":{"action":{"type":"TypeString","optional":true,"description":"The dead peer detection (DPD) action. A valid value is clear, hold, restart, disabled, or restart-by-peer. Default value is hold.","computed":true},"interval":{"type":"TypeInt","optional":true,"description":"The dead peer detection (DPD) interval, in seconds. A valid value is a positive integer. Default is 30.","computed":true},"timeout":{"type":"TypeInt","optional":true,"description":"The dead peer detection (DPD) timeout in seconds. A valid value is a positive integer that is greater than the DPD interval value. Default is 120.","computed":true}}}},"ikepolicy_id":{"type":"TypeString","required":true,"description":"The ID of the IKE policy. Changing this creates a new connection.","force_new":true},"initiator":{"type":"TypeString","optional":true,"description":"A valid value is response-only or bi-directional. Default is bi-directional.","computed":true},"ipsecpolicy_id":{"type":"TypeString","required":true,"description":"The ID of the IPsec policy. Changing this creates a new connection.","force_new":true},"local_ep_group_id":{"type":"TypeString","optional":true,"description":"The ID for the endpoint group that contains private subnets for the local side of the connection. You must specify this parameter with the peer_ep_group_id parameter unless in backward- compatible mode where peer_cidrs is provided with a subnet_id for the VPN service. Changing this updates the existing connection."},"local_id":{"type":"TypeString","optional":true,"description":"An ID to be used instead of the external IP address for a virtual router used in traffic between instances on different networks in east-west traffic. Most often, local ID would be domain name, email address, etc. If this is not configured then the external IP address will be used as the ID."},"mtu":{"type":"TypeInt","optional":true,"description":"The maximum transmission unit (MTU) value to address fragmentation. Minimum value is 68 for IPv4, and 1280 for IPv6.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the connection. Changing this updates the name of the existing connection."},"peer_address":{"type":"TypeString","required":true,"description":"The peer gateway public IPv4 or IPv6 address or FQDN."},"peer_cidrs":{"type":"TypeList","optional":true,"description":"Unique list of valid peer private CIDRs in the form \u003c net_address \u003e / \u003c prefix \u003e.","elem":{"type":"TypeString"}},"peer_ep_group_id":{"type":"TypeString","optional":true,"description":"The ID for the endpoint group that contains private CIDRs in the form \u003c net_address \u003e / \u003c prefix \u003e for the peer side of the connection. You must specify this parameter with the local_ep_group_id parameter unless in backward-compatible mode where peer_cidrs is provided with a subnet_id for the VPN service."},"peer_id":{"type":"TypeString","required":true,"description":"The peer router identity for authentication. A valid value is an IPv4 address, IPv6 address, e-mail address, key ID, or FQDN. Typically, this value matches the peer_address value. Changing this updates the existing policy."},"psk":{"type":"TypeString","required":true,"description":"The pre-shared key. A valid value is any string."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create an IPSec site connection. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new site connection.","computed":true,"force_new":true},"vpnservice_id":{"type":"TypeString","required":true,"description":"The ID of the VPN service. Changing this creates a new connection.","force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a IPSec site connection resource within VKCS."}},"data_sources":{"vkcs_blockstorage_snapshot":{"schema":{"description":{"type":"TypeString","description":"The snapshot's description.","computed":true},"metadata":{"type":"TypeMap","description":"The snapshot's metadata.","computed":true},"most_recent":{"type":"TypeBool","optional":true,"description":"Pick the most recently created snapshot if there are multiple results."},"name":{"type":"TypeString","optional":true,"description":"The name of the snapshot.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Block Storage client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"size":{"type":"TypeInt","description":"The size of the snapshot.","computed":true},"status":{"type":"TypeString","optional":true,"description":"The status of the snapshot.","computed":true},"volume_id":{"type":"TypeString","optional":true,"description":"The ID of the snapshot's volume.","computed":true}},"description":"Use this data source to get information about an existing snapshot."},"vkcs_blockstorage_volume":{"schema":{"availability_zone":{"type":"TypeString","description":"The name of the availability zone of the volume.","computed":true},"bootable":{"type":"TypeString","optional":true,"description":"Indicates if the volume is bootable.","computed":true},"metadata":{"type":"TypeMap","optional":true,"description":"Metadata key/value pairs associated with the volume.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the volume.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Block Storage client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"size":{"type":"TypeInt","description":"The size of the volume in GBs.","computed":true},"source_volume_id":{"type":"TypeString","description":"The ID of the volume from which the current volume was created.","computed":true},"status":{"type":"TypeString","optional":true,"description":"The status of the volume.","computed":true},"volume_type":{"type":"TypeString","optional":true,"description":"The type of the volume.","computed":true}},"description":"Use this data source to get information about an existing volume."},"vkcs_compute_availability_zones":{"schema":{"id":{"type":"TypeString","description":"Hash of the returned zone list.","computed":true},"names":{"type":"TypeList","description":"The names of the availability zones, ordered alphanumerically, that match the queried ` + "`" + `state` + "`" + `","computed":true,"elem":{"type":"TypeString"}},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `","computed":true},"state":{"type":"TypeString","optional":true,"default":"available","description":"The ` + "`" + `state` + "`" + ` of the availability zones to match, default (\"available\")."}},"description":"Use this data source to get a list of availability zones from VKCS"},"vkcs_compute_flavor":{"schema":{"disk":{"type":"TypeInt","optional":true,"description":"The exact amount of disk (in gigabytes).","force_new":true},"extra_specs":{"type":"TypeMap","description":"Key/Value pairs of metadata for the flavor.","computed":true},"flavor_id":{"type":"TypeString","optional":true,"description":"The ID of the flavor. Conflicts with the ` + "`" + `name` + "`" + `, ` + "`" + `min_ram` + "`" + ` and ` + "`" + `min_disk` + "`" + `","force_new":true},"id":{"type":"TypeString","description":"ID of the found flavor.","computed":true},"is_public":{"type":"TypeBool","optional":true,"description":"The flavor visibility.","force_new":true},"min_disk":{"type":"TypeInt","optional":true,"description":"The minimum amount of disk (in gigabytes). Conflicts with the ` + "`" + `flavor_id` + "`" + `.","force_new":true},"min_ram":{"type":"TypeInt","optional":true,"description":"The minimum amount of RAM (in megabytes). Conflicts with the ` + "`" + `flavor_id` + "`" + `.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"The name of the flavor. Conflicts with the ` + "`" + `flavor_id` + "`" + `.","force_new":true},"ram":{"type":"TypeInt","optional":true,"description":"The exact amount of RAM (in megabytes).","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"rx_tx_factor":{"type":"TypeFloat","optional":true,"description":"The ` + "`" + `rx_tx_factor` + "`" + ` of the flavor.","force_new":true},"swap":{"type":"TypeInt","optional":true,"description":"The amount of swap (in gigabytes).","force_new":true},"vcpus":{"type":"TypeInt","optional":true,"description":"The amount of VCPUs.","force_new":true}},"description":"Use this data source to get the ID of an available VKCS flavor."},"vkcs_compute_instance":{"schema":{"access_ip_v4":{"type":"TypeString","description":"The first IPv4 address assigned to this server.","computed":true},"availability_zone":{"type":"TypeString","description":"The availability zone of this server.","computed":true},"flavor_id":{"type":"TypeString","description":"The flavor ID used to create the server.","computed":true},"flavor_name":{"type":"TypeString","description":"The flavor name used to create the server.","computed":true},"id":{"type":"TypeString","required":true,"description":"The UUID of the instance"},"image_id":{"type":"TypeString","description":"The image ID used to create the server.","computed":true},"image_name":{"type":"TypeString","description":"The image name used to create the server.","computed":true},"key_pair":{"type":"TypeString","description":"The name of the key pair assigned to this server.","computed":true},"metadata":{"type":"TypeMap","description":"A set of key/value pairs made available to the server.","computed":true},"name":{"type":"TypeString","description":"The name of the server.","computed":true},"network":{"type":"TypeList","optional":true,"description":"An array of maps, detailed below.","computed":true,"elem":{"schema":{"fixed_ip_v4":{"type":"TypeString","description":"The IPv4 address assigned to this network port.","computed":true},"mac":{"type":"TypeString","description":"The MAC address assigned to this network interface.","computed":true},"name":{"type":"TypeString","description":"The name of the network","computed":true},"port":{"type":"TypeString","description":"The port UUID for this network","computed":true},"uuid":{"type":"TypeString","description":"The UUID of the network","computed":true}}}},"power_state":{"type":"TypeString","description":"VM state","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"security_groups":{"type":"TypeSet","description":"An array of security group names associated with this server.","computed":true,"elem":{"type":"TypeString"}},"tags":{"type":"TypeSet","description":"A set of string tags for the instance.","computed":true,"elem":{"type":"TypeString"}},"user_data":{"type":"TypeString","optional":true,"description":"The user data added when the server was created.","computed":true}},"description":"Use this data source to get the details of a running server"},"vkcs_compute_keypair":{"schema":{"fingerprint":{"type":"TypeString","description":"The fingerprint of the OpenSSH key.","computed":true},"name":{"type":"TypeString","required":true,"description":"The unique name of the keypair."},"public_key":{"type":"TypeString","description":"The OpenSSH-formatted public key of the keypair.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true}},"description":"Use this data source to get the ID and public key of an VKCS keypair."},"vkcs_compute_quotaset":{"schema":{"cores":{"type":"TypeInt","description":"The number of allowed server cores.","computed":true},"injected_file_content_bytes":{"type":"TypeInt","description":"The number of allowed bytes of content for each injected file.","computed":true},"injected_file_path_bytes":{"type":"TypeInt","description":"The number of allowed bytes for each injected file path.","computed":true},"injected_files":{"type":"TypeInt","description":"The number of allowed injected files.","computed":true},"instances":{"type":"TypeInt","description":"The number of allowed servers.","computed":true},"key_pairs":{"type":"TypeInt","description":"The number of allowed key pairs for each user.","computed":true},"metadata_items":{"type":"TypeInt","description":"The number of allowed metadata items for each server.","computed":true},"project_id":{"type":"TypeString","required":true,"description":"The id of the project to retrieve the quotaset.","force_new":true},"ram":{"type":"TypeInt","description":"The amount of allowed server RAM, in MiB.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"server_group_members":{"type":"TypeInt","description":"The number of allowed members for each server group.","computed":true},"server_groups":{"type":"TypeInt","description":"The number of allowed server groups.","computed":true}},"description":"Use this data source to get the compute quotaset of an VKCS project."},"vkcs_db_backup":{"schema":{"backup_id":{"type":"TypeString","required":true,"description":"The UUID of the backup."},"created":{"type":"TypeString","description":"Backup creation timestamp","computed":true},"datastore":{"type":"TypeList","description":"Object that represents datastore of backup","computed":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore."},"version":{"type":"TypeString","required":true,"description":"Version of the datastore."}}}},"dbms_id":{"type":"TypeString","description":"ID of the backed up instance or cluster","computed":true},"dbms_type":{"type":"TypeString","description":"Type of dbms of the backup, can be \"instance\" or \"cluster\".","computed":true},"description":{"type":"TypeString","optional":true,"description":"The description of the backup"},"location_ref":{"type":"TypeString","description":"Location of backup data on backup storage","computed":true},"meta":{"type":"TypeString","description":"Metadata of the backup","computed":true},"name":{"type":"TypeString","description":"The name of the backup.","computed":true},"size":{"type":"TypeFloat","description":"Backup's volume size","computed":true},"updated":{"type":"TypeString","description":"Timestamp of backup's last update","computed":true},"wal_size":{"type":"TypeFloat","description":"Backup's WAL volume size","computed":true}},"description":"Use this data source to get the information on a db backup resource."},"vkcs_db_config_group":{"schema":{"config_group_id":{"type":"TypeString","required":true,"description":"The UUID of the config_group."},"created":{"type":"TypeString","description":"Timestamp of config group's creation.","computed":true},"datastore":{"type":"TypeList","description":"Object that represents datastore of backup","computed":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore."},"version":{"type":"TypeString","required":true,"description":"Version of the datastore."}}}},"description":{"type":"TypeString","description":"The description of the config group.","computed":true},"name":{"type":"TypeString","description":"The name of the config group.","computed":true},"updated":{"type":"TypeString","description":"Timestamp of config group's last update.","computed":true},"values":{"type":"TypeMap","description":"Map of configuration parameters in format \"key\": \"value\".","computed":true,"elem":{"type":"TypeString"}}},"description":"Use this data source to get the information on a db config group resource.","new_since":"v0.1.7"},"vkcs_db_database":{"schema":{"charset":{"type":"TypeString","optional":true,"description":"Type of charset used for the database.","force_new":true},"collate":{"type":"TypeString","optional":true,"description":"Collate option of the database.","force_new":true},"dbms_id":{"type":"TypeString","optional":true,"description":"ID of the instance or cluster that database is created for."},"id":{"type":"TypeString","required":true,"description":"The id of the database in form \"dbms_id/db_name\"."},"name":{"type":"TypeString","optional":true,"description":"The name of the database."}},"description":"Use this data source to get the information on a db database resource."},"vkcs_db_datastore":{"schema":{"cluster_volume_types":{"type":"TypeList","description":"Supported volume types for the datastore when used in a cluster.","computed":true,"elem":{"type":"TypeString"}},"id":{"type":"TypeString","optional":true,"description":"The id of the datastore.","computed":true},"minimum_cpu":{"type":"TypeInt","description":"Minimum CPU required for instance of the datastore.","computed":true},"minimum_ram":{"type":"TypeInt","description":"Minimum RAM required for instance of the datastore.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the datastore.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `","computed":true},"versions":{"type":"TypeList","description":"Versions of the datastore.","computed":true,"elem":{"schema":{"id":{"type":"TypeString","description":"ID of a version of the datastore.","computed":true},"name":{"type":"TypeString","description":"Name of a version of the datastore.","computed":true}}}},"volume_types":{"type":"TypeList","description":"Supported volume types for the datastore.","computed":true,"elem":{"type":"TypeString"}}},"description":"Use this data source to get information on a VKCS db datastore.","new_since":"v0.2.0"},"vkcs_db_datastore_capabilities":{"schema":{"capabilities":{"type":"TypeList","description":"Versions of the datastore.","computed":true,"elem":{"schema":{"allow_major_upgrade":{"type":"TypeBool","description":"This attribute indicates whether a capability can be applied in the next major version of data store.","computed":true},"allow_upgrade_from_backup":{"type":"TypeBool","description":"This attribute indicates whether a capability can be applied to upgrade from backup.","computed":true},"description":{"type":"TypeString","description":"Description of data store capability.","computed":true},"name":{"type":"TypeString","description":"Name of data store capability.","computed":true},"params":{"type":"TypeList","computed":true,"elem":{"schema":{"default_value":{"type":"TypeString","description":"Default value for a parameter.","computed":true},"element_type":{"type":"TypeString","description":"Type of element value for a parameter of ` + "`" + `list` + "`" + ` type.","computed":true},"enum_values":{"type":"TypeList","description":"Supported values for a parameter.","computed":true,"elem":{"type":"TypeString"}},"masked":{"type":"TypeBool","description":"Masked indicates whether a parameter value must be a boolean mask.","computed":true},"max":{"type":"TypeFloat","description":"Maximum value for a parameter.","computed":true},"min":{"type":"TypeFloat","description":"Minimum value for a parameter.","computed":true},"name":{"type":"TypeString","description":"Name of a parameter.","computed":true},"regex":{"type":"TypeString","description":"Regular expression that a parameter value must match.","computed":true},"required":{"type":"TypeBool","description":"Required indicates whether a parameter value must be set.","computed":true},"type":{"type":"TypeString","description":"Type of value for a parameter.","computed":true}}}},"should_be_on_master":{"type":"TypeBool","description":"This attribute indicates whether a capability applies only to the master node.","computed":true}}}},"datastore_name":{"type":"TypeString","required":true,"description":"Name of the data store."},"datastore_version_id":{"type":"TypeString","required":true,"description":"ID of the version of the data store."},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `.","computed":true}},"description":"Use this data source to get capabilities supported for a VKCS datastore.","new_since":"v0.2.0"},"vkcs_db_datastore_parameters":{"schema":{"datastore_name":{"type":"TypeString","required":true,"description":"Name of the data store."},"datastore_version_id":{"type":"TypeString","required":true,"description":"ID of the version of the data store."},"parameters":{"type":"TypeList","description":"Versions of the datastore.","computed":true,"elem":{"schema":{"max":{"type":"TypeFloat","description":"Maximum value of a configuration parameter.","computed":true},"min":{"type":"TypeFloat","description":"Minimum value of a configuration parameter.","computed":true},"name":{"type":"TypeString","description":"Name of a configuration parameter.","computed":true},"restart_required":{"type":"TypeBool","description":"This attribute indicates whether a restart required when a parameter is set.","computed":true},"type":{"type":"TypeString","description":"Type of a configuration parameter.","computed":true}}}},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `.","computed":true}},"description":"Use this data source to get configuration parameters supported for a VKCS datastore.","new_since":"v0.2.0"},"vkcs_db_datastores":{"schema":{"datastores":{"type":"TypeList","computed":true,"elem":{"schema":{"id":{"type":"TypeString","description":"The id of the datastore.","computed":true},"name":{"type":"TypeString","description":"Name of the datastore.","computed":true}}}},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `","computed":true}},"description":"Use this data source to get a list of datastores from VKCS.","new_since":"v0.2.0"},"vkcs_db_instance":{"schema":{"backup_schedule":{"type":"TypeList","optional":true,"description":"Object that represents configuration of PITR backup. This functionality is available only for postgres datastore.","elem":{"schema":{"interval_hours":{"type":"TypeInt","required":true,"description":"Time interval between backups, specified in hours. Available values: 3, 6, 8, 12, 24."},"keep_count":{"type":"TypeInt","required":true,"description":"Number of backups to be stored."},"name":{"type":"TypeString","required":true,"description":"Name of the schedule."},"start_hours":{"type":"TypeInt","required":true,"description":"Hours part of timestamp of initial backup."},"start_minutes":{"type":"TypeInt","required":true,"description":"Minutes part of timestamp of initial backup."}}},"new_since":"v0.1.4"},"datastore":{"type":"TypeList","optional":true,"description":"Object that represents datastore of the instance.","elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore."},"version":{"type":"TypeString","required":true,"description":"Version of the datastore."}}},"max_items":1},"flavor_id":{"type":"TypeString","optional":true,"description":"The ID of flavor for the instance."},"hostname":{"type":"TypeString","optional":true,"description":"The hostname of the instance."},"id":{"type":"TypeString","required":true,"description":"The id of the instance."},"ip":{"type":"TypeList","optional":true,"description":"IP address of the instance.","elem":{"type":"TypeString"}},"name":{"type":"TypeString","optional":true,"description":"The name of the instance."},"region":{"type":"TypeString","optional":true,"description":"Region of the resource."},"status":{"type":"TypeString","optional":true,"description":"Instance status."},"volume":{"type":"TypeSet","optional":true,"description":"Object that describes volume of the instance.","elem":{"schema":{"size":{"type":"TypeInt","required":true,"description":"Size of the instance volume."},"used":{"type":"TypeFloat","required":true,"description":"Size of the used volume space."},"volume_id":{"type":"TypeString","required":true,"description":"ID of the instance volume."},"volume_type":{"type":"TypeString","required":true,"description":"Type of the instance volume."}}},"max_items":1}},"description":"Use this data source to get the information on a db instance resource."},"vkcs_db_user":{"schema":{"databases":{"type":"TypeList","optional":true,"description":"List of names of the databases, that user is created for.","elem":{"type":"TypeString"}},"dbms_id":{"type":"TypeString","optional":true,"description":"ID of the instance or cluster that user is created for."},"host":{"type":"TypeString","optional":true,"description":"IP address of the host that user will be accessible from."},"id":{"type":"TypeString","required":true,"description":"The id of the user in form \"dbms_id/user_name\"."},"name":{"type":"TypeString","optional":true,"description":"The name of the user. Changing this creates a new user."},"password":{"type":"TypeString","optional":true,"description":"The password of the user."}},"description":"Use this data source to get the information on a db user resource."},"vkcs_images_image":{"schema":{"checksum":{"type":"TypeString","description":"The checksum of the data associated with the image.","computed":true},"container_format":{"type":"TypeString","description":"The format of the image's container.","computed":true},"created_at":{"type":"TypeString","description":"The date the image was created.","computed":true},"disk_format":{"type":"TypeString","description":"The format of the image's disk.","computed":true},"file":{"type":"TypeString","description":"The trailing path after the endpoint that represent the location of the image or the path to retrieve it.","computed":true},"member_status":{"type":"TypeString","optional":true,"description":"Status for adding a new member (tenant) to an image member list.","force_new":true},"metadata":{"type":"TypeMap","description":"The metadata associated with the image. Image metadata allow for meaningfully define the image properties and tags. See https://docs.openstack.org/glance/latest/user/metadefs-concepts.html.","computed":true},"min_disk_gb":{"type":"TypeInt","description":"The minimum amount of disk space required to use the image.","computed":true},"min_ram_mb":{"type":"TypeInt","description":"The minimum amount of ram required to use the image.","computed":true},"most_recent":{"type":"TypeBool","optional":true,"default":false,"description":"If more than one result is returned, use the most recent image.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"The name of the image.","force_new":true},"owner":{"type":"TypeString","optional":true,"description":"The owner (UUID) of the image.","force_new":true},"properties":{"type":"TypeMap","optional":true,"description":"A map of key/value pairs to match an image with. All specified properties must be matched. Unlike other options filtering by ` + "`" + `properties` + "`" + ` does by client on the result of search query. Filtering is applied if server response contains at least 2 images. In case there is only one image the ` + "`" + `properties` + "`" + ` ignores.","force_new":true},"protected":{"type":"TypeBool","description":"Whether or not the image is protected.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Image client. An Image client is needed to create an Image that can be used with a compute instance. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"schema":{"type":"TypeString","description":"The path to the JSON-schema that represent the image or image","computed":true},"size_bytes":{"type":"TypeInt","description":"The size of the image (in bytes).","computed":true},"size_max":{"type":"TypeInt","optional":true,"description":"The maximum size (in bytes) of the image to return.","force_new":true},"size_min":{"type":"TypeInt","optional":true,"description":"The minimum size (in bytes) of the image to return.","force_new":true},"tag":{"type":"TypeString","optional":true,"description":"Search for images with a specific tag.","force_new":true},"tags":{"type":"TypeSet","description":"The tags list of the image.","computed":true,"elem":{"type":"TypeString"}},"updated_at":{"type":"TypeString","description":"The date the image was last updated.","computed":true},"visibility":{"type":"TypeString","optional":true,"description":"The visibility of the image. Must be one of \"private\", \"community\", or \"shared\". Defaults to \"private\".","force_new":true}},"description":"Use this data source to get the ID of an available VKCS image."},"vkcs_keymanager_container":{"schema":{"acl":{"type":"TypeList","description":"The list of ACLs assigned to a container.","computed":true,"elem":{"schema":{"read":{"type":"TypeList","optional":true,"description":"Block that describes read operation.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"project_access":{"type":"TypeBool","optional":true,"default":true,"description":"Whether the container is accessible project wide. Defaults to ` + "`" + `true` + "`" + `."},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true},"users":{"type":"TypeSet","optional":true,"description":"The list of user IDs, which are allowed to access the container, when ` + "`" + `project_access` + "`" + ` is set to ` + "`" + `false` + "`" + `.","elem":{"type":"TypeString"}}}},"max_items":1}}}},"consumers":{"type":"TypeList","description":"The list of the container consumers.","computed":true,"elem":{"schema":{"name":{"type":"TypeString","optional":true,"description":"The name of the consumer."},"url":{"type":"TypeString","optional":true,"description":"The consumer URL."}}}},"container_ref":{"type":"TypeString","description":"The container reference / where to find the container.","computed":true},"created_at":{"type":"TypeString","description":"The date the container was created.","computed":true},"creator_id":{"type":"TypeString","description":"The creator of the container.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The Container name."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the KeyManager client. A KeyManager client is needed to fetch a container. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"secret_refs":{"type":"TypeSet","description":"A set of dictionaries containing references to secrets.","computed":true,"elem":{"schema":{"name":{"type":"TypeString","optional":true},"secret_ref":{"type":"TypeString","optional":true}}}},"status":{"type":"TypeString","description":"The status of the container.","computed":true},"type":{"type":"TypeString","description":"The container type.","computed":true},"updated_at":{"type":"TypeString","description":"The date the container was last updated.","computed":true}},"description":"Use this data source to get the ID of an available Key container."},"vkcs_keymanager_secret":{"schema":{"acl":{"type":"TypeList","description":"The list of ACLs assigned to a secret.","computed":true,"elem":{"schema":{"read":{"type":"TypeList","optional":true,"description":"Block that describes read operation.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"project_access":{"type":"TypeBool","optional":true,"default":true,"description":"Whether the container is accessible project wide. Defaults to ` + "`" + `true` + "`" + `."},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true},"users":{"type":"TypeSet","optional":true,"description":"The list of user IDs, which are allowed to access the container, when ` + "`" + `project_access` + "`" + ` is set to ` + "`" + `false` + "`" + `.","elem":{"type":"TypeString"}}}},"max_items":1}}}},"acl_only":{"type":"TypeBool","optional":true,"description":"Select the Secret with an ACL that contains the user. Project scope is ignored. Defaults to ` + "`" + `false` + "`" + `."},"algorithm":{"type":"TypeString","optional":true,"description":"The Secret algorithm."},"bit_length":{"type":"TypeInt","optional":true,"description":"The Secret bit length."},"content_types":{"type":"TypeMap","description":"The map of the content types, assigned on the secret.","computed":true},"created_at":{"type":"TypeString","description":"The date the secret was created.","computed":true},"created_at_filter":{"type":"TypeString","optional":true,"description":"Date filter to select the Secret with created matching the specified criteria. See Date Filters below for more detail."},"creator_id":{"type":"TypeString","description":"The creator of the secret.","computed":true},"expiration":{"type":"TypeString","description":"The date the secret will expire.","computed":true},"expiration_filter":{"type":"TypeString","optional":true,"description":"Date filter to select the Secret with expiration matching the specified criteria. See Date Filters below for more detail."},"metadata":{"type":"TypeMap","description":"The map of metadata, assigned on the secret, which has been explicitly and implicitly added.","computed":true},"mode":{"type":"TypeString","optional":true,"description":"The Secret mode."},"name":{"type":"TypeString","optional":true,"description":"The Secret name."},"payload":{"type":"TypeString","description":"The secret payload.","computed":true},"payload_content_encoding":{"type":"TypeString","description":"The Secret encoding.","computed":true},"payload_content_type":{"type":"TypeString","description":"The Secret content type.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the KeyManager client. A KeyManager client is needed to fetch a secret. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"secret_ref":{"type":"TypeString","description":"The secret reference / where to find the secret.","computed":true},"secret_type":{"type":"TypeString","optional":true,"description":"The Secret type. For more information see [Secret types](https://docs.openstack.org/barbican/latest/api/reference/secret_types.html)."},"status":{"type":"TypeString","description":"The status of the secret.","computed":true},"updated_at":{"type":"TypeString","description":"The date the secret was last updated.","computed":true},"updated_at_filter":{"type":"TypeString","optional":true,"description":"Date filter to select the Secret with updated matching the specified criteria. See Date Filters below for more detail."}},"description":"Use this data source to get the ID and the payload of an available Key secret\n\n~\u003e **Important Security Notice** The payload of this data source will be stored *unencrypted* in your Terraform state file. **Use of this resource for production deployments is *not* recommended**. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_kubernetes_cluster":{"schema":{"api_address":{"type":"TypeString","description":"COE API address.","computed":true},"api_lb_fip":{"type":"TypeString","description":"API LoadBalancer fip.","computed":true},"api_lb_vip":{"type":"TypeString","description":"API LoadBalancer vip.","computed":true},"availability_zone":{"type":"TypeString","description":"Availability zone of the cluster.","computed":true},"cluster_id":{"type":"TypeString","optional":true,"description":"The UUID of the Kubernetes cluster template. **Note**: Only one of ` + "`" + `name` + "`" + ` or ` + "`" + `cluster_id` + "`" + ` must be specified.","computed":true},"cluster_template_id":{"type":"TypeString","description":"The UUID of the V1 Container Infra cluster template.","computed":true},"created_at":{"type":"TypeString","description":"The time at which cluster was created.","computed":true},"discovery_url":{"type":"TypeString","description":"The URL used for cluster node discovery.","computed":true},"dns_domain":{"type":"TypeString","optional":true,"description":"Custom DNS cluster domain.","computed":true},"floating_ip_enabled":{"type":"TypeBool","description":"Indicates whether floating ip is enabled for cluster.","computed":true},"ingress_floating_ip":{"type":"TypeString","description":"Floating IP created for ingress service.","computed":true},"insecure_registries":{"type":"TypeList","description":"Addresses of registries from which you can download images without checking certificates.","computed":true,"elem":{"type":"TypeString"}},"k8s_config":{"type":"TypeString","description":"Kubeconfig for cluster","computed":true},"keypair":{"type":"TypeString","description":"The name of the Compute service SSH keypair.","computed":true},"labels":{"type":"TypeMap","description":"The list of key value pairs representing additional properties of the cluster.","computed":true},"loadbalancer_subnet_id":{"type":"TypeString","description":"The ID of load balancer's subnet.","computed":true},"master_addresses":{"type":"TypeList","description":"IP addresses of the master node of the cluster.","computed":true,"elem":{"type":"TypeString"}},"master_count":{"type":"TypeInt","description":"The number of master nodes for the cluster.","computed":true},"master_flavor":{"type":"TypeString","description":"The ID of the flavor for the master nodes.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the cluster. **Note**: Only one of ` + "`" + `name` + "`" + ` or ` + "`" + `cluster_id` + "`" + ` must be specified.","computed":true},"network_id":{"type":"TypeString","description":"UUID of the cluster's network.","computed":true},"pods_network_cidr":{"type":"TypeString","description":"Network cidr of k8s virtual network.","computed":true},"project_id":{"type":"TypeString","description":"The project of the cluster.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Container Infra client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"registry_auth_password":{"type":"TypeString","description":"Docker registry access password.","computed":true},"stack_id":{"type":"TypeString","description":"UUID of the Orchestration service stack.","computed":true},"status":{"type":"TypeString","description":"Current state of a cluster.","computed":true},"subnet_id":{"type":"TypeString","description":"UUID of the cluster's subnet.","computed":true},"updated_at":{"type":"TypeString","description":"The time at which cluster was created.","computed":true},"user_id":{"type":"TypeString","description":"The user of the cluster.","computed":true}},"description":"Use this data source to get the ID of an available VKCS kubernetes cluster."},"vkcs_kubernetes_clustertemplate":{"schema":{"apiserver_port":{"type":"TypeInt","description":"The API server port for the Container Orchestration Engine for this cluster template.","computed":true},"cluster_distro":{"type":"TypeString","description":"The distro for the cluster (fedora-atomic, coreos, etc.).","computed":true},"cluster_template_uuid":{"type":"TypeString","optional":true,"description":"The UUID of the cluster template. **Note**: Only one of ` + "`" + `name` + "`" + ` or ` + "`" + `version` + "`" + ` or ` + "`" + `cluster_template_uuid` + "`" + ` must be specified.","computed":true},"created_at":{"type":"TypeString","description":"The time at which cluster template was created.","computed":true},"deprecated_at":{"type":"TypeString","description":"The time at which the cluster template is deprecated.","computed":true},"dns_nameserver":{"type":"TypeString","description":"Address of the DNS nameserver that is used in nodes of the cluster.","computed":true},"docker_storage_driver":{"type":"TypeString","description":"Docker storage driver. Changing this updates the Docker storage driver of the existing cluster template.","computed":true},"docker_volume_size":{"type":"TypeInt","description":"The size (in GB) of the Docker volume.","computed":true},"external_network_id":{"type":"TypeString","description":"The ID of the external network that will be used for the cluster.","computed":true},"flavor":{"type":"TypeString","description":"The ID of flavor for the nodes of the cluster.","computed":true},"floating_ip_enabled":{"type":"TypeBool","description":"Indicates whether created cluster should create IP floating IP for every node or not.","computed":true},"image":{"type":"TypeString","description":"The reference to an image that is used for nodes of the cluster.","computed":true},"insecure_registry":{"type":"TypeString","description":"The insecure registry URL for the cluster template.","computed":true},"keypair_id":{"type":"TypeString","description":"The name of the Compute service SSH keypair.","computed":true},"labels":{"type":"TypeMap","description":"The list of key value pairs representing additional properties of the cluster template.","computed":true},"master_flavor":{"type":"TypeString","description":"The ID of flavor for the master nodes.","computed":true},"master_lb_enabled":{"type":"TypeBool","description":"Indicates whether created cluster should has a loadbalancer for master nodes or not.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the cluster template. **Note**: Only one of ` + "`" + `name` + "`" + ` or ` + "`" + `version` + "`" + ` or ` + "`" + `cluster_template_uuid` + "`" + ` must be specified.","computed":true},"network_driver":{"type":"TypeString","description":"The name of the driver for the container network.","computed":true},"no_proxy":{"type":"TypeString","description":"A comma-separated list of IP addresses that shouldn't be used in the cluster.","computed":true},"project_id":{"type":"TypeString","description":"The project of the cluster template.","computed":true},"public":{"type":"TypeBool","description":"Indicates whether cluster template should be public.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V1 Container Infra client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"registry_enabled":{"type":"TypeBool","description":"Indicates whether Docker registry is enabled in the cluster.","computed":true},"server_type":{"type":"TypeString","description":"The server type for the cluster template.","computed":true},"tls_disabled":{"type":"TypeBool","description":"Indicates whether the TLS should be disabled in the cluster.","computed":true},"updated_at":{"type":"TypeString","description":"The time at which cluster template was updated.","computed":true},"user_id":{"type":"TypeString","description":"The user of the cluster template.","computed":true},"version":{"type":"TypeString","optional":true,"description":"Kubernetes version of the cluster.","computed":true},"volume_driver":{"type":"TypeString","description":"The name of the driver that is used for the volumes of the cluster nodes.","computed":true}},"description":"Use this data source to get the ID of an available VKCS kubernetes cluster template."},"vkcs_kubernetes_clustertemplates":{"schema":{"cluster_templates":{"type":"TypeList","description":"A list of available kubernetes cluster templates.\n - ` + "`" + `cluster_template_uuid` + "`" + ` **String** The UUID of the cluster template.\n\n - ` + "`" + `name` + "`" + ` **String** The name of the cluster template.\n\n - ` + "`" + `version` + "`" + ` **String** The version of the cluster template.","computed":true,"elem":{"schema":{"cluster_template_uuid":{"type":"TypeString","required":true,"description":"The UUID of the cluster template."},"name":{"type":"TypeString","required":true,"description":"The name of the cluster template."},"version":{"type":"TypeString","required":true,"description":"The version of the cluster template."}}}},"id":{"type":"TypeString","description":"Random identifier of the data source.","computed":true}},"description":"` + "`" + `vkcs_kubernetes_cluster_templates` + "`" + ` returns list of available VKCS Kubernetes Cluster Templates. To get details of each cluster template the data source can be combined with the ` + "`" + `vkcs_kubernetes_clustertemplate` + "`" + ` data source."},"vkcs_kubernetes_node_group":{"schema":{"autoscaling_enabled":{"type":"TypeBool","optional":true,"description":"Determines whether the autoscaling is enabled."},"availability_zones":{"type":"TypeList","description":"The list of availability zones of the node group.","computed":true,"elem":{"type":"TypeString"}},"cluster_id":{"type":"TypeString","description":"The UUID of cluster that node group belongs.","computed":true},"flavor_id":{"type":"TypeString","optional":true,"description":"The id of flavor."},"max_node_unavailable":{"type":"TypeInt","optional":true,"description":"Specified as a percentage. The maximum number of nodes that can fail during an upgrade.","computed":true},"max_nodes":{"type":"TypeInt","optional":true,"description":"The maximum amount of nodes in node group."},"min_nodes":{"type":"TypeInt","optional":true,"description":"The minimum amount of nodes in node group."},"name":{"type":"TypeString","optional":true,"description":"The name of the node group.","computed":true},"node_count":{"type":"TypeInt","optional":true,"description":"The count of nodes in node group."},"nodes":{"type":"TypeList","description":"The list of node group's node objects.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"Time when node was created.","computed":true},"name":{"type":"TypeString","description":"The name of the node.","computed":true},"node_group_id":{"type":"TypeString","description":"The node group id","computed":true},"updated_at":{"type":"TypeString","description":"Time when node was updated.","computed":true},"uuid":{"type":"TypeString","description":"The UUID of node.","computed":true}}}},"state":{"type":"TypeString","description":"Determines current state of node group (RUNNING, SHUTOFF, ERROR).","computed":true},"uuid":{"type":"TypeString","required":true,"description":"The UUID of the cluster's node group."},"volume_size":{"type":"TypeInt","optional":true,"description":"The amount of memory of volume in Gb."},"volume_type":{"type":"TypeString","optional":true,"description":"The type of volume."}},"description":"Use this data source to get the ID of an available VKCS kubernetes clusters node group."},"vkcs_lb_loadbalancer":{"schema":{"admin_state_up":{"type":"TypeBool","description":"The administrative state of the Loadbalancer.","computed":true},"availability_zone":{"type":"TypeString","description":"The availability zone of the Loadbalancer.","computed":true},"description":{"type":"TypeString","description":"Human-readable description of the Loadbalancer.","computed":true},"id":{"type":"TypeString","required":true,"description":"The UUID of the Loadbalancer"},"name":{"type":"TypeString","description":"The name of the Loadbalancer.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"security_group_ids":{"type":"TypeSet","description":"A list of security group IDs applied to the Loadbalancer.","computed":true,"elem":{"type":"TypeString"}},"tags":{"type":"TypeSet","description":"A list of simple strings assigned to the loadbalancer.","computed":true,"elem":{"type":"TypeString"}},"vip_address":{"type":"TypeString","description":"The ip address of the Loadbalancer.","computed":true},"vip_network_id":{"type":"TypeString","description":"The network on which to allocate the Loadbalancer's address. A tenant can only create Loadbalancers on networks authorized by policy (e.g. networks that belong to them or networks that are shared). Changing this creates a new loadbalancer.","computed":true},"vip_port_id":{"type":"TypeString","description":"The port UUID of the Loadbalancer.","computed":true},"vip_subnet_id":{"type":"TypeString","description":"The subnet on which the Loadbalancer's address is allocated.","computed":true}},"description":"Use this data source to get the details of a loadbalancer"},"vkcs_networking_floatingip":{"schema":{"address":{"type":"TypeString","optional":true,"description":"The IP address of the floating IP."},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the floating IP."},"fixed_ip":{"type":"TypeString","optional":true,"description":"The specific IP address of the internal port which should be associated with the floating IP."},"id":{"type":"TypeString","description":"ID of the found floating IP.","computed":true},"pool":{"type":"TypeString","optional":true,"description":"The name of the pool from which the floating IP belongs to."},"port_id":{"type":"TypeString","optional":true,"description":"The ID of the port the floating IP is attached."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve floating IP ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"status":{"type":"TypeString","optional":true,"description":"Status of the floating IP (ACTIVE/DOWN)."},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the floating IP."}},"description":"Use this data source to get the ID of an available VKCS floating IP."},"vkcs_networking_network":{"schema":{"admin_state_up":{"type":"TypeString","description":"The administrative state of the network.","computed":true},"all_tags":{"type":"TypeSet","description":"The set of string tags applied on the network.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the network."},"external":{"type":"TypeBool","optional":true,"description":"The external routing facility of the network."},"id":{"type":"TypeString","description":"ID of the found network.","computed":true},"matching_subnet_cidr":{"type":"TypeString","optional":true,"description":"The CIDR of a subnet within the network."},"name":{"type":"TypeString","optional":true,"description":"The name of the network."},"network_id":{"type":"TypeString","optional":true,"description":"The ID of the network."},"private_dns_domain":{"type":"TypeString","description":"Private dns domain name","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve networks ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"shared":{"type":"TypeString","description":"Specifies whether the network resource can be accessed by any tenant or not.","computed":true},"status":{"type":"TypeString","optional":true,"description":"The status of the network."},"subnets":{"type":"TypeList","description":"A list of subnet IDs belonging to the network.","computed":true,"elem":{"type":"TypeString"}},"tags":{"type":"TypeSet","optional":true,"description":"The list of network tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the network."},"vkcs_services_access":{"type":"TypeBool","optional":true,"description":"Specifies whether VKCS services access is enabled."}},"description":"Use this data source to get the ID of an available VKCS network."},"vkcs_networking_port":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"description":"The administrative state of the port."},"all_fixed_ips":{"type":"TypeList","description":"The collection of Fixed IP addresses on the port in the order returned by the Network v2 API.","computed":true,"elem":{"type":"TypeString"}},"all_security_group_ids":{"type":"TypeSet","description":"The set of security group IDs applied on the port.","computed":true,"elem":{"type":"TypeString"}},"all_tags":{"type":"TypeSet","description":"The set of string tags applied on the port.","computed":true,"elem":{"type":"TypeString"}},"allowed_address_pairs":{"type":"TypeSet","description":"An IP/MAC Address pair of additional IP addresses that can be active on this port. The structure is described below.","computed":true,"elem":{"schema":{"ip_address":{"type":"TypeString","description":"The additional IP address.","computed":true},"mac_address":{"type":"TypeString","description":"The additional MAC address.","computed":true}}}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the port."},"device_id":{"type":"TypeString","optional":true,"description":"The ID of the device the port belongs to."},"device_owner":{"type":"TypeString","optional":true,"description":"The device owner of the port."},"dns_assignment":{"type":"TypeList","description":"The list of maps representing port DNS assignments.","computed":true,"elem":{"type":"TypeMap"}},"dns_name":{"type":"TypeString","optional":true,"description":"The port DNS name to filter."},"extra_dhcp_option":{"type":"TypeList","description":"An extra DHCP option configured on the port. The structure is described below.","computed":true,"elem":{"schema":{"name":{"type":"TypeString","description":"Name of the DHCP option.","computed":true},"value":{"type":"TypeString","description":"Value of the DHCP option.","computed":true}}}},"fixed_ip":{"type":"TypeString","optional":true,"description":"The port IP address filter."},"id":{"type":"TypeString","description":"ID of the found port.","computed":true},"mac_address":{"type":"TypeString","optional":true,"description":"The MAC address of the port."},"name":{"type":"TypeString","optional":true,"description":"The name of the port."},"network_id":{"type":"TypeString","optional":true,"description":"The ID of the network the port belongs to."},"port_id":{"type":"TypeString","optional":true,"description":"The ID of the port."},"project_id":{"type":"TypeString","optional":true,"description":"The project_id of the owner of the port."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve port ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"security_group_ids":{"type":"TypeSet","optional":true,"description":"The list of port security group IDs to filter.","elem":{"type":"TypeString"}},"status":{"type":"TypeString","optional":true,"description":"The status of the port.","force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"The list of port tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The tenant_id of the owner of the port."}},"description":"Use this data source to get the ID of an available VKCS port."},"vkcs_networking_router":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"description":"Administrative up/down status for the router (must be \"true\" or \"false\" if provided)."},"all_tags":{"type":"TypeSet","description":"The set of string tags applied on the router.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the router."},"enable_snat":{"type":"TypeBool","optional":true,"description":"The value that points out if the Source NAT is enabled on the router.","computed":true},"external_network_id":{"type":"TypeString","description":"The network UUID of an external gateway for the router.","computed":true},"id":{"type":"TypeString","description":"ID of the found router.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the router."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve router ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"router_id":{"type":"TypeString","optional":true,"description":"The UUID of the router resource."},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"status":{"type":"TypeString","optional":true,"description":"The status of the router (ACTIVE/DOWN)."},"tags":{"type":"TypeSet","optional":true,"description":"The list of router tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the router."}},"description":"Use this data source to get the ID of an available VKCS router."},"vkcs_networking_secgroup":{"schema":{"all_tags":{"type":"TypeSet","description":"The set of string tags applied on the security group.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description the the subnet."},"id":{"type":"TypeString","description":"ID of the found security group.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the security group."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve security groups ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"secgroup_id":{"type":"TypeString","optional":true,"description":"The ID of the security group."},"tags":{"type":"TypeSet","optional":true,"description":"The list of security group tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the security group.","computed":true,"force_new":true}},"description":"Use this data source to get the ID of an available VKCS security group."},"vkcs_networking_subnet":{"schema":{"all_tags":{"type":"TypeSet","description":"A set of string tags applied on the subnet.","computed":true,"elem":{"type":"TypeString"}},"allocation_pools":{"type":"TypeList","description":"Allocation pools of the subnet.","computed":true,"elem":{"schema":{"end":{"type":"TypeString","description":"The ending address.","computed":true},"start":{"type":"TypeString","description":"The starting address.","computed":true}}}},"cidr":{"type":"TypeString","optional":true,"description":"The CIDR of the subnet.","computed":true},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the subnet.","computed":true},"dhcp_enabled":{"type":"TypeBool","optional":true,"description":"If the subnet has DHCP enabled."},"dns_nameservers":{"type":"TypeSet","description":"DNS Nameservers of the subnet.","computed":true,"elem":{"type":"TypeString"}},"enable_dhcp":{"type":"TypeBool","description":"Whether the subnet has DHCP enabled or not.","computed":true},"gateway_ip":{"type":"TypeString","optional":true,"description":"The IP of the subnet's gateway.","computed":true},"host_routes":{"type":"TypeList","description":"Host Routes of the subnet.","computed":true,"elem":{"schema":{"destination_cidr":{"type":"TypeString","computed":true},"next_hop":{"type":"TypeString","computed":true}}}},"id":{"type":"TypeString","description":"ID of the found subnet.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the subnet.","computed":true},"network_id":{"type":"TypeString","optional":true,"description":"The ID of the network the subnet belongs to.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve subnet ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"subnet_id":{"type":"TypeString","optional":true,"description":"The ID of the subnet.","computed":true},"subnetpool_id":{"type":"TypeString","optional":true,"description":"The ID of the subnetpool associated with the subnet.","computed":true},"tags":{"type":"TypeSet","optional":true,"description":"The list of subnet tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the subnet.","computed":true}},"description":"Use this data source to get the ID of an available VKCS subnet."},"vkcs_publicdns_zone":{"schema":{"admin_email":{"type":"TypeString","optional":true,"description":"The admin email of the zone SOA.","computed":true},"expire":{"type":"TypeInt","optional":true,"description":"The expire time of the zone SOA.","computed":true},"id":{"type":"TypeString","optional":true,"description":"The UUID of the DNS zone.","computed":true},"primary_dns":{"type":"TypeString","optional":true,"description":"The primary DNS of the zone SOA.","computed":true},"refresh":{"type":"TypeInt","optional":true,"description":"The refresh time of the zone SOA.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V2 Public DNS client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"retry":{"type":"TypeInt","optional":true,"description":"The retry time of the zone SOA.","computed":true},"serial":{"type":"TypeInt","optional":true,"description":"The serial number of the zone SOA.","computed":true},"status":{"type":"TypeString","optional":true,"description":"The status of the zone.","computed":true},"ttl":{"type":"TypeInt","optional":true,"description":"The TTL (time to live) of the zone SOA.","computed":true},"zone":{"type":"TypeString","optional":true,"description":"The name of the zone.","computed":true}},"description":"Use this data source to get the ID of a VKCS public DNS zone.","new_since":"v0.2.0"},"vkcs_region":{"schema":{"description":{"type":"TypeString","description":"Description of the region.","computed":true},"id":{"type":"TypeString","optional":true,"description":"ID of the region to learn or use. Use empty value to learn current region on the provider."},"parent_region":{"type":"TypeString","description":"Parent of the region.","computed":true}},"description":"` + "`" + `vkcs_region` + "`" + ` provides details about a specific VKCS region. As well as validating a given region name this resource can be used to discover the name of the region configured within the provider."},"vkcs_regions":{"schema":{"id":{"type":"TypeString","description":"Random identifier of the data source.","computed":true},"names":{"type":"TypeSet","description":"Names of regions that meets the criteria.","computed":true,"elem":{"type":"TypeString"}}},"description":"` + "`" + `vkcs_regions` + "`" + ` provides information about VKCS regions. To get details of each region the data source can be combined with the ` + "`" + `vkcs_region` + "`" + ` data source."},"vkcs_sharedfilesystem_share":{"schema":{"availability_zone":{"type":"TypeString","description":"The share availability zone.","computed":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the share.","computed":true},"export_location_path":{"type":"TypeString","optional":true,"description":"The export location path of the share.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the share.","computed":true},"project_id":{"type":"TypeString","description":"The owner of the share.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client.","computed":true},"share_network_id":{"type":"TypeString","required":true,"description":"The UUID of the share's share network."},"share_proto":{"type":"TypeString","description":"The share protocol.","computed":true},"size":{"type":"TypeInt","description":"The share size, in GBs.","computed":true},"snapshot_id":{"type":"TypeString","optional":true,"description":"The UUID of the share's base snapshot.","computed":true},"status":{"type":"TypeString","optional":true,"description":"A share status filter. A valid value is ` + "`" + `creating` + "`" + `, ` + "`" + `error` + "`" + `, ` + "`" + `available` + "`" + `, ` + "`" + `deleting` + "`" + `, ` + "`" + `error_deleting` + "`" + `, ` + "`" + `manage_starting` + "`" + `, ` + "`" + `manage_error` + "`" + `, ` + "`" + `unmanage_starting` + "`" + `, ` + "`" + `unmanage_error` + "`" + `, ` + "`" + `unmanaged` + "`" + `, ` + "`" + `extending` + "`" + `, ` + "`" + `extending_error` + "`" + `, ` + "`" + `shrinking` + "`" + `, ` + "`" + `shrinking_error` + "`" + `, or ` + "`" + `shrinking_possible_data_loss_error` + "`" + `.","computed":true}},"description":"Use this data source to get the ID of an available Shared File System share."},"vkcs_sharedfilesystem_sharenetwork":{"schema":{"cidr":{"type":"TypeString","description":"The share network CIDR.","computed":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description of the share network.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the share network.","computed":true},"neutron_net_id":{"type":"TypeString","optional":true,"description":"The neutron network UUID of the share network.","computed":true},"neutron_subnet_id":{"type":"TypeString","optional":true,"description":"The neutron subnet UUID of the share network.","computed":true},"project_id":{"type":"TypeString","description":"The owner of the share network.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to read a share network. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"security_service_id":{"type":"TypeString","optional":true,"description":"The security service IDs associated with the share network.","elem":{"type":"TypeString"}},"security_service_ids":{"type":"TypeSet","description":"The list of security service IDs associated with the share network.","computed":true,"elem":{"type":"TypeString"}}},"description":"Use this data source to get the ID of an available Shared File System share network."}}}}` +const ProviderSchemaJSON = `{"provider_name":"vkcs","schema_version":"1","provider_schema":{"schema":{"auth_url":{"type":"TypeString","optional":true,"description":"The Identity authentication URL."},"cloud_containers_api_version":{"type":"TypeString","optional":true,"default":"1.28","description":"Cloud Containers API version to use.\n_NOTE_ Only for custom VKCS deployments."},"password":{"type":"TypeString","required":true,"description":"Password to login with."},"project_id":{"type":"TypeString","required":true,"description":"The ID of Project to login with."},"region":{"type":"TypeString","optional":true,"description":"A region to use."},"user_domain_id":{"type":"TypeString","optional":true,"description":"The id of the domain where the user resides."},"user_domain_name":{"type":"TypeString","optional":true,"description":"The name of the domain where the user resides."},"username":{"type":"TypeString","required":true,"description":"User name to login with."}},"resources":{"vkcs_blockstorage_snapshot":{"schema":{"description":{"type":"TypeString","optional":true,"description":"The description of the volume."},"force":{"type":"TypeBool","optional":true,"description":"Allows or disallows snapshot of a volume when the volume is attached to an instance."},"metadata":{"type":"TypeMap","optional":true,"description":"Map of key-value metadata of the volume.","elem":{"type":"TypeString"}},"name":{"type":"TypeString","optional":true,"description":"The name of the snapshot."},"region":{"type":"TypeString","optional":true,"computed":true,"force_new":true},"volume_id":{"type":"TypeString","required":true,"description":"ID of the volume to create snapshot for. Changing this creates a new snapshot.","force_new":true}},"timeouts":{"create":30},"description":"Provides a blockstorage snapshot resource. This can be used to create, modify and delete blockstorage snapshot."},"vkcs_blockstorage_volume":{"schema":{"availability_zone":{"type":"TypeString","required":true,"description":"The name of the availability zone of the volume."},"description":{"type":"TypeString","optional":true,"description":"The description of the volume."},"image_id":{"type":"TypeString","optional":true,"description":"ID of the image to create volume with. Changing this creates a new volume. Only one of snapshot_id, source_volume_id, image_id fields may be set.","force_new":true},"metadata":{"type":"TypeMap","optional":true,"description":"Map of key-value metadata of the volume.","computed":true,"elem":{"type":"TypeString"}},"name":{"type":"TypeString","optional":true,"description":"The name of the volume."},"region":{"type":"TypeString","optional":true,"description":"Region to create resource in.","computed":true,"force_new":true},"size":{"type":"TypeInt","required":true,"description":"The size of the volume."},"snapshot_id":{"type":"TypeString","optional":true,"description":"ID of the snapshot of volume. Changing this creates a new volume. Only one of snapshot_id, source_volume_id, image_id fields may be set.","force_new":true},"source_vol_id":{"type":"TypeString","optional":true,"description":"ID of the source volume. Changing this creates a new volume. Only one of snapshot_id, source_volume_id, image_id fields may be set.","force_new":true},"volume_type":{"type":"TypeString","required":true,"description":"The type of the volume."}},"timeouts":{"create":30},"description":"Provides a blockstorage volume resource. This can be used to create, modify and delete blockstorage volume."},"vkcs_compute_floatingip_associate":{"schema":{"fixed_ip":{"type":"TypeString","optional":true,"description":"The specific IP address to direct traffic to.","force_new":true},"floating_ip":{"type":"TypeString","required":true,"description":"The floating IP to associate.","force_new":true},"instance_id":{"type":"TypeString","required":true,"description":"The instance to associate the floating IP with.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V2 Compute client. Keypairs are associated with accounts, but a Compute client is needed to create one. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new floatingip_associate.","computed":true,"force_new":true},"wait_until_associated":{"type":"TypeBool","optional":true,"description":"In cases where the VKCS environment does not automatically wait until the association has finished, set this option to have Terraform poll the instance until the floating IP has been associated. Defaults to false.","force_new":true}},"timeouts":{"create":10},"description":"Associate a floating IP to an instance."},"vkcs_compute_instance":{"schema":{"access_ip_v4":{"type":"TypeString","optional":true,"description":"The first detected Fixed IPv4 address.","computed":true},"admin_pass":{"type":"TypeString","optional":true,"description":"The administrative password to assign to the server. Changing this changes the root password on the existing server."},"all_metadata":{"type":"TypeMap","description":"Contains all instance metadata, even metadata not set by Terraform.","computed":true},"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the instance, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"availability_zone":{"type":"TypeString","optional":true,"description":"The availability zone in which to create the server. Conflicts with ` + "`" + `availability_zone_hints` + "`" + `. Changing this creates a new server.","computed":true,"force_new":true},"block_device":{"type":"TypeList","optional":true,"description":"Configuration of block devices. The block_device structure is documented below. Changing this creates a new server. You can specify multiple block devices which will create an instance with multiple disks. This configuration is very flexible, so please see the following [reference](https://docs.openstack.org/nova/latest/user/block-device-mapping.html) for more information.","elem":{"schema":{"boot_index":{"type":"TypeInt","optional":true,"default":-1,"description":"The boot index of the volume. It defaults to -1. Changing this creates a new server. _note_ You must set the boot index to 0 for one of the block devices if more than one is defined.","force_new":true},"delete_on_termination":{"type":"TypeBool","optional":true,"default":false,"description":"Delete the volume / block device upon termination of the instance. Defaults to false. Changing this creates a new server.","force_new":true},"destination_type":{"type":"TypeString","optional":true,"description":"The type that gets created. Possible values are \"volume\" and \"local\". Changing this creates a new server.","force_new":true},"device_type":{"type":"TypeString","optional":true,"description":"The low-level device type that will be used. Most common thing is to leave this empty. Changing this creates a new server.","force_new":true},"disk_bus":{"type":"TypeString","optional":true,"description":"The low-level disk bus that will be used. Most common thing is to leave this empty. Changing this creates a new server.","force_new":true},"guest_format":{"type":"TypeString","optional":true,"description":"Specifies the guest server disk file system format, such as ` + "`" + `ext2` + "`" + `, ` + "`" + `ext3` + "`" + `, ` + "`" + `ext4` + "`" + `, ` + "`" + `xfs` + "`" + ` or ` + "`" + `swap` + "`" + `. Swap block device mappings have the following restrictions: source_type must be blank and destination_type must be local and only one swap disk per server and the size of the swap disk must be less than or equal to the swap size of the flavor. Changing this creates a new server.","force_new":true},"source_type":{"type":"TypeString","required":true,"description":"The source type of the device. Must be one of \"blank\", \"image\", \"volume\", or \"snapshot\". Changing this creates a new server.","force_new":true},"uuid":{"type":"TypeString","optional":true,"description":"(Optional if ` + "`" + `source_type` + "`" + ` is set to ` + "`" + `\"blank\"` + "`" + ` ) The UUID of the image, volume, or snapshot. Changing this creates a new server.","force_new":true},"volume_size":{"type":"TypeInt","optional":true,"description":"The size of the volume to create (in gigabytes). Required in the following combinations: source=image and destination=volume, source=blank and destination=local, and source=blank and destination=volume. Changing this creates a new server.","force_new":true},"volume_type":{"type":"TypeString","optional":true,"description":"The volume type that will be used. Changing this creates a new server.","force_new":true}}}},"config_drive":{"type":"TypeBool","optional":true,"description":"Whether to use the config_drive feature to configure the instance. Changing this creates a new server.","force_new":true},"flavor_id":{"type":"TypeString","optional":true,"description":"(Required if ` + "`" + `flavor_name` + "`" + ` is empty) The flavor ID of the desired flavor for the server. Changing this resizes the existing server.","computed":true},"flavor_name":{"type":"TypeString","optional":true,"description":"(Required if ` + "`" + `flavor_id` + "`" + ` is empty) The name of the desired flavor for the server. Changing this resizes the existing server.","computed":true},"force_delete":{"type":"TypeBool","optional":true,"default":false,"description":"Whether to force the compute instance to be forcefully deleted. This is useful for environments that have reclaim / soft deletion enabled."},"image_id":{"type":"TypeString","optional":true,"description":"(Required if ` + "`" + `image_name` + "`" + ` is empty and not booting from a volume. Do not specify if booting from a volume.) The image ID of the desired image for the server. Changing this creates a new server.","computed":true,"force_new":true},"image_name":{"type":"TypeString","optional":true,"description":"(Required if ` + "`" + `image_id` + "`" + ` is empty and not booting from a volume. Do not specify if booting from a volume.) The name of the desired image for the server. Changing this creates a new server.","computed":true,"force_new":true},"key_pair":{"type":"TypeString","optional":true,"description":"The name of a key pair to put on the server. The key pair must already be created and associated with the tenant's account. Changing this creates a new server.","force_new":true},"metadata":{"type":"TypeMap","optional":true,"description":"Metadata key/value pairs to make available from within the instance. Changing this updates the existing server metadata."},"name":{"type":"TypeString","required":true,"description":"A unique name for the resource."},"network":{"type":"TypeList","optional":true,"description":"An array of one or more networks to attach to the instance. The network object structure is documented below. Changing this creates a new server.","computed":true,"force_new":true,"elem":{"schema":{"access_network":{"type":"TypeBool","optional":true,"default":false,"description":"Specifies if this network should be used for provisioning access. Accepts true or false. Defaults to false."},"fixed_ip_v4":{"type":"TypeString","optional":true,"description":"Specifies a fixed IPv4 address to be used on this network. Changing this creates a new server.","computed":true,"force_new":true},"mac":{"type":"TypeString","description":"The MAC address of the NIC on that network.","computed":true},"name":{"type":"TypeString","optional":true,"description":"(Optional if ` + "`" + `uuid` + "`" + ` or ` + "`" + `port` + "`" + ` is provided) The human-readable name of the network. Changing this creates a new server.","computed":true,"force_new":true},"port":{"type":"TypeString","optional":true,"description":"(Optional if ` + "`" + `uuid` + "`" + ` or ` + "`" + `name` + "`" + ` is provided) The port UUID of a network to attach to the server. Changing this creates a new server.","computed":true,"force_new":true},"uuid":{"type":"TypeString","optional":true,"description":"(Optional if ` + "`" + `port` + "`" + ` or ` + "`" + `name` + "`" + ` is provided) The network UUID to attach to the server. Changing this creates a new server.","computed":true,"force_new":true}}}},"network_mode":{"type":"TypeString","optional":true,"description":"Special string for ` + "`" + `network` + "`" + ` option to create the server. ` + "`" + `network_mode` + "`" + ` can be ` + "`" + `\"auto\"` + "`" + ` or ` + "`" + `\"none\"` + "`" + `. Please see the following [reference](https://docs.openstack.org/api-ref/compute/?expanded=create-server-detail#id11) for more information. Conflicts with ` + "`" + `network` + "`" + `.","force_new":true},"personality":{"type":"TypeSet","optional":true,"description":"Customize the personality of an instance by defining one or more files and their contents. The personality structure is described below.","force_new":true,"elem":{"schema":{"content":{"type":"TypeString","required":true,"description":"The contents of the file. Limited to 255 bytes."},"file":{"type":"TypeString","required":true,"description":"The absolute path of the destination file."}}}},"power_state":{"type":"TypeString","optional":true,"default":"active","description":"Provide the VM state. Only 'active' and 'shutoff' are supported values. *Note*: If the initial power_state is the shutoff the VM will be stopped immediately after build and the provisioners like remote-exec or files are not supported."},"region":{"type":"TypeString","optional":true,"description":"The region in which to create the server instance. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new server.","computed":true,"force_new":true},"scheduler_hints":{"type":"TypeSet","optional":true,"description":"Provide the Nova scheduler with hints on how the instance should be launched. The available hints are described below.","elem":{"schema":{"group":{"type":"TypeString","optional":true,"description":"A UUID of a Server Group. The instance will be placed into that group.","force_new":true}}}},"security_groups":{"type":"TypeSet","optional":true,"description":"An array of one or more security group names to associate with the server. Changing this results in adding/removing security groups from the existing server. *Note*: When attaching the instance to networks using Ports, place the security groups on the Port and not the instance. *Note*: Names should be used and not ids, as ids trigger unnecessary updates.","computed":true,"elem":{"type":"TypeString"}},"stop_before_destroy":{"type":"TypeBool","optional":true,"default":false,"description":"Whether to try stop instance gracefully before destroying it, thus giving chance for guest OS daemons to stop correctly. If instance doesn't stop within timeout, it will be destroyed anyway."},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the instance. Changing this updates the existing instance tags.","elem":{"type":"TypeString"}},"user_data":{"type":"TypeString","optional":true,"description":"The user data to provide when launching the instance.\tChanging this creates a new server.","force_new":true},"vendor_options":{"type":"TypeSet","optional":true,"description":"Map of additional vendor-specific options. Supported options are described below.","elem":{"schema":{"detach_ports_before_destroy":{"type":"TypeBool","optional":true,"default":false,"description":"Whether to try to detach all attached ports to the vm before destroying it to make sure the port state is correct after the vm destruction. This is helpful when the port is not deleted."},"ignore_resize_confirmation":{"type":"TypeBool","optional":true,"default":false,"description":"Boolean to control whether to ignore manual confirmation of the instance resizing."}}},"max_items":1,"min_items":1}},"timeouts":{"create":30,"delete":30,"update":30},"description":"Manages a compute VM instance resource.\n\n~\u003e **Note:** All arguments including the instance admin password will be stored in the raw state as plain-text. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_compute_interface_attach":{"schema":{"fixed_ip":{"type":"TypeString","optional":true,"description":"An IP address to assosciate with the port.\n_NOTE_: This option cannot be used with port_id. You must specify a network_id. The IP address must lie in a range on the supplied network.","computed":true,"force_new":true},"instance_id":{"type":"TypeString","required":true,"description":"The ID of the Instance to attach the Port or Network to.","force_new":true},"network_id":{"type":"TypeString","optional":true,"description":"The ID of the Network to attach to an Instance. A port will be created automatically.\n_NOTE_: This option and ` + "`" + `port_id` + "`" + ` are mutually exclusive.","computed":true,"force_new":true},"port_id":{"type":"TypeString","optional":true,"description":"The ID of the Port to attach to an Instance.\n_NOTE_: This option and ` + "`" + `network_id` + "`" + ` are mutually exclusive.","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to create the interface attachment. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new attachment.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Attaches a Network Interface (a Port) to an Instance using the VKCS Compute API."},"vkcs_compute_keypair":{"schema":{"fingerprint":{"type":"TypeString","description":"The fingerprint of the public key.","computed":true},"name":{"type":"TypeString","required":true,"description":"A unique name for the keypair. Changing this creates a new keypair.","force_new":true},"private_key":{"type":"TypeString","description":"The generated private key when no public key is specified.","computed":true},"public_key":{"type":"TypeString","optional":true,"description":"A pregenerated OpenSSH-formatted public key. Changing this creates a new keypair. If a public key is not specified, then a public/private key pair will be automatically generated. If a pair is created, then destroying this resource means you will lose access to that keypair forever.","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. Keypairs are associated with accounts, but a Compute client is needed to create one. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new keypair.","computed":true,"force_new":true},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"description":"Manages a keypair resource within VKCS.\n\n~\u003e **Important Security Notice** The private key generated by this resource will be stored *unencrypted* in your Terraform state file. **Use of this resource for production deployments is *not* recommended**. Instead, generate a private key file outside of Terraform and distribute it securely to the system where Terraform will be run."},"vkcs_compute_servergroup":{"schema":{"members":{"type":"TypeList","description":"The instances that are part of this server group.","computed":true,"elem":{"type":"TypeString"}},"name":{"type":"TypeString","required":true,"description":"A unique name for the server group. Changing this creates a new server group.","force_new":true},"policies":{"type":"TypeList","optional":true,"description":"The set of policies for the server group. All policies are mutually exclusive. See the Policies section for more information. Changing this creates a new server group.","force_new":true,"elem":{"type":"TypeString"}},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new server group.","computed":true,"force_new":true},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"description":"Manages a Server Group resource within VKCS."},"vkcs_compute_volume_attach":{"schema":{"instance_id":{"type":"TypeString","required":true,"description":"The ID of the Instance to attach the Volume to.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. A Compute client is needed to create a volume attachment. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new volume attachment.","computed":true,"force_new":true},"volume_id":{"type":"TypeString","required":true,"description":"The ID of the Volume to attach to an Instance.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Attaches a Block Storage Volume to an Instance using the VKCS Compute API."},"vkcs_db_backup":{"schema":{"container_prefix":{"type":"TypeString","optional":true,"description":"Prefix of S3 bucket ([prefix] - [project_id]) to store backup data. Default: databasebackups","force_new":true},"created":{"type":"TypeString","description":"Backup creation timestamp","computed":true},"datastore":{"type":"TypeList","description":"Object that represents datastore of backup","computed":true,"elem":{"schema":{"type":{"type":"TypeString","description":"Version of the datastore. Changing this creates a new instance.","computed":true},"version":{"type":"TypeString","description":"Type of the datastore. Changing this creates a new instance.","computed":true}}}},"dbms_id":{"type":"TypeString","required":true,"description":"ID of the instance or cluster, to create backup of.","force_new":true},"dbms_type":{"type":"TypeString","description":"Type of dbms for the backup, can be \"instance\" or \"cluster\".","computed":true},"description":{"type":"TypeString","optional":true,"description":"The description of the backup","force_new":true},"location_ref":{"type":"TypeString","description":"Location of backup data on backup storage","computed":true},"meta":{"type":"TypeString","description":"Metadata of the backup","computed":true},"name":{"type":"TypeString","required":true,"description":"The name of the backup. Changing this creates a new backup","force_new":true},"size":{"type":"TypeFloat","description":"Backup's volume size","computed":true},"updated":{"type":"TypeString","description":"Timestamp of backup's last update","computed":true},"wal_size":{"type":"TypeFloat","description":"Backup's WAL volume size","computed":true}},"timeouts":{"create":30,"delete":30},"description":"Provides a db backup resource. This can be used to create and delete db backup.","new_since":"v0.1.4"},"vkcs_db_cluster":{"schema":{"availability_zone":{"type":"TypeString","optional":true,"description":"The name of the availability zone of the cluster. Changing this creates a new cluster.","force_new":true},"backup_schedule":{"type":"TypeList","optional":true,"description":"Object that represents configuration of PITR backup. This functionality is available only for postgres datastore.","elem":{"schema":{"interval_hours":{"type":"TypeInt","required":true,"description":"Time interval between backups, specified in hours. Available values: 3, 6, 8, 12, 24."},"keep_count":{"type":"TypeInt","required":true,"description":"Number of backups to be stored."},"name":{"type":"TypeString","required":true,"description":"Name of the schedule."},"start_hours":{"type":"TypeInt","required":true,"description":"Hours part of timestamp of initial backup."},"start_minutes":{"type":"TypeInt","required":true,"description":"Minutes part of timestamp of initial backup."}}},"max_items":1,"new_since":"v0.1.4"},"capabilities":{"type":"TypeList","optional":true,"description":"Object that represents capability applied to cluster. There can be several instances of this object.","elem":{"schema":{"name":{"type":"TypeString","required":true,"description":"The name of the capability to apply."},"settings":{"type":"TypeMap","optional":true,"description":"Map of key-value settings of the capability.","elem":{"type":"TypeString"}}}}},"cloud_monitoring_enabled":{"type":"TypeBool","optional":true,"description":"Enable cloud monitoring for the cluster. Changing this for Redis or MongoDB creates a new instance.","new_since":"v0.2.0"},"cluster_size":{"type":"TypeInt","required":true,"description":"The number of instances in the cluster."},"configuration_id":{"type":"TypeString","optional":true,"description":"The id of the configuration attached to cluster."},"datastore":{"type":"TypeList","required":true,"description":"Object that represents datastore of the cluster. Changing this creates a new cluster.","force_new":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore. Changing this creates a new cluster. Type of the datastore can either be \"galera_mysql\", \"postgresql\" or \"tarantool\".","force_new":true},"version":{"type":"TypeString","required":true,"description":"Version of the datastore. Changing this creates a new cluster.","force_new":true}}},"max_items":1},"disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of the cluster.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for autoresize."}}},"max_items":1},"flavor_id":{"type":"TypeString","required":true,"description":"The ID of flavor for the cluster."},"floating_ip_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether floating ip is created for cluster. Changing this creates a new cluster.","force_new":true},"instances":{"type":"TypeList","description":"Cluster instances info.","computed":true,"elem":{"schema":{"instance_id":{"type":"TypeString","description":"The id of the instance.","computed":true},"ip":{"type":"TypeList","description":"IP address of the instance.","computed":true,"elem":{"type":"TypeString"}},"role":{"type":"TypeString","description":"The role of the instance in cluster.","computed":true}}}},"keypair":{"type":"TypeString","optional":true,"description":"Name of the keypair to be attached to cluster. Changing this creates a new cluster.","force_new":true},"loadbalancer_id":{"type":"TypeString","description":"The id of the loadbalancer attached to the cluster.","computed":true,"new_since":"v0.1.15"},"name":{"type":"TypeString","required":true,"description":"The name of the cluster. Changing this creates a new cluster.","force_new":true},"network":{"type":"TypeList","optional":true,"description":"Object that represents network of the cluster. Changing this creates a new cluster.","force_new":true,"elem":{"schema":{"port":{"type":"TypeString","optional":true,"description":"The port id of the network. Changing this creates a new cluster.","force_new":true,"deprecated":"This argument is deprecated, please do not use it."},"security_groups":{"type":"TypeSet","optional":true,"description":"An array of one or more security group IDs to associate with the cluster instances. Changing this creates a new cluster.","force_new":true,"elem":{"type":"TypeString"},"new_since":"v0.2.0"},"subnet_id":{"type":"TypeString","optional":true,"description":"The id of the subnet. Changing this creates a new cluster.","force_new":true,"new_since":"v0.1.15"},"uuid":{"type":"TypeString","optional":true,"description":"The id of the network. Changing this creates a new cluster.**Note** Although this argument is marked as optional, it is actually required at the moment. Not setting a value for it may cause an error.","force_new":true}}}},"region":{"type":"TypeString","optional":true,"description":"Region to create resource in.","computed":true,"force_new":true},"restore_point":{"type":"TypeList","optional":true,"description":"Object that represents backup to restore cluster from.","force_new":true,"elem":{"schema":{"backup_id":{"type":"TypeString","required":true,"description":"ID of the backup.","force_new":true},"target":{"type":"TypeString","optional":true,"description":"Used only for restoring from PITR backups. Timestamp of needed backup in format \"2021-10-06 01:02:00\". You can specify \"latest\" to use most recent backup.","force_new":true}}},"max_items":1,"new_since":"v0.1.4"},"root_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether root user is enabled for the cluster."},"root_password":{"type":"TypeString","optional":true,"description":"Password for the root user of the cluster.","computed":true},"shrink_options":{"type":"TypeList","optional":true,"description":"Used only for shrinking cluster. List of IDs of instances that should remain after shrink. If no options are supplied, shrink operation will choose first non-leader instance to delete.","elem":{"type":"TypeString"}},"volume_size":{"type":"TypeInt","required":true,"description":"Size of the cluster instance volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the cluster instance volume. Changing this creates a new cluster."},"wal_disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of wal volume of the cluster.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether wal volume autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for wal volume autoresize."}}},"max_items":1},"wal_volume":{"type":"TypeList","optional":true,"description":"Object that represents wal volume of the cluster. Changing this creates a new cluster.","elem":{"schema":{"size":{"type":"TypeInt","required":true,"description":"Size of the instance wal volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the cluster wal volume. Changing this creates a new cluster."}}}}},"timeouts":{"create":30,"delete":30},"description":"Provides a db cluster resource. This can be used to create, modify and delete db cluster for galera_mysql, postgresql, tarantool datastores."},"vkcs_db_cluster_with_shards":{"schema":{"capabilities":{"type":"TypeList","optional":true,"description":"Object that represents capability applied to cluster. There can be several instances of this object.","elem":{"schema":{"name":{"type":"TypeString","required":true,"description":"The name of the capability to apply."},"settings":{"type":"TypeMap","optional":true,"description":"Map of key-value settings of the capability.","elem":{"type":"TypeString"}}}}},"cloud_monitoring_enabled":{"type":"TypeBool","optional":true,"description":"Enable cloud monitoring for the cluster. Changing this for Redis or MongoDB creates a new instance.","new_since":"v0.2.0"},"configuration_id":{"type":"TypeString","optional":true,"description":"The id of the configuration attached to cluster."},"datastore":{"type":"TypeList","required":true,"description":"Object that represents datastore of the cluster. Changing this creates a new cluster.","force_new":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore. Changing this creates a new cluster. Type of the datastore must be \"clickhouse\".","force_new":true},"version":{"type":"TypeString","required":true,"description":"Version of the datastore. Changing this creates a new cluster.","force_new":true}}},"max_items":1},"disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of the cluster.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for autoresize."}}},"max_items":1},"floating_ip_enabled":{"type":"TypeBool","optional":true,"description":"Boolean field that indicates whether floating ip is created for cluster. Changing this creates a new cluster.","force_new":true},"keypair":{"type":"TypeString","optional":true,"description":"Name of the keypair to be attached to cluster. Changing this creates a new cluster.","force_new":true},"name":{"type":"TypeString","required":true,"description":"The name of the cluster. Changing this creates a new cluster.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"Region to create resource in.","computed":true,"force_new":true},"restore_point":{"type":"TypeList","optional":true,"description":"Object that represents backup to restore instance from.","force_new":true,"elem":{"schema":{"backup_id":{"type":"TypeString","required":true,"description":"ID of the backup.","force_new":true}}},"max_items":1,"new_since":"v0.1.4"},"root_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether root user is enabled for the cluster."},"root_password":{"type":"TypeString","optional":true,"description":"Password for the root user of the cluster.","computed":true},"shard":{"type":"TypeList","required":true,"description":"Object that represents cluster shard. There can be several instances of this object.","elem":{"schema":{"availability_zone":{"type":"TypeString","optional":true,"description":"The name of the availability zone of the cluster shard. Changing this creates a new cluster.","force_new":true},"flavor_id":{"type":"TypeString","required":true,"description":"The ID of flavor for the cluster shard."},"instances":{"type":"TypeList","description":"Shard instances info.","computed":true,"elem":{"schema":{"instance_id":{"type":"TypeString","description":"The id of the instance.","computed":true},"ip":{"type":"TypeList","description":"IP address of the instance.","computed":true,"elem":{"type":"TypeString"}}}},"new_since":"v0.1.15"},"network":{"type":"TypeList","optional":true,"force_new":true,"elem":{"schema":{"port":{"type":"TypeString","optional":true,"description":"The port id of the network. Changing this creates a new cluster.","force_new":true,"deprecated":"This argument is deprecated, please do not use it."},"security_groups":{"type":"TypeSet","optional":true,"description":"An array of one or more security group IDs to associate with the shard instances. Changing this creates a new cluster.","force_new":true,"elem":{"type":"TypeString"},"new_since":"v0.2.0"},"subnet_id":{"type":"TypeString","optional":true,"description":"The id of the subnet. Changing this creates a new cluster.","force_new":true,"new_since":"v0.1.15"},"uuid":{"type":"TypeString","optional":true,"description":"The id of the network. Changing this creates a new cluster.**Note** Although this argument is marked as optional, it is actually required at the moment. Not setting a value for it may cause an error.","force_new":true}},"description":"Object that represents network of the cluster shard. Changing this creates a new cluster."}},"shard_id":{"type":"TypeString","required":true,"description":"The ID of the shard. Changing this creates a new cluster.","force_new":true},"shrink_options":{"type":"TypeList","optional":true,"description":"Used only for shrinking cluster. List of IDs of instances that should remain after shrink. If no options are supplied, shrink operation will choose first non-leader instance to delete.","elem":{"type":"TypeString"}},"size":{"type":"TypeInt","required":true,"description":"The number of instances in the cluster shard."},"volume_size":{"type":"TypeInt","required":true,"description":"Size of the cluster shard instance volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the cluster shard instance volume."},"wal_volume":{"type":"TypeList","optional":true,"description":"Object that represents wal volume of the cluster.","elem":{"schema":{"size":{"type":"TypeInt","required":true,"description":"Size of the instance wal volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the cluster wal volume."}}}}}}},"wal_disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of wal volume of the cluster.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether wal volume autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for wal volume autoresize."}}},"max_items":1}},"timeouts":{"create":30,"delete":30},"description":"Provides a db cluster with shards resource. This can be used to create, modify and delete db cluster with shards for clickhouse datastore."},"vkcs_db_config_group":{"schema":{"created":{"type":"TypeString","description":"Timestamp of config group's creation","computed":true},"datastore":{"type":"TypeList","required":true,"description":"Object that represents datastore of the config group. Changing this creates a new config group.","force_new":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore.","force_new":true},"version":{"type":"TypeString","required":true,"description":"Version of the datastore.","force_new":true}}},"max_items":1},"description":{"type":"TypeString","optional":true,"description":"The description of the config group."},"name":{"type":"TypeString","required":true,"description":"The name of the config group."},"updated":{"type":"TypeString","description":"Timestamp of config group's last update","computed":true},"values":{"type":"TypeMap","required":true,"description":"Map of configuration parameters in format \"key\": \"value\".","elem":{"type":"TypeString"}}},"description":"Provides a db config group resource. This can be used to create, update and delete db config group.","new_since":"v0.1.7"},"vkcs_db_database":{"schema":{"charset":{"type":"TypeString","optional":true,"description":"Type of charset used for the database. Changing this creates a new database.","force_new":true},"collate":{"type":"TypeString","optional":true,"description":"Collate option of the database. Changing this creates a new database.","force_new":true},"dbms_id":{"type":"TypeString","required":true,"description":"ID of the instance or cluster that database is created for.","force_new":true},"dbms_type":{"type":"TypeString","description":"Type of dbms for the database, can be \"instance\" or \"cluster\".","computed":true},"name":{"type":"TypeString","required":true,"description":"The name of the database. Changing this creates a new database.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Provides a db database resource. This can be used to create, modify and delete db databases."},"vkcs_db_instance":{"schema":{"availability_zone":{"type":"TypeString","optional":true,"description":"The name of the availability zone of the instance. Changing this creates a new instance.","force_new":true},"backup_schedule":{"type":"TypeList","optional":true,"description":"Object that represents configuration of PITR backup. This functionality is available only for postgres datastore.","elem":{"schema":{"interval_hours":{"type":"TypeInt","required":true,"description":"Time interval between backups, specified in hours. Available values: 3, 6, 8, 12, 24."},"keep_count":{"type":"TypeInt","required":true,"description":"Number of backups to be stored."},"name":{"type":"TypeString","required":true,"description":"Name of the schedule."},"start_hours":{"type":"TypeInt","required":true,"description":"Hours part of timestamp of initial backup."},"start_minutes":{"type":"TypeInt","required":true,"description":"Minutes part of timestamp of initial backup."}}},"max_items":1,"new_since":"v0.1.4"},"capabilities":{"type":"TypeList","optional":true,"description":"Object that represents capability applied to instance. There can be several instances of this object (see example).","elem":{"schema":{"name":{"type":"TypeString","required":true,"description":"The name of the capability to apply."},"settings":{"type":"TypeMap","optional":true,"description":"Map of key-value settings of the capability.","elem":{"type":"TypeString"}}}}},"cloud_monitoring_enabled":{"type":"TypeBool","optional":true,"description":"Enable cloud monitoring for the instance. Changing this for Redis or MongoDB creates a new instance.","new_since":"v0.2.0"},"configuration_id":{"type":"TypeString","optional":true,"description":"The id of the configuration attached to instance."},"datastore":{"type":"TypeList","required":true,"description":"Object that represents datastore of the instance. Changing this creates a new instance.","force_new":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore. Changing this creates a new instance.","force_new":true},"version":{"type":"TypeString","required":true,"description":"Version of the datastore. Changing this creates a new instance.","force_new":true}}},"max_items":1},"disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of the instance.","computed":true,"elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for autoresize."}}},"max_items":1},"flavor_id":{"type":"TypeString","required":true,"description":"The ID of flavor for the instance."},"floating_ip_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether floating ip is created for instance. Changing this creates a new instance.","force_new":true},"ip":{"type":"TypeList","description":"IP address of the instance.","computed":true,"elem":{"type":"TypeString"}},"keypair":{"type":"TypeString","optional":true,"description":"Name of the keypair to be attached to instance. Changing this creates a new instance.","force_new":true},"name":{"type":"TypeString","required":true,"description":"The name of the instance. Changing this creates a new instance","force_new":true},"network":{"type":"TypeList","optional":true,"description":"Object that represents network of the instance. Changing this creates a new instance.","force_new":true,"elem":{"schema":{"fixed_ip_v4":{"type":"TypeString","optional":true,"description":"The IPv4 address. Changing this creates a new instance. **Note** This argument conflicts with \"replica_of\". Setting both at the same time causes \"fixed_ip_v4\" to be ignored.","force_new":true},"port":{"type":"TypeString","optional":true,"description":"The port id of the network. Changing this creates a new instance.","force_new":true,"deprecated":"This argument is deprecated, please do not use it."},"security_groups":{"type":"TypeSet","optional":true,"description":"An array of one or more security group IDs to associate with the instance. Changing this creates a new instance.","force_new":true,"elem":{"type":"TypeString"},"new_since":"v0.2.0"},"subnet_id":{"type":"TypeString","optional":true,"description":"The id of the subnet. Changing this creates a new instance.","force_new":true,"new_since":"v0.1.15"},"uuid":{"type":"TypeString","optional":true,"description":"The id of the network. Changing this creates a new instance.**Note** Although this argument is marked as optional, it is actually required at the moment. Not setting a value for it may cause an error.","force_new":true}}}},"region":{"type":"TypeString","optional":true,"description":"Region to create resource in.","computed":true,"force_new":true},"replica_of":{"type":"TypeString","optional":true,"description":"ID of the instance, that current instance is replica of."},"restore_point":{"type":"TypeList","optional":true,"description":"Object that represents backup to restore instance from.","force_new":true,"elem":{"schema":{"backup_id":{"type":"TypeString","required":true,"description":"ID of the backup.","force_new":true},"target":{"type":"TypeString","optional":true,"description":"Used only for restoring from postgresql PITR backups. Timestamp of needed backup in format \"2021-10-06 01:02:00\". You can specify \"latest\" to use most recent backup.","force_new":true}}},"max_items":1,"new_since":"v0.1.4"},"root_enabled":{"type":"TypeBool","optional":true,"description":"Indicates whether root user is enabled for the instance."},"root_password":{"type":"TypeString","optional":true,"description":"Password for the root user of the instance. If this field is empty and root user is enabled, then after creation of the instance this field will contain auto-generated root user password.","computed":true},"size":{"type":"TypeInt","required":true,"description":"Size of the instance volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the instance volume. Changing this creates a new instance.","force_new":true},"wal_disk_autoexpand":{"type":"TypeList","optional":true,"description":"Object that represents autoresize properties of the instance wal volume.","elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether wal volume autoresize is enabled."},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for wal volume autoresize."}}},"max_items":1},"wal_volume":{"type":"TypeList","optional":true,"description":"Object that represents wal volume of the instance. Changing this creates a new instance.","force_new":true,"elem":{"schema":{"autoexpand":{"type":"TypeBool","optional":true,"description":"Indicates whether wal volume autoresize is enabled.","deprecated":"Please, use wal_disk_autoexpand block instead"},"max_disk_size":{"type":"TypeInt","optional":true,"description":"Maximum disk size for wal volume autoresize.","deprecated":"Please, use wal_disk_autoexpand block instead"},"size":{"type":"TypeInt","required":true,"description":"Size of the instance wal volume."},"volume_type":{"type":"TypeString","required":true,"description":"The type of the instance wal volume.","force_new":true}}},"max_items":1}},"timeouts":{"create":30,"delete":30},"description":"Provides a db instance resource. This can be used to create, modify and delete db instance."},"vkcs_db_user":{"schema":{"databases":{"type":"TypeList","optional":true,"description":"List of names of the databases, that user is created for.","computed":true,"elem":{"type":"TypeString"}},"dbms_id":{"type":"TypeString","required":true,"description":"ID of the instance or cluster that user is created for.","force_new":true},"dbms_type":{"type":"TypeString","description":"Type of dbms for the user, can be \"instance\" or \"cluster\".","computed":true},"host":{"type":"TypeString","optional":true,"description":"IP address of the host that user will be accessible from."},"name":{"type":"TypeString","required":true,"description":"The name of the user. Changing this creates a new user."},"password":{"type":"TypeString","required":true,"description":"The password of the user."}},"timeouts":{"create":10,"delete":10},"description":"Provides a db user resource. This can be used to create, modify and delete db user."},"vkcs_images_image":{"schema":{"checksum":{"type":"TypeString","description":"The checksum of the data associated with the image.","computed":true},"container_format":{"type":"TypeString","required":true,"description":"The container format. Must be one of \"bare\".","force_new":true},"created_at":{"type":"TypeString","description":"The date the image was created.","computed":true},"disk_format":{"type":"TypeString","required":true,"description":"The disk format. Must be one of \"raw\", \"iso\".","force_new":true},"file":{"type":"TypeString","description":"The trailing path after the image endpoint that represent the location of the image or the path to retrieve it.","computed":true},"image_cache_path":{"type":"TypeString","optional":true,"default":"/home/panic/.terraform/image_cache","description":"This is the directory where the images will be downloaded. Images will be stored with a filename corresponding to the url's md5 hash. Defaults to \"$HOME/.terraform/image_cache\""},"image_source_password":{"type":"TypeString","optional":true,"description":"The password of basic auth to download ` + "`" + `image_source_url` + "`" + `."},"image_source_url":{"type":"TypeString","optional":true,"description":"This is the url of the raw image. The image will be downloaded in the ` + "`" + `image_cache_path` + "`" + ` before being uploaded to VKCS. Conflicts with ` + "`" + `local_file_path` + "`" + `.","force_new":true},"image_source_username":{"type":"TypeString","optional":true,"description":"The username of basic auth to download ` + "`" + `image_source_url` + "`" + `."},"local_file_path":{"type":"TypeString","optional":true,"description":"This is the filepath of the raw image file that will be uploaded to VKCS. Conflicts with ` + "`" + `image_source_url` + "`" + `","force_new":true},"metadata":{"type":"TypeMap","description":"The metadata associated with the image. Image metadata allow for meaningfully define the image properties and tags. See https://docs.openstack.org/glance/latest/user/metadefs-concepts.html.","computed":true},"min_disk_gb":{"type":"TypeInt","optional":true,"default":0,"description":"Amount of disk space (in GB) required to boot image. Defaults to 0."},"min_ram_mb":{"type":"TypeInt","optional":true,"default":0,"description":"Amount of ram (in MB) required to boot image. Defauts to 0."},"name":{"type":"TypeString","required":true,"description":"The name of the image."},"owner":{"type":"TypeString","description":"The id of the vkcs user who owns the image.","computed":true},"properties":{"type":"TypeMap","optional":true,"description":"A map of key/value pairs to set freeform information about an image. See the \"Notes\" section for further information about properties.","computed":true},"protected":{"type":"TypeBool","optional":true,"default":false,"description":"If true, image will not be deletable. Defaults to false."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Image client. An Image client is needed to create an Image that can be used with a compute instance. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new Image.","computed":true,"force_new":true},"schema":{"type":"TypeString","description":"The path to the JSON-schema that represent the image or image","computed":true},"size_bytes":{"type":"TypeInt","description":"The size in bytes of the data associated with the image.","computed":true},"status":{"type":"TypeString","description":"The status of the image. It can be \"queued\", \"active\" or \"saving\".","computed":true},"tags":{"type":"TypeSet","optional":true,"description":"The tags of the image. It must be a list of strings. At this time, it is not possible to delete all tags of an image.","elem":{"type":"TypeString"}},"updated_at":{"type":"TypeString","description":"The date the image was last updated.","computed":true},"verify_checksum":{"type":"TypeBool","optional":true,"description":"If false, the checksum will not be verified once the image is finished uploading."},"visibility":{"type":"TypeString","optional":true,"default":"private","description":"The visibility of the image. Must be one of \"private\", \"community\", or \"shared\". The ability to set the visibility depends upon the configuration of the VKCS cloud."}},"timeouts":{"create":30},"description":"Manages an Image resource within VKCS.\n\n~\u003e **Note:** All arguments including the source image URL password will be stored in the raw state as plain-text. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_keymanager_container":{"schema":{"acl":{"type":"TypeList","optional":true,"description":"Allows to control an access to a container. Currently only the ` + "`" + `read` + "`" + ` operation is supported. If not specified, the container is accessible project wide. The ` + "`" + `read` + "`" + ` structure is described below.","computed":true,"elem":{"schema":{"read":{"type":"TypeList","optional":true,"description":"Block that describes read operation.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"project_access":{"type":"TypeBool","optional":true,"default":true,"description":"Whether the container is accessible project wide. Defaults to ` + "`" + `true` + "`" + `."},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true},"users":{"type":"TypeSet","optional":true,"description":"The list of user IDs, which are allowed to access the container, when ` + "`" + `project_access` + "`" + ` is set to ` + "`" + `false` + "`" + `.","elem":{"type":"TypeString"}}}},"max_items":1}}},"max_items":1},"consumers":{"type":"TypeList","description":"The list of the container consumers. The structure is described below.","computed":true,"elem":{"schema":{"name":{"type":"TypeString","optional":true,"description":"The name of the consumer."},"url":{"type":"TypeString","optional":true,"description":"The consumer URL."}}}},"container_ref":{"type":"TypeString","description":"The container reference / where to find the container.","computed":true},"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"creator_id":{"type":"TypeString","description":"The creator of the container.","computed":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the Container. Does not have to be unique.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the KeyManager client. A KeyManager client is needed to create a container. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new container.","computed":true,"force_new":true},"secret_refs":{"type":"TypeSet","optional":true,"description":"A set of dictionaries containing references to secrets. The structure is described below.","force_new":true,"elem":{"schema":{"name":{"type":"TypeString","optional":true,"description":"The name of the secret reference. The reference names must correspond the container type, more details are available [here](https://docs.openstack.org/barbican/stein/api/reference/containers.html)."},"secret_ref":{"type":"TypeString","required":true,"description":"The secret reference / where to find the secret, URL."}}}},"status":{"type":"TypeString","description":"The status of the container.","computed":true},"type":{"type":"TypeString","required":true,"description":"Used to indicate the type of container. Must be one of ` + "`" + `generic` + "`" + `, ` + "`" + `rsa` + "`" + ` or ` + "`" + `certificate` + "`" + `.","force_new":true},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true}},"timeouts":{"create":30,"delete":30,"update":30},"description":"Manages a key container resource within VKCS."},"vkcs_keymanager_secret":{"schema":{"acl":{"type":"TypeList","optional":true,"description":"Allows to control an access to a secret. Currently only the ` + "`" + `read` + "`" + ` operation is supported. If not specified, the secret is accessible project wide.","computed":true,"elem":{"schema":{"read":{"type":"TypeList","optional":true,"description":"Block that describes read operation.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"project_access":{"type":"TypeBool","optional":true,"default":true,"description":"Whether the container is accessible project wide. Defaults to ` + "`" + `true` + "`" + `."},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true},"users":{"type":"TypeSet","optional":true,"description":"The list of user IDs, which are allowed to access the container, when ` + "`" + `project_access` + "`" + ` is set to ` + "`" + `false` + "`" + `.","elem":{"type":"TypeString"}}}},"max_items":1}}},"max_items":1},"algorithm":{"type":"TypeString","optional":true,"description":"Metadata provided by a user or system for informational purposes.","computed":true,"force_new":true},"all_metadata":{"type":"TypeMap","description":"The map of metadata, assigned on the secret, which has been explicitly and implicitly added.","computed":true},"bit_length":{"type":"TypeInt","optional":true,"description":"Metadata provided by a user or system for informational purposes.","computed":true,"force_new":true},"content_types":{"type":"TypeMap","description":"The map of the content types, assigned on the secret.","computed":true},"created_at":{"type":"TypeString","description":"The date the secret ACL was created.","computed":true},"creator_id":{"type":"TypeString","description":"The creator of the secret.","computed":true},"expiration":{"type":"TypeString","optional":true,"description":"The expiration time of the secret in the RFC3339 timestamp format (e.g. ` + "`" + `2019-03-09T12:58:49Z` + "`" + `). If omitted, a secret will never expire. Changing this creates a new secret.","force_new":true},"metadata":{"type":"TypeMap","optional":true,"description":"Additional Metadata for the secret."},"mode":{"type":"TypeString","optional":true,"description":"Metadata provided by a user or system for informational purposes.","computed":true,"force_new":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the Secret. Does not have to be unique.","force_new":true},"payload":{"type":"TypeString","optional":true,"description":"The secret's data to be stored. **payload\\_content\\_type** must also be supplied if **payload** is included.","computed":true,"force_new":true},"payload_content_encoding":{"type":"TypeString","optional":true,"description":"(required if **payload** is encoded) The encoding used for the payload to be able to include it in the JSON request. Must be either ` + "`" + `base64` + "`" + ` or ` + "`" + `binary` + "`" + `.","force_new":true},"payload_content_type":{"type":"TypeString","optional":true,"description":"(required if **payload** is included) The media type for the content of the payload. Must be one of ` + "`" + `text/plain` + "`" + `, ` + "`" + `text/plain;charset=utf-8` + "`" + `, ` + "`" + `text/plain; charset=utf-8` + "`" + `, ` + "`" + `application/octet-stream` + "`" + `, ` + "`" + `application/pkcs8` + "`" + `.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the KeyManager client. A KeyManager client is needed to create a secret. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new V1 secret.","computed":true,"force_new":true},"secret_ref":{"type":"TypeString","description":"The secret reference / where to find the secret.","computed":true},"secret_type":{"type":"TypeString","optional":true,"description":"Used to indicate the type of secret being stored. For more information see [Secret types](https://docs.openstack.org/barbican/latest/api/reference/secret_types.html).","computed":true,"force_new":true},"status":{"type":"TypeString","description":"The status of the secret.","computed":true},"updated_at":{"type":"TypeString","description":"The date the secret ACL was last updated.","computed":true}},"timeouts":{"create":30,"delete":30,"update":30},"description":"Manages a key secret resource within VKCS.\n\n~\u003e **Important Security Notice** The payload of this resource will be stored *unencrypted* in your Terraform state file. **Use of this resource for production deployments is *not* recommended**. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_kubernetes_cluster":{"schema":{"api_address":{"type":"TypeString","description":"COE API address.","computed":true,"force_new":true},"api_lb_fip":{"type":"TypeString","optional":true,"description":"API LoadBalancer fip.","computed":true,"force_new":true},"api_lb_vip":{"type":"TypeString","optional":true,"description":"API LoadBalancer vip.","computed":true,"force_new":true},"availability_zone":{"type":"TypeString","required":true,"description":"Availability zone of the cluster.","force_new":true},"cluster_template_id":{"type":"TypeString","required":true,"description":"The UUID of the Kubernetes cluster template. It can be obtained using the cluster_template data source."},"created_at":{"type":"TypeString","description":"The time at which cluster was created.","computed":true},"dns_domain":{"type":"TypeString","optional":true,"description":"Custom DNS cluster domain. Changing this creates a new cluster.","computed":true,"force_new":true},"floating_ip_enabled":{"type":"TypeBool","required":true,"description":"Floating ip is enabled.","force_new":true},"ingress_floating_ip":{"type":"TypeString","optional":true,"description":"Floating IP created for ingress service.","computed":true},"insecure_registries":{"type":"TypeList","optional":true,"description":"Addresses of registries from which you can download images without checking certificates. Changing this creates a new cluster.","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"keypair":{"type":"TypeString","optional":true,"description":"The name of the Compute service SSH keypair. Changing this creates a new cluster.","force_new":true},"labels":{"type":"TypeMap","optional":true,"description":"The list of optional key value pairs representing additional properties of the cluster. Changing this creates a new cluster.\n\n * ` + "`" + `calico_ipv4pool` + "`" + ` to set subnet where pods will be created. Default 10.100.0.0/16.\n * ` + "`" + `clean_volumes` + "`" + ` to remove pvc volumes when deleting a cluster. Default False.\n * ` + "`" + `cloud_monitoring` + "`" + ` to enable cloud monitoring feature.\n * ` + "`" + `docker_registry_enabled=true` + "`" + ` to preinstall Docker Registry.\n * ` + "`" + `etcd_volume_size` + "`" + ` to set etcd volume size. Default 10Gb.\n * ` + "`" + `ingress_controller=\"nginx\"` + "`" + ` to preinstall NGINX Ingress Controller.\n * ` + "`" + `kube_log_level` + "`" + ` to set log level for kubelet in range 0 to 8.\n * ` + "`" + `master_volume_size` + "`" + ` to set master vm volume size. Default 50Gb.\n * ` + "`" + `cluster_node_volume_type` + "`" + ` to set master vm volume type. Default ceph-hdd.\n * ` + "`" + `prometheus_monitoring=true` + "`" + ` to preinstall monitoring system based on Prometheus and Grafana.\n","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"loadbalancer_subnet_id":{"type":"TypeString","optional":true,"description":"The UUID of the load balancer's subnet. Changing this creates new cluster.","computed":true,"force_new":true},"master_addresses":{"type":"TypeList","description":"IP addresses of the master node of the cluster.","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"master_count":{"type":"TypeInt","optional":true,"description":"The number of master nodes for the cluster. Changing this creates a new cluster.","computed":true,"force_new":true},"master_flavor":{"type":"TypeString","optional":true,"description":"The UUID of a flavor for the master nodes. If master_flavor is not present, value from cluster_template will be used.","computed":true},"name":{"type":"TypeString","required":true,"description":"The name of the cluster. Changing this creates a new cluster. Should match the pattern ` + "`" + `^[a-zA-Z][a-zA-Z0-9_.-]*$` + "`" + `.","force_new":true},"network_id":{"type":"TypeString","required":true,"description":"UUID of the cluster's network.","force_new":true},"pods_network_cidr":{"type":"TypeString","optional":true,"description":"Network cidr of k8s virtual network","computed":true,"force_new":true},"project_id":{"type":"TypeString","description":"The project of the cluster.","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"Region to use for the cluster. Default is a region configured for provider.","computed":true,"force_new":true},"registry_auth_password":{"type":"TypeString","optional":true,"description":"Docker registry access password.","computed":true,"force_new":true},"stack_id":{"type":"TypeString","description":"UUID of the Orchestration service stack.","computed":true,"force_new":true},"status":{"type":"TypeString","optional":true,"description":"Current state of a cluster. Changing this to ` + "`" + `RUNNING` + "`" + ` or ` + "`" + `SHUTOFF` + "`" + ` will turn cluster on/off.","computed":true},"subnet_id":{"type":"TypeString","required":true,"description":"UUID of the cluster's subnet.","force_new":true},"updated_at":{"type":"TypeString","description":"The time at which cluster was created.","computed":true},"user_id":{"type":"TypeString","description":"The user of the cluster.","computed":true,"force_new":true}},"timeouts":{"create":60,"delete":30,"update":60},"description":"Provides a kubernetes cluster resource. This can be used to create, modify and delete kubernetes clusters."},"vkcs_kubernetes_node_group":{"schema":{"autoscaling_enabled":{"type":"TypeBool","optional":true,"default":false,"description":"Determines whether the autoscaling is enabled."},"availability_zones":{"type":"TypeList","optional":true,"description":"The list of availability zones of the node group. Zones ` + "`" + `MS1` + "`" + ` and ` + "`" + `GZ1` + "`" + ` are available. By default, node group is being created at cluster's zone.\n**Important:** Receiving default AZ add it manually to your main.tf config to sync it with state to avoid node groups force recreation in the future.","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"cluster_id":{"type":"TypeString","required":true,"description":"The UUID of the existing cluster.","force_new":true},"created_at":{"type":"TypeString","description":"The time at which node group was created.","computed":true},"flavor_id":{"type":"TypeString","optional":true,"description":"The flavor UUID of this node group.","computed":true,"force_new":true},"labels":{"type":"TypeList","optional":true,"description":"The list of objects representing representing additional properties of the node group. Each object should have attribute \"key\". Object may also have optional attribute \"value\".","elem":{"schema":{"key":{"type":"TypeString","required":true},"value":{"type":"TypeString","optional":true}}}},"max_node_unavailable":{"type":"TypeInt","optional":true,"description":"The maximum number of nodes that can fail during an upgrade. The default value is 25 percent.","computed":true},"max_nodes":{"type":"TypeInt","optional":true,"description":"The maximum allowed nodes for this node group.","computed":true},"min_nodes":{"type":"TypeInt","optional":true,"description":"The minimum allowed nodes for this node group. Default to 0 if not set.","computed":true},"name":{"type":"TypeString","required":true,"description":"The name of node group to create. Changing this will force to create a new node group.","force_new":true},"node_count":{"type":"TypeInt","required":true,"description":"The node count for this node group. Should be greater than 0. If ` + "`" + `autoscaling_enabled` + "`" + ` parameter is set, this attribute will be ignored during update."},"state":{"type":"TypeString","description":"Determines current state of node group (RUNNING, SHUTOFF, ERROR).","computed":true},"taints":{"type":"TypeList","optional":true,"description":"The list of objects representing node group taints. Each object should have following attributes: key, value, effect.","elem":{"schema":{"effect":{"type":"TypeString","required":true},"key":{"type":"TypeString","required":true},"value":{"type":"TypeString","required":true}}}},"updated_at":{"type":"TypeString","description":"The time at which node group was created.","computed":true},"uuid":{"type":"TypeString","description":"The UUID of the cluster's node group.","computed":true,"force_new":true},"volume_size":{"type":"TypeInt","optional":true,"description":"The size in GB for volume to load nodes from. Changing this will force to create a new node group.","computed":true,"force_new":true},"volume_type":{"type":"TypeString","optional":true,"description":"The volume type to load nodes from. Changing this will force to create a new node group.","computed":true,"force_new":true}},"timeouts":{"create":60,"delete":30,"update":60},"description":"Provides a cluster node group resource. This can be used to create, modify and delete cluster's node group."},"vkcs_lb_l7policy":{"schema":{"action":{"type":"TypeString","required":true,"description":"The L7 Policy action - can either be REDIRECT\\_TO\\_POOL, REDIRECT\\_TO\\_URL or REJECT."},"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the L7 Policy. A valid value is true (UP) or false (DOWN)."},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the L7 Policy."},"listener_id":{"type":"TypeString","required":true,"description":"The Listener on which the L7 Policy will be associated with. Changing this creates a new L7 Policy.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the L7 Policy. Does not have to be unique."},"position":{"type":"TypeInt","optional":true,"description":"The position of this policy on the listener. Positions start at 1.","computed":true},"redirect_pool_id":{"type":"TypeString","optional":true,"description":"Requests matching this policy will be redirected to the pool with this ID. Only valid if action is REDIRECT\\_TO\\_POOL."},"redirect_url":{"type":"TypeString","optional":true,"description":"Requests matching this policy will be redirected to this URL. Only valid if action is REDIRECT\\_TO\\_URL."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new L7 Policy.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a Load Balancer L7 Policy resource within VKCS."},"vkcs_lb_l7rule":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the L7 Rule. A valid value is true (UP) or false (DOWN)."},"compare_type":{"type":"TypeString","required":true,"description":"The comparison type for the L7 rule - can either be CONTAINS, STARTS\\_WITH, ENDS_WITH, EQUAL_TO or REGEX"},"invert":{"type":"TypeBool","optional":true,"default":false,"description":"When true the logic of the rule is inverted. For example, with invert true, equal to would become not equal to. Default is false."},"key":{"type":"TypeString","optional":true,"description":"The key to use for the comparison. For example, the name of the cookie to evaluate. Valid when ` + "`" + `type` + "`" + ` is set to COOKIE or HEADER."},"l7policy_id":{"type":"TypeString","required":true,"description":"The ID of the L7 Policy to query. Changing this creates a new L7 Rule.","force_new":true},"listener_id":{"type":"TypeString","description":"The ID of the Listener owning this resource.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new L7 Rule.","computed":true,"force_new":true},"type":{"type":"TypeString","required":true,"description":"The L7 Rule type - can either be COOKIE, FILE\\_TYPE, HEADER, HOST\\_NAME or PATH."},"value":{"type":"TypeString","required":true,"description":"The value to use for the comparison. For example, the file type to compare."}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a L7 Rule resource within VKCS."},"vkcs_lb_listener":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the Listener. A valid value is true (UP) or false (DOWN)."},"allowed_cidrs":{"type":"TypeList","optional":true,"description":"A list of CIDR blocks that are permitted to connect to this listener, denying all other source addresses. If not present, defaults to allow all.","elem":{"type":"TypeString"}},"connection_limit":{"type":"TypeInt","optional":true,"description":"The maximum number of connections allowed for the Listener.","computed":true},"default_pool_id":{"type":"TypeString","optional":true,"description":"The ID of the default pool with which the Listener is associated.","computed":true},"default_tls_container_ref":{"type":"TypeString","optional":true,"description":"A reference to a Keymanager Secrets container which stores TLS information. This is required if the protocol is ` + "`" + `TERMINATED_HTTPS` + "`" + `."},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the Listener."},"insert_headers":{"type":"TypeMap","optional":true,"description":"The list of key value pairs representing headers to insert into the request before it is sent to the backend members. Changing this updates the headers of the existing listener."},"loadbalancer_id":{"type":"TypeString","required":true,"description":"The load balancer on which to provision this Listener. Changing this creates a new Listener.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the Listener. Does not have to be unique.","computed":true},"protocol":{"type":"TypeString","required":true,"description":"The protocol - can either be TCP, HTTP, HTTPS, TERMINATED_HTTPS, UDP. Changing this creates a new Listener.","force_new":true},"protocol_port":{"type":"TypeInt","required":true,"description":"The port on which to listen for client traffic. Changing this creates a new Listener.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new Listener.","computed":true,"force_new":true},"sni_container_refs":{"type":"TypeList","optional":true,"description":"A list of references to Keymanager Secrets containers which store SNI information.","elem":{"type":"TypeString"}},"timeout_client_data":{"type":"TypeInt","optional":true,"description":"The client inactivity timeout in milliseconds.","computed":true},"timeout_member_connect":{"type":"TypeInt","optional":true,"description":"The member connection timeout in milliseconds.","computed":true},"timeout_member_data":{"type":"TypeInt","optional":true,"description":"The member inactivity timeout in milliseconds.","computed":true},"timeout_tcp_inspect":{"type":"TypeInt","optional":true,"description":"The time in milliseconds, to wait for additional TCP packets for content inspection.","computed":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a listener resource within VKCS."},"vkcs_lb_loadbalancer":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the Loadbalancer. A valid value is true (UP) or false (DOWN)."},"availability_zone":{"type":"TypeString","optional":true,"description":"The availability zone of the Loadbalancer. Changing this creates a new loadbalancer.","force_new":true},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the Loadbalancer."},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the Loadbalancer. Does not have to be unique."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new LB loadbalancer.","computed":true,"force_new":true},"security_group_ids":{"type":"TypeSet","optional":true,"description":"A list of security group IDs to apply to the loadbalancer. The security groups must be specified by ID and not name (as opposed to how they are configured with the Compute Instance).","computed":true,"elem":{"type":"TypeString"},"deprecated":"This argument is deprecated, please do not use it."},"tags":{"type":"TypeSet","optional":true,"description":"A list of simple strings assigned to the loadbalancer.","elem":{"type":"TypeString"}},"vip_address":{"type":"TypeString","optional":true,"description":"The ip address of the load balancer. Changing this creates a new loadbalancer.","computed":true,"force_new":true},"vip_network_id":{"type":"TypeString","optional":true,"description":"The network on which to allocate the Loadbalancer's address. A tenant can only create Loadbalancers on networks authorized by policy (e.g. networks that belong to them or networks that are shared). Changing this creates a new loadbalancer.","computed":true,"force_new":true},"vip_port_id":{"type":"TypeString","optional":true,"description":"The port UUID that the loadbalancer will use. Changing this creates a new loadbalancer.","computed":true,"force_new":true},"vip_subnet_id":{"type":"TypeString","optional":true,"description":"The subnet on which to allocate the Loadbalancer's address. A tenant can only create Loadbalancers on networks authorized by policy (e.g. networks that belong to them or networks that are shared). Changing this creates a new loadbalancer.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":5,"update":10},"description":"Manages a loadbalancer resource within VKCS."},"vkcs_lb_member":{"schema":{"address":{"type":"TypeString","required":true,"description":"The IP address of the member to receive traffic from the load balancer. Changing this creates a new member.","force_new":true},"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the member. A valid value is true (UP) or false (DOWN). Defaults to true."},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the member."},"pool_id":{"type":"TypeString","required":true,"description":"The id of the pool that this member will be assigned to. Changing this creates a new member.","force_new":true},"protocol_port":{"type":"TypeInt","required":true,"description":"The port on which to listen for client traffic. Changing this creates a new member.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new member.","computed":true,"force_new":true},"subnet_id":{"type":"TypeString","optional":true,"description":"The subnet in which to access the member. Changing this creates a new member.","force_new":true},"weight":{"type":"TypeInt","optional":true,"description":"A positive integer value that indicates the relative portion of traffic that this member should receive from the pool. For example, a member with a weight of 10 receives five times as much traffic as a member with a weight of 2. Defaults to 1.","computed":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a member resource within VKCS."},"vkcs_lb_members":{"schema":{"member":{"type":"TypeSet","optional":true,"description":"A set of dictionaries containing member parameters. The structure is described below.","elem":{"schema":{"address":{"type":"TypeString","required":true,"description":"The IP address of the members to receive traffic from the load balancer."},"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the member. A valid value is true (UP) or false (DOWN). Defaults to true."},"backup":{"type":"TypeBool","optional":true,"description":"A bool that indicates whether the member is backup."},"id":{"type":"TypeString","description":"The unique ID for the member.","computed":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the member."},"protocol_port":{"type":"TypeInt","required":true,"description":"The port on which to listen for client traffic."},"subnet_id":{"type":"TypeString","optional":true,"description":"The subnet in which to access the member."},"weight":{"type":"TypeInt","optional":true,"default":1,"description":"A positive integer value that indicates the relative portion of traffic that this members should receive from the pool. For example, a member with a weight of 10 receives five times as much traffic as a member with a weight of 2. Defaults to 1."}}}},"pool_id":{"type":"TypeString","required":true,"description":"The id of the pool that members will be assigned to. Changing this creates a new members resource.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new members resource.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10,"update":10}},"vkcs_lb_monitor":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the monitor. A valid value is true (UP) or false (DOWN)."},"delay":{"type":"TypeInt","required":true,"description":"The time, in seconds, between sending probes to members."},"expected_codes":{"type":"TypeString","optional":true,"description":"Required for HTTP(S) types. Expected HTTP codes for a passing HTTP(S) monitor. You can either specify a single status like \"200\", or a range like \"200-202\".","computed":true},"http_method":{"type":"TypeString","optional":true,"description":"Required for HTTP(S) types. The HTTP method used for requests by the monitor. If this attribute is not specified, it defaults to \"GET\".","computed":true},"max_retries":{"type":"TypeInt","required":true,"description":"Number of permissible ping failures before changing the member's status to INACTIVE. Must be a number between 1 and 10."},"max_retries_down":{"type":"TypeInt","optional":true,"description":"Number of permissible ping failures befor changing the member's status to ERROR. Must be a number between 1 and 10. Changing this updates the max_retries_down of the existing monitor.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The Name of the Monitor."},"pool_id":{"type":"TypeString","required":true,"description":"The id of the pool that this monitor will be assigned to.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new monitor.","computed":true,"force_new":true},"timeout":{"type":"TypeInt","required":true,"description":"Maximum number of seconds for a monitor to wait for a ping reply before it times out. The value must be less than the delay value."},"type":{"type":"TypeString","required":true,"description":"The type of probe, which is PING, TCP, HTTP, HTTPS, TLS-HELLO or UDP-CONNECT, that is sent by the load balancer to verify the member state. Changing this creates a new monitor.","force_new":true},"url_path":{"type":"TypeString","optional":true,"description":"Required for HTTP(S) types. URI path that will be accessed if monitor type is HTTP or HTTPS.","computed":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a monitor resource within VKCS."},"vkcs_lb_pool":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the pool. A valid value is true (UP) or false (DOWN)."},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the pool."},"lb_method":{"type":"TypeString","required":true,"description":"The load balancing algorithm to distribute traffic to the pool's members. Must be one of ROUND_ROBIN, LEAST_CONNECTIONS, SOURCE_IP, or SOURCE_IP_PORT."},"listener_id":{"type":"TypeString","optional":true,"description":"The Listener on which the members of the pool will be associated with. Changing this creates a new pool. Note: One of LoadbalancerID or ListenerID must be provided.","force_new":true},"loadbalancer_id":{"type":"TypeString","optional":true,"description":"The load balancer on which to provision this pool. Changing this creates a new pool. Note: One of LoadbalancerID or ListenerID must be provided.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"Human-readable name for the pool."},"persistence":{"type":"TypeList","optional":true,"description":"Omit this field to prevent session persistence. Indicates whether connections in the same session will be processed by the same Pool member or not. Changing this creates a new pool.","computed":true,"force_new":true,"elem":{"schema":{"cookie_name":{"type":"TypeString","optional":true,"description":"The name of the cookie if persistence mode is set appropriately. Required if ` + "`" + `type = APP_COOKIE` + "`" + `.","force_new":true},"type":{"type":"TypeString","required":true,"description":"The type of persistence mode. The current specification supports SOURCE_IP, HTTP_COOKIE, and APP_COOKIE.","force_new":true}}},"max_items":1},"protocol":{"type":"TypeString","required":true,"description":"The protocol - can either be TCP, HTTP, HTTPS, PROXY, or UDP. Changing this creates a new pool.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new pool.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a pool resource within VKCS."},"vkcs_networking_floatingip":{"schema":{"address":{"type":"TypeString","optional":true,"description":"The actual floating IP address itself.","computed":true,"force_new":true},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the floating IP."},"fixed_ip":{"type":"TypeString","optional":true,"description":"Fixed IP of the port to associate with this floating IP. Required if the port has multiple fixed IPs.","computed":true},"pool":{"type":"TypeString","required":true,"description":"The name of the pool from which to obtain the floating IP. Changing this creates a new floating IP.","force_new":true},"port_id":{"type":"TypeString","optional":true,"description":"ID of an existing port with at least one IP address to associate with this floating IP.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a floating IP that can be used with another networking resource, such as a load balancer. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new floating IP (which may or may not have a different address).","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"subnet_id":{"type":"TypeString","optional":true,"description":"The subnet ID of the floating IP pool. Specify this if the floating IP network has multiple subnets.","computed":true},"subnet_ids":{"type":"TypeList","optional":true,"description":"A list of external subnet IDs to try over each to allocate a floating IP address. If a subnet ID in a list has exhausted floating IP pool, the next subnet ID will be tried. This argument is used only during the resource creation. Conflicts with a ` + "`" + `subnet_id` + "`" + ` argument.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a floating IP resource within VKCS that can be used for load balancers."},"vkcs_networking_floatingip_associate":{"schema":{"fixed_ip":{"type":"TypeString","optional":true,"description":"One of the port's IP addresses.","computed":true},"floating_ip":{"type":"TypeString","required":true,"description":"IP Address of an existing floating IP.","force_new":true},"port_id":{"type":"TypeString","required":true,"description":"ID of an existing port with at least one IP address to associate with this floating IP."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a floating IP that can be used with another networking resource, such as a load balancer. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new floating IP (which may or may not have a different address).","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true}},"description":"Associates a floating IP to a port. This is useful for situations where you have a pre-allocated floating IP or are unable to use the ` + "`" + `vkcs_networking_floatingip` + "`" + ` resource to create a floating IP."},"vkcs_networking_network":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the network. Acceptable values are \"true\" and \"false\". Changing this value updates the state of the existing network."},"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the network, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the network. Changing this updates the name of the existing network."},"name":{"type":"TypeString","optional":true,"description":"The name of the network. Changing this updates the name of the existing network."},"port_security_enabled":{"type":"TypeBool","optional":true,"default":true,"description":"Whether to explicitly enable or disable port security on the network. Port Security is usually enabled by default, so omitting this argument will usually result in a value of \"true\". Setting this explicitly to ` + "`" + `false` + "`" + ` will disable port security. Valid values are ` + "`" + `true` + "`" + ` and ` + "`" + `false` + "`" + `."},"private_dns_domain":{"type":"TypeString","optional":true,"description":"Private dns domain name","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a network. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new network.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the network.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true},"vkcs_services_access":{"type":"TypeBool","optional":true,"description":"Whether VKCS services access is enabled. This feature should be enabled globally for your project. Access can be enabled for new or existing networks, but cannot be disabled for existing networks. Valid values are ` + "`" + `true` + "`" + ` and ` + "`" + `false` + "`" + `."}},"timeouts":{"create":10,"delete":10},"description":"Manages a network resource within VKCS."},"vkcs_networking_port":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"Administrative up/down status for the port (must be ` + "`" + `true` + "`" + ` or ` + "`" + `false` + "`" + ` if provided). Changing this updates the ` + "`" + `admin_state_up` + "`" + ` of an existing port."},"all_fixed_ips":{"type":"TypeList","description":"The collection of Fixed IP addresses on the port in the order returned by the Network v2 API.","computed":true,"elem":{"type":"TypeString"}},"all_security_group_ids":{"type":"TypeSet","description":"The collection of Security Group IDs on the port which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the port, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"allowed_address_pairs":{"type":"TypeSet","optional":true,"description":"An IP/MAC Address pair of additional IP addresses that can be active on this port. The structure is described below.","elem":{"schema":{"ip_address":{"type":"TypeString","required":true,"description":"The additional IP address."},"mac_address":{"type":"TypeString","optional":true,"description":"The additional MAC address."}}}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the port. Changing this updates the ` + "`" + `description` + "`" + ` of an existing port."},"device_id":{"type":"TypeString","optional":true,"description":"The ID of the device attached to the port. Changing this creates a new port.","computed":true,"force_new":true},"device_owner":{"type":"TypeString","optional":true,"description":"The device owner of the port. Changing this creates a new port.","computed":true,"force_new":true},"dns_assignment":{"type":"TypeList","description":"The list of maps representing port DNS assignments.","computed":true,"elem":{"type":"TypeMap"}},"dns_name":{"type":"TypeString","optional":true,"description":"The port DNS name.","computed":true},"extra_dhcp_option":{"type":"TypeSet","optional":true,"description":"An extra DHCP option that needs to be configured on the port. The structure is described below. Can be specified multiple times.","elem":{"schema":{"name":{"type":"TypeString","required":true,"description":"Name of the DHCP option."},"value":{"type":"TypeString","required":true,"description":"Value of the DHCP option."}}}},"fixed_ip":{"type":"TypeList","optional":true,"description":"(Conflicts with ` + "`" + `no_fixed_ip` + "`" + `) An array of desired IPs for this port. The structure is described below.","elem":{"schema":{"ip_address":{"type":"TypeString","optional":true,"description":"IP address desired in the subnet for this port. If you don't specify ` + "`" + `ip_address` + "`" + `, an available IP address from the specified subnet will be allocated to this port. This field will not be populated if it is left blank or omitted. To retrieve the assigned IP address, use the ` + "`" + `all_fixed_ips` + "`" + ` attribute."},"subnet_id":{"type":"TypeString","required":true,"description":"Subnet in which to allocate IP address for this port."}}}},"mac_address":{"type":"TypeString","optional":true,"description":"Specify a specific MAC address for the port. Changing this creates a new port.","computed":true,"force_new":true},"name":{"type":"TypeString","optional":true,"description":"A unique name for the port. Changing this updates the ` + "`" + `name` + "`" + ` of an existing port."},"network_id":{"type":"TypeString","required":true,"description":"The ID of the network to attach the port to. Changing this creates a new port.","force_new":true},"no_fixed_ip":{"type":"TypeBool","optional":true,"description":"(Conflicts with ` + "`" + `fixed_ip` + "`" + `) Create a port with no fixed IP address. This will also remove any fixed IPs previously set on a port. ` + "`" + `true` + "`" + ` is the only valid value for this argument."},"no_security_groups":{"type":"TypeBool","optional":true,"description":"(Conflicts with ` + "`" + `security_group_ids` + "`" + `) If set to ` + "`" + `true` + "`" + `, then no security groups are applied to the port. If set to ` + "`" + `false` + "`" + ` and no ` + "`" + `security_group_ids` + "`" + ` are specified, then the port will yield to the default behavior of the Networking service, which is to usually apply the \"default\" security group."},"port_security_enabled":{"type":"TypeBool","optional":true,"default":true,"description":"Whether to explicitly enable or disable port security on the port. Port Security is usually enabled by default, so omitting argument will usually result in a value of ` + "`" + `true` + "`" + `. Setting this explicitly to ` + "`" + `false` + "`" + ` will disable port security. In order to disable port security, the port must not have any security groups. Valid values are ` + "`" + `true` + "`" + ` and ` + "`" + `false` + "`" + `."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a port. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new port.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"security_group_ids":{"type":"TypeSet","optional":true,"description":"(Conflicts with ` + "`" + `no_security_groups` + "`" + `) A list of security group IDs to apply to the port. The security groups must be specified by ID and not name (as opposed to how they are configured with the Compute Instance).","elem":{"type":"TypeString"}},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the port.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a port resource within VKCS."},"vkcs_networking_port_secgroup_associate":{"schema":{"all_security_group_ids":{"type":"TypeSet","description":"The collection of Security Group IDs on the port which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"enforce":{"type":"TypeBool","optional":true,"default":false,"description":"Whether to replace or append the list of security groups, specified in the ` + "`" + `security_group_ids` + "`" + `. Defaults to ` + "`" + `false` + "`" + `."},"port_id":{"type":"TypeString","required":true,"description":"An UUID of the port to apply security groups to.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to manage a port. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new resource.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"security_group_ids":{"type":"TypeSet","required":true,"description":"A list of security group IDs to apply to the port. The security groups must be specified by ID and not name (as opposed to how they are configured with the Compute Instance).","elem":{"type":"TypeString"}}},"description":"Manages a port's security groups within VKCS. Useful, when the port was created not by Terraform. It should not be used, when the port was created directly within Terraform.\n\nWhen the resource is deleted, Terraform doesn't delete the port, but unsets the list of user defined security group IDs. However, if ` + "`" + `enforce` + "`" + ` is set to ` + "`" + `true` + "`" + ` and the resource is deleted, Terraform will remove all assigned security group IDs."},"vkcs_networking_router":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"description":"Administrative up/down status for the router (must be \"true\" or \"false\" if provided). Changing this updates the ` + "`" + `admin_state_up` + "`" + ` of an existing router.","computed":true},"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the router, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description for the router."},"external_network_id":{"type":"TypeString","optional":true,"description":"The network UUID of an external gateway for the router. A router with an external gateway is required if any compute instances or load balancers will be using floating IPs. Changing this updates the external gateway of the router.","computed":true},"name":{"type":"TypeString","optional":true,"description":"A unique name for the router. Changing this updates the ` + "`" + `name` + "`" + ` of an existing router."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to create a router. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new router.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the router.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional driver-specific options.","force_new":true},"vendor_options":{"type":"TypeSet","optional":true,"description":"Map of additional vendor-specific options. Supported options are described below.","elem":{"schema":{"set_router_gateway_after_create":{"type":"TypeBool","optional":true,"default":false,"description":"Boolean to control whether the Router gateway is assigned during creation or updated after creation."}}},"max_items":1,"min_items":1}},"timeouts":{"create":10,"delete":10},"description":"Manages a router resource within VKCS."},"vkcs_networking_router_interface":{"schema":{"port_id":{"type":"TypeString","optional":true,"description":"ID of the port this interface connects to. Changing this creates a new router interface.","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to create a router. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new router interface.","computed":true,"force_new":true},"router_id":{"type":"TypeString","required":true,"description":"ID of the router this interface belongs to. Changing this creates a new router interface.","force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"subnet_id":{"type":"TypeString","optional":true,"description":"ID of the subnet this interface connects to. Changing this creates a new router interface.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a router interface resource within VKCS."},"vkcs_networking_router_route":{"schema":{"destination_cidr":{"type":"TypeString","required":true,"description":"CIDR block to match on the packet’s destination IP. Changing this creates a new routing entry.","force_new":true},"next_hop":{"type":"TypeString","required":true,"description":"IP address of the next hop gateway. Changing this creates a new routing entry.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to configure a routing entry on a router. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new routing entry.","computed":true,"force_new":true},"router_id":{"type":"TypeString","required":true,"description":"ID of the router this routing entry belongs to. Changing this creates a new routing entry.","force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true}},"description":"Creates a routing entry on a VKCS router."},"vkcs_networking_secgroup":{"schema":{"all_tags":{"type":"TypeSet","description":"The collection of tags assigned on the security group, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"delete_default_rules":{"type":"TypeBool","optional":true,"description":"Whether or not to delete the default egress security rules. This is ` + "`" + `false` + "`" + ` by default. See the below note for more information.","force_new":true},"description":{"type":"TypeString","optional":true,"description":"A unique name for the security group.","computed":true},"name":{"type":"TypeString","required":true,"description":"A unique name for the security group."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to create a port. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new security group.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the security group.","elem":{"type":"TypeString"}}},"timeouts":{"delete":10},"description":"Manages a security group resource within VKCS."},"vkcs_networking_secgroup_rule":{"schema":{"description":{"type":"TypeString","optional":true,"description":"A description of the rule. Changing this creates a new security group rule.","force_new":true},"direction":{"type":"TypeString","required":true,"description":"The direction of the rule, valid values are __ingress__ or __egress__. Changing this creates a new security group rule.","force_new":true},"ethertype":{"type":"TypeString","optional":true,"default":"IPv4","description":"The layer 3 protocol type, the only valid value is __IPv4__. Changing this creates a new security group rule.","force_new":true,"deprecated":"Only IPv4 can be used as ethertype. This argument is deprecated, please do not use it."},"port_range_max":{"type":"TypeInt","optional":true,"description":"The higher part of the allowed port range, valid integer value needs to be between 1 and 65535. Changing this creates a new security group rule.","computed":true,"force_new":true},"port_range_min":{"type":"TypeInt","optional":true,"description":"The lower part of the allowed port range, valid integer value needs to be between 1 and 65535. Changing this creates a new security group rule.","computed":true,"force_new":true},"protocol":{"type":"TypeString","optional":true,"description":"The layer 4 protocol type, valid values are following. Changing this creates a new security group rule. This is required if you want to specify a port range.\n * __tcp__\n * __udp__\n * __icmp__\n * __ah__\n * __dccp__\n * __egp__\n * __esp__\n * __gre__\n * __igmp__\n * __ospf__\n * __pgm__\n * __rsvp__\n * __sctp__\n * __udplite__\n * __vrrp__","computed":true,"force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to create a port. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new security group rule.","computed":true,"force_new":true},"remote_group_id":{"type":"TypeString","optional":true,"description":"The remote group id, the value needs to be an ID of a security group in the same tenant. Changing this creates a new security group rule. **Note**: Only one of ` + "`" + `remote_group_id` + "`" + ` or ` + "`" + `remote_ip_prefix` + "`" + ` may be set.","computed":true,"force_new":true},"remote_ip_prefix":{"type":"TypeString","optional":true,"description":"The remote CIDR, the value needs to be a valid CIDR (i.e. 192.168.0.0/16). Changing this creates a new security group rule. **Note**: Only one of ` + "`" + `remote_group_id` + "`" + ` or ` + "`" + `remote_ip_prefix` + "`" + ` may be set.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"security_group_id":{"type":"TypeString","required":true,"description":"The security group id the rule should belong to, the value needs to be an ID of a security group in the same tenant. Changing this creates a new security group rule.","force_new":true}},"timeouts":{"delete":10},"description":"Manages a security group rule resource within VKCS."},"vkcs_networking_subnet":{"schema":{"all_tags":{"type":"TypeSet","description":"The collection of ags assigned on the subnet, which have been explicitly and implicitly added.","computed":true,"elem":{"type":"TypeString"}},"allocation_pool":{"type":"TypeSet","optional":true,"description":"A block declaring the start and end range of the IP addresses available for use with DHCP in this subnet. Multiple ` + "`" + `allocation_pool` + "`" + ` blocks can be declared, providing the subnet with more than one range of IP addresses to use with DHCP. However, each IP range must be from the same CIDR that the subnet is part of. The ` + "`" + `allocation_pool` + "`" + ` block is documented below.","computed":true,"elem":{"schema":{"end":{"type":"TypeString","required":true,"description":"The ending address."},"start":{"type":"TypeString","required":true,"description":"The starting address."}}}},"cidr":{"type":"TypeString","optional":true,"description":"CIDR representing IP range for this subnet, based on IP version. You can omit this option if you are creating a subnet from a subnet pool.","computed":true,"force_new":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the subnet. Changing this updates the name of the existing subnet."},"dns_nameservers":{"type":"TypeList","optional":true,"description":"An array of DNS name server names used by hosts in this subnet. Changing this updates the DNS name servers for the existing subnet.","elem":{"type":"TypeString"}},"enable_dhcp":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the network. Acceptable values are \"true\" and \"false\". Changing this value enables or disables the DHCP capabilities of the existing subnet. Defaults to true."},"gateway_ip":{"type":"TypeString","optional":true,"description":"Default gateway used by devices in this subnet. Leaving this blank and not setting ` + "`" + `no_gateway` + "`" + ` will cause a default gateway of ` + "`" + `.1` + "`" + ` to be used. Changing this updates the gateway IP of the existing subnet.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the subnet. Changing this updates the name of the existing subnet."},"network_id":{"type":"TypeString","required":true,"description":"The UUID of the parent network. Changing this creates a new subnet.","force_new":true},"no_gateway":{"type":"TypeBool","optional":true,"default":false,"description":"Do not set a gateway IP on this subnet. Changing this removes or adds a default gateway IP of the existing subnet."},"prefix_length":{"type":"TypeInt","optional":true,"description":"The prefix length to use when creating a subnet from a subnet pool. The default subnet pool prefix length that was defined when creating the subnet pool will be used if not provided. Changing this creates a new subnet.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a subnet. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new subnet.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"subnetpool_id":{"type":"TypeString","optional":true,"description":"The ID of the subnetpool associated with the subnet.","force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"A set of string tags for the subnet.","elem":{"type":"TypeString"}},"value_specs":{"type":"TypeMap","optional":true,"description":"Map of additional options.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a subnet resource within VKCS."},"vkcs_networking_subnet_route":{"schema":{"destination_cidr":{"type":"TypeString","required":true,"description":"CIDR block to match on the packet’s destination IP. Changing this creates a new routing entry.","force_new":true},"next_hop":{"type":"TypeString","required":true,"description":"IP address of the next hop gateway. Changing this creates a new routing entry.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the networking client. A networking client is needed to configure a routing entry on a subnet. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new routing entry.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\".","computed":true,"force_new":true},"subnet_id":{"type":"TypeString","required":true,"description":"ID of the subnet this routing entry belongs to. Changing this creates a new routing entry.","force_new":true}},"description":"Creates a routing entry on a VKCS subnet."},"vkcs_publicdns_record":{"schema":{"content":{"type":"TypeString","optional":true,"description":"The content of the record.","computed":true},"full_name":{"type":"TypeString","description":"The full name of the SRV record.","computed":true},"host":{"type":"TypeString","optional":true,"description":"The domain name of the target host.","computed":true},"ip":{"type":"TypeString","optional":true,"description":"The IP address of the record. It should be IPv4 for record of type \"A\" and IPv6 for record of type \"AAAA\".","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the record.","computed":true},"port":{"type":"TypeInt","optional":true,"description":"The port on the target host of the service.","computed":true},"priority":{"type":"TypeInt","optional":true,"description":"The priority of the record's server.","computed":true},"proto":{"type":"TypeString","optional":true,"description":"The name of the desired protocol."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V2 Public DNS client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new record.","computed":true,"force_new":true},"service":{"type":"TypeString","optional":true,"description":"The name of the desired service."},"ttl":{"type":"TypeInt","optional":true,"description":"The time to live of the record.","computed":true},"type":{"type":"TypeString","required":true,"description":"The type of the record. Must be one of following: \"A\", \"AAAA\", \"CNAME\", \"MX\", \"NS\", \"SRV\", \"TXT\".","force_new":true},"weight":{"type":"TypeInt","optional":true,"description":"The relative weight of the record's server.","computed":true},"zone_id":{"type":"TypeString","required":true,"description":"The ID of the zone to attach the record to.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a public DNS zone record resource within VKCS.\u003cbr\u003e\n**Note:** Although some arguments are marked as optional, it is actually required to set values for them depending on record \\\"type\\\". Use this map to get information about which arguments you have to set:\n\n| Record type | Required arguments |\n| ----------- | ------------------ |\n| A | ip |\n| AAAA | ip |\n| CNAME | name, content |\n| MX | priority, content |\n| NS | content |\n| SRV | service, proto, priority, weight, host, port |\n| TXT | content |\n\n\n","new_since":"v0.2.0"},"vkcs_publicdns_zone":{"schema":{"admin_email":{"type":"TypeString","optional":true,"description":"The admin email of the zone SOA."},"expire":{"type":"TypeInt","optional":true,"description":"The expire time of the zone SOA.","computed":true},"primary_dns":{"type":"TypeString","optional":true,"description":"The primary DNS of the zone SOA.","computed":true},"refresh":{"type":"TypeInt","optional":true,"description":"The refresh time of the zone SOA.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V2 Public DNS client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new zone.","computed":true,"force_new":true},"retry":{"type":"TypeInt","optional":true,"description":"The retry time of the zone SOA.","computed":true},"serial":{"type":"TypeInt","description":"The serial number of the zone SOA.","computed":true},"status":{"type":"TypeString","description":"The status of the zone.","computed":true},"ttl":{"type":"TypeInt","optional":true,"description":"The TTL (time to live) of the zone SOA.","computed":true},"zone":{"type":"TypeString","required":true,"description":"The name of the zone. **Changes this creates a new zone**.","force_new":true}},"timeouts":{"create":10,"delete":10},"description":"Manages a public DNS record resource within VKCS.","new_since":"v0.2.0"},"vkcs_sharedfilesystem_securityservice":{"schema":{"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the security service. Changing this updates the description of the existing security service."},"dns_ip":{"type":"TypeString","optional":true,"description":"The security service DNS IP address that is used inside the tenant network."},"domain":{"type":"TypeString","optional":true,"description":"The security service domain."},"name":{"type":"TypeString","optional":true,"description":"The name of the security service. Changing this updates the name of the existing security service."},"password":{"type":"TypeString","optional":true,"description":"The user password, if you specify a user."},"project_id":{"type":"TypeString","description":"The owner of the Security Service.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to create a security service. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new security service.","computed":true,"force_new":true},"server":{"type":"TypeString","optional":true,"description":"The security service host name or IP address."},"type":{"type":"TypeString","required":true,"description":"The security service type - can either be active\\_directory, kerberos or ldap. Changing this updates the existing security service."},"user":{"type":"TypeString","optional":true,"description":"The security service user or group name that is used by the tenant."}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Use this resource to configure a security service.\n\n~\u003e **Note:** All arguments including the security service password will be stored in the raw state as plain-text. [Read more about sensitive data in state](/docs/state/sensitive-data.html).\n\nA security service stores configuration information for clients for authentication and authorization (AuthN/AuthZ). For example, a share server will be the client for an existing service such as LDAP, Kerberos, or Microsoft Active Directory."},"vkcs_sharedfilesystem_share":{"schema":{"all_metadata":{"type":"TypeMap","description":"The map of metadata, assigned on the share, which has been explicitly and implicitly added.","computed":true},"availability_zone":{"type":"TypeString","optional":true,"description":"The share availability zone. Changing this creates a new share.","computed":true,"force_new":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the share. Changing this updates the description of the existing share."},"export_location_path":{"type":"TypeString","description":"The export location path of the share.","computed":true,"new_since":"v0.1.15"},"name":{"type":"TypeString","required":true,"description":"The name of the share. Changing this updates the name of the existing share."},"project_id":{"type":"TypeString","description":"The owner of the Share.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to create a share. Changing this creates a new share.","computed":true,"force_new":true},"share_network_id":{"type":"TypeString","required":true,"description":"The UUID of the share network."},"share_proto":{"type":"TypeString","required":true,"description":"The share protocol - can either be NFS, CIFS, CEPHFS, GLUSTERFS, HDFS or MAPRFS. Changing this creates a new share.","force_new":true},"share_server_id":{"type":"TypeString","description":"The UUID of the share server.","computed":true},"share_type":{"type":"TypeString","optional":true,"description":"The share type name. If you omit this parameter, the default share type is used.","computed":true,"force_new":true},"size":{"type":"TypeInt","required":true,"description":"The share size, in GBs. The requested share size cannot be greater than the allowed GB quota. Changing this resizes the existing share."},"snapshot_id":{"type":"TypeString","optional":true,"description":"The UUID of the share's base snapshot. Changing this creates a new share.","force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Use this resource to configure a share."},"vkcs_sharedfilesystem_share_access":{"schema":{"access_level":{"type":"TypeString","required":true,"description":"The access level to the share. Can either be ` + "`" + `rw` + "`" + ` or ` + "`" + `ro` + "`" + `.","force_new":true},"access_to":{"type":"TypeString","required":true,"description":"The value that defines the access. Can either be an IP address or a username verified by configured Security Service of the Share Network.","force_new":true},"access_type":{"type":"TypeString","required":true,"description":"The access rule type. Can either be an ip, user, cert, or cephx.","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to create a share access. Changing this creates a new share access.","computed":true,"force_new":true},"share_id":{"type":"TypeString","required":true,"description":"The UUID of the share to which you are granted access.","force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Use this resource to control the share access lists.\n\n~\u003e **Important Security Notice** The access key assigned by this resource will be stored *unencrypted* in your Terraform state file. If you use this resource in production, please make sure your state file is sufficiently protected. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_sharedfilesystem_sharenetwork":{"schema":{"cidr":{"type":"TypeString","description":"The share network CIDR.","computed":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the share network. Changing this updates the description of the existing share network."},"name":{"type":"TypeString","optional":true,"description":"The name for the share network. Changing this updates the name of the existing share network."},"neutron_net_id":{"type":"TypeString","required":true,"description":"The UUID of a neutron network when setting up or updating a share network. Changing this updates the existing share network if it's not used by shares."},"neutron_subnet_id":{"type":"TypeString","required":true,"description":"The UUID of the neutron subnet when setting up or updating a share network. Changing this updates the existing share network if it's not used by shares."},"project_id":{"type":"TypeString","description":"The owner of the Share Network.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to create a share network. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new share network.","computed":true,"force_new":true},"security_service_ids":{"type":"TypeSet","optional":true,"description":"The list of security service IDs to associate with the share network. The security service must be specified by ID and not name.","elem":{"type":"TypeString"}}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Use this resource to configure a share network.\n\nA share network stores network information that share servers can use when shares are created."},"vkcs_vpnaas_endpoint_group":{"schema":{"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the group. Changing this updates the description of the existing group."},"endpoints":{"type":"TypeSet","optional":true,"description":"List of endpoints of the same type, for the endpoint group. The values will depend on the type. Changing this creates a new group.","force_new":true,"elem":{"type":"TypeString"}},"name":{"type":"TypeString","optional":true,"description":"The name of the group. Changing this updates the name of the existing group."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create an endpoint group. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new group.","computed":true,"force_new":true},"type":{"type":"TypeString","optional":true,"description":"The type of the endpoints in the group. A valid value is subnet, cidr, network, router, or vlan. Changing this creates a new group.","computed":true,"force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages an Endpoint Group resource within VKCS."},"vkcs_vpnaas_ike_policy":{"schema":{"auth_algorithm":{"type":"TypeString","optional":true,"default":"sha1","description":"The authentication hash algorithm. Valid values are sha1, sha256, sha384, sha512. Default is sha1. Changing this updates the algorithm of the existing policy."},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the policy. Changing this updates the description of the existing policy."},"encryption_algorithm":{"type":"TypeString","optional":true,"default":"aes-128","description":"The encryption algorithm. Valid values are 3des, aes-128, aes-192 and so on. The default value is aes-128. Changing this updates the existing policy."},"ike_version":{"type":"TypeString","optional":true,"default":"v1","description":"The IKE mode. A valid value is v1 or v2. Default is v1. Changing this updates the existing policy."},"lifetime":{"type":"TypeSet","optional":true,"description":"The lifetime of the security association. Consists of Unit and Value.","computed":true,"elem":{"schema":{"units":{"type":"TypeString","optional":true,"description":"The units for the lifetime of the security association. Can be either seconds or kilobytes. Default is seconds.","computed":true},"value":{"type":"TypeInt","optional":true,"description":"The value for the lifetime of the security association. Must be a positive integer. Default is 3600.","computed":true}}}},"name":{"type":"TypeString","optional":true,"description":"The name of the policy. Changing this updates the name of the existing policy."},"pfs":{"type":"TypeString","optional":true,"default":"group5","description":"The perfect forward secrecy mode. Valid values are Group2, Group5 and Group14. Default is Group5. Changing this updates the existing policy."},"phase1_negotiation_mode":{"type":"TypeString","optional":true,"default":"main","description":"The IKE mode. A valid value is main, which is the default. Changing this updates the existing policy."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a VPN service. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new service.","computed":true,"force_new":true}},"timeouts":{"create":10},"description":"Manages a IKE policy resource within VKCS."},"vkcs_vpnaas_ipsec_policy":{"schema":{"auth_algorithm":{"type":"TypeString","optional":true,"description":"The authentication hash algorithm. Valid values are sha1, sha256, sha384, sha512. Default is sha1. Changing this updates the algorithm of the existing policy.","computed":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the policy. Changing this updates the description of the existing policy."},"encapsulation_mode":{"type":"TypeString","optional":true,"description":"The encapsulation mode. Valid values are tunnel and transport. Default is tunnel. Changing this updates the existing policy.","computed":true},"encryption_algorithm":{"type":"TypeString","optional":true,"description":"The encryption algorithm. Valid values are 3des, aes-128, aes-192 and so on. The default value is aes-128. Changing this updates the existing policy.","computed":true},"lifetime":{"type":"TypeSet","optional":true,"description":"The lifetime of the security association. Consists of Unit and Value.","computed":true,"elem":{"schema":{"units":{"type":"TypeString","optional":true,"description":"The units for the lifetime of the security association. Can be either seconds or kilobytes. Default is seconds.","computed":true},"value":{"type":"TypeInt","optional":true,"description":"The value for the lifetime of the security association. Must be a positive integer. Default is 3600.","computed":true}}}},"name":{"type":"TypeString","optional":true,"description":"The name of the policy. Changing this updates the name of the existing policy."},"pfs":{"type":"TypeString","optional":true,"description":"The perfect forward secrecy mode. Valid values are Group2, Group5 and Group14. Default is Group5. Changing this updates the existing policy.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create an IPSec policy. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new policy.","computed":true,"force_new":true},"transform_protocol":{"type":"TypeString","optional":true,"description":"The transform protocol. Valid values are ESP, AH and AH-ESP. Changing this updates the existing policy. Default is ESP.","computed":true}},"timeouts":{"create":10},"description":"Manages a IPSec policy resource within VKCS."},"vkcs_vpnaas_service":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the resource. Can either be up(true) or down(false). Changing this updates the administrative state of the existing service."},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the service. Changing this updates the description of the existing service."},"external_v4_ip":{"type":"TypeString","description":"The read-only external (public) IPv4 address that is used for the VPN service.","computed":true},"external_v6_ip":{"type":"TypeString","description":"The read-only external (public) IPv6 address that is used for the VPN service.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the service. Changing this updates the name of the existing service."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create a VPN service. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new service.","computed":true,"force_new":true},"router_id":{"type":"TypeString","required":true,"description":"The ID of the router. Changing this creates a new service.","force_new":true},"status":{"type":"TypeString","description":"Indicates whether IPsec VPN service is currently operational. Values are ACTIVE, DOWN, BUILD, ERROR, PENDING_CREATE, PENDING_UPDATE, or PENDING_DELETE.","computed":true},"subnet_id":{"type":"TypeString","optional":true,"description":"SubnetID is the ID of the subnet. Default is null.","force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a VPN service resource within VKCS."},"vkcs_vpnaas_site_connection":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"default":true,"description":"The administrative state of the resource. Can either be up(true) or down(false). Changing this updates the administrative state of the existing connection."},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the connection. Changing this updates the description of the existing connection."},"dpd":{"type":"TypeSet","optional":true,"description":"A dictionary with dead peer detection (DPD) protocol controls.","computed":true,"elem":{"schema":{"action":{"type":"TypeString","optional":true,"description":"The dead peer detection (DPD) action. A valid value is clear, hold, restart, disabled, or restart-by-peer. Default value is hold.","computed":true},"interval":{"type":"TypeInt","optional":true,"description":"The dead peer detection (DPD) interval, in seconds. A valid value is a positive integer. Default is 30.","computed":true},"timeout":{"type":"TypeInt","optional":true,"description":"The dead peer detection (DPD) timeout in seconds. A valid value is a positive integer that is greater than the DPD interval value. Default is 120.","computed":true}}}},"ikepolicy_id":{"type":"TypeString","required":true,"description":"The ID of the IKE policy. Changing this creates a new connection.","force_new":true},"initiator":{"type":"TypeString","optional":true,"description":"A valid value is response-only or bi-directional. Default is bi-directional.","computed":true},"ipsecpolicy_id":{"type":"TypeString","required":true,"description":"The ID of the IPsec policy. Changing this creates a new connection.","force_new":true},"local_ep_group_id":{"type":"TypeString","optional":true,"description":"The ID for the endpoint group that contains private subnets for the local side of the connection. You must specify this parameter with the peer_ep_group_id parameter unless in backward- compatible mode where peer_cidrs is provided with a subnet_id for the VPN service. Changing this updates the existing connection."},"local_id":{"type":"TypeString","optional":true,"description":"An ID to be used instead of the external IP address for a virtual router used in traffic between instances on different networks in east-west traffic. Most often, local ID would be domain name, email address, etc. If this is not configured then the external IP address will be used as the ID."},"mtu":{"type":"TypeInt","optional":true,"description":"The maximum transmission unit (MTU) value to address fragmentation. Minimum value is 68 for IPv4, and 1280 for IPv6.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the connection. Changing this updates the name of the existing connection."},"peer_address":{"type":"TypeString","required":true,"description":"The peer gateway public IPv4 or IPv6 address or FQDN."},"peer_cidrs":{"type":"TypeList","optional":true,"description":"Unique list of valid peer private CIDRs in the form \u003c net_address \u003e / \u003c prefix \u003e.","elem":{"type":"TypeString"}},"peer_ep_group_id":{"type":"TypeString","optional":true,"description":"The ID for the endpoint group that contains private CIDRs in the form \u003c net_address \u003e / \u003c prefix \u003e for the peer side of the connection. You must specify this parameter with the local_ep_group_id parameter unless in backward-compatible mode where peer_cidrs is provided with a subnet_id for the VPN service."},"peer_id":{"type":"TypeString","required":true,"description":"The peer router identity for authentication. A valid value is an IPv4 address, IPv6 address, e-mail address, key ID, or FQDN. Typically, this value matches the peer_address value. Changing this updates the existing policy."},"psk":{"type":"TypeString","required":true,"description":"The pre-shared key. A valid value is any string."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Networking client. A Networking client is needed to create an IPSec site connection. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used. Changing this creates a new site connection.","computed":true,"force_new":true},"vpnservice_id":{"type":"TypeString","required":true,"description":"The ID of the VPN service. Changing this creates a new connection.","force_new":true}},"timeouts":{"create":10,"delete":10,"update":10},"description":"Manages a IPSec site connection resource within VKCS."}},"data_sources":{"vkcs_blockstorage_snapshot":{"schema":{"description":{"type":"TypeString","description":"The snapshot's description.","computed":true},"metadata":{"type":"TypeMap","description":"The snapshot's metadata.","computed":true},"most_recent":{"type":"TypeBool","optional":true,"description":"Pick the most recently created snapshot if there are multiple results."},"name":{"type":"TypeString","optional":true,"description":"The name of the snapshot.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Block Storage client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"size":{"type":"TypeInt","description":"The size of the snapshot.","computed":true},"status":{"type":"TypeString","optional":true,"description":"The status of the snapshot.","computed":true},"volume_id":{"type":"TypeString","optional":true,"description":"The ID of the snapshot's volume.","computed":true}},"description":"Use this data source to get information about an existing snapshot."},"vkcs_blockstorage_volume":{"schema":{"availability_zone":{"type":"TypeString","description":"The name of the availability zone of the volume.","computed":true},"bootable":{"type":"TypeString","optional":true,"description":"Indicates if the volume is bootable.","computed":true},"metadata":{"type":"TypeMap","optional":true,"description":"Metadata key/value pairs associated with the volume.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the volume.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Block Storage client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"size":{"type":"TypeInt","description":"The size of the volume in GBs.","computed":true},"source_volume_id":{"type":"TypeString","description":"The ID of the volume from which the current volume was created.","computed":true},"status":{"type":"TypeString","optional":true,"description":"The status of the volume.","computed":true},"volume_type":{"type":"TypeString","optional":true,"description":"The type of the volume.","computed":true}},"description":"Use this data source to get information about an existing volume."},"vkcs_compute_availability_zones":{"schema":{"id":{"type":"TypeString","description":"Hash of the returned zone list.","computed":true},"names":{"type":"TypeList","description":"The names of the availability zones, ordered alphanumerically, that match the queried ` + "`" + `state` + "`" + `","computed":true,"elem":{"type":"TypeString"}},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `","computed":true},"state":{"type":"TypeString","optional":true,"default":"available","description":"The ` + "`" + `state` + "`" + ` of the availability zones to match, default (\"available\")."}},"description":"Use this data source to get a list of availability zones from VKCS"},"vkcs_compute_flavor":{"schema":{"disk":{"type":"TypeInt","optional":true,"description":"The exact amount of disk (in gigabytes).","force_new":true},"extra_specs":{"type":"TypeMap","description":"Key/Value pairs of metadata for the flavor.","computed":true},"flavor_id":{"type":"TypeString","optional":true,"description":"The ID of the flavor. Conflicts with the ` + "`" + `name` + "`" + `, ` + "`" + `min_ram` + "`" + ` and ` + "`" + `min_disk` + "`" + `","force_new":true},"id":{"type":"TypeString","description":"ID of the found flavor.","computed":true},"is_public":{"type":"TypeBool","optional":true,"description":"The flavor visibility.","force_new":true},"min_disk":{"type":"TypeInt","optional":true,"description":"The minimum amount of disk (in gigabytes). Conflicts with the ` + "`" + `flavor_id` + "`" + `.","force_new":true},"min_ram":{"type":"TypeInt","optional":true,"description":"The minimum amount of RAM (in megabytes). Conflicts with the ` + "`" + `flavor_id` + "`" + `.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"The name of the flavor. Conflicts with the ` + "`" + `flavor_id` + "`" + `.","force_new":true},"ram":{"type":"TypeInt","optional":true,"description":"The exact amount of RAM (in megabytes).","force_new":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"rx_tx_factor":{"type":"TypeFloat","optional":true,"description":"The ` + "`" + `rx_tx_factor` + "`" + ` of the flavor.","force_new":true},"swap":{"type":"TypeInt","optional":true,"description":"The amount of swap (in gigabytes).","force_new":true},"vcpus":{"type":"TypeInt","optional":true,"description":"The amount of VCPUs.","force_new":true}},"description":"Use this data source to get the ID of an available VKCS flavor."},"vkcs_compute_instance":{"schema":{"access_ip_v4":{"type":"TypeString","description":"The first IPv4 address assigned to this server.","computed":true},"availability_zone":{"type":"TypeString","description":"The availability zone of this server.","computed":true},"flavor_id":{"type":"TypeString","description":"The flavor ID used to create the server.","computed":true},"flavor_name":{"type":"TypeString","description":"The flavor name used to create the server.","computed":true},"id":{"type":"TypeString","required":true,"description":"The UUID of the instance"},"image_id":{"type":"TypeString","description":"The image ID used to create the server.","computed":true},"image_name":{"type":"TypeString","description":"The image name used to create the server.","computed":true},"key_pair":{"type":"TypeString","description":"The name of the key pair assigned to this server.","computed":true},"metadata":{"type":"TypeMap","description":"A set of key/value pairs made available to the server.","computed":true},"name":{"type":"TypeString","description":"The name of the server.","computed":true},"network":{"type":"TypeList","optional":true,"description":"An array of maps, detailed below.","computed":true,"elem":{"schema":{"fixed_ip_v4":{"type":"TypeString","description":"The IPv4 address assigned to this network port.","computed":true},"mac":{"type":"TypeString","description":"The MAC address assigned to this network interface.","computed":true},"name":{"type":"TypeString","description":"The name of the network","computed":true},"port":{"type":"TypeString","description":"The port UUID for this network","computed":true},"uuid":{"type":"TypeString","description":"The UUID of the network","computed":true}}}},"power_state":{"type":"TypeString","description":"VM state","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"security_groups":{"type":"TypeSet","description":"An array of security group names associated with this server.","computed":true,"elem":{"type":"TypeString"}},"tags":{"type":"TypeSet","description":"A set of string tags for the instance.","computed":true,"elem":{"type":"TypeString"}},"user_data":{"type":"TypeString","optional":true,"description":"The user data added when the server was created.","computed":true}},"description":"Use this data source to get the details of a running server"},"vkcs_compute_keypair":{"schema":{"fingerprint":{"type":"TypeString","description":"The fingerprint of the OpenSSH key.","computed":true},"name":{"type":"TypeString","required":true,"description":"The unique name of the keypair."},"public_key":{"type":"TypeString","description":"The OpenSSH-formatted public key of the keypair.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true}},"description":"Use this data source to get the ID and public key of an VKCS keypair."},"vkcs_compute_quotaset":{"schema":{"cores":{"type":"TypeInt","description":"The number of allowed server cores.","computed":true},"injected_file_content_bytes":{"type":"TypeInt","description":"The number of allowed bytes of content for each injected file.","computed":true},"injected_file_path_bytes":{"type":"TypeInt","description":"The number of allowed bytes for each injected file path.","computed":true},"injected_files":{"type":"TypeInt","description":"The number of allowed injected files.","computed":true},"instances":{"type":"TypeInt","description":"The number of allowed servers.","computed":true},"key_pairs":{"type":"TypeInt","description":"The number of allowed key pairs for each user.","computed":true},"metadata_items":{"type":"TypeInt","description":"The number of allowed metadata items for each server.","computed":true},"project_id":{"type":"TypeString","required":true,"description":"The id of the project to retrieve the quotaset.","force_new":true},"ram":{"type":"TypeInt","description":"The amount of allowed server RAM, in MiB.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Compute client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"server_group_members":{"type":"TypeInt","description":"The number of allowed members for each server group.","computed":true},"server_groups":{"type":"TypeInt","description":"The number of allowed server groups.","computed":true}},"description":"Use this data source to get the compute quotaset of an VKCS project."},"vkcs_db_backup":{"schema":{"backup_id":{"type":"TypeString","required":true,"description":"The UUID of the backup."},"created":{"type":"TypeString","description":"Backup creation timestamp","computed":true},"datastore":{"type":"TypeList","description":"Object that represents datastore of backup","computed":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore."},"version":{"type":"TypeString","required":true,"description":"Version of the datastore."}}}},"dbms_id":{"type":"TypeString","description":"ID of the backed up instance or cluster","computed":true},"dbms_type":{"type":"TypeString","description":"Type of dbms of the backup, can be \"instance\" or \"cluster\".","computed":true},"description":{"type":"TypeString","optional":true,"description":"The description of the backup"},"location_ref":{"type":"TypeString","description":"Location of backup data on backup storage","computed":true},"meta":{"type":"TypeString","description":"Metadata of the backup","computed":true},"name":{"type":"TypeString","description":"The name of the backup.","computed":true},"size":{"type":"TypeFloat","description":"Backup's volume size","computed":true},"updated":{"type":"TypeString","description":"Timestamp of backup's last update","computed":true},"wal_size":{"type":"TypeFloat","description":"Backup's WAL volume size","computed":true}},"description":"Use this data source to get the information on a db backup resource."},"vkcs_db_config_group":{"schema":{"config_group_id":{"type":"TypeString","required":true,"description":"The UUID of the config_group."},"created":{"type":"TypeString","description":"Timestamp of config group's creation.","computed":true},"datastore":{"type":"TypeList","description":"Object that represents datastore of backup","computed":true,"elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore."},"version":{"type":"TypeString","required":true,"description":"Version of the datastore."}}}},"description":{"type":"TypeString","description":"The description of the config group.","computed":true},"name":{"type":"TypeString","description":"The name of the config group.","computed":true},"updated":{"type":"TypeString","description":"Timestamp of config group's last update.","computed":true},"values":{"type":"TypeMap","description":"Map of configuration parameters in format \"key\": \"value\".","computed":true,"elem":{"type":"TypeString"}}},"description":"Use this data source to get the information on a db config group resource.","new_since":"v0.1.7"},"vkcs_db_database":{"schema":{"charset":{"type":"TypeString","optional":true,"description":"Type of charset used for the database.","force_new":true},"collate":{"type":"TypeString","optional":true,"description":"Collate option of the database.","force_new":true},"dbms_id":{"type":"TypeString","optional":true,"description":"ID of the instance or cluster that database is created for."},"id":{"type":"TypeString","required":true,"description":"The id of the database in form \"dbms_id/db_name\"."},"name":{"type":"TypeString","optional":true,"description":"The name of the database."}},"description":"Use this data source to get the information on a db database resource."},"vkcs_db_datastore":{"schema":{"cluster_volume_types":{"type":"TypeList","description":"Supported volume types for the datastore when used in a cluster.","computed":true,"elem":{"type":"TypeString"}},"id":{"type":"TypeString","optional":true,"description":"The id of the datastore.","computed":true},"minimum_cpu":{"type":"TypeInt","description":"Minimum CPU required for instance of the datastore.","computed":true},"minimum_ram":{"type":"TypeInt","description":"Minimum RAM required for instance of the datastore.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the datastore.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `","computed":true},"versions":{"type":"TypeList","description":"Versions of the datastore.","computed":true,"elem":{"schema":{"id":{"type":"TypeString","description":"ID of a version of the datastore.","computed":true},"name":{"type":"TypeString","description":"Name of a version of the datastore.","computed":true}}}},"volume_types":{"type":"TypeList","description":"Supported volume types for the datastore.","computed":true,"elem":{"type":"TypeString"}}},"description":"Use this data source to get information on a VKCS db datastore.","new_since":"v0.2.0"},"vkcs_db_datastore_capabilities":{"schema":{"capabilities":{"type":"TypeList","description":"Versions of the datastore.","computed":true,"elem":{"schema":{"allow_major_upgrade":{"type":"TypeBool","description":"This attribute indicates whether a capability can be applied in the next major version of data store.","computed":true},"allow_upgrade_from_backup":{"type":"TypeBool","description":"This attribute indicates whether a capability can be applied to upgrade from backup.","computed":true},"description":{"type":"TypeString","description":"Description of data store capability.","computed":true},"name":{"type":"TypeString","description":"Name of data store capability.","computed":true},"params":{"type":"TypeList","computed":true,"elem":{"schema":{"default_value":{"type":"TypeString","description":"Default value for a parameter.","computed":true},"element_type":{"type":"TypeString","description":"Type of element value for a parameter of ` + "`" + `list` + "`" + ` type.","computed":true},"enum_values":{"type":"TypeList","description":"Supported values for a parameter.","computed":true,"elem":{"type":"TypeString"}},"masked":{"type":"TypeBool","description":"Masked indicates whether a parameter value must be a boolean mask.","computed":true},"max":{"type":"TypeFloat","description":"Maximum value for a parameter.","computed":true},"min":{"type":"TypeFloat","description":"Minimum value for a parameter.","computed":true},"name":{"type":"TypeString","description":"Name of a parameter.","computed":true},"regex":{"type":"TypeString","description":"Regular expression that a parameter value must match.","computed":true},"required":{"type":"TypeBool","description":"Required indicates whether a parameter value must be set.","computed":true},"type":{"type":"TypeString","description":"Type of value for a parameter.","computed":true}}}},"should_be_on_master":{"type":"TypeBool","description":"This attribute indicates whether a capability applies only to the master node.","computed":true}}}},"datastore_name":{"type":"TypeString","required":true,"description":"Name of the data store."},"datastore_version_id":{"type":"TypeString","required":true,"description":"ID of the version of the data store."},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `.","computed":true}},"description":"Use this data source to get capabilities supported for a VKCS datastore.","new_since":"v0.2.0"},"vkcs_db_datastore_parameters":{"schema":{"datastore_name":{"type":"TypeString","required":true,"description":"Name of the data store."},"datastore_version_id":{"type":"TypeString","required":true,"description":"ID of the version of the data store."},"parameters":{"type":"TypeList","description":"Versions of the datastore.","computed":true,"elem":{"schema":{"max":{"type":"TypeFloat","description":"Maximum value of a configuration parameter.","computed":true},"min":{"type":"TypeFloat","description":"Minimum value of a configuration parameter.","computed":true},"name":{"type":"TypeString","description":"Name of a configuration parameter.","computed":true},"restart_required":{"type":"TypeBool","description":"This attribute indicates whether a restart required when a parameter is set.","computed":true},"type":{"type":"TypeString","description":"Type of a configuration parameter.","computed":true}}}},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `.","computed":true}},"description":"Use this data source to get configuration parameters supported for a VKCS datastore.","new_since":"v0.2.0"},"vkcs_db_datastores":{"schema":{"datastores":{"type":"TypeList","computed":true,"elem":{"schema":{"id":{"type":"TypeString","description":"The id of the datastore.","computed":true},"name":{"type":"TypeString","description":"Name of the datastore.","computed":true}}}},"region":{"type":"TypeString","optional":true,"description":"The ` + "`" + `region` + "`" + ` to fetch availability zones from, defaults to the provider's ` + "`" + `region` + "`" + `","computed":true}},"description":"Use this data source to get a list of datastores from VKCS.","new_since":"v0.2.0"},"vkcs_db_instance":{"schema":{"backup_schedule":{"type":"TypeList","optional":true,"description":"Object that represents configuration of PITR backup. This functionality is available only for postgres datastore.","elem":{"schema":{"interval_hours":{"type":"TypeInt","required":true,"description":"Time interval between backups, specified in hours. Available values: 3, 6, 8, 12, 24."},"keep_count":{"type":"TypeInt","required":true,"description":"Number of backups to be stored."},"name":{"type":"TypeString","required":true,"description":"Name of the schedule."},"start_hours":{"type":"TypeInt","required":true,"description":"Hours part of timestamp of initial backup."},"start_minutes":{"type":"TypeInt","required":true,"description":"Minutes part of timestamp of initial backup."}}},"new_since":"v0.1.4"},"datastore":{"type":"TypeList","optional":true,"description":"Object that represents datastore of the instance.","elem":{"schema":{"type":{"type":"TypeString","required":true,"description":"Type of the datastore."},"version":{"type":"TypeString","required":true,"description":"Version of the datastore."}}},"max_items":1},"flavor_id":{"type":"TypeString","optional":true,"description":"The ID of flavor for the instance."},"hostname":{"type":"TypeString","optional":true,"description":"The hostname of the instance."},"id":{"type":"TypeString","required":true,"description":"The id of the instance."},"ip":{"type":"TypeList","optional":true,"description":"IP address of the instance.","elem":{"type":"TypeString"}},"name":{"type":"TypeString","optional":true,"description":"The name of the instance."},"region":{"type":"TypeString","optional":true,"description":"Region of the resource."},"status":{"type":"TypeString","optional":true,"description":"Instance status."},"volume":{"type":"TypeSet","optional":true,"description":"Object that describes volume of the instance.","elem":{"schema":{"size":{"type":"TypeInt","required":true,"description":"Size of the instance volume."},"used":{"type":"TypeFloat","required":true,"description":"Size of the used volume space."},"volume_id":{"type":"TypeString","required":true,"description":"ID of the instance volume."},"volume_type":{"type":"TypeString","required":true,"description":"Type of the instance volume."}}},"max_items":1}},"description":"Use this data source to get the information on a db instance resource."},"vkcs_db_user":{"schema":{"databases":{"type":"TypeList","optional":true,"description":"List of names of the databases, that user is created for.","elem":{"type":"TypeString"}},"dbms_id":{"type":"TypeString","optional":true,"description":"ID of the instance or cluster that user is created for."},"host":{"type":"TypeString","optional":true,"description":"IP address of the host that user will be accessible from."},"id":{"type":"TypeString","required":true,"description":"The id of the user in form \"dbms_id/user_name\"."},"name":{"type":"TypeString","optional":true,"description":"The name of the user. Changing this creates a new user."},"password":{"type":"TypeString","optional":true,"description":"The password of the user."}},"description":"Use this data source to get the information on a db user resource."},"vkcs_images_image":{"schema":{"checksum":{"type":"TypeString","description":"The checksum of the data associated with the image.","computed":true},"container_format":{"type":"TypeString","description":"The format of the image's container.","computed":true},"created_at":{"type":"TypeString","description":"The date the image was created.","computed":true},"disk_format":{"type":"TypeString","description":"The format of the image's disk.","computed":true},"file":{"type":"TypeString","description":"The trailing path after the endpoint that represent the location of the image or the path to retrieve it.","computed":true},"member_status":{"type":"TypeString","optional":true,"description":"Status for adding a new member (tenant) to an image member list.","force_new":true},"metadata":{"type":"TypeMap","description":"The metadata associated with the image. Image metadata allow for meaningfully define the image properties and tags. See https://docs.openstack.org/glance/latest/user/metadefs-concepts.html.","computed":true},"min_disk_gb":{"type":"TypeInt","description":"The minimum amount of disk space required to use the image.","computed":true},"min_ram_mb":{"type":"TypeInt","description":"The minimum amount of ram required to use the image.","computed":true},"most_recent":{"type":"TypeBool","optional":true,"default":false,"description":"If more than one result is returned, use the most recent image.","force_new":true},"name":{"type":"TypeString","optional":true,"description":"The name of the image.","force_new":true},"owner":{"type":"TypeString","optional":true,"description":"The owner (UUID) of the image.","force_new":true},"properties":{"type":"TypeMap","optional":true,"description":"A map of key/value pairs to match an image with. All specified properties must be matched. Unlike other options filtering by ` + "`" + `properties` + "`" + ` does by client on the result of search query. Filtering is applied if server response contains at least 2 images. In case there is only one image the ` + "`" + `properties` + "`" + ` ignores.","force_new":true},"protected":{"type":"TypeBool","description":"Whether or not the image is protected.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Image client. An Image client is needed to create an Image that can be used with a compute instance. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"schema":{"type":"TypeString","description":"The path to the JSON-schema that represent the image or image","computed":true},"size_bytes":{"type":"TypeInt","description":"The size of the image (in bytes).","computed":true},"size_max":{"type":"TypeInt","optional":true,"description":"The maximum size (in bytes) of the image to return.","force_new":true},"size_min":{"type":"TypeInt","optional":true,"description":"The minimum size (in bytes) of the image to return.","force_new":true},"tag":{"type":"TypeString","optional":true,"description":"Search for images with a specific tag.","force_new":true},"tags":{"type":"TypeSet","description":"The tags list of the image.","computed":true,"elem":{"type":"TypeString"}},"updated_at":{"type":"TypeString","description":"The date the image was last updated.","computed":true},"visibility":{"type":"TypeString","optional":true,"description":"The visibility of the image. Must be one of \"private\", \"community\", or \"shared\". Defaults to \"private\".","force_new":true}},"description":"Use this data source to get the ID of an available VKCS image."},"vkcs_keymanager_container":{"schema":{"acl":{"type":"TypeList","description":"The list of ACLs assigned to a container.","computed":true,"elem":{"schema":{"read":{"type":"TypeList","optional":true,"description":"Block that describes read operation.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"project_access":{"type":"TypeBool","optional":true,"default":true,"description":"Whether the container is accessible project wide. Defaults to ` + "`" + `true` + "`" + `."},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true},"users":{"type":"TypeSet","optional":true,"description":"The list of user IDs, which are allowed to access the container, when ` + "`" + `project_access` + "`" + ` is set to ` + "`" + `false` + "`" + `.","elem":{"type":"TypeString"}}}},"max_items":1}}}},"consumers":{"type":"TypeList","description":"The list of the container consumers.","computed":true,"elem":{"schema":{"name":{"type":"TypeString","optional":true,"description":"The name of the consumer."},"url":{"type":"TypeString","optional":true,"description":"The consumer URL."}}}},"container_ref":{"type":"TypeString","description":"The container reference / where to find the container.","computed":true},"created_at":{"type":"TypeString","description":"The date the container was created.","computed":true},"creator_id":{"type":"TypeString","description":"The creator of the container.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The Container name."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the KeyManager client. A KeyManager client is needed to fetch a container. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"secret_refs":{"type":"TypeSet","description":"A set of dictionaries containing references to secrets.","computed":true,"elem":{"schema":{"name":{"type":"TypeString","optional":true},"secret_ref":{"type":"TypeString","optional":true}}}},"status":{"type":"TypeString","description":"The status of the container.","computed":true},"type":{"type":"TypeString","description":"The container type.","computed":true},"updated_at":{"type":"TypeString","description":"The date the container was last updated.","computed":true}},"description":"Use this data source to get the ID of an available Key container."},"vkcs_keymanager_secret":{"schema":{"acl":{"type":"TypeList","description":"The list of ACLs assigned to a secret.","computed":true,"elem":{"schema":{"read":{"type":"TypeList","optional":true,"description":"Block that describes read operation.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"The date the container ACL was created.","computed":true},"project_access":{"type":"TypeBool","optional":true,"default":true,"description":"Whether the container is accessible project wide. Defaults to ` + "`" + `true` + "`" + `."},"updated_at":{"type":"TypeString","description":"The date the container ACL was last updated.","computed":true},"users":{"type":"TypeSet","optional":true,"description":"The list of user IDs, which are allowed to access the container, when ` + "`" + `project_access` + "`" + ` is set to ` + "`" + `false` + "`" + `.","elem":{"type":"TypeString"}}}},"max_items":1}}}},"acl_only":{"type":"TypeBool","optional":true,"description":"Select the Secret with an ACL that contains the user. Project scope is ignored. Defaults to ` + "`" + `false` + "`" + `."},"algorithm":{"type":"TypeString","optional":true,"description":"The Secret algorithm."},"bit_length":{"type":"TypeInt","optional":true,"description":"The Secret bit length."},"content_types":{"type":"TypeMap","description":"The map of the content types, assigned on the secret.","computed":true},"created_at":{"type":"TypeString","description":"The date the secret was created.","computed":true},"created_at_filter":{"type":"TypeString","optional":true,"description":"Date filter to select the Secret with created matching the specified criteria. See Date Filters below for more detail."},"creator_id":{"type":"TypeString","description":"The creator of the secret.","computed":true},"expiration":{"type":"TypeString","description":"The date the secret will expire.","computed":true},"expiration_filter":{"type":"TypeString","optional":true,"description":"Date filter to select the Secret with expiration matching the specified criteria. See Date Filters below for more detail."},"metadata":{"type":"TypeMap","description":"The map of metadata, assigned on the secret, which has been explicitly and implicitly added.","computed":true},"mode":{"type":"TypeString","optional":true,"description":"The Secret mode."},"name":{"type":"TypeString","optional":true,"description":"The Secret name."},"payload":{"type":"TypeString","description":"The secret payload.","computed":true},"payload_content_encoding":{"type":"TypeString","description":"The Secret encoding.","computed":true},"payload_content_type":{"type":"TypeString","description":"The Secret content type.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the KeyManager client. A KeyManager client is needed to fetch a secret. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"secret_ref":{"type":"TypeString","description":"The secret reference / where to find the secret.","computed":true},"secret_type":{"type":"TypeString","optional":true,"description":"The Secret type. For more information see [Secret types](https://docs.openstack.org/barbican/latest/api/reference/secret_types.html)."},"status":{"type":"TypeString","description":"The status of the secret.","computed":true},"updated_at":{"type":"TypeString","description":"The date the secret was last updated.","computed":true},"updated_at_filter":{"type":"TypeString","optional":true,"description":"Date filter to select the Secret with updated matching the specified criteria. See Date Filters below for more detail."}},"description":"Use this data source to get the ID and the payload of an available Key secret\n\n~\u003e **Important Security Notice** The payload of this data source will be stored *unencrypted* in your Terraform state file. **Use of this resource for production deployments is *not* recommended**. [Read more about sensitive data in state](https://www.terraform.io/docs/language/state/sensitive-data.html)."},"vkcs_kubernetes_cluster":{"schema":{"api_address":{"type":"TypeString","description":"COE API address.","computed":true},"api_lb_fip":{"type":"TypeString","description":"API LoadBalancer fip.","computed":true},"api_lb_vip":{"type":"TypeString","description":"API LoadBalancer vip.","computed":true},"availability_zone":{"type":"TypeString","description":"Availability zone of the cluster.","computed":true},"cluster_id":{"type":"TypeString","optional":true,"description":"The UUID of the Kubernetes cluster template. **Note**: Only one of ` + "`" + `name` + "`" + ` or ` + "`" + `cluster_id` + "`" + ` must be specified.","computed":true},"cluster_template_id":{"type":"TypeString","description":"The UUID of the V1 Container Infra cluster template.","computed":true},"created_at":{"type":"TypeString","description":"The time at which cluster was created.","computed":true},"discovery_url":{"type":"TypeString","description":"The URL used for cluster node discovery.","computed":true},"dns_domain":{"type":"TypeString","optional":true,"description":"Custom DNS cluster domain.","computed":true},"floating_ip_enabled":{"type":"TypeBool","description":"Indicates whether floating ip is enabled for cluster.","computed":true},"ingress_floating_ip":{"type":"TypeString","description":"Floating IP created for ingress service.","computed":true},"insecure_registries":{"type":"TypeList","description":"Addresses of registries from which you can download images without checking certificates.","computed":true,"elem":{"type":"TypeString"}},"k8s_config":{"type":"TypeString","description":"Kubeconfig for cluster","computed":true},"keypair":{"type":"TypeString","description":"The name of the Compute service SSH keypair.","computed":true},"labels":{"type":"TypeMap","description":"The list of key value pairs representing additional properties of the cluster.","computed":true},"loadbalancer_subnet_id":{"type":"TypeString","description":"The ID of load balancer's subnet.","computed":true},"master_addresses":{"type":"TypeList","description":"IP addresses of the master node of the cluster.","computed":true,"elem":{"type":"TypeString"}},"master_count":{"type":"TypeInt","description":"The number of master nodes for the cluster.","computed":true},"master_flavor":{"type":"TypeString","description":"The ID of the flavor for the master nodes.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the cluster. **Note**: Only one of ` + "`" + `name` + "`" + ` or ` + "`" + `cluster_id` + "`" + ` must be specified.","computed":true},"network_id":{"type":"TypeString","description":"UUID of the cluster's network.","computed":true},"pods_network_cidr":{"type":"TypeString","description":"Network cidr of k8s virtual network.","computed":true},"project_id":{"type":"TypeString","description":"The project of the cluster.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Container Infra client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"registry_auth_password":{"type":"TypeString","description":"Docker registry access password.","computed":true},"stack_id":{"type":"TypeString","description":"UUID of the Orchestration service stack.","computed":true},"status":{"type":"TypeString","description":"Current state of a cluster.","computed":true},"subnet_id":{"type":"TypeString","description":"UUID of the cluster's subnet.","computed":true},"updated_at":{"type":"TypeString","description":"The time at which cluster was created.","computed":true},"user_id":{"type":"TypeString","description":"The user of the cluster.","computed":true}},"description":"Use this data source to get the ID of an available VKCS kubernetes cluster."},"vkcs_kubernetes_clustertemplate":{"schema":{"apiserver_port":{"type":"TypeInt","description":"The API server port for the Container Orchestration Engine for this cluster template.","computed":true},"cluster_distro":{"type":"TypeString","description":"The distro for the cluster (fedora-atomic, coreos, etc.).","computed":true},"cluster_template_uuid":{"type":"TypeString","optional":true,"description":"The UUID of the cluster template. **Note**: Only one of ` + "`" + `name` + "`" + ` or ` + "`" + `version` + "`" + ` or ` + "`" + `cluster_template_uuid` + "`" + ` must be specified.","computed":true},"created_at":{"type":"TypeString","description":"The time at which cluster template was created.","computed":true},"deprecated_at":{"type":"TypeString","description":"The time at which the cluster template is deprecated.","computed":true},"dns_nameserver":{"type":"TypeString","description":"Address of the DNS nameserver that is used in nodes of the cluster.","computed":true},"docker_storage_driver":{"type":"TypeString","description":"Docker storage driver. Changing this updates the Docker storage driver of the existing cluster template.","computed":true},"docker_volume_size":{"type":"TypeInt","description":"The size (in GB) of the Docker volume.","computed":true},"external_network_id":{"type":"TypeString","description":"The ID of the external network that will be used for the cluster.","computed":true},"flavor":{"type":"TypeString","description":"The ID of flavor for the nodes of the cluster.","computed":true},"floating_ip_enabled":{"type":"TypeBool","description":"Indicates whether created cluster should create IP floating IP for every node or not.","computed":true},"image":{"type":"TypeString","description":"The reference to an image that is used for nodes of the cluster.","computed":true},"insecure_registry":{"type":"TypeString","description":"The insecure registry URL for the cluster template.","computed":true},"keypair_id":{"type":"TypeString","description":"The name of the Compute service SSH keypair.","computed":true},"labels":{"type":"TypeMap","description":"The list of key value pairs representing additional properties of the cluster template.","computed":true},"master_flavor":{"type":"TypeString","description":"The ID of flavor for the master nodes.","computed":true},"master_lb_enabled":{"type":"TypeBool","description":"Indicates whether created cluster should has a loadbalancer for master nodes or not.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the cluster template. **Note**: Only one of ` + "`" + `name` + "`" + ` or ` + "`" + `version` + "`" + ` or ` + "`" + `cluster_template_uuid` + "`" + ` must be specified.","computed":true},"network_driver":{"type":"TypeString","description":"The name of the driver for the container network.","computed":true},"no_proxy":{"type":"TypeString","description":"A comma-separated list of IP addresses that shouldn't be used in the cluster.","computed":true},"project_id":{"type":"TypeString","description":"The project of the cluster template.","computed":true},"public":{"type":"TypeBool","description":"Indicates whether cluster template should be public.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V1 Container Infra client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"registry_enabled":{"type":"TypeBool","description":"Indicates whether Docker registry is enabled in the cluster.","computed":true},"server_type":{"type":"TypeString","description":"The server type for the cluster template.","computed":true},"tls_disabled":{"type":"TypeBool","description":"Indicates whether the TLS should be disabled in the cluster.","computed":true},"updated_at":{"type":"TypeString","description":"The time at which cluster template was updated.","computed":true},"user_id":{"type":"TypeString","description":"The user of the cluster template.","computed":true},"version":{"type":"TypeString","optional":true,"description":"Kubernetes version of the cluster.","computed":true},"volume_driver":{"type":"TypeString","description":"The name of the driver that is used for the volumes of the cluster nodes.","computed":true}},"description":"Use this data source to get the ID of an available VKCS kubernetes cluster template."},"vkcs_kubernetes_clustertemplates":{"schema":{"cluster_templates":{"type":"TypeList","description":"A list of available kubernetes cluster templates.\n - ` + "`" + `cluster_template_uuid` + "`" + ` **String** The UUID of the cluster template.\n\n - ` + "`" + `name` + "`" + ` **String** The name of the cluster template.\n\n - ` + "`" + `version` + "`" + ` **String** The version of the cluster template.","computed":true,"elem":{"schema":{"cluster_template_uuid":{"type":"TypeString","required":true,"description":"The UUID of the cluster template."},"name":{"type":"TypeString","required":true,"description":"The name of the cluster template."},"version":{"type":"TypeString","required":true,"description":"The version of the cluster template."}}}},"id":{"type":"TypeString","description":"Random identifier of the data source.","computed":true}},"description":"` + "`" + `vkcs_kubernetes_cluster_templates` + "`" + ` returns list of available VKCS Kubernetes Cluster Templates. To get details of each cluster template the data source can be combined with the ` + "`" + `vkcs_kubernetes_clustertemplate` + "`" + ` data source."},"vkcs_kubernetes_node_group":{"schema":{"autoscaling_enabled":{"type":"TypeBool","optional":true,"description":"Determines whether the autoscaling is enabled."},"availability_zones":{"type":"TypeList","description":"The list of availability zones of the node group.","computed":true,"elem":{"type":"TypeString"}},"cluster_id":{"type":"TypeString","description":"The UUID of cluster that node group belongs.","computed":true},"flavor_id":{"type":"TypeString","optional":true,"description":"The id of flavor."},"max_node_unavailable":{"type":"TypeInt","optional":true,"description":"Specified as a percentage. The maximum number of nodes that can fail during an upgrade.","computed":true},"max_nodes":{"type":"TypeInt","optional":true,"description":"The maximum amount of nodes in node group."},"min_nodes":{"type":"TypeInt","optional":true,"description":"The minimum amount of nodes in node group."},"name":{"type":"TypeString","optional":true,"description":"The name of the node group.","computed":true},"node_count":{"type":"TypeInt","optional":true,"description":"The count of nodes in node group."},"nodes":{"type":"TypeList","description":"The list of node group's node objects.","computed":true,"elem":{"schema":{"created_at":{"type":"TypeString","description":"Time when node was created.","computed":true},"name":{"type":"TypeString","description":"The name of the node.","computed":true},"node_group_id":{"type":"TypeString","description":"The node group id","computed":true},"updated_at":{"type":"TypeString","description":"Time when node was updated.","computed":true},"uuid":{"type":"TypeString","description":"The UUID of node.","computed":true}}}},"state":{"type":"TypeString","description":"Determines current state of node group (RUNNING, SHUTOFF, ERROR).","computed":true},"uuid":{"type":"TypeString","required":true,"description":"The UUID of the cluster's node group."},"volume_size":{"type":"TypeInt","optional":true,"description":"The amount of memory of volume in Gb."},"volume_type":{"type":"TypeString","optional":true,"description":"The type of volume."}},"description":"Use this data source to get the ID of an available VKCS kubernetes clusters node group."},"vkcs_lb_loadbalancer":{"schema":{"admin_state_up":{"type":"TypeBool","description":"The administrative state of the Loadbalancer.","computed":true},"availability_zone":{"type":"TypeString","description":"The availability zone of the Loadbalancer.","computed":true},"description":{"type":"TypeString","description":"Human-readable description of the Loadbalancer.","computed":true},"id":{"type":"TypeString","required":true,"description":"The UUID of the Loadbalancer"},"name":{"type":"TypeString","description":"The name of the Loadbalancer.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Loadbalancer client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"security_group_ids":{"type":"TypeSet","description":"A list of security group IDs applied to the Loadbalancer.","computed":true,"elem":{"type":"TypeString"}},"tags":{"type":"TypeSet","description":"A list of simple strings assigned to the loadbalancer.","computed":true,"elem":{"type":"TypeString"}},"vip_address":{"type":"TypeString","description":"The ip address of the Loadbalancer.","computed":true},"vip_network_id":{"type":"TypeString","description":"The network on which to allocate the Loadbalancer's address. A tenant can only create Loadbalancers on networks authorized by policy (e.g. networks that belong to them or networks that are shared). Changing this creates a new loadbalancer.","computed":true},"vip_port_id":{"type":"TypeString","description":"The port UUID of the Loadbalancer.","computed":true},"vip_subnet_id":{"type":"TypeString","description":"The subnet on which the Loadbalancer's address is allocated.","computed":true}},"description":"Use this data source to get the details of a loadbalancer"},"vkcs_networking_floatingip":{"schema":{"address":{"type":"TypeString","optional":true,"description":"The IP address of the floating IP."},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the floating IP."},"fixed_ip":{"type":"TypeString","optional":true,"description":"The specific IP address of the internal port which should be associated with the floating IP."},"id":{"type":"TypeString","description":"ID of the found floating IP.","computed":true},"pool":{"type":"TypeString","optional":true,"description":"The name of the pool from which the floating IP belongs to."},"port_id":{"type":"TypeString","optional":true,"description":"The ID of the port the floating IP is attached."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve floating IP ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"status":{"type":"TypeString","optional":true,"description":"Status of the floating IP (ACTIVE/DOWN)."},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the floating IP."}},"description":"Use this data source to get the ID of an available VKCS floating IP."},"vkcs_networking_network":{"schema":{"admin_state_up":{"type":"TypeString","description":"The administrative state of the network.","computed":true},"all_tags":{"type":"TypeSet","description":"The set of string tags applied on the network.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the network."},"external":{"type":"TypeBool","optional":true,"description":"The external routing facility of the network."},"id":{"type":"TypeString","description":"ID of the found network.","computed":true},"matching_subnet_cidr":{"type":"TypeString","optional":true,"description":"The CIDR of a subnet within the network."},"name":{"type":"TypeString","optional":true,"description":"The name of the network."},"network_id":{"type":"TypeString","optional":true,"description":"The ID of the network."},"private_dns_domain":{"type":"TypeString","description":"Private dns domain name","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve networks ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"shared":{"type":"TypeString","description":"Specifies whether the network resource can be accessed by any tenant or not.","computed":true},"status":{"type":"TypeString","optional":true,"description":"The status of the network."},"subnets":{"type":"TypeList","description":"A list of subnet IDs belonging to the network.","computed":true,"elem":{"type":"TypeString"}},"tags":{"type":"TypeSet","optional":true,"description":"The list of network tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the network."},"vkcs_services_access":{"type":"TypeBool","optional":true,"description":"Specifies whether VKCS services access is enabled."}},"description":"Use this data source to get the ID of an available VKCS network."},"vkcs_networking_port":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"description":"The administrative state of the port."},"all_fixed_ips":{"type":"TypeList","description":"The collection of Fixed IP addresses on the port in the order returned by the Network v2 API.","computed":true,"elem":{"type":"TypeString"}},"all_security_group_ids":{"type":"TypeSet","description":"The set of security group IDs applied on the port.","computed":true,"elem":{"type":"TypeString"}},"all_tags":{"type":"TypeSet","description":"The set of string tags applied on the port.","computed":true,"elem":{"type":"TypeString"}},"allowed_address_pairs":{"type":"TypeSet","description":"An IP/MAC Address pair of additional IP addresses that can be active on this port. The structure is described below.","computed":true,"elem":{"schema":{"ip_address":{"type":"TypeString","description":"The additional IP address.","computed":true},"mac_address":{"type":"TypeString","description":"The additional MAC address.","computed":true}}}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the port."},"device_id":{"type":"TypeString","optional":true,"description":"The ID of the device the port belongs to."},"device_owner":{"type":"TypeString","optional":true,"description":"The device owner of the port."},"dns_assignment":{"type":"TypeList","description":"The list of maps representing port DNS assignments.","computed":true,"elem":{"type":"TypeMap"}},"dns_name":{"type":"TypeString","optional":true,"description":"The port DNS name to filter."},"extra_dhcp_option":{"type":"TypeList","description":"An extra DHCP option configured on the port. The structure is described below.","computed":true,"elem":{"schema":{"name":{"type":"TypeString","description":"Name of the DHCP option.","computed":true},"value":{"type":"TypeString","description":"Value of the DHCP option.","computed":true}}}},"fixed_ip":{"type":"TypeString","optional":true,"description":"The port IP address filter."},"id":{"type":"TypeString","description":"ID of the found port.","computed":true},"mac_address":{"type":"TypeString","optional":true,"description":"The MAC address of the port."},"name":{"type":"TypeString","optional":true,"description":"The name of the port."},"network_id":{"type":"TypeString","optional":true,"description":"The ID of the network the port belongs to."},"port_id":{"type":"TypeString","optional":true,"description":"The ID of the port."},"project_id":{"type":"TypeString","optional":true,"description":"The project_id of the owner of the port."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve port ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"security_group_ids":{"type":"TypeSet","optional":true,"description":"The list of port security group IDs to filter.","elem":{"type":"TypeString"}},"status":{"type":"TypeString","optional":true,"description":"The status of the port.","force_new":true},"tags":{"type":"TypeSet","optional":true,"description":"The list of port tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The tenant_id of the owner of the port."}},"description":"Use this data source to get the ID of an available VKCS port."},"vkcs_networking_router":{"schema":{"admin_state_up":{"type":"TypeBool","optional":true,"description":"Administrative up/down status for the router (must be \"true\" or \"false\" if provided)."},"all_tags":{"type":"TypeSet","description":"The set of string tags applied on the router.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the router."},"enable_snat":{"type":"TypeBool","optional":true,"description":"The value that points out if the Source NAT is enabled on the router.","computed":true},"external_network_id":{"type":"TypeString","description":"The network UUID of an external gateway for the router.","computed":true},"id":{"type":"TypeString","description":"ID of the found router.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the router."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve router ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used."},"router_id":{"type":"TypeString","optional":true,"description":"The UUID of the router resource."},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"status":{"type":"TypeString","optional":true,"description":"The status of the router (ACTIVE/DOWN)."},"tags":{"type":"TypeSet","optional":true,"description":"The list of router tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the router."}},"description":"Use this data source to get the ID of an available VKCS router."},"vkcs_networking_secgroup":{"schema":{"all_tags":{"type":"TypeSet","description":"The set of string tags applied on the security group.","computed":true,"elem":{"type":"TypeString"}},"description":{"type":"TypeString","optional":true,"description":"Human-readable description the the subnet."},"id":{"type":"TypeString","description":"ID of the found security group.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the security group."},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve security groups ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"secgroup_id":{"type":"TypeString","optional":true,"description":"The ID of the security group."},"tags":{"type":"TypeSet","optional":true,"description":"The list of security group tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the security group.","computed":true,"force_new":true}},"description":"Use this data source to get the ID of an available VKCS security group."},"vkcs_networking_subnet":{"schema":{"all_tags":{"type":"TypeSet","description":"A set of string tags applied on the subnet.","computed":true,"elem":{"type":"TypeString"}},"allocation_pools":{"type":"TypeList","description":"Allocation pools of the subnet.","computed":true,"elem":{"schema":{"end":{"type":"TypeString","description":"The ending address.","computed":true},"start":{"type":"TypeString","description":"The starting address.","computed":true}}}},"cidr":{"type":"TypeString","optional":true,"description":"The CIDR of the subnet.","computed":true},"description":{"type":"TypeString","optional":true,"description":"Human-readable description of the subnet.","computed":true},"dhcp_enabled":{"type":"TypeBool","optional":true,"description":"If the subnet has DHCP enabled."},"dns_nameservers":{"type":"TypeSet","description":"DNS Nameservers of the subnet.","computed":true,"elem":{"type":"TypeString"}},"enable_dhcp":{"type":"TypeBool","description":"Whether the subnet has DHCP enabled or not.","computed":true},"gateway_ip":{"type":"TypeString","optional":true,"description":"The IP of the subnet's gateway.","computed":true},"host_routes":{"type":"TypeList","description":"Host Routes of the subnet.","computed":true,"elem":{"schema":{"destination_cidr":{"type":"TypeString","computed":true},"next_hop":{"type":"TypeString","computed":true}}}},"id":{"type":"TypeString","description":"ID of the found subnet.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the subnet.","computed":true},"network_id":{"type":"TypeString","optional":true,"description":"The ID of the network the subnet belongs to.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Network client. A Network client is needed to retrieve subnet ids. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true,"force_new":true},"sdn":{"type":"TypeString","optional":true,"description":"SDN to use for this resource. Must be one of following: \"neutron\", \"sprut\". Default value is \"neutron\"."},"subnet_id":{"type":"TypeString","optional":true,"description":"The ID of the subnet.","computed":true},"subnetpool_id":{"type":"TypeString","optional":true,"description":"The ID of the subnetpool associated with the subnet.","computed":true},"tags":{"type":"TypeSet","optional":true,"description":"The list of subnet tags to filter.","elem":{"type":"TypeString"}},"tenant_id":{"type":"TypeString","optional":true,"description":"The owner of the subnet.","computed":true}},"description":"Use this data source to get the ID of an available VKCS subnet."},"vkcs_publicdns_zone":{"schema":{"admin_email":{"type":"TypeString","optional":true,"description":"The admin email of the zone SOA.","computed":true},"expire":{"type":"TypeInt","optional":true,"description":"The expire time of the zone SOA.","computed":true},"id":{"type":"TypeString","optional":true,"description":"The UUID of the DNS zone.","computed":true},"primary_dns":{"type":"TypeString","optional":true,"description":"The primary DNS of the zone SOA.","computed":true},"refresh":{"type":"TypeInt","optional":true,"description":"The refresh time of the zone SOA.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the V2 Public DNS client. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"retry":{"type":"TypeInt","optional":true,"description":"The retry time of the zone SOA.","computed":true},"serial":{"type":"TypeInt","optional":true,"description":"The serial number of the zone SOA.","computed":true},"status":{"type":"TypeString","optional":true,"description":"The status of the zone.","computed":true},"ttl":{"type":"TypeInt","optional":true,"description":"The TTL (time to live) of the zone SOA.","computed":true},"zone":{"type":"TypeString","optional":true,"description":"The name of the zone.","computed":true}},"description":"Use this data source to get the ID of a VKCS public DNS zone.","new_since":"v0.2.0"},"vkcs_region":{"schema":{"description":{"type":"TypeString","description":"Description of the region.","computed":true},"id":{"type":"TypeString","optional":true,"description":"ID of the region to learn or use. Use empty value to learn current region on the provider."},"parent_region":{"type":"TypeString","description":"Parent of the region.","computed":true}},"description":"` + "`" + `vkcs_region` + "`" + ` provides details about a specific VKCS region. As well as validating a given region name this resource can be used to discover the name of the region configured within the provider."},"vkcs_regions":{"schema":{"id":{"type":"TypeString","description":"Random identifier of the data source.","computed":true},"names":{"type":"TypeSet","description":"Names of regions that meets the criteria.","computed":true,"elem":{"type":"TypeString"}}},"description":"` + "`" + `vkcs_regions` + "`" + ` provides information about VKCS regions. To get details of each region the data source can be combined with the ` + "`" + `vkcs_region` + "`" + ` data source."},"vkcs_sharedfilesystem_share":{"schema":{"availability_zone":{"type":"TypeString","description":"The share availability zone.","computed":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description for the share.","computed":true},"export_location_path":{"type":"TypeString","optional":true,"description":"The export location path of the share.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the share.","computed":true},"project_id":{"type":"TypeString","description":"The owner of the share.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client.","computed":true},"share_network_id":{"type":"TypeString","required":true,"description":"The UUID of the share's share network."},"share_proto":{"type":"TypeString","description":"The share protocol.","computed":true},"size":{"type":"TypeInt","description":"The share size, in GBs.","computed":true},"snapshot_id":{"type":"TypeString","optional":true,"description":"The UUID of the share's base snapshot.","computed":true},"status":{"type":"TypeString","optional":true,"description":"A share status filter. A valid value is ` + "`" + `creating` + "`" + `, ` + "`" + `error` + "`" + `, ` + "`" + `available` + "`" + `, ` + "`" + `deleting` + "`" + `, ` + "`" + `error_deleting` + "`" + `, ` + "`" + `manage_starting` + "`" + `, ` + "`" + `manage_error` + "`" + `, ` + "`" + `unmanage_starting` + "`" + `, ` + "`" + `unmanage_error` + "`" + `, ` + "`" + `unmanaged` + "`" + `, ` + "`" + `extending` + "`" + `, ` + "`" + `extending_error` + "`" + `, ` + "`" + `shrinking` + "`" + `, ` + "`" + `shrinking_error` + "`" + `, or ` + "`" + `shrinking_possible_data_loss_error` + "`" + `.","computed":true}},"description":"Use this data source to get the ID of an available Shared File System share."},"vkcs_sharedfilesystem_sharenetwork":{"schema":{"cidr":{"type":"TypeString","description":"The share network CIDR.","computed":true},"description":{"type":"TypeString","optional":true,"description":"The human-readable description of the share network.","computed":true},"name":{"type":"TypeString","optional":true,"description":"The name of the share network.","computed":true},"neutron_net_id":{"type":"TypeString","optional":true,"description":"The neutron network UUID of the share network.","computed":true},"neutron_subnet_id":{"type":"TypeString","optional":true,"description":"The neutron subnet UUID of the share network.","computed":true},"project_id":{"type":"TypeString","description":"The owner of the share network.","computed":true},"region":{"type":"TypeString","optional":true,"description":"The region in which to obtain the Shared File System client. A Shared File System client is needed to read a share network. If omitted, the ` + "`" + `region` + "`" + ` argument of the provider is used.","computed":true},"security_service_id":{"type":"TypeString","optional":true,"description":"The security service IDs associated with the share network.","elem":{"type":"TypeString"}},"security_service_ids":{"type":"TypeSet","description":"The list of security service IDs associated with the share network.","computed":true,"elem":{"type":"TypeString"}}},"description":"Use this data source to get the ID of an available Shared File System share network."}}}}` diff --git a/vkcs/internal/providerwrapper/schema_base_gen.go b/vkcs/internal/providerwrapper/schema_base_gen.go new file mode 100644 index 00000000..2051fbdc --- /dev/null +++ b/vkcs/internal/providerwrapper/schema_base_gen.go @@ -0,0 +1,3 @@ +package providerwrapper + +//go:generate go run ../generate/providerschema/main.go -package providerwrapper -schemajson ../../../.release/provider-schema.json diff --git a/vkcs/internal/providerwrapper/sdk/wrapper_provider.go b/vkcs/internal/providerwrapper/sdk/wrapper_provider.go new file mode 100644 index 00000000..7740dff5 --- /dev/null +++ b/vkcs/internal/providerwrapper/sdk/wrapper_provider.go @@ -0,0 +1,91 @@ +package sdk + +import ( + "encoding/json" + "fmt" + "strings" + + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" + jsonschema "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson/schema" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/providerwrapper" +) + +func WrapProvider(p *schema.Provider) (*schema.Provider, error) { + var wrapperJSON jsonschema.ProviderWrapper + err := json.Unmarshal([]byte(providerwrapper.ProviderSchemaJSON), &wrapperJSON) + if err != nil { + return nil, err + } + + providerJSON := wrapperJSON.ProviderSchema + + for name, rs := range p.ResourcesMap { + rsJSON := providerJSON.ResourcesMap[name] + + if rs.DeprecationMessage != "" && !strings.Contains(strings.ToLower(rs.Description), "deprecated") { + rs.Description += fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(rs.DeprecationMessage, ".")) + } + + if rs.DeprecationMessage == "" && rsJSON.NewSince != "" { + rs.Description += fmt.Sprintf(" **New since %s**.", rsJSON.NewSince) + } + + for propertyName, propertySchema := range rs.Schema { + // Get the same from the base json + propertyJSON := rsJSON.Schema[propertyName] + customizeSchema(propertyJSON, propertySchema, propertyName) + } + } + + for name, ds := range p.DataSourcesMap { + dsJSON := providerJSON.DataSourcesMap[name] + + if ds.DeprecationMessage != "" && !strings.Contains(strings.ToLower(ds.Description), "deprecated") { + ds.Description += fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(ds.DeprecationMessage, ".")) + } + + if ds.DeprecationMessage == "" && dsJSON.NewSince != "" { + ds.Description += fmt.Sprintf(" **New since %s**.", dsJSON.NewSince) + } + + for propertyName, propertySchema := range ds.Schema { + // Get the same from the base json + propertyJSON := dsJSON.Schema[propertyName] + customizeSchema(propertyJSON, propertySchema, propertyName) + } + } + + return p, nil +} + +func customizeSchema(sJSON jsonschema.SchemaJSON, s *schema.Schema, nodeName string) { + if s.Deprecated != "" && !strings.Contains(strings.ToLower(s.Description), "deprecated") { + s.Description += fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(s.Deprecated, ".")) + } + + if s.Deprecated == "" && sJSON.NewSince != "" { + s.Description += fmt.Sprintf(" **New since %s**.", sJSON.NewSince) + } + + if nodeIsBlock(s) { + current := s.Elem.(*schema.Resource).Schema + var base map[string]jsonschema.SchemaJSON + if jsonschema.NodeIsBlock(sJSON) { + base = sJSON.Elem.(jsonschema.ResourceJSON).Schema + } + for k, c := range current { + b := base[k] + customizeSchema(b, c, k) + } + } +} + +func nodeIsBlock(input *schema.Schema) bool { + if input.Type == schema.TypeList || input.Type == schema.TypeSet { + if _, ok := input.Elem.(*schema.Resource); ok { + return true + } + } + + return false +} diff --git a/vkcs/internal/util/util.go b/vkcs/internal/util/util.go index 0e4d0c7c..cc4dc783 100755 --- a/vkcs/internal/util/util.go +++ b/vkcs/internal/util/util.go @@ -1,13 +1,16 @@ package util import ( + "context" "fmt" "reflect" "strings" "time" "github.com/gophercloud/gophercloud" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/path" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/mitchellh/mapstructure" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -81,6 +84,19 @@ func CheckDeleted(d *schema.ResourceData, err error, msg string) error { return fmt.Errorf("%s %s: %s", msg, d.Id(), err) } +// checkDeletedDatasource checks the error to see if it's a 404 (Not Found) and, if so, +// sets the resource ID to the empty string instead of throwing an error. +func CheckDeletedDatasource(ctx context.Context, r *datasource.ReadResponse, err error) error { + if _, ok := err.(gophercloud.ErrDefault404); ok { + r.State.SetAttribute(ctx, path.Root("id"), "") + return nil + } + var id string + r.State.GetAttribute(ctx, path.Root("id"), &id) + + return fmt.Errorf("%s: %s", id, err) +} + func CheckAlreadyExists(err error, msg, resourceName, conflict string) error { if _, ok := err.(gophercloud.ErrDefault409); ok { return fmt.Errorf("%s: %s with %s already exists", msg, resourceName, conflict) @@ -122,22 +138,22 @@ func MapValueSpecs(d *schema.ResourceData) map[string]string { return m } -func CheckForRetryableError(err error) *resource.RetryError { +func CheckForRetryableError(err error) *retry.RetryError { switch e := err.(type) { case gophercloud.ErrDefault500: - return resource.RetryableError(err) + return retry.RetryableError(err) case gophercloud.ErrDefault409: - return resource.RetryableError(err) + return retry.RetryableError(err) case gophercloud.ErrDefault503: - return resource.RetryableError(err) + return retry.RetryableError(err) case gophercloud.ErrUnexpectedResponseCode: if e.GetStatusCode() == 504 || e.GetStatusCode() == 502 { - return resource.RetryableError(err) + return retry.RetryableError(err) } else { - return resource.NonRetryableError(err) + return retry.NonRetryableError(err) } default: - return resource.NonRetryableError(err) + return retry.NonRetryableError(err) } } diff --git a/vkcs/keymanager/data_source_vkcs_keymanager_container_test.go b/vkcs/keymanager/data_source_vkcs_keymanager_container_test.go index 80fa22dd..2ad369dc 100644 --- a/vkcs/keymanager/data_source_vkcs_keymanager_container_test.go +++ b/vkcs/keymanager/data_source_vkcs_keymanager_container_test.go @@ -3,7 +3,7 @@ package keymanager_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/keymanager/data_source_vkcs_keymanager_secret_test.go b/vkcs/keymanager/data_source_vkcs_keymanager_secret_test.go index 2ca090ea..bc209238 100644 --- a/vkcs/keymanager/data_source_vkcs_keymanager_secret_test.go +++ b/vkcs/keymanager/data_source_vkcs_keymanager_secret_test.go @@ -3,7 +3,7 @@ package keymanager_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/keymanager/import_vkcs_keymanager_container_test.go b/vkcs/keymanager/import_vkcs_keymanager_container_test.go index 136fbbe3..b9d0455a 100644 --- a/vkcs/keymanager/import_vkcs_keymanager_container_test.go +++ b/vkcs/keymanager/import_vkcs_keymanager_container_test.go @@ -3,7 +3,7 @@ package keymanager_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/keymanager/import_vkcs_keymanager_secret_test.go b/vkcs/keymanager/import_vkcs_keymanager_secret_test.go index 4d265b84..a4a346d2 100644 --- a/vkcs/keymanager/import_vkcs_keymanager_secret_test.go +++ b/vkcs/keymanager/import_vkcs_keymanager_secret_test.go @@ -3,7 +3,7 @@ package keymanager_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/keymanager/keymanager_container.go b/vkcs/keymanager/keymanager_container.go index 0f07b5fe..701638c4 100644 --- a/vkcs/keymanager/keymanager_container.go +++ b/vkcs/keymanager/keymanager_container.go @@ -4,14 +4,14 @@ import ( "fmt" "strings" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/keymanager/v1/containers" ) -func keyManagerContainerWaitForContainerDeletion(kmClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func keyManagerContainerWaitForContainerDeletion(kmClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { err := containers.Delete(kmClient, id).Err if err == nil { @@ -41,7 +41,7 @@ func keyManagerContainerType(v string) containers.ContainerType { return ctype } -func keyManagerContainerWaitForContainerCreation(kmClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func keyManagerContainerWaitForContainerCreation(kmClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { container, err := containers.Get(kmClient, id).Extract() if err != nil { diff --git a/vkcs/keymanager/keymanager_secret.go b/vkcs/keymanager/keymanager_secret.go index 2a1f95e2..734afd81 100644 --- a/vkcs/keymanager/keymanager_secret.go +++ b/vkcs/keymanager/keymanager_secret.go @@ -6,14 +6,14 @@ import ( "log" "strings" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/keymanager/v1/secrets" ) -func keyManagerSecretWaitForSecretDeletion(kmClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func keyManagerSecretWaitForSecretDeletion(kmClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { err := secrets.Delete(kmClient, id).Err if err == nil { @@ -48,7 +48,7 @@ func keyManagerSecretSecretType(v string) secrets.SecretType { return stype } -func keyManagerSecretWaitForSecretCreation(kmClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func keyManagerSecretWaitForSecretCreation(kmClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { secret, err := secrets.Get(kmClient, id).Extract() if err != nil { @@ -83,7 +83,7 @@ func flattenKeyManagerSecretMetadata(d *schema.ResourceData) map[string]string { return m } -func keyManagerSecretMetadataV1WaitForSecretMetadataCreation(kmClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func keyManagerSecretMetadataV1WaitForSecretMetadataCreation(kmClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { metadata, err := secrets.GetMetadata(kmClient, id).Extract() if err != nil { diff --git a/vkcs/keymanager/resource_vkcs_keymanager_container.go b/vkcs/keymanager/resource_vkcs_keymanager_container.go index 84bce10c..5e16bcc9 100644 --- a/vkcs/keymanager/resource_vkcs_keymanager_container.go +++ b/vkcs/keymanager/resource_vkcs_keymanager_container.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -178,7 +178,7 @@ func resourceKeyManagerContainerCreate(ctx context.Context, d *schema.ResourceDa uuid := keyManagerContainerGetUUIDfromContainerRef(container.ContainerRef) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING"}, Target: []string{"ACTIVE"}, Refresh: keyManagerContainerWaitForContainerCreation(kmClient, uuid), @@ -278,7 +278,7 @@ func resourceKeyManagerContainerDelete(ctx context.Context, d *schema.ResourceDa return diag.Errorf("Error creating VKCS keymanager client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING"}, Target: []string{"DELETED"}, Refresh: keyManagerContainerWaitForContainerDeletion(kmClient, d.Id()), diff --git a/vkcs/keymanager/resource_vkcs_keymanager_container_test.go b/vkcs/keymanager/resource_vkcs_keymanager_container_test.go index 6122393b..d747e677 100644 --- a/vkcs/keymanager/resource_vkcs_keymanager_container_test.go +++ b/vkcs/keymanager/resource_vkcs_keymanager_container_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/keymanager/resource_vkcs_keymanager_secret.go b/vkcs/keymanager/resource_vkcs_keymanager_secret.go index 016c1825..5a32be2a 100644 --- a/vkcs/keymanager/resource_vkcs_keymanager_secret.go +++ b/vkcs/keymanager/resource_vkcs_keymanager_secret.go @@ -9,7 +9,7 @@ import ( "github.com/hashicorp/terraform-plugin-sdk/v2/diag" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/customdiff" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -240,7 +240,7 @@ func resourceKeyManagerSecretCreate(ctx context.Context, d *schema.ResourceData, uuid := KeyManagerSecretGetUUIDfromSecretRef(secret.SecretRef) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING"}, Target: []string{"ACTIVE"}, Refresh: keyManagerSecretWaitForSecretCreation(kmClient, uuid), @@ -297,7 +297,7 @@ func resourceKeyManagerSecretCreate(ctx context.Context, d *schema.ResourceData, return diag.Errorf("Error creating metadata for vkcs_keymanager_secret with ID %s: %s", uuid, err) } - stateConf = &resource.StateChangeConf{ + stateConf = &retry.StateChangeConf{ Pending: []string{"PENDING"}, Target: []string{"ACTIVE"}, Refresh: keyManagerSecretMetadataV1WaitForSecretMetadataCreation(kmClient, uuid), @@ -466,7 +466,7 @@ func resourceKeyManagerSecretDelete(ctx context.Context, d *schema.ResourceData, return diag.Errorf("Error creating VKCS keymanager client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING"}, Target: []string{"DELETED"}, Refresh: keyManagerSecretWaitForSecretDeletion(kmClient, d.Id()), diff --git a/vkcs/keymanager/resource_vkcs_keymanager_secret_test.go b/vkcs/keymanager/resource_vkcs_keymanager_secret_test.go index 832d6e4d..9293cc43 100644 --- a/vkcs/keymanager/resource_vkcs_keymanager_secret_test.go +++ b/vkcs/keymanager/resource_vkcs_keymanager_secret_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/keymanager" diff --git a/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_template_test.go b/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_template_test.go index 9ebfa7c1..4d936016 100755 --- a/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_template_test.go +++ b/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_template_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_templates_test.go b/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_templates_test.go index 5337351e..bc8610b6 100755 --- a/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_templates_test.go +++ b/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_templates_test.go @@ -5,8 +5,8 @@ import ( "strconv" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_test.go b/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_test.go index df0d99f0..b94cbf5a 100755 --- a/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_test.go +++ b/vkcs/kubernetes/data_source_vkcs_kubernetes_cluster_test.go @@ -4,15 +4,15 @@ import ( "fmt" "testing" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) func TestAccKubernetesClusterDataSourceBasic(t *testing.T) { - var clusterName = "testcluster" + sdk_acctest.RandStringFromCharSet(8, sdk_acctest.CharSetAlphaNum) + var clusterName = "testcluster" + fm_acctest.RandStringFromCharSet(8, fm_acctest.CharSetAlphaNum) datasourceName := "data.vkcs_kubernetes_cluster." + clusterName createClusterFixture := clusterFixture(clusterName, acctest.ClusterTemplateID, acctest.OsFlavorID, diff --git a/vkcs/kubernetes/data_source_vkcs_kubernetes_node_group_test.go b/vkcs/kubernetes/data_source_vkcs_kubernetes_node_group_test.go index 1bb5ab1b..317359ed 100755 --- a/vkcs/kubernetes/data_source_vkcs_kubernetes_node_group_test.go +++ b/vkcs/kubernetes/data_source_vkcs_kubernetes_node_group_test.go @@ -4,25 +4,25 @@ import ( "fmt" "testing" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/containerinfra/v1/clusters" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/containerinfra/v1/nodegroups" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" ) func TestAccKubernetesNodeGroupDataSource_basic(t *testing.T) { var cluster clusters.Cluster var nodeGroup nodegroups.NodeGroup - clusterName := "testcluster" + sdk_acctest.RandStringFromCharSet(8, sdk_acctest.CharSetAlphaNum) + clusterName := "testcluster" + fm_acctest.RandStringFromCharSet(8, fm_acctest.CharSetAlphaNum) createClusterFixture := clusterFixture(clusterName, acctest.ClusterTemplateID, acctest.OsFlavorID, acctest.OsKeypairName, acctest.OsNetworkID, acctest.OsSubnetworkID, "MS1", 1) clusterResourceName := "vkcs_kubernetes_cluster." + clusterName - nodeGroupName := "testng" + sdk_acctest.RandStringFromCharSet(8, sdk_acctest.CharSetAlphaNum) + nodeGroupName := "testng" + fm_acctest.RandStringFromCharSet(8, fm_acctest.CharSetAlphaNum) nodeGroupFixture := nodeGroupFixture(nodeGroupName, acctest.OsFlavorID, 1, 3, 1, false) nodeGroupResourceName := "vkcs_kubernetes_node_group." + nodeGroupName nodeGroupDataSourceName := "data.vkcs_kubernetes_node_group." + nodeGroupName diff --git a/vkcs/kubernetes/kubernetes_shared.go b/vkcs/kubernetes/kubernetes_shared.go index 1f3f7062..cde9f088 100755 --- a/vkcs/kubernetes/kubernetes_shared.go +++ b/vkcs/kubernetes/kubernetes_shared.go @@ -4,7 +4,7 @@ import ( "fmt" "github.com/gophercloud/gophercloud" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/mitchellh/mapstructure" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/containerinfra/v1/clusters" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/containerinfra/v1/nodegroups" @@ -86,7 +86,7 @@ func flattenNodeGroupTaintsList(v []nodegroups.Taint) []map[string]interface{} { return taints } -func kubernetesStateRefreshFunc(client *gophercloud.ServiceClient, clusterID string) resource.StateRefreshFunc { +func kubernetesStateRefreshFunc(client *gophercloud.ServiceClient, clusterID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { c, err := clusters.Get(client, clusterID).Extract() if err != nil { diff --git a/vkcs/kubernetes/resource_vkcs_kubernetes_cluster.go b/vkcs/kubernetes/resource_vkcs_kubernetes_cluster.go index 41ef60ac..4e443605 100755 --- a/vkcs/kubernetes/resource_vkcs_kubernetes_cluster.go +++ b/vkcs/kubernetes/resource_vkcs_kubernetes_cluster.go @@ -8,7 +8,7 @@ import ( "github.com/gophercloud/gophercloud" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/containerinfra/v1/clusters" @@ -319,7 +319,7 @@ func resourceKubernetesClusterCreate(ctx context.Context, d *schema.ResourceData // Store the cluster ID. d.SetId(s) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(clusterStatusProvisioning)}, Target: []string{string(clusterStatusRunning)}, Refresh: kubernetesStateRefreshFunc(containerInfraClient, s), @@ -412,7 +412,7 @@ func resourceKubernetesClusterUpdate(ctx context.Context, d *schema.ResourceData return diag.Errorf("error creating container infra client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Refresh: kubernetesStateRefreshFunc(containerInfraClient, d.Id()), Timeout: d.Timeout(schema.TimeoutUpdate), Delay: createUpdateDelay * time.Minute, @@ -464,7 +464,7 @@ func resourceKubernetesClusterUpdate(ctx context.Context, d *schema.ResourceData return resourceKubernetesClusterRead(ctx, d, meta) } -func checkForClusterTemplateID(ctx context.Context, d *schema.ResourceData, containerInfraClient *gophercloud.ServiceClient, stateConf *resource.StateChangeConf) error { +func checkForClusterTemplateID(ctx context.Context, d *schema.ResourceData, containerInfraClient *gophercloud.ServiceClient, stateConf *retry.StateChangeConf) error { if d.HasChange("cluster_template_id") { upgradeOpts := clusters.UpgradeOpts{ ClusterTemplateID: d.Get("cluster_template_id").(string), @@ -485,7 +485,7 @@ func checkForClusterTemplateID(ctx context.Context, d *schema.ResourceData, cont return nil } -func checkForMasterFlavor(ctx context.Context, d *schema.ResourceData, containerInfraClient *gophercloud.ServiceClient, stateConf *resource.StateChangeConf) error { +func checkForMasterFlavor(ctx context.Context, d *schema.ResourceData, containerInfraClient *gophercloud.ServiceClient, stateConf *retry.StateChangeConf) error { if d.HasChange("master_flavor") { upgradeOpts := clusters.ActionsBaseOpts{ Action: "resize_masters", @@ -510,7 +510,7 @@ func checkForMasterFlavor(ctx context.Context, d *schema.ResourceData, container func checkForStatus(ctx context.Context, d *schema.ResourceData, containerInfraClient *gophercloud.ServiceClient, cluster *clusters.Cluster) (bool, error) { - turnOffConf := &resource.StateChangeConf{ + turnOffConf := &retry.StateChangeConf{ Refresh: kubernetesStateRefreshFunc(containerInfraClient, d.Id()), Timeout: d.Timeout(schema.TimeoutUpdate), Delay: createUpdateDelay * time.Minute, @@ -519,7 +519,7 @@ func checkForStatus(ctx context.Context, d *schema.ResourceData, containerInfraC Target: []string{string(clusterStatusShutoff)}, } - turnOnConf := &resource.StateChangeConf{ + turnOnConf := &retry.StateChangeConf{ Refresh: kubernetesStateRefreshFunc(containerInfraClient, d.Id()), Timeout: d.Timeout(schema.TimeoutUpdate), Delay: createUpdateDelay * time.Minute, @@ -541,7 +541,7 @@ func checkForStatus(ctx context.Context, d *schema.ResourceData, containerInfraC return false, fmt.Errorf("error during switching state: %s", err) } - var switchStateConf *resource.StateChangeConf + var switchStateConf *retry.StateChangeConf switch currentStatus { case clusterStatusRunning: switchStateConf = turnOnConf @@ -573,7 +573,7 @@ func resourceKubernetesClusterDelete(ctx context.Context, d *schema.ResourceData return diag.FromErr(util.CheckDeleted(d, err, "failed to delete vkcs_kubernetes_cluster")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(clusterStatusDeleting), string(clusterStatusDeleted)}, Target: []string{string(clusterStatusNotFound)}, Refresh: kubernetesStateRefreshFunc(client, d.Id()), diff --git a/vkcs/kubernetes/resource_vkcs_kubernetes_cluster_test.go b/vkcs/kubernetes/resource_vkcs_kubernetes_cluster_test.go index 54f75dd9..2e1f903a 100755 --- a/vkcs/kubernetes/resource_vkcs_kubernetes_cluster_test.go +++ b/vkcs/kubernetes/resource_vkcs_kubernetes_cluster_test.go @@ -6,9 +6,9 @@ import ( "testing" "github.com/gophercloud/gophercloud" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" uuid "github.com/satori/go.uuid" "github.com/stretchr/testify/mock" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" @@ -72,7 +72,7 @@ func TestMockAccKubernetesCluster_basic(t *testing.T) { dummyConfig.On("util.GetRegion").Return("") // Create cluster fixtures - clusterName := "testcluster" + sdk_acctest.RandStringFromCharSet(8, sdk_acctest.CharSetAlphaNum) + clusterName := "testcluster" + fm_acctest.RandStringFromCharSet(8, fm_acctest.CharSetAlphaNum) resourceName := "vkcs_kubernetes_cluster." + clusterName createClusterFixture := clusterFixture(clusterName, acctest.ClusterTemplateID, acctest.OsFlavorID, diff --git a/vkcs/kubernetes/resource_vkcs_kubernetes_node_group.go b/vkcs/kubernetes/resource_vkcs_kubernetes_node_group.go index ca900a78..724e672b 100755 --- a/vkcs/kubernetes/resource_vkcs_kubernetes_node_group.go +++ b/vkcs/kubernetes/resource_vkcs_kubernetes_node_group.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -248,7 +248,7 @@ func resourceKubernetesNodeGroupCreate(ctx context.Context, d *schema.ResourceDa // Store the node Group ID. d.SetId(s.UUID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(clusterStatusReconciling)}, Target: []string{string(clusterStatusRunning)}, Refresh: kubernetesStateRefreshFunc(containerInfraClient, s.ClusterID), @@ -330,7 +330,7 @@ func resourceKubernetesNodeGroupUpdate(ctx context.Context, d *schema.ResourceDa return diag.Errorf("error creating container infra client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Refresh: kubernetesStateRefreshFunc(containerInfraClient, d.Get("cluster_id").(string)), Timeout: d.Timeout(schema.TimeoutUpdate), Delay: createUpdateDelay * time.Minute, @@ -450,7 +450,7 @@ func resourceKubernetesNodeGroupDelete(ctx context.Context, d *schema.ResourceDa return diag.FromErr(util.CheckDeleted(d, err, "error deleting vkcs_kubernetes_node_group")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{string(clusterStatusReconciling)}, Target: []string{string(clusterStatusRunning)}, Refresh: kubernetesStateRefreshFunc(containerInfraClient, d.Get("cluster_id").(string)), diff --git a/vkcs/kubernetes/resource_vkcs_kubernetes_node_group_test.go b/vkcs/kubernetes/resource_vkcs_kubernetes_node_group_test.go index 2dad22ac..7fba038b 100755 --- a/vkcs/kubernetes/resource_vkcs_kubernetes_node_group_test.go +++ b/vkcs/kubernetes/resource_vkcs_kubernetes_node_group_test.go @@ -5,9 +5,9 @@ import ( "strconv" "testing" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/containerinfra/v1/clusters" @@ -42,12 +42,12 @@ func TestAccKubernetesNodeGroup_basic(t *testing.T) { var cluster clusters.Cluster var nodeGroup nodegroups.NodeGroup - clusterName := "testcluster" + sdk_acctest.RandStringFromCharSet(8, sdk_acctest.CharSetAlphaNum) + clusterName := "testcluster" + fm_acctest.RandStringFromCharSet(8, fm_acctest.CharSetAlphaNum) createClusterFixture := clusterFixture(clusterName, acctest.ClusterTemplateID, acctest.OsFlavorID, acctest.OsKeypairName, acctest.OsNetworkID, acctest.OsSubnetworkID, "MS1", 1) clusterResourceName := "vkcs_kubernetes_cluster." + clusterName - nodeGroupName := "testng" + sdk_acctest.RandStringFromCharSet(8, sdk_acctest.CharSetAlphaNum) + nodeGroupName := "testng" + fm_acctest.RandStringFromCharSet(8, fm_acctest.CharSetAlphaNum) ngFixture := nodeGroupFixture(nodeGroupName, acctest.OsFlavorID, 1, 5, 1, false) nodeGroupResourceName := "vkcs_kubernetes_node_group." + nodeGroupName diff --git a/vkcs/lb/data_source_vkcs_lb_loadbalancer_test.go b/vkcs/lb/data_source_vkcs_lb_loadbalancer_test.go index 5ebd7d8c..57dfac58 100644 --- a/vkcs/lb/data_source_vkcs_lb_loadbalancer_test.go +++ b/vkcs/lb/data_source_vkcs_lb_loadbalancer_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/import_vkcs_lb_l7policy_test.go b/vkcs/lb/import_vkcs_lb_l7policy_test.go index 0a67eeef..72ada405 100644 --- a/vkcs/lb/import_vkcs_lb_l7policy_test.go +++ b/vkcs/lb/import_vkcs_lb_l7policy_test.go @@ -3,7 +3,7 @@ package lb_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/import_vkcs_lb_l7rule_test.go b/vkcs/lb/import_vkcs_lb_l7rule_test.go index 47cef2d8..b08a11d1 100644 --- a/vkcs/lb/import_vkcs_lb_l7rule_test.go +++ b/vkcs/lb/import_vkcs_lb_l7rule_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/import_vkcs_lb_listener_test.go b/vkcs/lb/import_vkcs_lb_listener_test.go index 11c089b6..ca6364e7 100644 --- a/vkcs/lb/import_vkcs_lb_listener_test.go +++ b/vkcs/lb/import_vkcs_lb_listener_test.go @@ -3,7 +3,7 @@ package lb_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/import_vkcs_lb_loadbalancer_test.go b/vkcs/lb/import_vkcs_lb_loadbalancer_test.go index b5e6b65e..2a1bbb60 100644 --- a/vkcs/lb/import_vkcs_lb_loadbalancer_test.go +++ b/vkcs/lb/import_vkcs_lb_loadbalancer_test.go @@ -3,7 +3,7 @@ package lb_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/import_vkcs_lb_member_test.go b/vkcs/lb/import_vkcs_lb_member_test.go index ef2b4010..4d4b1a05 100644 --- a/vkcs/lb/import_vkcs_lb_member_test.go +++ b/vkcs/lb/import_vkcs_lb_member_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/import_vkcs_lb_members_test.go b/vkcs/lb/import_vkcs_lb_members_test.go index 4b45736f..2a8c2a45 100644 --- a/vkcs/lb/import_vkcs_lb_members_test.go +++ b/vkcs/lb/import_vkcs_lb_members_test.go @@ -3,7 +3,7 @@ package lb_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/import_vkcs_lb_monitor_test.go b/vkcs/lb/import_vkcs_lb_monitor_test.go index 7fc5001c..77b867de 100644 --- a/vkcs/lb/import_vkcs_lb_monitor_test.go +++ b/vkcs/lb/import_vkcs_lb_monitor_test.go @@ -3,7 +3,7 @@ package lb_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/import_vkcs_lb_pool_test.go b/vkcs/lb/import_vkcs_lb_pool_test.go index 1122296e..5beb19d3 100644 --- a/vkcs/lb/import_vkcs_lb_pool_test.go +++ b/vkcs/lb/import_vkcs_lb_pool_test.go @@ -3,7 +3,7 @@ package lb_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/lb/lb_shared.go b/vkcs/lb/lb_shared.go index f0f64b6d..e32c33b5 100644 --- a/vkcs/lb/lb_shared.go +++ b/vkcs/lb/lb_shared.go @@ -6,7 +6,7 @@ import ( "log" "time" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -65,7 +65,7 @@ func waitForLBListener(ctx context.Context, lbClient *gophercloud.ServiceClient, lbID := listener.Loadbalancers[0].ID - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{target}, Pending: pending, Refresh: resourceLBListenerRefreshFunc(lbClient, lbID, listener), @@ -88,7 +88,7 @@ func waitForLBListener(ctx context.Context, lbClient *gophercloud.ServiceClient, return nil } -func resourceLBListenerRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, listener *octavialisteners.Listener) resource.StateRefreshFunc { +func resourceLBListenerRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, listener *octavialisteners.Listener) retry.StateRefreshFunc { if listener.ProvisioningStatus != "" { return func() (interface{}, string, error) { lb, status, err := resourceLBLoadBalancerRefreshFunc(lbClient, lbID)() @@ -114,7 +114,7 @@ func resourceLBListenerRefreshFunc(lbClient *gophercloud.ServiceClient, lbID str func waitForLBLoadBalancer(ctx context.Context, lbClient *gophercloud.ServiceClient, lbID string, target string, pending []string, timeout time.Duration) error { log.Printf("[DEBUG] Waiting for loadbalancer %s to become %s.", lbID, target) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{target}, Pending: pending, Refresh: resourceLBLoadBalancerRefreshFunc(lbClient, lbID), @@ -139,7 +139,7 @@ func waitForLBLoadBalancer(ctx context.Context, lbClient *gophercloud.ServiceCli return nil } -func resourceLBLoadBalancerRefreshFunc(lbClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func resourceLBLoadBalancerRefreshFunc(lbClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { lb, err := octavialoadbalancers.Get(lbClient, id).Extract() if err != nil { @@ -158,7 +158,7 @@ func waitForLBMember(ctx context.Context, lbClient *gophercloud.ServiceClient, p return err } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{target}, Pending: pending, Refresh: resourceLBMemberRefreshFunc(lbClient, lbID, parentPool.ID, member), @@ -181,7 +181,7 @@ func waitForLBMember(ctx context.Context, lbClient *gophercloud.ServiceClient, p return nil } -func resourceLBMemberRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, poolID string, member *octaviapools.Member) resource.StateRefreshFunc { +func resourceLBMemberRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, poolID string, member *octaviapools.Member) retry.StateRefreshFunc { if member.ProvisioningStatus != "" { return func() (interface{}, string, error) { lb, status, err := resourceLBLoadBalancerRefreshFunc(lbClient, lbID)() @@ -212,7 +212,7 @@ func waitForLBMonitor(ctx context.Context, lbClient *gophercloud.ServiceClient, return err } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{target}, Pending: pending, Refresh: resourceLBMonitorRefreshFunc(lbClient, lbID, monitor), @@ -234,7 +234,7 @@ func waitForLBMonitor(ctx context.Context, lbClient *gophercloud.ServiceClient, return nil } -func resourceLBMonitorRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, monitor *octaviamonitors.Monitor) resource.StateRefreshFunc { +func resourceLBMonitorRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, monitor *octaviamonitors.Monitor) retry.StateRefreshFunc { if monitor.ProvisioningStatus != "" { return func() (interface{}, string, error) { lb, status, err := resourceLBLoadBalancerRefreshFunc(lbClient, lbID)() @@ -265,7 +265,7 @@ func waitForLBPool(ctx context.Context, lbClient *gophercloud.ServiceClient, poo return err } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{target}, Pending: pending, Refresh: resourceLBPoolRefreshFunc(lbClient, lbID, pool), @@ -288,7 +288,7 @@ func waitForLBPool(ctx context.Context, lbClient *gophercloud.ServiceClient, poo return nil } -func resourceLBPoolRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, pool *octaviapools.Pool) resource.StateRefreshFunc { +func resourceLBPoolRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, pool *octaviapools.Pool) retry.StateRefreshFunc { if pool.ProvisioningStatus != "" { return func() (interface{}, string, error) { lb, status, err := resourceLBLoadBalancerRefreshFunc(lbClient, lbID)() @@ -331,7 +331,7 @@ func lbFindLBIDviaPool(lbClient *gophercloud.ServiceClient, pool *octaviapools.P return "", fmt.Errorf("unable to determine loadbalancer ID from pool %s", pool.ID) } -func resourceLBLoadBalancerStatusRefreshFuncNeutron(lbClient *gophercloud.ServiceClient, lbID, resourceType, resourceID string, parentID string) resource.StateRefreshFunc { +func resourceLBLoadBalancerStatusRefreshFuncNeutron(lbClient *gophercloud.ServiceClient, lbID, resourceType, resourceID string, parentID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { statuses, err := octavialoadbalancers.GetStatuses(lbClient, lbID).Extract() if err != nil { @@ -435,7 +435,7 @@ func resourceLBLoadBalancerStatusRefreshFuncNeutron(lbClient *gophercloud.Servic } } -func resourceLBL7PolicyRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, l7policy *octavial7policies.L7Policy) resource.StateRefreshFunc { +func resourceLBL7PolicyRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, l7policy *octavial7policies.L7Policy) retry.StateRefreshFunc { if l7policy.ProvisioningStatus != "" { return func() (interface{}, string, error) { lb, status, err := resourceLBLoadBalancerRefreshFunc(lbClient, lbID)() @@ -467,7 +467,7 @@ func waitForLBL7Policy(ctx context.Context, lbClient *gophercloud.ServiceClient, lbID := parentListener.Loadbalancers[0].ID - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{target}, Pending: pending, Refresh: resourceLBL7PolicyRefreshFunc(lbClient, lbID, l7policy), @@ -519,7 +519,7 @@ func getListenerIDForL7Policy(lbClient *gophercloud.ServiceClient, id string) (s return "", fmt.Errorf("unable to find Listener ID associated with the %s L7 Policy ID", id) } -func resourceLBL7RuleRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, l7policyID string, l7rule *octavial7policies.Rule) resource.StateRefreshFunc { +func resourceLBL7RuleRefreshFunc(lbClient *gophercloud.ServiceClient, lbID string, l7policyID string, l7rule *octavial7policies.Rule) retry.StateRefreshFunc { if l7rule.ProvisioningStatus != "" { return func() (interface{}, string, error) { lb, status, err := resourceLBLoadBalancerRefreshFunc(lbClient, lbID)() @@ -551,7 +551,7 @@ func waitForLBL7Rule(ctx context.Context, lbClient *gophercloud.ServiceClient, p lbID := parentListener.Loadbalancers[0].ID - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{target}, Pending: pending, Refresh: resourceLBL7RuleRefreshFunc(lbClient, lbID, parentL7policy.ID, l7rule), diff --git a/vkcs/lb/resource_vkcs_lb_l7policy.go b/vkcs/lb/resource_vkcs_lb_l7policy.go index 021401e5..44ec6344 100644 --- a/vkcs/lb/resource_vkcs_lb_l7policy.go +++ b/vkcs/lb/resource_vkcs_lb_l7policy.go @@ -8,7 +8,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -177,7 +177,7 @@ func resourceL7PolicyCreate(ctx context.Context, d *schema.ResourceData, meta in log.Printf("[DEBUG] Attempting to create L7 Policy") var l7Policy *l7policies.L7Policy - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { l7Policy, err = l7policies.Create(lbClient, createOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -314,7 +314,7 @@ func resourceL7PolicyUpdate(ctx context.Context, d *schema.ResourceData, meta in } log.Printf("[DEBUG] Updating L7 Policy %s with options: %#v", d.Id(), updateOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { _, err = l7policies.Update(lbClient, d.Id(), updateOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -364,7 +364,7 @@ func resourceL7PolicyDelete(ctx context.Context, d *schema.ResourceData, meta in } log.Printf("[DEBUG] Attempting to delete L7 Policy %s", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = l7policies.Delete(lbClient, d.Id()).ExtractErr() if err != nil { return util.CheckForRetryableError(err) diff --git a/vkcs/lb/resource_vkcs_lb_l7policy_test.go b/vkcs/lb/resource_vkcs_lb_l7policy_test.go index 97286b77..a311a4dd 100644 --- a/vkcs/lb/resource_vkcs_lb_l7policy_test.go +++ b/vkcs/lb/resource_vkcs_lb_l7policy_test.go @@ -5,8 +5,8 @@ import ( "regexp" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/lb/resource_vkcs_lb_l7rule.go b/vkcs/lb/resource_vkcs_lb_l7rule.go index 1a42e945..4eae8167 100644 --- a/vkcs/lb/resource_vkcs_lb_l7rule.go +++ b/vkcs/lb/resource_vkcs_lb_l7rule.go @@ -8,7 +8,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -174,7 +174,7 @@ func resourceL7RuleCreate(ctx context.Context, d *schema.ResourceData, meta inte log.Printf("[DEBUG] Attempting to create L7 Rule") var l7Rule *l7policies.Rule - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { l7Rule, err = l7policies.CreateRule(lbClient, l7policyID, createOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -296,7 +296,7 @@ func resourceL7RuleUpdate(ctx context.Context, d *schema.ResourceData, meta inte } log.Printf("[DEBUG] Updating L7 Rule %s with options: %#v", d.Id(), updateOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { _, err := l7policies.UpdateRule(lbClient, l7policyID, d.Id(), updateOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -354,7 +354,7 @@ func resourceL7RuleDelete(ctx context.Context, d *schema.ResourceData, meta inte } log.Printf("[DEBUG] Attempting to delete L7 Rule %s", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = l7policies.DeleteRule(lbClient, l7policyID, d.Id()).ExtractErr() if err != nil { return util.CheckForRetryableError(err) diff --git a/vkcs/lb/resource_vkcs_lb_l7rule_test.go b/vkcs/lb/resource_vkcs_lb_l7rule_test.go index dfbda158..36b56cca 100644 --- a/vkcs/lb/resource_vkcs_lb_l7rule_test.go +++ b/vkcs/lb/resource_vkcs_lb_l7rule_test.go @@ -5,8 +5,8 @@ import ( "regexp" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/lb/resource_vkcs_lb_listener.go b/vkcs/lb/resource_vkcs_lb_listener.go index bb1bb0ab..7bfdd51b 100644 --- a/vkcs/lb/resource_vkcs_lb_listener.go +++ b/vkcs/lb/resource_vkcs_lb_listener.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -240,7 +240,7 @@ func resourceListenerCreate(ctx context.Context, d *schema.ResourceData, meta in log.Printf("[DEBUG] vkcs_lb_listener create options: %#v", createOpts) var listener *octavialisteners.Listener - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { listener, err = octavialisteners.Create(lbClient, createOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -428,7 +428,7 @@ func resourceListenerUpdate(ctx context.Context, d *schema.ResourceData, meta in } log.Printf("[DEBUG] vkcs_lb_listener %s update options: %#v", d.Id(), updateOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { _, err = octavialisteners.Update(lbClient, d.Id(), updateOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -465,7 +465,7 @@ func resourceListenerDelete(ctx context.Context, d *schema.ResourceData, meta in timeout := d.Timeout(schema.TimeoutDelete) log.Printf("[DEBUG] Deleting vkcs_lb_listener %s", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = octavialisteners.Delete(lbClient, d.Id()).ExtractErr() if err != nil { return util.CheckForRetryableError(err) diff --git a/vkcs/lb/resource_vkcs_lb_listener_test.go b/vkcs/lb/resource_vkcs_lb_listener_test.go index e62ccb3f..40ab8231 100644 --- a/vkcs/lb/resource_vkcs_lb_listener_test.go +++ b/vkcs/lb/resource_vkcs_lb_listener_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/lb/resource_vkcs_lb_loadbalancer.go b/vkcs/lb/resource_vkcs_lb_loadbalancer.go index 7aa8d547..08237a2d 100644 --- a/vkcs/lb/resource_vkcs_lb_loadbalancer.go +++ b/vkcs/lb/resource_vkcs_lb_loadbalancer.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" @@ -257,7 +257,7 @@ func resourceLoadBalancerUpdate(ctx context.Context, d *schema.ResourceData, met } log.Printf("[DEBUG] Updating vkcs_lb_loadbalancer %s with options: %#v", d.Id(), updateOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { _, err = octavialoadbalancers.Update(lbClient, d.Id(), updateOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -288,7 +288,7 @@ func resourceLoadBalancerDelete(ctx context.Context, d *schema.ResourceData, met log.Printf("[DEBUG] Deleting vkcs_lb_loadbalancer %s", d.Id()) timeout := d.Timeout(schema.TimeoutDelete) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = octavialoadbalancers.Delete(lbClient, d.Id(), nil).ExtractErr() if err != nil { return util.CheckForRetryableError(err) diff --git a/vkcs/lb/resource_vkcs_lb_loadbalancer_test.go b/vkcs/lb/resource_vkcs_lb_loadbalancer_test.go index 6768150a..9a38201f 100644 --- a/vkcs/lb/resource_vkcs_lb_loadbalancer_test.go +++ b/vkcs/lb/resource_vkcs_lb_loadbalancer_test.go @@ -5,8 +5,8 @@ import ( "regexp" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/lb/resource_vkcs_lb_member.go b/vkcs/lb/resource_vkcs_lb_member.go index b0e51249..ad1f01c0 100644 --- a/vkcs/lb/resource_vkcs_lb_member.go +++ b/vkcs/lb/resource_vkcs_lb_member.go @@ -8,7 +8,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -141,7 +141,7 @@ func resourceMemberCreate(ctx context.Context, d *schema.ResourceData, meta inte log.Printf("[DEBUG] Attempting to create member") var member *pools.Member - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { member, err = pools.CreateMember(lbClient, poolID, createOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -239,7 +239,7 @@ func resourceMemberUpdate(ctx context.Context, d *schema.ResourceData, meta inte } log.Printf("[DEBUG] Updating member %s with options: %#v", d.Id(), updateOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { _, err = pools.UpdateMember(lbClient, poolID, d.Id(), updateOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -288,7 +288,7 @@ func resourceMemberDelete(ctx context.Context, d *schema.ResourceData, meta inte } log.Printf("[DEBUG] Attempting to delete member %s", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = pools.DeleteMember(lbClient, poolID, d.Id()).ExtractErr() if err != nil { return util.CheckForRetryableError(err) diff --git a/vkcs/lb/resource_vkcs_lb_member_test.go b/vkcs/lb/resource_vkcs_lb_member_test.go index 9107195f..c27bb362 100644 --- a/vkcs/lb/resource_vkcs_lb_member_test.go +++ b/vkcs/lb/resource_vkcs_lb_member_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/lb/resource_vkcs_lb_members.go b/vkcs/lb/resource_vkcs_lb_members.go index acfdcc1a..862ab480 100644 --- a/vkcs/lb/resource_vkcs_lb_members.go +++ b/vkcs/lb/resource_vkcs_lb_members.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -137,7 +137,7 @@ func resourceMembersCreate(ctx context.Context, d *schema.ResourceData, meta int } log.Printf("[DEBUG] Attempting to create members") - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = octaviapools.BatchUpdateMembers(lbClient, poolID, createOpts).ExtractErr() if err != nil { return util.CheckForRetryableError(err) @@ -210,7 +210,7 @@ func resourceMembersUpdate(ctx context.Context, d *schema.ResourceData, meta int } log.Printf("[DEBUG] Updating %s pool members with options: %#v", d.Id(), updateOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = octaviapools.BatchUpdateMembers(lbClient, d.Id(), updateOpts).ExtractErr() if err != nil { return util.CheckForRetryableError(err) @@ -253,7 +253,7 @@ func resourceMembersDelete(ctx context.Context, d *schema.ResourceData, meta int } log.Printf("[DEBUG] Attempting to delete %s pool members", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = octaviapools.BatchUpdateMembers(lbClient, d.Id(), []octaviapools.BatchUpdateMemberOpts{}).ExtractErr() if err != nil { return util.CheckForRetryableError(err) diff --git a/vkcs/lb/resource_vkcs_lb_members_test.go b/vkcs/lb/resource_vkcs_lb_members_test.go index 3b31f709..0b015af6 100644 --- a/vkcs/lb/resource_vkcs_lb_members_test.go +++ b/vkcs/lb/resource_vkcs_lb_members_test.go @@ -4,9 +4,9 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/lb" diff --git a/vkcs/lb/resource_vkcs_lb_monitor.go b/vkcs/lb/resource_vkcs_lb_monitor.go index 53ee9956..d2461e5c 100644 --- a/vkcs/lb/resource_vkcs_lb_monitor.go +++ b/vkcs/lb/resource_vkcs_lb_monitor.go @@ -8,7 +8,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -162,7 +162,7 @@ func resourceMonitorCreate(ctx context.Context, d *schema.ResourceData, meta int log.Printf("[DEBUG] vkcs_lb_monitor create options: %#v", createOpts) var monitor *octaviamonitors.Monitor - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { monitor, err = octaviamonitors.Create(lbClient, createOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -300,7 +300,7 @@ func resourceMonitorUpdate(ctx context.Context, d *schema.ResourceData, meta int } log.Printf("[DEBUG] vkcs_lb_monitor %s update options: %#v", d.Id(), updateOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { _, err = octaviamonitors.Update(lbClient, d.Id(), updateOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -350,7 +350,7 @@ func resourceMonitorDelete(ctx context.Context, d *schema.ResourceData, meta int } log.Printf("[DEBUG] Deleting vkcs_lb_monitor %s", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = octaviamonitors.Delete(lbClient, d.Id()).ExtractErr() if err != nil { return util.CheckForRetryableError(err) diff --git a/vkcs/lb/resource_vkcs_lb_monitor_test.go b/vkcs/lb/resource_vkcs_lb_monitor_test.go index e352b6c4..2e66b770 100644 --- a/vkcs/lb/resource_vkcs_lb_monitor_test.go +++ b/vkcs/lb/resource_vkcs_lb_monitor_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/lb/resource_vkcs_lb_pool.go b/vkcs/lb/resource_vkcs_lb_pool.go index 453d15a6..eb78a390 100644 --- a/vkcs/lb/resource_vkcs_lb_pool.go +++ b/vkcs/lb/resource_vkcs_lb_pool.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -200,7 +200,7 @@ func resourcePoolCreate(ctx context.Context, d *schema.ResourceData, meta interf log.Printf("[DEBUG] Attempting to create pool") var pool *pools.Pool - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { pool, err = pools.Create(lbClient, createOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -288,7 +288,7 @@ func resourcePoolUpdate(ctx context.Context, d *schema.ResourceData, meta interf } log.Printf("[DEBUG] Updating pool %s with options: %#v", d.Id(), updateOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { _, err = pools.Update(lbClient, d.Id(), updateOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -325,7 +325,7 @@ func resourcePoolDelete(ctx context.Context, d *schema.ResourceData, meta interf } log.Printf("[DEBUG] Attempting to delete pool %s", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = pools.Delete(lbClient, d.Id()).ExtractErr() if err != nil { return util.CheckForRetryableError(err) diff --git a/vkcs/lb/resource_vkcs_lb_pool_test.go b/vkcs/lb/resource_vkcs_lb_pool_test.go index ac621ef8..c8c04892 100644 --- a/vkcs/lb/resource_vkcs_lb_pool_test.go +++ b/vkcs/lb/resource_vkcs_lb_pool_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/networking/data_source_vkcs_networking_floatingip_test.go b/vkcs/networking/data_source_vkcs_networking_floatingip_test.go index e568e88c..4430cc50 100644 --- a/vkcs/networking/data_source_vkcs_networking_floatingip_test.go +++ b/vkcs/networking/data_source_vkcs_networking_floatingip_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/data_source_vkcs_networking_network_test.go b/vkcs/networking/data_source_vkcs_networking_network_test.go index 17de245e..26908acd 100644 --- a/vkcs/networking/data_source_vkcs_networking_network_test.go +++ b/vkcs/networking/data_source_vkcs_networking_network_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/data_source_vkcs_networking_port_test.go b/vkcs/networking/data_source_vkcs_networking_port_test.go index 1c92d414..19658f40 100644 --- a/vkcs/networking/data_source_vkcs_networking_port_test.go +++ b/vkcs/networking/data_source_vkcs_networking_port_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/data_source_vkcs_networking_router_test.go b/vkcs/networking/data_source_vkcs_networking_router_test.go index 8901daf4..6593609b 100644 --- a/vkcs/networking/data_source_vkcs_networking_router_test.go +++ b/vkcs/networking/data_source_vkcs_networking_router_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/data_source_vkcs_networking_subnet_test.go b/vkcs/networking/data_source_vkcs_networking_subnet_test.go index 47d218f7..8348e6cf 100644 --- a/vkcs/networking/data_source_vkcs_networking_subnet_test.go +++ b/vkcs/networking/data_source_vkcs_networking_subnet_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_floatingip_associate_test.go b/vkcs/networking/import_vkcs_networking_floatingip_associate_test.go index 5aad533c..4f0136e7 100644 --- a/vkcs/networking/import_vkcs_networking_floatingip_associate_test.go +++ b/vkcs/networking/import_vkcs_networking_floatingip_associate_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_floatingip_test.go b/vkcs/networking/import_vkcs_networking_floatingip_test.go index 3d1e602d..682ef65b 100644 --- a/vkcs/networking/import_vkcs_networking_floatingip_test.go +++ b/vkcs/networking/import_vkcs_networking_floatingip_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_network_test.go b/vkcs/networking/import_vkcs_networking_network_test.go index 0c0993f6..26ba21fd 100644 --- a/vkcs/networking/import_vkcs_networking_network_test.go +++ b/vkcs/networking/import_vkcs_networking_network_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_port_test.go b/vkcs/networking/import_vkcs_networking_port_test.go index 7de74fd7..e92fcaa1 100644 --- a/vkcs/networking/import_vkcs_networking_port_test.go +++ b/vkcs/networking/import_vkcs_networking_port_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_router_interface_test.go b/vkcs/networking/import_vkcs_networking_router_interface_test.go index 1826d710..446f6aba 100644 --- a/vkcs/networking/import_vkcs_networking_router_interface_test.go +++ b/vkcs/networking/import_vkcs_networking_router_interface_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_router_route_test.go b/vkcs/networking/import_vkcs_networking_router_route_test.go index d3a605ca..56b15b2c 100644 --- a/vkcs/networking/import_vkcs_networking_router_route_test.go +++ b/vkcs/networking/import_vkcs_networking_router_route_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_router_test.go b/vkcs/networking/import_vkcs_networking_router_test.go index c7ecc251..c0f85093 100644 --- a/vkcs/networking/import_vkcs_networking_router_test.go +++ b/vkcs/networking/import_vkcs_networking_router_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_subnet_route_test.go b/vkcs/networking/import_vkcs_networking_subnet_route_test.go index fcc451b1..5879c273 100644 --- a/vkcs/networking/import_vkcs_networking_subnet_route_test.go +++ b/vkcs/networking/import_vkcs_networking_subnet_route_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/import_vkcs_networking_subnet_test.go b/vkcs/networking/import_vkcs_networking_subnet_test.go index 67569987..57a47b6a 100644 --- a/vkcs/networking/import_vkcs_networking_subnet_test.go +++ b/vkcs/networking/import_vkcs_networking_subnet_test.go @@ -3,7 +3,7 @@ package networking_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/networking/networking_floatingip.go b/vkcs/networking/networking_floatingip.go index 3562b990..fbc151b1 100644 --- a/vkcs/networking/networking_floatingip.go +++ b/vkcs/networking/networking_floatingip.go @@ -3,11 +3,10 @@ package networking import ( "fmt" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/dns" "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/layer3/floatingips" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) type floatingIPExtended struct { @@ -41,7 +40,7 @@ func networkingFloatingIPV2ID(client *gophercloud.ServiceClient, floatingIP stri return allFloatingIPs[0].ID, nil } -func networkingFloatingIPV2StateRefreshFunc(client *gophercloud.ServiceClient, fipID string) resource.StateRefreshFunc { +func networkingFloatingIPV2StateRefreshFunc(client *gophercloud.ServiceClient, fipID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { fip, err := floatingips.Get(client, fipID).Extract() if err != nil { diff --git a/vkcs/networking/networking_network.go b/vkcs/networking/networking_network.go index 50515121..b1d01c87 100644 --- a/vkcs/networking/networking_network.go +++ b/vkcs/networking/networking_network.go @@ -3,7 +3,7 @@ package networking import ( "fmt" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -99,7 +99,7 @@ func networkingNetworkName(d *schema.ResourceData, meta interface{}, networkID s return networkName, err } -func resourceNetworkingNetworkStateRefreshFunc(client *gophercloud.ServiceClient, networkID string) resource.StateRefreshFunc { +func resourceNetworkingNetworkStateRefreshFunc(client *gophercloud.ServiceClient, networkID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { n, err := networks.Get(client, networkID).Extract() if err != nil { diff --git a/vkcs/networking/networking_port.go b/vkcs/networking/networking_port.go index deff9486..cc82b502 100644 --- a/vkcs/networking/networking_port.go +++ b/vkcs/networking/networking_port.go @@ -4,7 +4,7 @@ import ( "bytes" "fmt" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -25,7 +25,7 @@ type portExtended struct { policies.QoSPolicyExt } -func resourceNetworkingPortStateRefreshFunc(client *gophercloud.ServiceClient, portID string) resource.StateRefreshFunc { +func resourceNetworkingPortStateRefreshFunc(client *gophercloud.ServiceClient, portID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { n, err := ports.Get(client, portID).Extract() if err != nil { diff --git a/vkcs/networking/networking_router.go b/vkcs/networking/networking_router.go index ff49f694..2bcab2ab 100644 --- a/vkcs/networking/networking_router.go +++ b/vkcs/networking/networking_router.go @@ -1,13 +1,12 @@ package networking import ( - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/layer3/routers" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) -func resourceNetworkingRouterStateRefreshFunc(client *gophercloud.ServiceClient, routerID string) resource.StateRefreshFunc { +func resourceNetworkingRouterStateRefreshFunc(client *gophercloud.ServiceClient, routerID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { n, err := routers.Get(client, routerID).Extract() if err != nil { diff --git a/vkcs/networking/networking_router_interface.go b/vkcs/networking/networking_router_interface.go index 27fe0ece..476a9471 100644 --- a/vkcs/networking/networking_router_interface.go +++ b/vkcs/networking/networking_router_interface.go @@ -3,7 +3,7 @@ package networking import ( "log" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/gophercloud/gophercloud" @@ -11,7 +11,7 @@ import ( "github.com/gophercloud/gophercloud/openstack/networking/v2/ports" ) -func resourceNetworkingRouterInterfaceStateRefreshFunc(networkingClient *gophercloud.ServiceClient, portID string) resource.StateRefreshFunc { +func resourceNetworkingRouterInterfaceStateRefreshFunc(networkingClient *gophercloud.ServiceClient, portID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { r, err := ports.Get(networkingClient, portID).Extract() if err != nil { @@ -26,7 +26,7 @@ func resourceNetworkingRouterInterfaceStateRefreshFunc(networkingClient *gopherc } } -func resourceNetworkingRouterInterfaceDeleteRefreshFunc(networkingClient *gophercloud.ServiceClient, d *schema.ResourceData) resource.StateRefreshFunc { +func resourceNetworkingRouterInterfaceDeleteRefreshFunc(networkingClient *gophercloud.ServiceClient, d *schema.ResourceData) retry.StateRefreshFunc { return func() (interface{}, string, error) { routerID := d.Get("router_id").(string) routerInterfaceID := d.Id() diff --git a/vkcs/networking/networking_subnet.go b/vkcs/networking/networking_subnet.go index 91572d7d..f2101a34 100644 --- a/vkcs/networking/networking_subnet.go +++ b/vkcs/networking/networking_subnet.go @@ -4,15 +4,15 @@ import ( "fmt" "log" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/networking/v2/subnets" ) -// networkingSubnetStateRefreshFunc returns a standard resource.StateRefreshFunc to wait for subnet status. -func networkingSubnetStateRefreshFunc(client *gophercloud.ServiceClient, subnetID string) resource.StateRefreshFunc { +// networkingSubnetStateRefreshFunc returns a standard retry.StateRefreshFunc to wait for subnet status. +func networkingSubnetStateRefreshFunc(client *gophercloud.ServiceClient, subnetID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { subnet, err := subnets.Get(client, subnetID).Extract() if err != nil { @@ -27,8 +27,8 @@ func networkingSubnetStateRefreshFunc(client *gophercloud.ServiceClient, subnetI } } -// networkingSubnetStateRefreshFuncDelete returns a special case resource.StateRefreshFunc to try to delete a subnet. -func networkingSubnetStateRefreshFuncDelete(networkingClient *gophercloud.ServiceClient, subnetID string) resource.StateRefreshFunc { +// networkingSubnetStateRefreshFuncDelete returns a special case retry.StateRefreshFunc to try to delete a subnet. +func networkingSubnetStateRefreshFuncDelete(networkingClient *gophercloud.ServiceClient, subnetID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { log.Printf("[DEBUG] Attempting to delete vkcs_networking_subnet %s", subnetID) diff --git a/vkcs/networking/resource_vkcs_networking_floatingip.go b/vkcs/networking/resource_vkcs_networking_floatingip.go index dafa117b..1975b42e 100644 --- a/vkcs/networking/resource_vkcs_networking_floatingip.go +++ b/vkcs/networking/resource_vkcs_networking_floatingip.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -185,7 +185,7 @@ func resourceNetworkFloatingIPCreate(ctx context.Context, d *schema.ResourceData log.Printf("[DEBUG] Waiting for vkcs_networking_floatingip %s to become available.", fip.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{"ACTIVE", "DOWN"}, Refresh: networkingFloatingIPV2StateRefreshFunc(networkingClient, fip.ID), Timeout: d.Timeout(schema.TimeoutCreate), @@ -292,7 +292,7 @@ func resourceNetworkFloatingIPDelete(ctx context.Context, d *schema.ResourceData return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_networking_floatingip")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE", "DOWN"}, Target: []string{"DELETED"}, Refresh: networkingFloatingIPV2StateRefreshFunc(networkingClient, d.Id()), diff --git a/vkcs/networking/resource_vkcs_networking_floatingip_associate_test.go b/vkcs/networking/resource_vkcs_networking_floatingip_associate_test.go index e24c6ffc..466dc2a5 100644 --- a/vkcs/networking/resource_vkcs_networking_floatingip_associate_test.go +++ b/vkcs/networking/resource_vkcs_networking_floatingip_associate_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_floatingip_test.go b/vkcs/networking/resource_vkcs_networking_floatingip_test.go index b6d1173d..5c2f9224 100644 --- a/vkcs/networking/resource_vkcs_networking_floatingip_test.go +++ b/vkcs/networking/resource_vkcs_networking_floatingip_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_network.go b/vkcs/networking/resource_vkcs_networking_network.go index 1f092f6e..79b64fec 100644 --- a/vkcs/networking/resource_vkcs_networking_network.go +++ b/vkcs/networking/resource_vkcs_networking_network.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -156,7 +156,7 @@ func resourceNetworkingNetworkCreate(ctx context.Context, d *schema.ResourceData log.Printf("[DEBUG] Waiting for vkcs_networking_network %s to become available.", n.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"BUILD"}, Target: []string{"ACTIVE", "DOWN"}, Refresh: resourceNetworkingNetworkStateRefreshFunc(networkingClient, n.ID), @@ -294,7 +294,7 @@ func resourceNetworkingNetworkDelete(ctx context.Context, d *schema.ResourceData return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_networking_network")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: resourceNetworkingNetworkStateRefreshFunc(networkingClient, d.Id()), diff --git a/vkcs/networking/resource_vkcs_networking_network_test.go b/vkcs/networking/resource_vkcs_networking_network_test.go index bcac9228..e8dec33f 100644 --- a/vkcs/networking/resource_vkcs_networking_network_test.go +++ b/vkcs/networking/resource_vkcs_networking_network_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_port.go b/vkcs/networking/resource_vkcs_networking_port.go index 1d2a5841..5e3c9210 100644 --- a/vkcs/networking/resource_vkcs_networking_port.go +++ b/vkcs/networking/resource_vkcs_networking_port.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -336,7 +336,7 @@ func resourceNetworkingPortCreate(ctx context.Context, d *schema.ResourceData, m log.Printf("[DEBUG] Waiting for vkcs_networking_port %s to become available.", port.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{"ACTIVE", "DOWN"}, Refresh: resourceNetworkingPortStateRefreshFunc(networkingClient, port.ID), Timeout: d.Timeout(schema.TimeoutCreate), @@ -562,7 +562,7 @@ func resourceNetworkingPortDelete(ctx context.Context, d *schema.ResourceData, m return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_networking_port")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: resourceNetworkingPortStateRefreshFunc(networkingClient, d.Id()), diff --git a/vkcs/networking/resource_vkcs_networking_port_secgroup_associate_test.go b/vkcs/networking/resource_vkcs_networking_port_secgroup_associate_test.go index 12ce0714..f89c20e8 100644 --- a/vkcs/networking/resource_vkcs_networking_port_secgroup_associate_test.go +++ b/vkcs/networking/resource_vkcs_networking_port_secgroup_associate_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_port_test.go b/vkcs/networking/resource_vkcs_networking_port_test.go index 7030c1cf..4b232904 100644 --- a/vkcs/networking/resource_vkcs_networking_port_test.go +++ b/vkcs/networking/resource_vkcs_networking_port_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_router.go b/vkcs/networking/resource_vkcs_networking_router.go index db24aaea..7ccc6878 100644 --- a/vkcs/networking/resource_vkcs_networking_router.go +++ b/vkcs/networking/resource_vkcs_networking_router.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -178,7 +178,7 @@ func resourceNetworkingRouterCreate(ctx context.Context, d *schema.ResourceData, log.Printf("[DEBUG] Waiting for vkcs_networking_router %s to become available.", r.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"BUILD", "PENDING_CREATE", "PENDING_UPDATE"}, Target: []string{"ACTIVE"}, Refresh: resourceNetworkingRouterStateRefreshFunc(networkingClient, r.ID), @@ -341,7 +341,7 @@ func resourceNetworkingRouterDelete(ctx context.Context, d *schema.ResourceData, return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_networking_router")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: resourceNetworkingRouterStateRefreshFunc(networkingClient, d.Id()), diff --git a/vkcs/networking/resource_vkcs_networking_router_interface.go b/vkcs/networking/resource_vkcs_networking_router_interface.go index 0413ba71..b166c753 100644 --- a/vkcs/networking/resource_vkcs_networking_router_interface.go +++ b/vkcs/networking/resource_vkcs_networking_router_interface.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -95,7 +95,7 @@ func resourceNetworkingRouterInterfaceCreate(ctx context.Context, d *schema.Reso log.Printf("[DEBUG] Waiting for vkcs_networking_router_interface %s to become available", r.PortID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"BUILD", "PENDING_CREATE", "PENDING_UPDATE"}, Target: []string{"ACTIVE", "DOWN"}, Refresh: resourceNetworkingRouterInterfaceStateRefreshFunc(networkingClient, r.PortID), @@ -160,7 +160,7 @@ func resourceNetworkingRouterInterfaceDelete(ctx context.Context, d *schema.Reso return diag.Errorf("Error creating VKCS networking client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: resourceNetworkingRouterInterfaceDeleteRefreshFunc(networkingClient, d), diff --git a/vkcs/networking/resource_vkcs_networking_router_interface_test.go b/vkcs/networking/resource_vkcs_networking_router_interface_test.go index 3745626d..92681732 100644 --- a/vkcs/networking/resource_vkcs_networking_router_interface_test.go +++ b/vkcs/networking/resource_vkcs_networking_router_interface_test.go @@ -8,8 +8,8 @@ import ( "github.com/gophercloud/gophercloud/openstack/networking/v2/networks" "github.com/gophercloud/gophercloud/openstack/networking/v2/ports" "github.com/gophercloud/gophercloud/openstack/networking/v2/subnets" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_router_route_test.go b/vkcs/networking/resource_vkcs_networking_router_route_test.go index fc8a2a21..a95b4b7a 100644 --- a/vkcs/networking/resource_vkcs_networking_router_route_test.go +++ b/vkcs/networking/resource_vkcs_networking_router_route_test.go @@ -7,8 +7,8 @@ import ( "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/layer3/routers" "github.com/gophercloud/gophercloud/openstack/networking/v2/networks" "github.com/gophercloud/gophercloud/openstack/networking/v2/subnets" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_router_test.go b/vkcs/networking/resource_vkcs_networking_router_test.go index f77994ee..c4cde927 100644 --- a/vkcs/networking/resource_vkcs_networking_router_test.go +++ b/vkcs/networking/resource_vkcs_networking_router_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_subnet.go b/vkcs/networking/resource_vkcs_networking_subnet.go index d9bb76f0..008c8e5f 100644 --- a/vkcs/networking/resource_vkcs_networking_subnet.go +++ b/vkcs/networking/resource_vkcs_networking_subnet.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -251,7 +251,7 @@ func resourceNetworkingSubnetCreate(ctx context.Context, d *schema.ResourceData, } log.Printf("[DEBUG] Waiting for vkcs_networking_subnet %s to become available", s.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{"ACTIVE"}, Refresh: networkingSubnetStateRefreshFunc(networkingClient, s.ID), Timeout: d.Timeout(schema.TimeoutCreate), @@ -413,7 +413,7 @@ func resourceNetworkingSubnetDelete(ctx context.Context, d *schema.ResourceData, return diag.Errorf("Error creating VKCS networking client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: networkingSubnetStateRefreshFuncDelete(networkingClient, d.Id()), diff --git a/vkcs/networking/resource_vkcs_networking_subnet_route_test.go b/vkcs/networking/resource_vkcs_networking_subnet_route_test.go index d2423ab1..5965d834 100644 --- a/vkcs/networking/resource_vkcs_networking_subnet_route_test.go +++ b/vkcs/networking/resource_vkcs_networking_subnet_route_test.go @@ -7,8 +7,8 @@ import ( "github.com/gophercloud/gophercloud/openstack/networking/v2/extensions/layer3/routers" "github.com/gophercloud/gophercloud/openstack/networking/v2/networks" "github.com/gophercloud/gophercloud/openstack/networking/v2/subnets" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/networking/resource_vkcs_networking_subnet_test.go b/vkcs/networking/resource_vkcs_networking_subnet_test.go index d203e265..ee0504b7 100644 --- a/vkcs/networking/resource_vkcs_networking_subnet_test.go +++ b/vkcs/networking/resource_vkcs_networking_subnet_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/provider/provider.go b/vkcs/provider/provider.go index d7d5fbcc..9d7ab3a7 100755 --- a/vkcs/provider/provider.go +++ b/vkcs/provider/provider.go @@ -3,191 +3,98 @@ package provider import ( "context" - "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/blockstorage" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/compute" + "github.com/hashicorp/terraform-plugin-framework/datasource" + "github.com/hashicorp/terraform-plugin-framework/provider" + "github.com/hashicorp/terraform-plugin-framework/provider/schema" + "github.com/hashicorp/terraform-plugin-framework/resource" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/db" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/firewall" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/images" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/keymanager" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/kubernetes" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/lb" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/networking" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/publicdns" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/regions" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/sharedfilesystem" - "github.com/vk-cs/terraform-provider-vkcs/vkcs/vpnaas" + wrapper "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/providerwrapper/framework" +) + +// Ensure the implementation satisfies the expected interfaces +var ( + _ provider.Provider = &vkcsProvider{} ) -// Provider returns a schema.Provider for VKCS. -func ProviderBase() *schema.Provider { - provider := &schema.Provider{ - Schema: map[string]*schema.Schema{ - "auth_url": { - Type: schema.TypeString, +// Provider is a helper function to simplify provider server and testing implementation. +func Provider() provider.Provider { + return wrapper.NewProviderWrapper(ProviderBase()) +} + +func ProviderBase() provider.Provider { + return &vkcsProvider{} +} + +// vkcsProvider is the provider implementation. +type vkcsProvider struct{} + +// Metadata returns the provider type name. +func (p *vkcsProvider) Metadata(_ context.Context, _ provider.MetadataRequest, resp *provider.MetadataResponse) { + resp.TypeName = "vkcs_framework" +} + +// Schema defines the provider-level schema for configuration data. +func (p *vkcsProvider) Schema(_ context.Context, _ provider.SchemaRequest, resp *provider.SchemaResponse) { + resp.Schema = schema.Schema{ + Attributes: map[string]schema.Attribute{ + "auth_url": schema.StringAttribute{ Optional: true, - DefaultFunc: schema.EnvDefaultFunc("OS_AUTH_URL", clients.DefaultIdentityEndpoint), Description: "The Identity authentication URL.", }, - "project_id": { - Type: schema.TypeString, - Required: true, - DefaultFunc: schema.EnvDefaultFunc("OS_PROJECT_ID", ""), + "project_id": schema.StringAttribute{ + Optional: true, Description: "The ID of Project to login with.", }, - "password": { - Type: schema.TypeString, - Required: true, + "password": schema.StringAttribute{ + Optional: true, Sensitive: true, - DefaultFunc: schema.EnvDefaultFunc("OS_PASSWORD", ""), Description: "Password to login with.", }, - "username": { - Type: schema.TypeString, - Required: true, - DefaultFunc: schema.EnvDefaultFunc("OS_USERNAME", ""), + "username": schema.StringAttribute{ + Optional: true, Description: "User name to login with.", }, - "user_domain_id": { - Type: schema.TypeString, + "user_domain_id": schema.StringAttribute{ Optional: true, - DefaultFunc: schema.EnvDefaultFunc("OS_USER_DOMAIN_ID", ""), Description: "The id of the domain where the user resides.", }, - "user_domain_name": { - Type: schema.TypeString, + "user_domain_name": schema.StringAttribute{ Optional: true, - DefaultFunc: schema.EnvDefaultFunc("OS_USER_DOMAIN_NAME", clients.DefaultUserDomainName), Description: "The name of the domain where the user resides.", }, - "region": { - Type: schema.TypeString, + "region": schema.StringAttribute{ Optional: true, - DefaultFunc: schema.EnvDefaultFunc("OS_REGION_NAME", clients.DefaultRegionName), Description: "A region to use.", }, - "cloud_containers_api_version": { - Type: schema.TypeString, + "cloud_containers_api_version": schema.StringAttribute{ Optional: true, - Default: clients.ContainerInfraAPIVersion, Description: "Cloud Containers API version to use. _note_ Only for custom VKCS deployments.", }, }, - - DataSourcesMap: map[string]*schema.Resource{ - "vkcs_compute_keypair": compute.DataSourceComputeKeypair(), - "vkcs_compute_instance": compute.DataSourceComputeInstance(), - "vkcs_compute_availability_zones": compute.DataSourceComputeAvailabilityZones(), - "vkcs_compute_flavor": compute.DataSourceComputeFlavor(), - "vkcs_compute_quotaset": compute.DataSourceComputeQuotaset(), - "vkcs_images_image": images.DataSourceImagesImage(), - "vkcs_networking_network": networking.DataSourceNetworkingNetwork(), - "vkcs_networking_subnet": networking.DataSourceNetworkingSubnet(), - "vkcs_networking_router": networking.DataSourceNetworkingRouter(), - "vkcs_networking_port": networking.DataSourceNetworkingPort(), - "vkcs_networking_secgroup": firewall.DataSourceNetworkingSecGroup(), - "vkcs_networking_floatingip": networking.DataSourceNetworkingFloatingIP(), - "vkcs_keymanager_secret": keymanager.DataSourceKeyManagerSecret(), - "vkcs_keymanager_container": keymanager.DataSourceKeyManagerContainer(), - "vkcs_blockstorage_volume": blockstorage.DataSourceBlockStorageVolume(), - "vkcs_blockstorage_snapshot": blockstorage.DataSourceBlockStorageSnapshot(), - "vkcs_lb_loadbalancer": lb.DataSourceLoadBalancer(), - "vkcs_sharedfilesystem_sharenetwork": sharedfilesystem.DataSourceSharedFilesystemShareNetwork(), - "vkcs_sharedfilesystem_share": sharedfilesystem.DataSourceSharedFilesystemShare(), - "vkcs_db_database": db.DataSourceDatabaseDatabase(), - "vkcs_db_datastore": db.DataSourceDatabaseDatastore(), - "vkcs_db_datastore_capabilities": db.DataSourceDatabaseDatastoreCapabilities(), - "vkcs_db_datastore_parameters": db.DataSourceDatabaseDatastoreParameters(), - "vkcs_db_datastores": db.DataSourceDatabaseDatastores(), - "vkcs_db_instance": db.DataSourceDatabaseInstance(), - "vkcs_db_user": db.DataSourceDatabaseUser(), - "vkcs_db_backup": db.DataSourceDatabaseBackup(), - "vkcs_db_config_group": db.DataSourceDatabaseConfigGroup(), - "vkcs_kubernetes_clustertemplate": kubernetes.DataSourceKubernetesClusterTemplate(), - "vkcs_kubernetes_clustertemplates": kubernetes.DataSourceKubernetesClusterTemplates(), - "vkcs_kubernetes_cluster": kubernetes.DataSourceKubernetesCluster(), - "vkcs_kubernetes_node_group": kubernetes.DataSourceKubernetesNodeGroup(), - "vkcs_region": regions.DataSourceVkcsRegion(), - "vkcs_regions": regions.DataSourceVkcsRegions(), - "vkcs_publicdns_zone": publicdns.DataSourcePublicDNSZone(), - }, - - ResourcesMap: map[string]*schema.Resource{ - "vkcs_compute_instance": compute.ResourceComputeInstance(), - "vkcs_compute_interface_attach": compute.ResourceComputeInterfaceAttach(), - "vkcs_compute_keypair": compute.ResourceComputeKeypair(), - "vkcs_compute_volume_attach": compute.ResourceComputeVolumeAttach(), - "vkcs_compute_floatingip_associate": compute.ResourceComputeFloatingIPAssociate(), - "vkcs_compute_servergroup": compute.ResourceComputeServerGroup(), - "vkcs_images_image": images.ResourceImagesImage(), - "vkcs_networking_network": networking.ResourceNetworkingNetwork(), - "vkcs_networking_subnet": networking.ResourceNetworkingSubnet(), - "vkcs_networking_subnet_route": networking.ResourceNetworkingSubnetRoute(), - "vkcs_networking_router": networking.ResourceNetworkingRouter(), - "vkcs_networking_router_interface": networking.ResourceNetworkingRouterInterface(), - "vkcs_networking_router_route": networking.ResourceNetworkingRouterRoute(), - "vkcs_networking_port": networking.ResourceNetworkingPort(), - "vkcs_networking_port_secgroup_associate": networking.ResourceNetworkingPortSecGroupAssociate(), - "vkcs_networking_secgroup": firewall.ResourceNetworkingSecGroup(), - "vkcs_networking_secgroup_rule": firewall.ResourceNetworkingSecGroupRule(), - "vkcs_networking_floatingip": networking.ResourceNetworkingFloating(), - "vkcs_networking_floatingip_associate": networking.ResourceNetworkingFloatingIPAssociate(), - "vkcs_keymanager_secret": keymanager.ResourceKeyManagerSecret(), - "vkcs_keymanager_container": keymanager.ResourceKeyManagerContainer(), - "vkcs_blockstorage_volume": blockstorage.ResourceBlockStorageVolume(), - "vkcs_blockstorage_snapshot": blockstorage.ResourceBlockStorageSnapshot(), - "vkcs_lb_l7policy": lb.ResourceL7Policy(), - "vkcs_lb_l7rule": lb.ResourceL7Rule(), - "vkcs_lb_listener": lb.ResourceListener(), - "vkcs_lb_loadbalancer": lb.ResourceLoadBalancer(), - "vkcs_lb_member": lb.ResourceMember(), - "vkcs_lb_members": lb.ResourceMembers(), - "vkcs_lb_monitor": lb.ResourceMonitor(), - "vkcs_lb_pool": lb.ResourcePool(), - "vkcs_vpnaas_endpoint_group": vpnaas.ResourceEndpointGroup(), - "vkcs_vpnaas_ike_policy": vpnaas.ResourceIKEPolicy(), - "vkcs_vpnaas_ipsec_policy": vpnaas.ResourceIPSecPolicy(), - "vkcs_vpnaas_service": vpnaas.ResourceService(), - "vkcs_vpnaas_site_connection": vpnaas.ResourceSiteConnection(), - "vkcs_sharedfilesystem_securityservice": sharedfilesystem.ResourceSharedFilesystemSecurityService(), - "vkcs_sharedfilesystem_sharenetwork": sharedfilesystem.ResourceSharedFilesystemShareNetwork(), - "vkcs_sharedfilesystem_share": sharedfilesystem.ResourceSharedFilesystemShare(), - "vkcs_sharedfilesystem_share_access": sharedfilesystem.ResourceSharedFilesystemShareAccess(), - "vkcs_db_backup": db.ResourceDatabaseBackup(), - "vkcs_db_instance": db.ResourceDatabaseInstance(), - "vkcs_db_database": db.ResourceDatabaseDatabase(), - "vkcs_db_user": db.ResourceDatabaseUser(), - "vkcs_db_cluster": db.ResourceDatabaseCluster(), - "vkcs_db_cluster_with_shards": db.ResourceDatabaseClusterWithShards(), - "vkcs_db_config_group": db.ResourceDatabaseConfigGroup(), - "vkcs_kubernetes_cluster": kubernetes.ResourceKubernetesCluster(), - "vkcs_kubernetes_node_group": kubernetes.ResourceKubernetesNodeGroup(), - "vkcs_publicdns_zone": publicdns.ResourcePublicDNSZone(), - "vkcs_publicdns_record": publicdns.ResourcePublicDNSRecord(), - }, } +} - provider.ConfigureContextFunc = func(_ context.Context, d *schema.ResourceData) (interface{}, diag.Diagnostics) { - terraformVersion := provider.TerraformVersion - if terraformVersion == "" { - // Terraform 0.12 introduced this field to the protocol - // We can therefore assume that if it's missing it's 0.10 or 0.11 - terraformVersion = "0.11+compatible" - } - return clients.ConfigureProvider(d, terraformVersion) +// Configure prepares a HashiCups API client for data sources and resources. +func (p *vkcsProvider) Configure(ctx context.Context, req provider.ConfigureRequest, resp *provider.ConfigureResponse) { + config, diags := clients.ConfigureProvider(ctx, req) + resp.Diagnostics.Append(diags...) + if resp.Diagnostics.HasError() { + return } - - return provider + resp.DataSourceData = config + resp.ResourceData = config } -// Provider returns a schema.Provider for VKCS. -func Provider() *schema.Provider { - provider, err := wrapProvider(ProviderBase()) - if err != nil { - panic(err) +// DataSources defines the data sources implemented in the provider. +func (p *vkcsProvider) DataSources(_ context.Context) []func() datasource.DataSource { + return []func() datasource.DataSource{ + db.NewDatastoreCapabilitiesDataSource, } +} - return provider +// Resources defines the resources implemented in the provider. +func (p *vkcsProvider) Resources(_ context.Context) []func() resource.Resource { + return nil } diff --git a/vkcs/provider/provider_test.go b/vkcs/provider/provider_test.go index 63b1797e..6dcff998 100755 --- a/vkcs/provider/provider_test.go +++ b/vkcs/provider/provider_test.go @@ -12,13 +12,13 @@ import ( ) func TestProvider(t *testing.T) { - if err := provider.Provider().InternalValidate(); err != nil { + if err := provider.SDKProvider().InternalValidate(); err != nil { t.Fatalf("err: %s", err) } } func TestProvider_impl(t *testing.T) { - var _ = provider.Provider() + var _ = provider.SDKProvider() } // Steps for configuring OpenStack with SSL validation are here: @@ -31,7 +31,7 @@ func TestAccProvider_caCertFile(t *testing.T) { t.Skip("OS_CACERT is not set; skipping VKCS CA test.") } - p := provider.Provider() + p := provider.SDKProvider() caFile, err := envVarFile("OS_CACERT") if err != nil { @@ -57,7 +57,7 @@ func TestAccProvider_caCertString(t *testing.T) { t.Skip("OS_CACERT is not set; skipping VKCS CA test.") } - p := provider.Provider() + p := provider.SDKProvider() caContents, err := envVarContents("OS_CACERT") if err != nil { @@ -81,7 +81,7 @@ func TestAccProvider_clientCertFile(t *testing.T) { t.Skip("OS_CERT or OS_KEY is not set; skipping VKCS client SSL auth test.") } - p := provider.Provider() + p := provider.SDKProvider() certFile, err := envVarFile("OS_CERT") if err != nil { @@ -113,7 +113,7 @@ func TestAccProvider_clientCertString(t *testing.T) { t.Skip("OS_CERT or OS_KEY is not set; skipping VKCS client SSL auth test.") } - p := provider.Provider() + p := provider.SDKProvider() certContents, err := envVarContents("OS_CERT") if err != nil { diff --git a/vkcs/provider/sdk_provider.go b/vkcs/provider/sdk_provider.go new file mode 100644 index 00000000..4a9db5da --- /dev/null +++ b/vkcs/provider/sdk_provider.go @@ -0,0 +1,186 @@ +package provider + +import ( + "context" + + sdkdiag "github.com/hashicorp/terraform-plugin-sdk/v2/diag" + sdkschema "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" + + "github.com/vk-cs/terraform-provider-vkcs/vkcs/blockstorage" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/compute" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/db" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/firewall" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/images" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/keymanager" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/kubernetes" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/lb" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/networking" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/publicdns" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/regions" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/sharedfilesystem" + "github.com/vk-cs/terraform-provider-vkcs/vkcs/vpnaas" + + wrapper "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/providerwrapper/sdk" +) + +// SDKProvider returns a SDKv2 schema.Provider for VKCS. +func SDKProvider() *sdkschema.Provider { + provider, err := wrapper.WrapProvider(SDKProviderBase()) + if err != nil { + panic(err) + } + + return provider +} + +func SDKProviderBase() *sdkschema.Provider { + provider := &sdkschema.Provider{ + Schema: map[string]*sdkschema.Schema{ + "auth_url": { + Type: sdkschema.TypeString, + Optional: true, + Description: "The Identity authentication URL.", + }, + "project_id": { + Type: sdkschema.TypeString, + Optional: true, + Description: "The ID of Project to login with.", + }, + "password": { + Type: sdkschema.TypeString, + Optional: true, + Sensitive: true, + Description: "Password to login with.", + }, + "username": { + Type: sdkschema.TypeString, + Optional: true, + Description: "User name to login with.", + }, + "user_domain_id": { + Type: sdkschema.TypeString, + Optional: true, + Description: "The id of the domain where the user resides.", + }, + "user_domain_name": { + Type: sdkschema.TypeString, + Optional: true, + Description: "The name of the domain where the user resides.", + }, + "region": { + Type: sdkschema.TypeString, + Optional: true, + Description: "A region to use.", + }, + "cloud_containers_api_version": { + Type: sdkschema.TypeString, + Optional: true, + Description: "Cloud Containers API version to use. _note_ Only for custom VKCS deployments.", + }, + }, + + DataSourcesMap: map[string]*sdkschema.Resource{ + "vkcs_compute_keypair": compute.DataSourceComputeKeypair(), + "vkcs_compute_instance": compute.DataSourceComputeInstance(), + "vkcs_compute_availability_zones": compute.DataSourceComputeAvailabilityZones(), + "vkcs_compute_flavor": compute.DataSourceComputeFlavor(), + "vkcs_compute_quotaset": compute.DataSourceComputeQuotaset(), + "vkcs_images_image": images.DataSourceImagesImage(), + "vkcs_networking_network": networking.DataSourceNetworkingNetwork(), + "vkcs_networking_subnet": networking.DataSourceNetworkingSubnet(), + "vkcs_networking_router": networking.DataSourceNetworkingRouter(), + "vkcs_networking_port": networking.DataSourceNetworkingPort(), + "vkcs_networking_secgroup": firewall.DataSourceNetworkingSecGroup(), + "vkcs_networking_floatingip": networking.DataSourceNetworkingFloatingIP(), + "vkcs_keymanager_secret": keymanager.DataSourceKeyManagerSecret(), + "vkcs_keymanager_container": keymanager.DataSourceKeyManagerContainer(), + "vkcs_blockstorage_volume": blockstorage.DataSourceBlockStorageVolume(), + "vkcs_blockstorage_snapshot": blockstorage.DataSourceBlockStorageSnapshot(), + "vkcs_lb_loadbalancer": lb.DataSourceLoadBalancer(), + "vkcs_sharedfilesystem_sharenetwork": sharedfilesystem.DataSourceSharedFilesystemShareNetwork(), + "vkcs_sharedfilesystem_share": sharedfilesystem.DataSourceSharedFilesystemShare(), + "vkcs_db_database": db.DataSourceDatabaseDatabase(), + "vkcs_db_datastore": db.DataSourceDatabaseDatastore(), + "vkcs_db_datastore_parameters": db.DataSourceDatabaseDatastoreParameters(), + "vkcs_db_datastores": db.DataSourceDatabaseDatastores(), + "vkcs_db_instance": db.DataSourceDatabaseInstance(), + "vkcs_db_user": db.DataSourceDatabaseUser(), + "vkcs_db_backup": db.DataSourceDatabaseBackup(), + "vkcs_db_config_group": db.DataSourceDatabaseConfigGroup(), + "vkcs_kubernetes_clustertemplate": kubernetes.DataSourceKubernetesClusterTemplate(), + "vkcs_kubernetes_clustertemplates": kubernetes.DataSourceKubernetesClusterTemplates(), + "vkcs_kubernetes_cluster": kubernetes.DataSourceKubernetesCluster(), + "vkcs_kubernetes_node_group": kubernetes.DataSourceKubernetesNodeGroup(), + "vkcs_region": regions.DataSourceVkcsRegion(), + "vkcs_regions": regions.DataSourceVkcsRegions(), + "vkcs_publicdns_zone": publicdns.DataSourcePublicDNSZone(), + }, + + ResourcesMap: map[string]*sdkschema.Resource{ + "vkcs_compute_instance": compute.ResourceComputeInstance(), + "vkcs_compute_interface_attach": compute.ResourceComputeInterfaceAttach(), + "vkcs_compute_keypair": compute.ResourceComputeKeypair(), + "vkcs_compute_volume_attach": compute.ResourceComputeVolumeAttach(), + "vkcs_compute_floatingip_associate": compute.ResourceComputeFloatingIPAssociate(), + "vkcs_compute_servergroup": compute.ResourceComputeServerGroup(), + "vkcs_images_image": images.ResourceImagesImage(), + "vkcs_networking_network": networking.ResourceNetworkingNetwork(), + "vkcs_networking_subnet": networking.ResourceNetworkingSubnet(), + "vkcs_networking_subnet_route": networking.ResourceNetworkingSubnetRoute(), + "vkcs_networking_router": networking.ResourceNetworkingRouter(), + "vkcs_networking_router_interface": networking.ResourceNetworkingRouterInterface(), + "vkcs_networking_router_route": networking.ResourceNetworkingRouterRoute(), + "vkcs_networking_port": networking.ResourceNetworkingPort(), + "vkcs_networking_port_secgroup_associate": networking.ResourceNetworkingPortSecGroupAssociate(), + "vkcs_networking_secgroup": firewall.ResourceNetworkingSecGroup(), + "vkcs_networking_secgroup_rule": firewall.ResourceNetworkingSecGroupRule(), + "vkcs_networking_floatingip": networking.ResourceNetworkingFloating(), + "vkcs_networking_floatingip_associate": networking.ResourceNetworkingFloatingIPAssociate(), + "vkcs_keymanager_secret": keymanager.ResourceKeyManagerSecret(), + "vkcs_keymanager_container": keymanager.ResourceKeyManagerContainer(), + "vkcs_blockstorage_volume": blockstorage.ResourceBlockStorageVolume(), + "vkcs_blockstorage_snapshot": blockstorage.ResourceBlockStorageSnapshot(), + "vkcs_lb_l7policy": lb.ResourceL7Policy(), + "vkcs_lb_l7rule": lb.ResourceL7Rule(), + "vkcs_lb_listener": lb.ResourceListener(), + "vkcs_lb_loadbalancer": lb.ResourceLoadBalancer(), + "vkcs_lb_member": lb.ResourceMember(), + "vkcs_lb_members": lb.ResourceMembers(), + "vkcs_lb_monitor": lb.ResourceMonitor(), + "vkcs_lb_pool": lb.ResourcePool(), + "vkcs_vpnaas_endpoint_group": vpnaas.ResourceEndpointGroup(), + "vkcs_vpnaas_ike_policy": vpnaas.ResourceIKEPolicy(), + "vkcs_vpnaas_ipsec_policy": vpnaas.ResourceIPSecPolicy(), + "vkcs_vpnaas_service": vpnaas.ResourceService(), + "vkcs_vpnaas_site_connection": vpnaas.ResourceSiteConnection(), + "vkcs_sharedfilesystem_securityservice": sharedfilesystem.ResourceSharedFilesystemSecurityService(), + "vkcs_sharedfilesystem_sharenetwork": sharedfilesystem.ResourceSharedFilesystemShareNetwork(), + "vkcs_sharedfilesystem_share": sharedfilesystem.ResourceSharedFilesystemShare(), + "vkcs_sharedfilesystem_share_access": sharedfilesystem.ResourceSharedFilesystemShareAccess(), + "vkcs_db_backup": db.ResourceDatabaseBackup(), + "vkcs_db_instance": db.ResourceDatabaseInstance(), + "vkcs_db_database": db.ResourceDatabaseDatabase(), + "vkcs_db_user": db.ResourceDatabaseUser(), + "vkcs_db_cluster": db.ResourceDatabaseCluster(), + "vkcs_db_cluster_with_shards": db.ResourceDatabaseClusterWithShards(), + "vkcs_db_config_group": db.ResourceDatabaseConfigGroup(), + "vkcs_kubernetes_cluster": kubernetes.ResourceKubernetesCluster(), + "vkcs_kubernetes_node_group": kubernetes.ResourceKubernetesNodeGroup(), + "vkcs_publicdns_zone": publicdns.ResourcePublicDNSZone(), + "vkcs_publicdns_record": publicdns.ResourcePublicDNSRecord(), + }, + } + + provider.ConfigureContextFunc = func(_ context.Context, d *sdkschema.ResourceData) (interface{}, sdkdiag.Diagnostics) { + terraformVersion := provider.TerraformVersion + if terraformVersion == "" { + // Terraform 0.12 introduced this field to the protocol + // We can therefore assume that if it's missing it's 0.10 or 0.11 + terraformVersion = "0.11+compatible" + } + return clients.ConfigureSdkProvider(d, terraformVersion) + } + + return provider +} diff --git a/vkcs/provider/wrapper_provider.go b/vkcs/provider/wrapper_provider.go deleted file mode 100644 index 338e9fcc..00000000 --- a/vkcs/provider/wrapper_provider.go +++ /dev/null @@ -1,82 +0,0 @@ -package provider - -import ( - "encoding/json" - "fmt" - "strings" - - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" - "github.com/vk-cs/terraform-provider-vkcs/helpers/providerjson" -) - -//go:generate go run ../internal/generate/providerschema/main.go -schemajson ../../.release/provider-schema.json - -func wrapProvider(p *schema.Provider) (*schema.Provider, error) { - var wrapperBase providerjson.ProviderWrapper - err := json.Unmarshal([]byte(providerSchemaBase), &wrapperBase) - if err != nil { - return nil, err - } - - base := wrapperBase.ProviderSchema - - for resource, rs := range p.ResourcesMap { - bRs := base.ResourcesMap[resource] - if bRs.NewSince != "" { - rs.Description += fmt.Sprintf(" **New since %s**.", bRs.NewSince) - } - - for propertyName, propertySchema := range rs.Schema { - // Get the same from the base json - bS := bRs.Schema[propertyName] - customizeSchema(bS, propertySchema, propertyName) - } - } - - for resource, rs := range p.DataSourcesMap { - bRs := base.DataSourcesMap[resource] - if bRs.NewSince != "" { - rs.Description += fmt.Sprintf(" **New since %s**.", bRs.NewSince) - } - - for propertyName, propertySchema := range rs.Schema { - // Get the same from the base json - bS := bRs.Schema[propertyName] - customizeSchema(bS, propertySchema, propertyName) - } - } - - return p, nil -} - -func customizeSchema(baseS providerjson.SchemaJSON, s *schema.Schema, nodeName string) { - if s.Deprecated != "" && !strings.Contains(strings.ToLower(s.Description), "deprecated") { - s.Description += fmt.Sprintf(" **Deprecated** %s.", strings.TrimSuffix(s.Deprecated, ".")) - } - - if s.Deprecated == "" && baseS.NewSince != "" { - s.Description += fmt.Sprintf(" **New since %s**.", baseS.NewSince) - } - - if nodeIsBlock(s) { - current := s.Elem.(*schema.Resource).Schema - var base map[string]providerjson.SchemaJSON - if providerjson.NodeIsBlock(baseS) { - base = baseS.Elem.(providerjson.ResourceJSON).Schema - } - for k, c := range current { - b := base[k] - customizeSchema(b, c, k) - } - } -} - -func nodeIsBlock(input *schema.Schema) bool { - if input.Type == schema.TypeList || input.Type == schema.TypeSet { - if _, ok := input.Elem.(*schema.Resource); ok { - return true - } - } - - return false -} diff --git a/vkcs/publicdns/data_source_vkcs_publicdns_zone_test.go b/vkcs/publicdns/data_source_vkcs_publicdns_zone_test.go index 9476da8d..5d57bfad 100644 --- a/vkcs/publicdns/data_source_vkcs_publicdns_zone_test.go +++ b/vkcs/publicdns/data_source_vkcs_publicdns_zone_test.go @@ -4,14 +4,14 @@ import ( "fmt" "testing" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) func TestAccPublicDNSZoneDataSource_basic(t *testing.T) { - zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", sdk_acctest.RandString(5)) + zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", fm_acctest.RandString(5)) resource.Test(t, resource.TestCase{ PreCheck: func() { acctest.AccTestPreCheck(t) }, diff --git a/vkcs/publicdns/import_vkcs_publicdns_record_test.go b/vkcs/publicdns/import_vkcs_publicdns_record_test.go index 5e957070..70f23615 100644 --- a/vkcs/publicdns/import_vkcs_publicdns_record_test.go +++ b/vkcs/publicdns/import_vkcs_publicdns_record_test.go @@ -5,15 +5,15 @@ import ( "strings" "testing" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) func TestAccPublicDNSRecord_importBasic(t *testing.T) { resourceName := "vkcs_publicdns_record.record_a" - zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", sdk_acctest.RandString(5)) + zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", fm_acctest.RandString(5)) resource.Test(t, resource.TestCase{ ProviderFactories: acctest.AccTestProviders, diff --git a/vkcs/publicdns/import_vkcs_publicdns_zone_test.go b/vkcs/publicdns/import_vkcs_publicdns_zone_test.go index c23f63d2..8d5ac47a 100644 --- a/vkcs/publicdns/import_vkcs_publicdns_zone_test.go +++ b/vkcs/publicdns/import_vkcs_publicdns_zone_test.go @@ -4,14 +4,14 @@ import ( "fmt" "testing" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) func TestAccPublicDNSZone_importBasic(t *testing.T) { resourceName := "vkcs_publicdns_zone.zone_1" - zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", sdk_acctest.RandString(5)) + zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", fm_acctest.RandString(5)) resource.Test(t, resource.TestCase{ ProviderFactories: acctest.AccTestProviders, diff --git a/vkcs/publicdns/publicdns_record.go b/vkcs/publicdns/publicdns_record.go index 00c17d33..81fbb475 100644 --- a/vkcs/publicdns/publicdns_record.go +++ b/vkcs/publicdns/publicdns_record.go @@ -5,7 +5,7 @@ import ( "strings" "github.com/gophercloud/gophercloud" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/publicdns/v2/records" ) @@ -45,7 +45,7 @@ func PublicDNSRecordExtract(res recordResult, recordType string) (interface{}, e return r, err } -func publicDNSRecordStateRefreshFunc(client *gophercloud.ServiceClient, zoneID string, id string, recordType string) resource.StateRefreshFunc { +func publicDNSRecordStateRefreshFunc(client *gophercloud.ServiceClient, zoneID string, id string, recordType string) retry.StateRefreshFunc { return func() (interface{}, string, error) { res := records.Get(client, zoneID, id, recordType) record, err := PublicDNSRecordExtract(res, recordType) diff --git a/vkcs/publicdns/publicdns_zone.go b/vkcs/publicdns/publicdns_zone.go index b5e6f1bd..51becdec 100644 --- a/vkcs/publicdns/publicdns_zone.go +++ b/vkcs/publicdns/publicdns_zone.go @@ -2,11 +2,11 @@ package publicdns import ( "github.com/gophercloud/gophercloud" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/publicdns/v2/zones" ) -func publicDNSZoneStateRefreshFunc(client *gophercloud.ServiceClient, zoneID string) resource.StateRefreshFunc { +func publicDNSZoneStateRefreshFunc(client *gophercloud.ServiceClient, zoneID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { zone, err := zones.Get(client, zoneID).Extract() diff --git a/vkcs/publicdns/resource_vkcs_publicdns_record.go b/vkcs/publicdns/resource_vkcs_publicdns_record.go index a903ef88..3d475310 100644 --- a/vkcs/publicdns/resource_vkcs_publicdns_record.go +++ b/vkcs/publicdns/resource_vkcs_publicdns_record.go @@ -11,7 +11,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/mitchellh/mapstructure" @@ -391,7 +391,7 @@ func resourcePublicDNSRecordDelete(ctx context.Context, d *schema.ResourceData, fmt.Sprintf("Error deleting vkcs_publicdns_record: zone_id: %s, type: %s, id:", zoneID, recordType))) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{recordStatusActive}, Target: []string{recordStatusDeleted}, Refresh: publicDNSRecordStateRefreshFunc(client, zoneID, d.Id(), recordType), diff --git a/vkcs/publicdns/resource_vkcs_publicdns_record_test.go b/vkcs/publicdns/resource_vkcs_publicdns_record_test.go index 88c01601..81ac850b 100644 --- a/vkcs/publicdns/resource_vkcs_publicdns_record_test.go +++ b/vkcs/publicdns/resource_vkcs_publicdns_record_test.go @@ -4,9 +4,9 @@ import ( "fmt" "testing" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/publicdns/v2/records" @@ -18,7 +18,7 @@ import ( func TestAccPublicDNSRecord_basic(t *testing.T) { var z zones.Zone var r map[string]interface{} - zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", sdk_acctest.RandString(5)) + zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", fm_acctest.RandString(5)) resource.Test(t, resource.TestCase{ ProviderFactories: acctest.AccTestProviders, @@ -40,7 +40,7 @@ func TestAccPublicDNSRecord_basic(t *testing.T) { } func TestAccPublicDNSRecord_update(t *testing.T) { - zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", sdk_acctest.RandString(5)) + zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", fm_acctest.RandString(5)) resource.Test(t, resource.TestCase{ ProviderFactories: acctest.AccTestProviders, diff --git a/vkcs/publicdns/resource_vkcs_publicdns_zone.go b/vkcs/publicdns/resource_vkcs_publicdns_zone.go index 808728a5..ca1ebfc0 100644 --- a/vkcs/publicdns/resource_vkcs_publicdns_zone.go +++ b/vkcs/publicdns/resource_vkcs_publicdns_zone.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/publicdns/v2/zones" @@ -211,7 +211,7 @@ func resourcePublicDNSZoneDelete(ctx context.Context, d *schema.ResourceData, me return diag.FromErr(util.CheckDeleted(d, err, "Error deleting vkcs_publicdns_zone")) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{zoneStatusActive}, Target: []string{zoneStatusDeleted}, Refresh: publicDNSZoneStateRefreshFunc(client, d.Id()), diff --git a/vkcs/publicdns/resource_vkcs_publicdns_zone_test.go b/vkcs/publicdns/resource_vkcs_publicdns_zone_test.go index 2f13b591..3c9dce50 100644 --- a/vkcs/publicdns/resource_vkcs_publicdns_zone_test.go +++ b/vkcs/publicdns/resource_vkcs_publicdns_zone_test.go @@ -4,9 +4,9 @@ import ( "fmt" "testing" - sdk_acctest "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + fm_acctest "github.com/hashicorp/terraform-plugin-testing/helper/acctest" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/publicdns/v2/zones" @@ -14,7 +14,7 @@ import ( func TestAccPublicDNSZone_basic(t *testing.T) { var z zones.Zone - zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", sdk_acctest.RandString(5)) + zoneName := fmt.Sprintf("vkcs-tf-acctest-%s.com", fm_acctest.RandString(5)) resource.Test(t, resource.TestCase{ ProviderFactories: acctest.AccTestProviders, diff --git a/vkcs/regions/data_source_vkcs_region_test.go b/vkcs/regions/data_source_vkcs_region_test.go index f13af247..3497dd1b 100755 --- a/vkcs/regions/data_source_vkcs_region_test.go +++ b/vkcs/regions/data_source_vkcs_region_test.go @@ -3,7 +3,7 @@ package regions_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/regions/data_source_vkcs_regions_test.go b/vkcs/regions/data_source_vkcs_regions_test.go index a5cf60a2..cd091db1 100755 --- a/vkcs/regions/data_source_vkcs_regions_test.go +++ b/vkcs/regions/data_source_vkcs_regions_test.go @@ -5,8 +5,8 @@ import ( "strconv" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/sharedfilesystem/data_source_vkcs_sharedfilesystem_share_test.go b/vkcs/sharedfilesystem/data_source_vkcs_sharedfilesystem_share_test.go index de047b02..5c700b4c 100644 --- a/vkcs/sharedfilesystem/data_source_vkcs_sharedfilesystem_share_test.go +++ b/vkcs/sharedfilesystem/data_source_vkcs_sharedfilesystem_share_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/sharedfilesystem/data_source_vkcs_sharedfilesystem_sharenetwork_test.go b/vkcs/sharedfilesystem/data_source_vkcs_sharedfilesystem_sharenetwork_test.go index 3a1b0693..acbf83ca 100644 --- a/vkcs/sharedfilesystem/data_source_vkcs_sharedfilesystem_sharenetwork_test.go +++ b/vkcs/sharedfilesystem/data_source_vkcs_sharedfilesystem_sharenetwork_test.go @@ -3,7 +3,7 @@ package sharedfilesystem_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_securityservice_test.go b/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_securityservice_test.go index 4c1357ba..6febf88d 100644 --- a/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_securityservice_test.go +++ b/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_securityservice_test.go @@ -3,7 +3,7 @@ package sharedfilesystem_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_share_access_test.go b/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_share_access_test.go index 4192d9ff..850ee925 100644 --- a/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_share_access_test.go +++ b/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_share_access_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_share_test.go b/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_share_test.go index 061b2745..c1d1a382 100644 --- a/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_share_test.go +++ b/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_share_test.go @@ -3,7 +3,7 @@ package sharedfilesystem_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_sharenetwork_test.go b/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_sharenetwork_test.go index 3313a65a..e40b95f0 100644 --- a/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_sharenetwork_test.go +++ b/vkcs/sharedfilesystem/import_vkcs_sharedfilesystem_sharenetwork_test.go @@ -3,7 +3,7 @@ package sharedfilesystem_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_securityservice_test.go b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_securityservice_test.go index b583b335..4555781e 100644 --- a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_securityservice_test.go +++ b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_securityservice_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share.go b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share.go index 047b0c68..94f5ee29 100644 --- a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share.go +++ b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -164,7 +164,7 @@ func resourceSharedFilesystemShareCreate(ctx context.Context, d *schema.Resource log.Printf("[DEBUG] Attempting to create share") var share *shares.Share - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { share, err = shares.Create(sfsClient, createOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -263,7 +263,7 @@ func resourceSharedFilesystemShareUpdate(ctx context.Context, d *schema.Resource } log.Printf("[DEBUG] Attempting to update share") - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { _, err := shares.Update(sfsClient, d.Id(), updateOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -297,7 +297,7 @@ func resourceSharedFilesystemShareUpdate(ctx context.Context, d *schema.Resource pending = append(pending, "extending") resizeOpts := shares.ExtendOpts{NewSize: newSize.(int)} log.Printf("[DEBUG] Resizing share %s with options: %#v", d.Id(), resizeOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err := shares.Extend(sfsClient, d.Id(), resizeOpts).Err log.Printf("[DEBUG] Resizing share %s with options: %#v", d.Id(), resizeOpts) if err != nil { @@ -309,7 +309,7 @@ func resourceSharedFilesystemShareUpdate(ctx context.Context, d *schema.Resource pending = append(pending, "shrinking") resizeOpts := shares.ShrinkOpts{NewSize: newSize.(int)} log.Printf("[DEBUG] Resizing share %s with options: %#v", d.Id(), resizeOpts) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err := shares.Shrink(sfsClient, d.Id(), resizeOpts).Err log.Printf("[DEBUG] Resizing share %s with options: %#v", d.Id(), resizeOpts) if err != nil { @@ -349,7 +349,7 @@ func resourceSharedFilesystemShareDelete(ctx context.Context, d *schema.Resource timeout := d.Timeout(schema.TimeoutDelete) log.Printf("[DEBUG] Attempting to delete share %s", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = shares.Delete(sfsClient, d.Id()).ExtractErr() if err != nil { return util.CheckForRetryableError(err) @@ -386,7 +386,7 @@ func resourceSharedFilesystemShareDelete(ctx context.Context, d *schema.Resource func waitForSFShare(ctx context.Context, sfsClient *gophercloud.ServiceClient, id string, target string, pending []string, timeout time.Duration) error { log.Printf("[DEBUG] Waiting for share %s to become %s.", id, target) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{target}, Pending: pending, Refresh: resourceSFShareRefreshFunc(sfsClient, id), @@ -416,7 +416,7 @@ func waitForSFShare(ctx context.Context, sfsClient *gophercloud.ServiceClient, i return nil } -func resourceSFShareRefreshFunc(sfsClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func resourceSFShareRefreshFunc(sfsClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { share, err := shares.Get(sfsClient, id).Extract() if err != nil { diff --git a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_access.go b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_access.go index 226d70eb..5b9de609 100644 --- a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_access.go +++ b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_access.go @@ -8,7 +8,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/validation" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" @@ -108,7 +108,7 @@ func resourceSharedFilesystemShareAccessCreate(ctx context.Context, d *schema.Re timeout := d.Timeout(schema.TimeoutCreate) var access *shares.AccessRight - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { access, err = shares.GrantAccess(sfsClient, shareID, grantOpts).Extract() if err != nil { return util.CheckForRetryableError(err) @@ -128,7 +128,7 @@ func resourceSharedFilesystemShareAccessCreate(ctx context.Context, d *schema.Re } log.Printf("[DEBUG] Waiting for vkcs_sharedfilesystem_share_access %s to become available.", access.ID) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{"active"}, Pending: []string{"new", "queued_to_apply", "applying"}, Refresh: sharedFilesystemShareAccessStateRefreshFunc(sfsClient, shareID, access.ID), @@ -196,7 +196,7 @@ func resourceSharedFilesystemShareAccessDelete(ctx context.Context, d *schema.Re timeout := d.Timeout(schema.TimeoutDelete) log.Printf("[DEBUG] Attempting to delete vkcs_sharedfilesystem_share_access %s", d.Id()) - err = resource.RetryContext(ctx, timeout, func() *resource.RetryError { + err = retry.RetryContext(ctx, timeout, func() *retry.RetryError { err = shares.RevokeAccess(sfsClient, shareID, revokeOpts).ExtractErr() if err != nil { return util.CheckForRetryableError(err) @@ -220,7 +220,7 @@ func resourceSharedFilesystemShareAccessDelete(ctx context.Context, d *schema.Re } log.Printf("[DEBUG] Waiting for vkcs_sharedfilesystem_share_access %s to become denied.", d.Id()) - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Target: []string{"denied"}, Pending: []string{"active", "new", "queued_to_deny", "denying"}, Refresh: sharedFilesystemShareAccessStateRefreshFunc(sfsClient, shareID, d.Id()), diff --git a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_access_test.go b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_access_test.go index 2bc6f4f0..95c4f3df 100644 --- a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_access_test.go +++ b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_access_test.go @@ -5,8 +5,8 @@ import ( "regexp" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/sharedfilesystem" diff --git a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_test.go b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_test.go index 36eb9922..8420908e 100644 --- a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_test.go +++ b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_share_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" diff --git a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_sharenetwork_test.go b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_sharenetwork_test.go index fdf614b9..b9c9d459 100644 --- a/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_sharenetwork_test.go +++ b/vkcs/sharedfilesystem/resource_vkcs_sharedfilesystem_sharenetwork_test.go @@ -8,8 +8,8 @@ import ( "strings" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/sharedfilesystem" diff --git a/vkcs/sharedfilesystem/sharedfilesystem_share_access.go b/vkcs/sharedfilesystem/sharedfilesystem_share_access.go index 9850a2fe..07a34a96 100644 --- a/vkcs/sharedfilesystem/sharedfilesystem_share_access.go +++ b/vkcs/sharedfilesystem/sharedfilesystem_share_access.go @@ -1,13 +1,12 @@ package sharedfilesystem import ( - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/gophercloud/gophercloud" "github.com/gophercloud/gophercloud/openstack/sharedfilesystems/v2/shares" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" ) -func sharedFilesystemShareAccessStateRefreshFunc(client *gophercloud.ServiceClient, shareID string, accessID string) resource.StateRefreshFunc { +func sharedFilesystemShareAccessStateRefreshFunc(client *gophercloud.ServiceClient, shareID string, accessID string) retry.StateRefreshFunc { return func() (interface{}, string, error) { access, err := shares.ListAccessRights(client, shareID).Extract() if err != nil { diff --git a/vkcs/vpnaas/import_vkcs_vpnaas_endpoint_group_test.go b/vkcs/vpnaas/import_vkcs_vpnaas_endpoint_group_test.go index 69e0d4a3..3be64ccc 100644 --- a/vkcs/vpnaas/import_vkcs_vpnaas_endpoint_group_test.go +++ b/vkcs/vpnaas/import_vkcs_vpnaas_endpoint_group_test.go @@ -3,7 +3,7 @@ package vpnaas_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/vpnaas/import_vkcs_vpnaas_ike_policy_test.go b/vkcs/vpnaas/import_vkcs_vpnaas_ike_policy_test.go index 35d9bc02..903d6063 100644 --- a/vkcs/vpnaas/import_vkcs_vpnaas_ike_policy_test.go +++ b/vkcs/vpnaas/import_vkcs_vpnaas_ike_policy_test.go @@ -3,7 +3,7 @@ package vpnaas_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/vpnaas/import_vkcs_vpnaas_ipsecpolicy_test.go b/vkcs/vpnaas/import_vkcs_vpnaas_ipsecpolicy_test.go index c6bc9906..e62aa8ec 100644 --- a/vkcs/vpnaas/import_vkcs_vpnaas_ipsecpolicy_test.go +++ b/vkcs/vpnaas/import_vkcs_vpnaas_ipsecpolicy_test.go @@ -3,7 +3,7 @@ package vpnaas_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/vpnaas/import_vkcs_vpnaas_service_test.go b/vkcs/vpnaas/import_vkcs_vpnaas_service_test.go index f3215c70..2f171f7f 100644 --- a/vkcs/vpnaas/import_vkcs_vpnaas_service_test.go +++ b/vkcs/vpnaas/import_vkcs_vpnaas_service_test.go @@ -3,7 +3,7 @@ package vpnaas_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/vpnaas/import_vkcs_vpnaas_site_connection_test.go b/vkcs/vpnaas/import_vkcs_vpnaas_site_connection_test.go index d3da7ef3..0f73b2ed 100644 --- a/vkcs/vpnaas/import_vkcs_vpnaas_site_connection_test.go +++ b/vkcs/vpnaas/import_vkcs_vpnaas_site_connection_test.go @@ -3,7 +3,7 @@ package vpnaas_test import ( "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" ) diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_endpoint_group.go b/vkcs/vpnaas/resource_vkcs_vpnaas_endpoint_group.go index 8b199001..974bb228 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_endpoint_group.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_endpoint_group.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -99,7 +99,7 @@ func resourceEndpointGroupCreate(ctx context.Context, d *schema.ResourceData, me return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING_CREATE"}, Target: []string{"ACTIVE"}, Refresh: waitForEndpointGroupCreation(networkingClient, group.ID), @@ -177,7 +177,7 @@ func resourceEndpointGroupUpdate(ctx context.Context, d *schema.ResourceData, me if err != nil { return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING_UPDATE"}, Target: []string{"UPDATED"}, Refresh: waitForEndpointGroupUpdate(networkingClient, group.ID), @@ -212,7 +212,7 @@ func resourceEndpointGroupDelete(ctx context.Context, d *schema.ResourceData, me return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"DELETING"}, Target: []string{"DELETED"}, Refresh: waitForEndpointGroupDeletion(networkingClient, d.Id()), @@ -226,7 +226,7 @@ func resourceEndpointGroupDelete(ctx context.Context, d *schema.ResourceData, me return diag.FromErr(err) } -func waitForEndpointGroupDeletion(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForEndpointGroupDeletion(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { group, err := endpointgroups.Get(networkingClient, id).Extract() log.Printf("[DEBUG] Got group %s => %#v", id, group) @@ -244,7 +244,7 @@ func waitForEndpointGroupDeletion(networkingClient *gophercloud.ServiceClient, i } } -func waitForEndpointGroupCreation(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForEndpointGroupCreation(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { group, err := endpointgroups.Get(networkingClient, id).Extract() if err != nil { @@ -254,7 +254,7 @@ func waitForEndpointGroupCreation(networkingClient *gophercloud.ServiceClient, i } } -func waitForEndpointGroupUpdate(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForEndpointGroupUpdate(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { group, err := endpointgroups.Get(networkingClient, id).Extract() if err != nil { diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_endpoint_group_test.go b/vkcs/vpnaas/resource_vkcs_vpnaas_endpoint_group_test.go index 275e75ae..d5092b89 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_endpoint_group_test.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_endpoint_group_test.go @@ -6,8 +6,8 @@ import ( "strings" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_ike_policy.go b/vkcs/vpnaas/resource_vkcs_vpnaas_ike_policy.go index 70f2d7dd..9bfad709 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_ike_policy.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_ike_policy.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -138,7 +138,7 @@ func resourceIKEPolicyCreate(ctx context.Context, d *schema.ResourceData, meta i return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING_CREATE"}, Target: []string{"ACTIVE"}, Refresh: waitForIKEPolicyCreation(networkingClient, policy.ID), @@ -254,7 +254,7 @@ func resourceIKEPolicyUpdate(ctx context.Context, d *schema.ResourceData, meta i if err != nil { return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING_UPDATE"}, Target: []string{"ACTIVE"}, Refresh: waitForIKEPolicyUpdate(networkingClient, d.Id()), @@ -279,7 +279,7 @@ func resourceIKEPolicyDelete(ctx context.Context, d *schema.ResourceData, meta i return diag.Errorf("Error creating VKCS networking client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: waitForIKEPolicyDeletion(networkingClient, d.Id()), @@ -295,7 +295,7 @@ func resourceIKEPolicyDelete(ctx context.Context, d *schema.ResourceData, meta i return nil } -func waitForIKEPolicyDeletion(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForIKEPolicyDeletion(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { err := ikepolicies.Delete(networkingClient, id).Err if err == nil { @@ -306,7 +306,7 @@ func waitForIKEPolicyDeletion(networkingClient *gophercloud.ServiceClient, id st } } -func waitForIKEPolicyCreation(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForIKEPolicyCreation(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { policy, err := ikepolicies.Get(networkingClient, id).Extract() if err != nil { @@ -316,7 +316,7 @@ func waitForIKEPolicyCreation(networkingClient *gophercloud.ServiceClient, id st } } -func waitForIKEPolicyUpdate(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForIKEPolicyUpdate(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { policy, err := ikepolicies.Get(networkingClient, id).Extract() if err != nil { diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_ike_policy_test.go b/vkcs/vpnaas/resource_vkcs_vpnaas_ike_policy_test.go index b521b3df..d07a57cd 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_ike_policy_test.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_ike_policy_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_ipsec_policy.go b/vkcs/vpnaas/resource_vkcs_vpnaas_ipsec_policy.go index 7f302439..30d7d955 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_ipsec_policy.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_ipsec_policy.go @@ -6,7 +6,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -139,7 +139,7 @@ func resourceIPSecPolicyCreate(ctx context.Context, d *schema.ResourceData, meta return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING_CREATE"}, Target: []string{"ACTIVE"}, Refresh: waitForIPSecPolicyCreation(networkingClient, policy.ID), @@ -259,7 +259,7 @@ func resourceIPSecPolicyUpdate(ctx context.Context, d *schema.ResourceData, meta return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING_UPDATE"}, Target: []string{"ACTIVE"}, Refresh: waitForIPSecPolicyUpdate(networkingClient, d.Id()), @@ -283,7 +283,7 @@ func resourceIPSecPolicyDelete(ctx context.Context, d *schema.ResourceData, meta return diag.Errorf("Error creating VKCS networking client: %s", err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"ACTIVE"}, Target: []string{"DELETED"}, Refresh: waitForIPSecPolicyDeletion(networkingClient, d.Id()), @@ -299,7 +299,7 @@ func resourceIPSecPolicyDelete(ctx context.Context, d *schema.ResourceData, meta return nil } -func waitForIPSecPolicyDeletion(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForIPSecPolicyDeletion(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { err := ipsecpolicies.Delete(networkingClient, id).Err if err == nil { @@ -314,7 +314,7 @@ func waitForIPSecPolicyDeletion(networkingClient *gophercloud.ServiceClient, id } } -func waitForIPSecPolicyCreation(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForIPSecPolicyCreation(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { policy, err := ipsecpolicies.Get(networkingClient, id).Extract() if err != nil { @@ -324,7 +324,7 @@ func waitForIPSecPolicyCreation(networkingClient *gophercloud.ServiceClient, id } } -func waitForIPSecPolicyUpdate(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForIPSecPolicyUpdate(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { policy, err := ipsecpolicies.Get(networkingClient, id).Extract() if err != nil { diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_ipsec_policy_test.go b/vkcs/vpnaas/resource_vkcs_vpnaas_ipsec_policy_test.go index f43d669d..da3e0fff 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_ipsec_policy_test.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_ipsec_policy_test.go @@ -6,8 +6,8 @@ import ( "strings" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_service.go b/vkcs/vpnaas/resource_vkcs_vpnaas_service.go index 0fbdff51..273b12b4 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_service.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_service.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -117,7 +117,7 @@ func resourceServiceCreate(ctx context.Context, d *schema.ResourceData, meta int return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"NOT_CREATED"}, Target: []string{"PENDING_CREATE"}, Refresh: waitForServiceCreation(networkingClient, service.ID), @@ -205,7 +205,7 @@ func resourceServiceUpdate(ctx context.Context, d *schema.ResourceData, meta int if err != nil { return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING_UPDATE"}, Target: []string{"UPDATED"}, Refresh: waitForServiceUpdate(networkingClient, service.ID), @@ -240,7 +240,7 @@ func resourceServiceDelete(ctx context.Context, d *schema.ResourceData, meta int return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"DELETING"}, Target: []string{"DELETED"}, Refresh: waitForServiceDeletion(networkingClient, d.Id()), @@ -254,7 +254,7 @@ func resourceServiceDelete(ctx context.Context, d *schema.ResourceData, meta int return diag.FromErr(err) } -func waitForServiceDeletion(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForServiceDeletion(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { serv, err := services.Get(networkingClient, id).Extract() log.Printf("[DEBUG] Got service %s => %#v", id, serv) @@ -272,7 +272,7 @@ func waitForServiceDeletion(networkingClient *gophercloud.ServiceClient, id stri } } -func waitForServiceCreation(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForServiceCreation(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { service, err := services.Get(networkingClient, id).Extract() if err != nil { @@ -282,7 +282,7 @@ func waitForServiceCreation(networkingClient *gophercloud.ServiceClient, id stri } } -func waitForServiceUpdate(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForServiceUpdate(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { service, err := services.Get(networkingClient, id).Extract() if err != nil { diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_service_test.go b/vkcs/vpnaas/resource_vkcs_vpnaas_service_test.go index 3263f61a..3744268f 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_service_test.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_service_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking" diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_site_connection.go b/vkcs/vpnaas/resource_vkcs_vpnaas_site_connection.go index 226ffd24..5d308452 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_site_connection.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_site_connection.go @@ -7,7 +7,7 @@ import ( "time" "github.com/hashicorp/terraform-plugin-sdk/v2/diag" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" + "github.com/hashicorp/terraform-plugin-sdk/v2/helper/retry" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/schema" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/util" @@ -204,7 +204,7 @@ func resourceSiteConnectionCreate(ctx context.Context, d *schema.ResourceData, m return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"NOT_CREATED"}, Target: []string{"PENDING_CREATE"}, Refresh: waitForSiteConnectionCreation(networkingClient, conn.ID), @@ -362,7 +362,7 @@ func resourceSiteConnectionUpdate(ctx context.Context, d *schema.ResourceData, m if err != nil { return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"PENDING_UPDATE"}, Target: []string{"UPDATED"}, Refresh: waitForSiteConnectionUpdate(networkingClient, conn.ID), @@ -397,7 +397,7 @@ func resourceSiteConnectionDelete(ctx context.Context, d *schema.ResourceData, m return diag.FromErr(err) } - stateConf := &resource.StateChangeConf{ + stateConf := &retry.StateChangeConf{ Pending: []string{"DELETING"}, Target: []string{"DELETED"}, Refresh: waitForSiteConnectionDeletion(networkingClient, d.Id()), @@ -411,7 +411,7 @@ func resourceSiteConnectionDelete(ctx context.Context, d *schema.ResourceData, m return diag.FromErr(err) } -func waitForSiteConnectionDeletion(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForSiteConnectionDeletion(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { conn, err := siteconnections.Get(networkingClient, id).Extract() log.Printf("[DEBUG] Got site connection %s => %#v", id, conn) @@ -429,7 +429,7 @@ func waitForSiteConnectionDeletion(networkingClient *gophercloud.ServiceClient, } } -func waitForSiteConnectionCreation(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForSiteConnectionCreation(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { service, err := siteconnections.Get(networkingClient, id).Extract() if err != nil { @@ -439,7 +439,7 @@ func waitForSiteConnectionCreation(networkingClient *gophercloud.ServiceClient, } } -func waitForSiteConnectionUpdate(networkingClient *gophercloud.ServiceClient, id string) resource.StateRefreshFunc { +func waitForSiteConnectionUpdate(networkingClient *gophercloud.ServiceClient, id string) retry.StateRefreshFunc { return func() (interface{}, string, error) { conn, err := siteconnections.Get(networkingClient, id).Extract() if err != nil { diff --git a/vkcs/vpnaas/resource_vkcs_vpnaas_site_connection_test.go b/vkcs/vpnaas/resource_vkcs_vpnaas_site_connection_test.go index dcac5281..a6c8c017 100644 --- a/vkcs/vpnaas/resource_vkcs_vpnaas_site_connection_test.go +++ b/vkcs/vpnaas/resource_vkcs_vpnaas_site_connection_test.go @@ -4,8 +4,8 @@ import ( "fmt" "testing" - "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" - "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" + "github.com/hashicorp/terraform-plugin-testing/helper/resource" + "github.com/hashicorp/terraform-plugin-testing/terraform" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/acctest" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/clients" "github.com/vk-cs/terraform-provider-vkcs/vkcs/internal/services/networking"