зеркало из https://github.com/microsoft/cobalt.git
This change updates the project dependencies for Go and Terraform (#172)
Go has been updated from v1.11 --> v1.12.5 Terraform has been udpated from v0.11.13 --> v0.12.1 The test harness has also been upgraded to perform a structural comparison against the new terraform plan format introduced in v0.12.0
This commit is contained in:
Родитель
6468a73912
Коммит
883bcc58c6
|
@ -1,6 +1,6 @@
|
|||
ARM_SUBSCRIPTION_ID="<az-service-principal-subscription-id>"
|
||||
GO_VERSION=1.11
|
||||
TF_VERSION=0.11.13
|
||||
GO_VERSION=1.12.5
|
||||
TF_VERSION=0.12.1
|
||||
BUILD_BUILDID=1
|
||||
ARM_CLIENT_ID="<az-service-principal-client-id>"
|
||||
ARM_CLIENT_SECRET="<az-service-principal-auth-secret>"
|
||||
|
|
|
@ -35,9 +35,9 @@ pool:
|
|||
variables:
|
||||
- group: "KV Secrets"
|
||||
- name: GO_VERSION
|
||||
value: '1.11'
|
||||
value: '1.12.5'
|
||||
- name: TF_VERSION
|
||||
value: '0.11.13'
|
||||
value: '0.12.1'
|
||||
- name: TEST_HARNESS_BASE_IMAGE_TAG
|
||||
value: 'g$(GO_VERSION)t$(TF_VERSION)'
|
||||
- name: TEST_HARNESS_BASE_IMAGE
|
||||
|
|
11
go.mod
11
go.mod
|
@ -3,10 +3,11 @@ module github.com/microsoft/cobalt
|
|||
go 1.12
|
||||
|
||||
require (
|
||||
github.com/gruntwork-io/terratest v0.15.9
|
||||
github.com/hashicorp/terraform v0.11.14
|
||||
github.com/go-sql-driver/mysql v1.4.1 // indirect
|
||||
github.com/google/uuid v1.1.1 // indirect
|
||||
github.com/gruntwork-io/terratest v0.16.1
|
||||
github.com/hashicorp/terraform v0.12.1
|
||||
github.com/magefile/mage v1.8.0
|
||||
github.com/mitchellh/go-homedir v1.1.0
|
||||
github.com/spf13/cobra v0.0.4
|
||||
github.com/spf13/viper v1.3.2
|
||||
github.com/pquerna/otp v1.2.0 // indirect
|
||||
github.com/stretchr/testify v1.3.0
|
||||
)
|
||||
|
|
480
go.sum
480
go.sum
|
@ -1,226 +1,406 @@
|
|||
cloud.google.com/go v0.15.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
|
||||
github.com/Azure/azure-sdk-for-go v10.3.0-beta+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc=
|
||||
github.com/Azure/go-autorest v9.10.0+incompatible/go.mod h1:r+4oMnoxhatjLLJ6zxSWATqVooLgysK6ZNox3g/xq24=
|
||||
github.com/Azure/go-ntlmssp v0.0.0-20170803034930-c92175d54006/go.mod h1:chxPXzSsl7ZWRAuOIE23GDNzjWuZquvFlgA8xmpunjU=
|
||||
cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
|
||||
cloud.google.com/go v0.31.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
|
||||
cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
|
||||
cloud.google.com/go v0.36.0 h1:+aCSj7tOo2LODWVEuZDZeGCckdt6MlSF+X/rB3wUiS8=
|
||||
cloud.google.com/go v0.36.0/go.mod h1:RUoy9p/M4ge0HzT8L+SDZ8jg+Q6fth0CiBuhFJpSV40=
|
||||
dmitri.shuralyov.com/app/changes v0.0.0-20180602232624-0a106ad413e3/go.mod h1:Yl+fi1br7+Rr3LqpNJf1/uxUdtRUV+Tnj0o93V2B9MU=
|
||||
dmitri.shuralyov.com/html/belt v0.0.0-20180602232347-f7d459c86be0/go.mod h1:JLBrvjyP0v+ecvNYvCpyZgu5/xkfAUhi6wJj28eUfSU=
|
||||
dmitri.shuralyov.com/service/change v0.0.0-20181023043359-a85b471d5412/go.mod h1:a1inKt/atXimZ4Mv927x+r7UpyzRUf4emIoiiSC2TN4=
|
||||
dmitri.shuralyov.com/state v0.0.0-20180228185332-28bcc343414c/go.mod h1:0PRwlb0D6DFvNNtx+9ybjezNCa8XF0xaYcETyp6rHWU=
|
||||
git.apache.org/thrift.git v0.0.0-20180902110319-2566ecd5d999/go.mod h1:fPE2ZNJGynbRyZ4dJvy6G277gSllfV2HJqblrnkyeyg=
|
||||
github.com/Azure/azure-sdk-for-go v21.3.0+incompatible/go.mod h1:9XXNKU+eRnpl9moKnB4QOLf1HestfXbmab5FXxiDBjc=
|
||||
github.com/Azure/go-autorest v10.15.4+incompatible/go.mod h1:r+4oMnoxhatjLLJ6zxSWATqVooLgysK6ZNox3g/xq24=
|
||||
github.com/Azure/go-ntlmssp v0.0.0-20180810175552-4a21cbd618b4/go.mod h1:chxPXzSsl7ZWRAuOIE23GDNzjWuZquvFlgA8xmpunjU=
|
||||
github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
|
||||
github.com/ChrisTrenkamp/goxpath v0.0.0-20170625215350-4fe035839290/go.mod h1:nuWgzSkT5PnyOd+272uUmV0dnAnAn42Mk7PiQC5VzN4=
|
||||
github.com/ChrisTrenkamp/goxpath v0.0.0-20170922090931-c385f95c6022/go.mod h1:nuWgzSkT5PnyOd+272uUmV0dnAnAn42Mk7PiQC5VzN4=
|
||||
github.com/Unknwon/com v0.0.0-20151008135407-28b053d5a292/go.mod h1:KYCjqMOeHpNuTOiFQU6WEcTG7poCJrUs0YgyHNtn1no=
|
||||
github.com/abdullin/seq v0.0.0-20160510034733-d5467c17e7af/go.mod h1:5Jv4cbFiHJMsVxt52+i0Ha45fjshj6wxYr1r19tB9bw=
|
||||
github.com/agext/levenshtein v1.2.1 h1:QmvMAjj2aEICytGiWzmxoE0x2KZvE0fvmqMOfy2tjT8=
|
||||
github.com/agext/levenshtein v1.2.1/go.mod h1:JEDfjyjHDjOF/1e4FlBE/PkbqA9OfWu2ki2W0IB5558=
|
||||
github.com/agext/levenshtein v1.2.2 h1:0S/Yg6LYmFJ5stwQeRp6EeOcCbj7xiqQSdNelsXvaqE=
|
||||
github.com/agext/levenshtein v1.2.2/go.mod h1:JEDfjyjHDjOF/1e4FlBE/PkbqA9OfWu2ki2W0IB5558=
|
||||
github.com/agl/ed25519 v0.0.0-20150830182803-278e1ec8e8a6/go.mod h1:WPjqKcmVOxf0XSf3YxCJs6N6AOSrOx3obionmG7T0y0=
|
||||
github.com/antchfx/xpath v0.0.0-20170728053731-b5c552e1acbd/go.mod h1:Yee4kTMuNiPYJ7nSNorELQMr1J33uOpXDMByNYhvtNk=
|
||||
github.com/antchfx/xquery v0.0.0-20170730121040-eb8c3c172607/go.mod h1:LzD22aAzDP8/dyiCKFp31He4m2GPjl0AFyzDtZzUu9M=
|
||||
github.com/apparentlymart/go-cidr v0.0.0-20170616213631-2bd8b58cf427 h1:2P/DTyNDU+7qJOB6E5KeIpdc3qcT9IYjyA8hZ9HGz50=
|
||||
github.com/apparentlymart/go-cidr v0.0.0-20170616213631-2bd8b58cf427/go.mod h1:EBcsNrHc3zQeuaeCeCtQruQm+n9/YjEn/vI25Lg7Gwc=
|
||||
github.com/apparentlymart/go-textseg v0.0.0-20170531203952-b836f5c4d331 h1:AIKxo1t7QE7MAqADwrmzMiaFC+QfHfXOk8lrmibN5Lk=
|
||||
github.com/apparentlymart/go-textseg v0.0.0-20170531203952-b836f5c4d331/go.mod h1:z96Txxhf3xSFMPmb5X/1W05FF/Nj9VFpLOpjS5yuumk=
|
||||
github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o=
|
||||
github.com/armon/consul-api v0.0.0-20180202201655-eb2c6b5be1b6/go.mod h1:grANhF5doyWs3UAsr3K4I6qtAmlQcZDesFNEHPZAzj8=
|
||||
github.com/anmitsu/go-shlex v0.0.0-20161002113705-648efa622239/go.mod h1:2FmKhYUyUczH0OGQWaF5ceTx0UBShxjsH6f8oGKYe2c=
|
||||
github.com/antchfx/xpath v0.0.0-20190129040759-c8489ed3251e/go.mod h1:Yee4kTMuNiPYJ7nSNorELQMr1J33uOpXDMByNYhvtNk=
|
||||
github.com/antchfx/xquery v0.0.0-20180515051857-ad5b8c7a47b0/go.mod h1:LzD22aAzDP8/dyiCKFp31He4m2GPjl0AFyzDtZzUu9M=
|
||||
github.com/apparentlymart/go-cidr v1.0.0 h1:lGDvXx8Lv9QHjrAVP7jyzleG4F9+FkRhJcEsDFxeb8w=
|
||||
github.com/apparentlymart/go-cidr v1.0.0/go.mod h1:EBcsNrHc3zQeuaeCeCtQruQm+n9/YjEn/vI25Lg7Gwc=
|
||||
github.com/apparentlymart/go-dump v0.0.0-20180507223929-23540a00eaa3/go.mod h1:oL81AME2rN47vu18xqj1S1jPIPuN7afo62yKTNn3XMM=
|
||||
github.com/apparentlymart/go-dump v0.0.0-20190214190832-042adf3cf4a0/go.mod h1:oL81AME2rN47vu18xqj1S1jPIPuN7afo62yKTNn3XMM=
|
||||
github.com/apparentlymart/go-textseg v1.0.0 h1:rRmlIsPEEhUTIKQb7T++Nz/A5Q6C9IuX2wFoYVvnCs0=
|
||||
github.com/apparentlymart/go-textseg v1.0.0/go.mod h1:z96Txxhf3xSFMPmb5X/1W05FF/Nj9VFpLOpjS5yuumk=
|
||||
github.com/armon/circbuf v0.0.0-20190214190532-5111143e8da2/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o=
|
||||
github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY=
|
||||
github.com/armon/go-radix v0.0.0-20160115234725-4239b77079c7 h1:MBXhrxjNkjdqJysfNbKMMPFNXlz6EzpOnPcsoYBeD3E=
|
||||
github.com/armon/go-radix v0.0.0-20160115234725-4239b77079c7/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8=
|
||||
github.com/aws/aws-sdk-go v1.16.36 h1:POeH34ZME++pr7GBGh+ZO6Y5kOwSMQpqp5BGUgooJ6k=
|
||||
github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8=
|
||||
github.com/armon/go-radix v1.0.0 h1:F4z6KzEeeQIMeLFa97iZU6vupzoecKdU5TX24SNppXI=
|
||||
github.com/armon/go-radix v1.0.0/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8=
|
||||
github.com/aws/aws-sdk-go v1.15.78/go.mod h1:E3/ieXAlvM0XWO57iftYVDLLvQ824smPP3ATZkfNZeM=
|
||||
github.com/aws/aws-sdk-go v1.16.36/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo=
|
||||
github.com/aws/aws-sdk-go v1.19.18 h1:Hb3+b9HCqrOrbAtFstUWg7H5TQ+/EcklJtE8VShVs8o=
|
||||
github.com/aws/aws-sdk-go v1.19.18/go.mod h1:KmX6BPdI08NWTb3/sm4ZGu5ShLoqVDhKgpiN924inxo=
|
||||
github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q=
|
||||
github.com/bgentry/go-netrc v0.0.0-20140422174119-9fd32a8b3d3d h1:xDfNPAt8lFiC1UJrqV3uuy861HCTo708pDMbjHHdCas=
|
||||
github.com/bgentry/go-netrc v0.0.0-20140422174119-9fd32a8b3d3d/go.mod h1:6QX/PXZ00z/TKoufEY6K/a0k6AhaJrQKdFe6OfVXsa4=
|
||||
github.com/bgentry/speakeasy v0.0.0-20161015143505-675b82c74c0e h1:giZ2nnSSH4ntzmoNPwdncPXXA2nWdlO7NiebK0gozNI=
|
||||
github.com/bgentry/speakeasy v0.0.0-20161015143505-675b82c74c0e/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs=
|
||||
github.com/blang/semver v0.0.0-20170202183821-4a1e882c79dc h1:J/iAaGTCZYfT/allw61NfW/CEoflFsNdhQJny4iLU+0=
|
||||
github.com/blang/semver v0.0.0-20170202183821-4a1e882c79dc/go.mod h1:kRBLl5iJ+tD4TcOOxsy/0fnwebNt5EWlYSAyrTnjyyk=
|
||||
github.com/chzyer/logex v1.1.11-0.20160617073814-96a4d311aa9b/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI=
|
||||
github.com/bgentry/speakeasy v0.1.0 h1:ByYyxL9InA1OWqxJqqp2A5pYHUrCiAL6K3J+LKSsQkY=
|
||||
github.com/bgentry/speakeasy v0.1.0/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs=
|
||||
github.com/blang/semver v3.5.1+incompatible h1:cQNTCjp13qL8KC3Nbxr/y2Bqb63oX6wdnnjpJbkM4JQ=
|
||||
github.com/blang/semver v3.5.1+incompatible/go.mod h1:kRBLl5iJ+tD4TcOOxsy/0fnwebNt5EWlYSAyrTnjyyk=
|
||||
github.com/boltdb/bolt v1.3.1/go.mod h1:clJnj/oiGkjum5o1McbSZDSLxVThjynRyGBgiAx27Ps=
|
||||
github.com/boombuler/barcode v1.0.1-0.20190219062509-6c824513bacc h1:biVzkmvwrH8WK8raXaxBx6fRVTlJILwEwQGL1I/ByEI=
|
||||
github.com/boombuler/barcode v1.0.1-0.20190219062509-6c824513bacc/go.mod h1:paBWMcWSl3LHKBqUq+rly7CNSldXjb2rDl3JlRe0mD8=
|
||||
github.com/bradfitz/go-smtpd v0.0.0-20170404230938-deb6d6237625/go.mod h1:HYsPBTaaSFSlLx/70C2HPIMNZpVV8+vt/A+FMnYP11g=
|
||||
github.com/bsm/go-vlq v0.0.0-20150828105119-ec6e8d4f5f4e/go.mod h1:N+BjUcTjSxc2mtRGSCPsat1kze3CUtvJN3/jTXlp29k=
|
||||
github.com/cheggaaa/pb v1.0.27/go.mod h1:pQciLPpbU0oxA0h+VJYYLxO+XeDQb5pZijXscXHm81s=
|
||||
github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI=
|
||||
github.com/chzyer/readline v0.0.0-20161106042343-c914be64f07d/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI=
|
||||
github.com/chzyer/test v0.0.0-20160617131543-bea8f082b6fd/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU=
|
||||
github.com/coreos/bbolt v1.3.1-coreos.1/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk=
|
||||
github.com/coreos/etcd v3.2.0-rc.1.0.20170908195435-80aa810309d4+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE=
|
||||
github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU=
|
||||
github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw=
|
||||
github.com/coreos/bbolt v1.3.0/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk=
|
||||
github.com/coreos/etcd v3.3.10+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE=
|
||||
github.com/coreos/go-etcd v2.0.0+incompatible/go.mod h1:Jez6KQU2B/sWsbdaef3ED8NzMklzPG4d5KIOhIy30Tk=
|
||||
github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk=
|
||||
github.com/coreos/go-systemd v0.0.0-20161114122254-48702e0da86b/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4=
|
||||
github.com/coreos/pkg v0.0.0-20160727233714-3ac0863d7acf/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA=
|
||||
github.com/cpuguy83/go-md2man v1.0.10/go.mod h1:SmD6nW6nTyfqj6ABTjUi3V3JVMnlJmwcJI5acqYI6dE=
|
||||
github.com/coreos/go-systemd v0.0.0-20181012123002-c6f51f82210d/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4=
|
||||
github.com/coreos/pkg v0.0.0-20180928190104-399ea9e2e55f/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA=
|
||||
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/dgrijalva/jwt-go v0.0.0-20160617170158-f0777076321a/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ=
|
||||
github.com/dnaeon/go-vcr v0.0.0-20170218072653-87d4990451a8/go.mod h1:aBB1+wY4s93YsC3HHjMBMrwTj2R9FHDzUr9KyGc8n1E=
|
||||
github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ=
|
||||
github.com/dimchansky/utfbom v1.0.0/go.mod h1:rO41eb7gLfo8SF1jd9F8HplJm1Fewwi4mQvIirEdv+8=
|
||||
github.com/dnaeon/go-vcr v0.0.0-20180920040454-5637cf3d8a31/go.mod h1:aBB1+wY4s93YsC3HHjMBMrwTj2R9FHDzUr9KyGc8n1E=
|
||||
github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk=
|
||||
github.com/dylanmei/iso8601 v0.1.0/go.mod h1:w9KhXSgIyROl1DefbMYIE7UVSIvELTbMrCfx+QkYnoQ=
|
||||
github.com/dylanmei/winrmtest v0.0.0-20170819153634-c2fbb09e6c08/go.mod h1:VBVDFSBXCIW8JaHQpI8lldSKfYaLMzP9oyq6IJ4fhzY=
|
||||
github.com/fsnotify/fsnotify v1.4.7 h1:IXs+QLmnXW2CcXuY+8Mzv/fWEsPGWxqefPtCP5CnV9I=
|
||||
github.com/dylanmei/winrmtest v0.0.0-20190225150635-99b7fe2fddf1/go.mod h1:lcy9/2gH1jn/VCLouHA6tOEwLoNVd4GW6zhuKLmHC2Y=
|
||||
github.com/fatih/color v1.7.0 h1:DkWD4oS2D8LGGgTQ6IvwJJXSL5Vp2ffcQg58nFV38Ys=
|
||||
github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4=
|
||||
github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc=
|
||||
github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo=
|
||||
github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04=
|
||||
github.com/gliderlabs/ssh v0.1.1/go.mod h1:U7qILu1NlMHj9FlMhZLlkCdDnU1DBEAqr0aevW3Awn0=
|
||||
github.com/go-sql-driver/mysql v1.4.1 h1:g24URVg0OFbNUTx9qqY1IRZ9D9z3iPyi5zKhQZpNwpA=
|
||||
github.com/go-sql-driver/mysql v1.4.1/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w=
|
||||
github.com/go-test/deep v1.0.1 h1:UQhStjbkDClarlmv0am7OXXO4/GaPdCGiUiMTvi28sg=
|
||||
github.com/go-test/deep v1.0.1/go.mod h1:wGDj63lr65AM2AQyKZd/NYHGb0R+1RLqB8NKt3aSFNA=
|
||||
github.com/gogo/protobuf v0.0.0-20170307180453-100ba4e88506/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
|
||||
github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc=
|
||||
github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
|
||||
github.com/gogo/protobuf v1.2.0/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
|
||||
github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q=
|
||||
github.com/golang/groupcache v0.0.0-20180513044358-24b0969c4cb7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc=
|
||||
github.com/golang/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:tluoj9z5200jBnyusfRPU2LqT6J+DAorxEvtC7LHB+E=
|
||||
github.com/golang/mock v1.1.1/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
|
||||
github.com/golang/mock v1.2.0/go.mod h1:oTYuIxOrZwtPieC+H1uAHpcLFnEyAGVDL/k47Jfbm0A=
|
||||
github.com/golang/mock v1.3.1/go.mod h1:sBzyDLLjw3U8JLTeZvSv8jJB+tU5PVekmnlKIyFUx0Y=
|
||||
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.0 h1:kbxbvI4Un1LUWKxufD+BiE6AEExYYgkQLQmLFqA1LFk=
|
||||
github.com/golang/protobuf v1.3.0/go.mod h1:Qd/q+1AKNOZr9uGQzbzCmRO6sUih6GTPZv6a1/R87v0=
|
||||
github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db/go.mod h1:/XxbfmMg8lxefKM7IXC3fBNl/7bRcc72aCRzEWrmP2Q=
|
||||
github.com/google/btree v0.0.0-20180813153112-4030bb1f1f0c/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ=
|
||||
github.com/google/go-cmp v0.1.1-0.20171002171727-8ebdfab36c66/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
|
||||
github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M=
|
||||
github.com/google/go-cmp v0.3.0 h1:crn/baboCvb5fXaQ0IJ1SGTsTVrWpDsCWC8EGETZijY=
|
||||
github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU=
|
||||
github.com/google/go-github v17.0.0+incompatible/go.mod h1:zLgOLi98H3fifZn+44m+umXrS52loVEgC2AApnigrVQ=
|
||||
github.com/google/go-querystring v1.0.0/go.mod h1:odCYkC5MyYFN7vkCjXpyrEuKhc/BUO6wN/zVPAxq5ck=
|
||||
github.com/googleapis/gax-go v0.0.0-20161107002406-da06d194a00e/go.mod h1:SFVmujtThgffbyetf+mdk2eWhX2bMyUtNHzFKcPA9HY=
|
||||
github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs=
|
||||
github.com/google/pprof v0.0.0-20181206194817-3ea8567a2e57/go.mod h1:zfwlbNMJ+OItoe0UupaVj+oy1omPYYDuagoSzA8v9mc=
|
||||
github.com/google/uuid v1.1.1 h1:Gkbcsh/GbpXz7lPftLA3P6TYMwjCLYm83jiFQZF/3gY=
|
||||
github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
|
||||
github.com/googleapis/gax-go v2.0.0+incompatible h1:j0GKcs05QVmm7yesiZq2+9cxHkNK9YM6zKx4D2qucQU=
|
||||
github.com/googleapis/gax-go v2.0.0+incompatible/go.mod h1:SFVmujtThgffbyetf+mdk2eWhX2bMyUtNHzFKcPA9HY=
|
||||
github.com/googleapis/gax-go/v2 v2.0.3 h1:siORttZ36U2R/WjiJuDz8znElWBiAlO9rVt+mqJt0Cc=
|
||||
github.com/googleapis/gax-go/v2 v2.0.3/go.mod h1:LLvjysVCY1JZeum8Z6l8qUty8fiNwE08qbEPm1M08qg=
|
||||
github.com/gophercloud/gophercloud v0.0.0-20190208042652-bc37892e1968/go.mod h1:3WdhXV3rUYy9p6AUW8d94kr+HS62Y4VL9mBnFxsD8q4=
|
||||
github.com/gophercloud/utils v0.0.0-20190128072930-fbb6ab446f01/go.mod h1:wjDF8z83zTeg5eMLml5EBSlAhbF7G8DobyI1YsMuyzw=
|
||||
github.com/gopherjs/gopherjs v0.0.0-20181103185306-d547d1d9531e/go.mod h1:wJfORRmW1u3UXTncJ5qlYoELFm8eSnnEO6hX4iZ3EWY=
|
||||
github.com/grpc-ecosystem/go-grpc-prometheus v0.0.0-20160910222444-6b7015e65d36/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk=
|
||||
github.com/grpc-ecosystem/grpc-gateway v1.2.2/go.mod h1:RSKVYQBd5MCa4OVpNdGskqpgL2+G+NZTnrVHpWWfpdw=
|
||||
github.com/gruntwork-io/terratest v0.15.9 h1:SBYLlpa6AUm+uRDAErUyQuCmdvP86omWdEGWhQrQPl0=
|
||||
github.com/gruntwork-io/terratest v0.15.9/go.mod h1:NjUn6YXA5Skxt8Rs20t3isYx5Rl+EgvGB8/+RRXddqk=
|
||||
github.com/hashicorp/atlas-go v0.0.0-20161107204910-1792bd8de119/go.mod h1:ckHDuH0pxfnmXZkq1niVSguIIV0pA65gifQv3so9llw=
|
||||
github.com/hashicorp/aws-sdk-go-base v0.3.0/go.mod h1:ZIWACGGi0N7a4DZbf15yuE1JQORmWLtBcVM6F5SXNFU=
|
||||
github.com/gopherjs/gopherjs v0.0.0-20181017120253-0766667cb4d1/go.mod h1:wJfORRmW1u3UXTncJ5qlYoELFm8eSnnEO6hX4iZ3EWY=
|
||||
github.com/gorilla/websocket v1.4.0/go.mod h1:E7qHFY5m1UJ88s3WnNqhKjPHQ0heANvMoAMk2YaljkQ=
|
||||
github.com/gregjones/httpcache v0.0.0-20180305231024-9cad4c3443a7/go.mod h1:FecbI9+v66THATjSRHfNgh1IVFe/9kFxbXtjV0ctIMA=
|
||||
github.com/grpc-ecosystem/go-grpc-middleware v1.0.0/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs=
|
||||
github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk=
|
||||
github.com/grpc-ecosystem/grpc-gateway v1.5.0/go.mod h1:RSKVYQBd5MCa4OVpNdGskqpgL2+G+NZTnrVHpWWfpdw=
|
||||
github.com/grpc-ecosystem/grpc-gateway v1.5.1/go.mod h1:RSKVYQBd5MCa4OVpNdGskqpgL2+G+NZTnrVHpWWfpdw=
|
||||
github.com/gruntwork-io/terratest v0.16.1 h1:r4kQps7wevleXDik2fGMXnT+ehWAFMrRy/yQQQtA3bo=
|
||||
github.com/gruntwork-io/terratest v0.16.1/go.mod h1:NjUn6YXA5Skxt8Rs20t3isYx5Rl+EgvGB8/+RRXddqk=
|
||||
github.com/hashicorp/aws-sdk-go-base v0.2.0/go.mod h1:ZIWACGGi0N7a4DZbf15yuE1JQORmWLtBcVM6F5SXNFU=
|
||||
github.com/hashicorp/consul v0.0.0-20171026175957-610f3c86a089/go.mod h1:mFrjN1mfidgJfYP1xrJCF+AfRhr6Eaqhb2+sfyn/OOI=
|
||||
github.com/hashicorp/errwrap v0.0.0-20180715044906-d6c0cd880357/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
|
||||
github.com/hashicorp/errwrap v1.0.0 h1:hLrqtEDnRye3+sgx6z4qVLNuviH3MR5aQ0ykNJa/UYA=
|
||||
github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
|
||||
github.com/hashicorp/go-checkpoint v0.0.0-20171009173528-1545e56e46de/go.mod h1:xIwEieBHERyEvaeKF/TcHh1Hu+lxPM+n2vT1+g9I4m4=
|
||||
github.com/hashicorp/go-azure-helpers v0.0.0-20190129193224-166dfd221bb2/go.mod h1:lu62V//auUow6k0IykxLK2DCNW8qTmpm8KqhYVWattA=
|
||||
github.com/hashicorp/go-checkpoint v0.5.0/go.mod h1:7nfLNL10NsxqO4iWuW6tWW0HjZuDrwkBuEQsVcpCOgg=
|
||||
github.com/hashicorp/go-cleanhttp v0.5.0 h1:wvCrVc9TjDls6+YGAF2hAifE1E5U1+b4tH6KdvN3Gig=
|
||||
github.com/hashicorp/go-cleanhttp v0.5.0/go.mod h1:JpRdi6/HCYpAwUzNwuwqhbovhLtngrth3wmdIIUrZ80=
|
||||
github.com/hashicorp/go-getter v0.0.0-20180327010114-90bb99a48d86 h1:hLYM35twiyKH44g36g+GFYODcrZQetEAY4+zrJtGea0=
|
||||
github.com/hashicorp/go-getter v0.0.0-20180327010114-90bb99a48d86/go.mod h1:6rdJFnhkXnzGOJbvkrdv4t9nLwKcVA+tmbQeUlkIzrU=
|
||||
github.com/hashicorp/go-hclog v0.0.0-20170716174523-b4e5765d1e5f/go.mod h1:9bjs9uLqI8l75knNv3lV1kA55veR+WUPSiKIWcQHudI=
|
||||
github.com/hashicorp/go-immutable-radix v1.0.0/go.mod h1:0y9vanUI8NX6FsYoO3zeMjhV/C5i9g4Q3DwcSNZ4P60=
|
||||
github.com/hashicorp/go-msgpack v0.5.3/go.mod h1:ahLV/dePpqEmjfWmKiqvPkv/twdG7iPBM1vqhUKIvfM=
|
||||
github.com/hashicorp/go-getter v1.3.0 h1:pFMSFlI9l5NaeuzkpE3L7BYk9qQ9juTAgXW/H0cqxcU=
|
||||
github.com/hashicorp/go-getter v1.3.0/go.mod h1:/O1k/AizTN0QmfEKknCYGvICeyKUDqCYA8vvWtGWDeQ=
|
||||
github.com/hashicorp/go-hclog v0.0.0-20180709165350-ff2cf002a8dd/go.mod h1:9bjs9uLqI8l75knNv3lV1kA55veR+WUPSiKIWcQHudI=
|
||||
github.com/hashicorp/go-hclog v0.0.0-20181001195459-61d530d6c27f/go.mod h1:5CU+agLiy3J7N7QjHK5d05KxGsuXiQLrjA0H7acj2lQ=
|
||||
github.com/hashicorp/go-immutable-radix v0.0.0-20180129170900-7f3cd4390caa/go.mod h1:6ij3Z20p+OhOkCSrA0gImAWoHYQRGbnlcuk6XYTiaRw=
|
||||
github.com/hashicorp/go-msgpack v0.5.4/go.mod h1:ahLV/dePpqEmjfWmKiqvPkv/twdG7iPBM1vqhUKIvfM=
|
||||
github.com/hashicorp/go-multierror v0.0.0-20180717150148-3d5d8f294aa0/go.mod h1:JMRHfdO9jKNzS/+BTlxCjKNQHg/jZAft8U7LloJvN7I=
|
||||
github.com/hashicorp/go-multierror v1.0.0 h1:iVjPR7a6H0tWELX5NxNe7bYopibicUzc7uPribsnS6o=
|
||||
github.com/hashicorp/go-multierror v1.0.0/go.mod h1:dHtQlpGsu+cZNNAkkCN/P3hoUDHhCYQXV3UM06sGGrk=
|
||||
github.com/hashicorp/go-plugin v0.0.0-20180125190438-e53f54cbf51e/go.mod h1:JSqWYsict+jzcj0+xElxyrBQRPNoiWQuddnxArJ7XHQ=
|
||||
github.com/hashicorp/go-plugin v1.0.1-0.20190430211030-5692942914bb/go.mod h1:++UyYGoz3o5w9ZzAdZxtQKrWWP+iqPBn3cQptSMzBuY=
|
||||
github.com/hashicorp/go-retryablehttp v0.5.2/go.mod h1:9B5zBasrRhHXnJnui7y6sL7es7NDiJgTc6Er0maI1Xs=
|
||||
github.com/hashicorp/go-rootcerts v0.0.0-20160503143440-6bb64b370b90/go.mod h1:o4zcYY1e0GEZI6eSEr+43QDYmuGglw1qSO6qdHUHCgg=
|
||||
github.com/hashicorp/go-safetemp v0.0.0-20180326211150-b1a1dbde6fdc h1:wAa9fGALVHfjYxZuXRnmuJG2CnwRpJYOTvY6YdErAh0=
|
||||
github.com/hashicorp/go-safetemp v0.0.0-20180326211150-b1a1dbde6fdc/go.mod h1:oaerMy3BhqiTbVye6QuFhFtIceqFoDHxNAB65b+Rj1I=
|
||||
github.com/hashicorp/go-rootcerts v1.0.0/go.mod h1:K6zTfqpRlCUIjkwsN4Z+hiSfzSTQa6eBIzfwKfwNnHU=
|
||||
github.com/hashicorp/go-safetemp v1.0.0 h1:2HR189eFNrjHQyENnQMMpCiBAsRxzbTMIgBhEyExpmo=
|
||||
github.com/hashicorp/go-safetemp v1.0.0/go.mod h1:oaerMy3BhqiTbVye6QuFhFtIceqFoDHxNAB65b+Rj1I=
|
||||
github.com/hashicorp/go-slug v0.3.0/go.mod h1:I5tq5Lv0E2xcNXNkmx7BSfzi1PsJ2cNjs3cC3LwyhK8=
|
||||
github.com/hashicorp/go-sockaddr v1.0.0/go.mod h1:7Xibr9yA9JjQq1JpNB2Vw7kxv8xerXegt+ozgdvDeDU=
|
||||
github.com/hashicorp/go-tfe v0.3.14/go.mod h1:SuPHR+OcxvzBZNye7nGPfwZTEyd3rWPfLVbCgyZPezM=
|
||||
github.com/hashicorp/go-sockaddr v0.0.0-20180320115054-6d291a969b86/go.mod h1:7Xibr9yA9JjQq1JpNB2Vw7kxv8xerXegt+ozgdvDeDU=
|
||||
github.com/hashicorp/go-tfe v0.3.16/go.mod h1:SuPHR+OcxvzBZNye7nGPfwZTEyd3rWPfLVbCgyZPezM=
|
||||
github.com/hashicorp/go-uuid v1.0.0/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
|
||||
github.com/hashicorp/go-uuid v1.0.1 h1:fv1ep09latC32wFoVwnqcnKJGnMSdBanPczbHAYm1BE=
|
||||
github.com/hashicorp/go-uuid v1.0.1/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
|
||||
github.com/hashicorp/go-version v1.0.0 h1:21MVWPKDphxa7ineQQTrCU5brh7OuVVAzGOCnnCPtE8=
|
||||
github.com/hashicorp/go-version v1.0.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA=
|
||||
github.com/hashicorp/go-version v1.1.0 h1:bPIoEKD27tNdebFGGxxYwcL4nepeY4j1QP23PFRGzg0=
|
||||
github.com/hashicorp/go-version v1.1.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA=
|
||||
github.com/hashicorp/golang-lru v0.5.0/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ4Ao+sR/qLZy8=
|
||||
github.com/hashicorp/hcl v0.0.0-20170504190234-a4b07c25de5f h1:UdxlrJz4JOnY8W+DbLISwf2B8WXEolNRA8BGCwI9jws=
|
||||
github.com/hashicorp/hcl v0.0.0-20170504190234-a4b07c25de5f/go.mod h1:oZtUIOe8dh44I2q6ScRibXws4Ajl+d+nod3AaR9vL5w=
|
||||
github.com/hashicorp/hcl v1.0.0 h1:0Anlzjpi4vEasTeNFn2mLJgTSwt0+6sfsiTG8qcWGx4=
|
||||
github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ=
|
||||
github.com/hashicorp/hcl2 v0.0.0-20180308163058-5f8ed954abd8 h1:laCE8EKBOUVN6LwBt7Be9IX7i2RQ2cnfbt+Z5a+0PRI=
|
||||
github.com/hashicorp/hcl2 v0.0.0-20180308163058-5f8ed954abd8/go.mod h1:xp1eMAxqhQKBxz+yQUTsig9bBMRRWRWw+rK3FJmHf/A=
|
||||
github.com/hashicorp/hil v0.0.0-20170627220502-fa9f258a9250 h1:fooK5IvDL/KIsi4LxF/JH68nVdrBSiGNPhS2JAQjtjo=
|
||||
github.com/hashicorp/hil v0.0.0-20170627220502-fa9f258a9250/go.mod h1:KHvg/R2/dPtaePb16oW4qIyzkMxXOL38xjRN64adsts=
|
||||
github.com/hashicorp/logutils v0.0.0-20150609070431-0dc08b1671f3/go.mod h1:QIAnNjmIWmVIIkWDTG1z5v++HQmx9WQRO+LraFDTW64=
|
||||
github.com/hashicorp/memberlist v0.0.0-20170208211506-23ad4b7d7b38/go.mod h1:ncdBp14cuox2iFOq3kDiquKU6fqsTBc3W6JvZwjxxsE=
|
||||
github.com/hashicorp/serf v0.8.2-0.20171022020050-c20a0b1b1ea9/go.mod h1:h/Ru6tmZazX7WO/GDmwdpS975F019L4t5ng5IgwbNrE=
|
||||
github.com/hashicorp/terraform v0.11.14 h1:2PnZWaQ9Apr+6QciC7JY0NsnPq7B+4Le406gn8ZPmuA=
|
||||
github.com/hashicorp/terraform v0.11.14/go.mod h1:bES0uNzlesKO5m01e2zTbu1jO2KNXd1gvj22zBIDL3M=
|
||||
github.com/hashicorp/vault v0.0.0-20161029210149-9a60bf2a50e4/go.mod h1:KfSyffbKxoVyspOdlaGVjIuwLobi07qD1bAbosPMpP0=
|
||||
github.com/hashicorp/yamux v0.0.0-20160720233140-d1caa6c97c9f/go.mod h1:+NfK9FKeTrX5uv1uIXGdwYDTeHna2qgaIlx54MXqjAM=
|
||||
github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8=
|
||||
github.com/hashicorp/hcl2 v0.0.0-20181208003705-670926858200/go.mod h1:ShfpTh661oAaxo7VcNxg0zcZW6jvMa7Moy2oFx7e5dE=
|
||||
github.com/hashicorp/hcl2 v0.0.0-20190515223218-4b22149b7cef h1:xZRvbcwHY8zhaxDwgkmpAp2emwZkVn7p3gat0zhq2X0=
|
||||
github.com/hashicorp/hcl2 v0.0.0-20190515223218-4b22149b7cef/go.mod h1:4oI94iqF3GB10QScn46WqbG0kgTUpha97SAzzg2+2ec=
|
||||
github.com/hashicorp/hil v0.0.0-20190212112733-ab17b08d6590 h1:2yzhWGdgQUWZUCNK+AoO35V+HTsgEmcM4J9IkArh7PI=
|
||||
github.com/hashicorp/hil v0.0.0-20190212112733-ab17b08d6590/go.mod h1:n2TSygSNwsLJ76m8qFXTSc7beTb+auJxYdqrnoqwZWE=
|
||||
github.com/hashicorp/logutils v1.0.0 h1:dLEQVugN8vlakKOUE3ihGLTZJRB4j+M2cdTm/ORI65Y=
|
||||
github.com/hashicorp/logutils v1.0.0/go.mod h1:QIAnNjmIWmVIIkWDTG1z5v++HQmx9WQRO+LraFDTW64=
|
||||
github.com/hashicorp/memberlist v0.1.0/go.mod h1:ncdBp14cuox2iFOq3kDiquKU6fqsTBc3W6JvZwjxxsE=
|
||||
github.com/hashicorp/serf v0.0.0-20160124182025-e4ec8cc423bb/go.mod h1:h/Ru6tmZazX7WO/GDmwdpS975F019L4t5ng5IgwbNrE=
|
||||
github.com/hashicorp/terraform v0.12.1 h1:A56pUiGbDZ372cvDKWixzVciTGZkqZ01hH58GTNQ4lg=
|
||||
github.com/hashicorp/terraform v0.12.1/go.mod h1:T3xp83QKah46oRMg37OPBbEVjEwokcGdn7+aNQtQbKo=
|
||||
github.com/hashicorp/terraform-config-inspect v0.0.0-20190327195015-8022a2663a70 h1:oZm5nE11yhzsTRz/YrUyDMSvixePqjoZihwn8ipuOYI=
|
||||
github.com/hashicorp/terraform-config-inspect v0.0.0-20190327195015-8022a2663a70/go.mod h1:ItvqtvbC3K23FFET62ZwnkwtpbKZm8t8eMcWjmVVjD8=
|
||||
github.com/hashicorp/vault v0.10.4/go.mod h1:KfSyffbKxoVyspOdlaGVjIuwLobi07qD1bAbosPMpP0=
|
||||
github.com/hashicorp/yamux v0.0.0-20180604194846-3520598351bb/go.mod h1:+NfK9FKeTrX5uv1uIXGdwYDTeHna2qgaIlx54MXqjAM=
|
||||
github.com/hpcloud/tail v1.0.0/go.mod h1:ab1qPbhIpdTxEkNHXyeSf5vhxWSCs/tWer42PpOxQnU=
|
||||
github.com/jellevandenhooff/dkim v0.0.0-20150330215556-f50fe3d243e1/go.mod h1:E0B/fFc00Y+Rasa88328GlI/XbtyysCtTHZS8h7IrBU=
|
||||
github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI=
|
||||
github.com/jmespath/go-jmespath v0.0.0-20160202185014-0b12d6b521d8/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k=
|
||||
github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af h1:pmfjZENx5imkbgOkpRUYLnmbU7UEFbjtDA2hxJ1ichM=
|
||||
github.com/jmespath/go-jmespath v0.0.0-20180206201540-c2b33e8439af/go.mod h1:Nht3zPeWKUH0NzdCt2Blrr5ys8VGpn0CEB0cQHVjt7k=
|
||||
github.com/jonboulle/clockwork v0.1.0/go.mod h1:Ii8DK3G1RaLaWxj9trq07+26W01tbo22gdxWY5EU2bo=
|
||||
github.com/joyent/triton-go v0.0.0-20180313100802-d8f9c0314926/go.mod h1:U+RSyWxWd04xTqnuOQxnai7XGS2PrPY2cfGoDKtMHjA=
|
||||
github.com/jtolds/gls v4.2.1+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU=
|
||||
github.com/kardianos/osext v0.0.0-20160811001526-c2c54e542fb7/go.mod h1:1NbS8ALrpOvjt0rHPNLyCIeMtbizbir8U//inJ+zuB8=
|
||||
github.com/kardianos/osext v0.0.0-20170510131534-ae77be60afb1/go.mod h1:1NbS8ALrpOvjt0rHPNLyCIeMtbizbir8U//inJ+zuB8=
|
||||
github.com/kardianos/osext v0.0.0-20190222173326-2bc1f35cddc0/go.mod h1:1NbS8ALrpOvjt0rHPNLyCIeMtbizbir8U//inJ+zuB8=
|
||||
github.com/keybase/go-crypto v0.0.0-20161004153544-93f5b35093ba/go.mod h1:ghbZscTyKdM07+Fw3KSi0hcJm+AlEUWj8QLlPtijN/M=
|
||||
github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
|
||||
github.com/konsorten/go-windows-terminal-sequences v0.0.0-20180402223658-b729f2633dfe/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
|
||||
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
|
||||
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
|
||||
github.com/kr/pty v1.1.3/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
|
||||
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
|
||||
github.com/kylelemons/godebug v0.0.0-20170820004349-d65d576e9348/go.mod h1:B69LEHPfb2qLo0BaaOLcbitczOKLWTsrBG9LczfCD4k=
|
||||
github.com/lib/pq v1.0.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo=
|
||||
github.com/lusis/go-artifactory v0.0.0-20160115162124-7e4ce345df82/go.mod h1:y54tfGmO3NKssKveTEFFzH8C/akrSOy/iW9qEAUDV84=
|
||||
github.com/magefile/mage v1.8.0 h1:mzL+xIopvPURVBwHG9A50JcjBO+xV3b5iZ7khFRI+5E=
|
||||
github.com/magefile/mage v1.8.0/go.mod h1:IUDi13rsHje59lecXokTfGX0QIzO45uVPlXnJYsXepA=
|
||||
github.com/magiconair/properties v1.8.0 h1:LLgXmsheXeRoUOBOjtwPQCWIYqM/LU1ayDtDePerRcY=
|
||||
github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ=
|
||||
github.com/masterzen/azure-sdk-for-go v0.0.0-20161014135628-ee4f0065d00c/go.mod h1:mf8fjOu33zCqxUjuiU3I8S1lJMyEAlH+0F2+M5xl3hE=
|
||||
github.com/marstr/guid v1.1.0/go.mod h1:74gB1z2wpxxInTG6yaqA7KrtM0NZ+RbrcqDvYHefzho=
|
||||
github.com/masterzen/simplexml v0.0.0-20160608183007-4572e39b1ab9/go.mod h1:kCEbxUJlNDEBNbdQMkPSp6yaKcRXVI6f4ddk8Riv4bc=
|
||||
github.com/masterzen/winrm v0.0.0-20180224160350-7e40f93ae939/go.mod h1:CfZSN7zwz5gJiFhZJz49Uzk7mEBHIceWmbFmYx7Hf7E=
|
||||
github.com/mattn/go-colorable v0.0.0-20160220075935-9cbef7c35391/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
|
||||
github.com/mattn/go-isatty v0.0.0-20161123143637-30a891c33c7c h1:YHHK/dEmr2Jo1cWD1VMB2waEeHJhHFp3CEylwWy/VcY=
|
||||
github.com/mattn/go-isatty v0.0.0-20161123143637-30a891c33c7c/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=
|
||||
github.com/mattn/go-shellwords v1.0.1/go.mod h1:3xCvwCdWdlDJUrvuMn7Wuy9eWs4pE8vqg+NOMyg4B2o=
|
||||
github.com/masterzen/winrm v0.0.0-20190223112901-5e5c9a7fe54b/go.mod h1:wr1VqkwW0AB5JS0QLy5GpVMS9E3VtRoSYXUYyVk46KY=
|
||||
github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
|
||||
github.com/mattn/go-colorable v0.1.1 h1:G1f5SKeVxmagw/IyvzvtZE4Gybcc4Tr1tf7I8z0XgOg=
|
||||
github.com/mattn/go-colorable v0.1.1/go.mod h1:FuOcm+DKB9mbwrcAfNl7/TZVBZ6rcnceauSikq3lYCQ=
|
||||
github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=
|
||||
github.com/mattn/go-isatty v0.0.4/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=
|
||||
github.com/mattn/go-isatty v0.0.5 h1:tHXDdz1cpzGaovsTB+TVB8q90WEokoVmfMqoVcrLUgw=
|
||||
github.com/mattn/go-isatty v0.0.5/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s=
|
||||
github.com/mattn/go-runewidth v0.0.4/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU=
|
||||
github.com/mattn/go-shellwords v1.0.4/go.mod h1:3xCvwCdWdlDJUrvuMn7Wuy9eWs4pE8vqg+NOMyg4B2o=
|
||||
github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0=
|
||||
github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg=
|
||||
github.com/mitchellh/cli v0.0.0-20171129193617-33edc47170b5 h1:OYr3N2fY3e3kP/x/d81CJXlcZrIV2hH8gPnuRLpiME4=
|
||||
github.com/mitchellh/cli v0.0.0-20171129193617-33edc47170b5/go.mod h1:oGumspjLm2kTyiT1QMGpFqRlmxnKHfCvhZEVnx+5UeE=
|
||||
github.com/mitchellh/colorstring v0.0.0-20150917214807-8631ce90f286/go.mod h1:l0dey0ia/Uv7NcFFVbCLtqEBQbrT4OCwCSKTEv6enCw=
|
||||
github.com/mitchellh/copystructure v0.0.0-20170525013902-d23ffcb85de3 h1:dECZqiJYhKdj9QlLpiQaRDXHDXRTdiyZI3owdDGhlYY=
|
||||
github.com/mitchellh/copystructure v0.0.0-20170525013902-d23ffcb85de3/go.mod h1:eOsF2yLPlBBJPvD+nhl5QMTBSOBbOph6N7j/IDUw7PY=
|
||||
github.com/mitchellh/go-homedir v0.0.0-20161203194507-b8bc1bf76747/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
|
||||
github.com/mitchellh/go-homedir v1.1.0 h1:lukF9ziXFxDFPkA1vsr5zpc1XuPDn/wFntq5mG+4E0Y=
|
||||
github.com/mitchellh/go-homedir v1.1.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
|
||||
github.com/mitchellh/go-linereader v0.0.0-20141013185533-07bab5fdd958/go.mod h1:OaY7UOoTkkrX3wRwjpYRKafIkkyeD0UtweSHAWWiqQM=
|
||||
github.com/mitchellh/go-testing-interface v0.0.0-20170730050907-9a441910b168 h1:FW/lWFII8EehRx+hVNy5OkkIhWXz9NC69vO5Zr2RExY=
|
||||
github.com/mitchellh/go-testing-interface v0.0.0-20170730050907-9a441910b168/go.mod h1:kRemZodwjscx+RGhAo8eIhFbs2+BFgRtFPeD/KE+zxI=
|
||||
github.com/mitchellh/go-wordwrap v0.0.0-20150314170334-ad45545899c7 h1:DpOJ2HYzCv8LZP15IdmG+YdwD2luVPHITV96TkirNBM=
|
||||
github.com/microcosm-cc/bluemonday v1.0.1/go.mod h1:hsXNsILzKxV+sX77C5b8FSuKF00vh2OMYv+xgHpAMF4=
|
||||
github.com/miekg/dns v1.0.8/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg=
|
||||
github.com/mitchellh/cli v1.0.0 h1:iGBIsUe3+HZ/AD/Vd7DErOt5sU9fa8Uj7A2s1aggv1Y=
|
||||
github.com/mitchellh/cli v1.0.0/go.mod h1:hNIlj7HEI86fIcpObd7a0FcrxTWetlwJDGcceTlRvqc=
|
||||
github.com/mitchellh/colorstring v0.0.0-20190213212951-d06e56a500db h1:62I3jR2EmQ4l5rM/4FEfDWcRD+abF5XlKShorW5LRoQ=
|
||||
github.com/mitchellh/colorstring v0.0.0-20190213212951-d06e56a500db/go.mod h1:l0dey0ia/Uv7NcFFVbCLtqEBQbrT4OCwCSKTEv6enCw=
|
||||
github.com/mitchellh/copystructure v1.0.0 h1:Laisrj+bAB6b/yJwB5Bt3ITZhGJdqmxquMKeZ+mmkFQ=
|
||||
github.com/mitchellh/copystructure v1.0.0/go.mod h1:SNtv71yrdKgLRyLFxmLdkAbkKEFWgYaq1OVrnRcwhnw=
|
||||
github.com/mitchellh/go-homedir v1.0.0 h1:vKb8ShqSby24Yrqr/yDYkuFz8d0WUjys40rvnGC8aR0=
|
||||
github.com/mitchellh/go-homedir v1.0.0/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
|
||||
github.com/mitchellh/go-linereader v0.0.0-20190213213312-1b945b3263eb/go.mod h1:OaY7UOoTkkrX3wRwjpYRKafIkkyeD0UtweSHAWWiqQM=
|
||||
github.com/mitchellh/go-testing-interface v0.0.0-20171004221916-a61a99592b77/go.mod h1:kRemZodwjscx+RGhAo8eIhFbs2+BFgRtFPeD/KE+zxI=
|
||||
github.com/mitchellh/go-testing-interface v1.0.0 h1:fzU/JVNcaqHQEcVFAKeR41fkiLdIPrefOvVG1VZ96U0=
|
||||
github.com/mitchellh/go-testing-interface v1.0.0/go.mod h1:kRemZodwjscx+RGhAo8eIhFbs2+BFgRtFPeD/KE+zxI=
|
||||
github.com/mitchellh/go-wordwrap v0.0.0-20150314170334-ad45545899c7/go.mod h1:ZXFpozHsX6DPmq2I0TCekCxypsnAUbP2oI0UX1GXzOo=
|
||||
github.com/mitchellh/hashstructure v0.0.0-20160209213820-6b17d669fac5 h1:h+4fp6yIoLPf/K2egDK3kvYM2zqb28gJIWWMiDzBdKM=
|
||||
github.com/mitchellh/hashstructure v0.0.0-20160209213820-6b17d669fac5/go.mod h1:QjSHrPWS+BGUVBYkbTZWEnOh3G1DutKwClXU/ABz6AQ=
|
||||
github.com/mitchellh/mapstructure v0.0.0-20170307201123-53818660ed49/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y=
|
||||
github.com/mitchellh/go-wordwrap v1.0.0 h1:6GlHJ/LTGMrIJbwgdqdl2eEH8o+Exx/0m8ir9Gns0u4=
|
||||
github.com/mitchellh/go-wordwrap v1.0.0/go.mod h1:ZXFpozHsX6DPmq2I0TCekCxypsnAUbP2oI0UX1GXzOo=
|
||||
github.com/mitchellh/hashstructure v1.0.0 h1:ZkRJX1CyOoTkar7p/mLS5TZU4nJ1Rn/F8u9dGS02Q3Y=
|
||||
github.com/mitchellh/hashstructure v1.0.0/go.mod h1:QjSHrPWS+BGUVBYkbTZWEnOh3G1DutKwClXU/ABz6AQ=
|
||||
github.com/mitchellh/mapstructure v1.1.2 h1:fmNYVwqnSfB9mZU6OS2O6GsXM+wcskZDuKQzvN1EDeE=
|
||||
github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y=
|
||||
github.com/mitchellh/panicwrap v0.0.0-20161208170302-ba9e1a65e0f7/go.mod h1:QuAqW7/z+iv6aWFJdrA8kCbsF0OOJVKCICqTcYBexuY=
|
||||
github.com/mitchellh/prefixedio v0.0.0-20151214002211-6e6954073784/go.mod h1:kB1naBgV9ORnkiTVeyJOI1DavaJkG4oNIq0Af6ZVKUo=
|
||||
github.com/mitchellh/reflectwalk v0.0.0-20170726202117-63d60e9d0dbc h1:gqYjvctjtX4GHzgfutJxZpvZ7XhGwQLGR5BASwhpO2o=
|
||||
github.com/mitchellh/reflectwalk v0.0.0-20170726202117-63d60e9d0dbc/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw=
|
||||
github.com/mitchellh/panicwrap v0.0.0-20190213213626-17011010aaa4/go.mod h1:YYMf4xtQnR8LRC0vKi3afvQ5QwRPQ17zjcpkBCufb+I=
|
||||
github.com/mitchellh/prefixedio v0.0.0-20190213213902-5733675afd51/go.mod h1:kB1naBgV9ORnkiTVeyJOI1DavaJkG4oNIq0Af6ZVKUo=
|
||||
github.com/mitchellh/reflectwalk v1.0.0 h1:9D+8oIskB4VJBN5SFlmc27fSlIBZaov1Wpk/IfikLNY=
|
||||
github.com/mitchellh/reflectwalk v1.0.0/go.mod h1:mSTlrgnPZtwu0c4WaC2kGObEpuNDbx0jmZXqmk4esnw=
|
||||
github.com/neelance/astrewrite v0.0.0-20160511093645-99348263ae86/go.mod h1:kHJEU3ofeGjhHklVoIGuVj85JJwZ6kWPaJwCIxgnFmo=
|
||||
github.com/neelance/sourcemap v0.0.0-20151028013722-8c68805598ab/go.mod h1:Qr6/a/Q4r9LP1IltGz7tA7iOK1WonHEYhu1HRBA7ZiM=
|
||||
github.com/nu7hatch/gouuid v0.0.0-20131221200532-179d4d0c4d8d/go.mod h1:YUTz3bUH2ZwIWBy3CJBeOBEugqcmXREj14T+iG/4k4U=
|
||||
github.com/oklog/run v1.0.0/go.mod h1:dlhp/R75TPv97u0XWUtDeV/lRKWPKSdTuV0TZvrmrQA=
|
||||
github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE=
|
||||
github.com/onsi/ginkgo v1.7.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE=
|
||||
github.com/onsi/gomega v1.4.3/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY=
|
||||
github.com/openzipkin/zipkin-go v0.1.1/go.mod h1:NtoC/o8u3JlF1lSlyPNswIbeQH9bJTmOf0Erfk+hxe8=
|
||||
github.com/packer-community/winrmcp v0.0.0-20180102160824-81144009af58/go.mod h1:f6Izs6JvFTdnRbziASagjZ2vmf55NSIkC/weStxCHqk=
|
||||
github.com/pascaldekloe/goe v0.0.0-20180627143212-57f6aae5913c/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc=
|
||||
github.com/pelletier/go-toml v1.2.0 h1:T5zMGML61Wp+FlcbWjRDT7yAxhJNAiPPLOFECq181zc=
|
||||
github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic=
|
||||
github.com/pkg/errors v0.0.0-20170505043639-c605e284fe17/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
|
||||
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 v0.0.0-20171219111128-6bee943216c8 h1:lcb1zvdlaZyEbl2OXifN3uOYYyIvllofUbmp9bwbL+0=
|
||||
github.com/posener/complete v0.0.0-20171219111128-6bee943216c8/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI=
|
||||
github.com/posener/complete v1.1.1/go.mod h1:em0nMJCgc9GFtwrmVmEMR/ZL6WyhyjMBndrE9hABlRI=
|
||||
github.com/posener/complete v1.2.1 h1:LrvDIY//XNo65Lq84G/akBuMGlawHvGBABv8f/ZN6DI=
|
||||
github.com/posener/complete v1.2.1/go.mod h1:6gapUrK/U1TAN7ciCoNRIdVC5sbdBTUh1DKN0g6uH7E=
|
||||
github.com/pquerna/otp v1.2.0 h1:/A3+Jn+cagqayeR3iHs/L62m5ue7710D35zl1zJ1kok=
|
||||
github.com/pquerna/otp v1.2.0/go.mod h1:dkJfzwRKNiegxyNb54X/3fLwhCynbMspSyWKnvi1AEg=
|
||||
github.com/prometheus/client_golang v0.8.0/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXPKyh/dDVn+NZz0KFw=
|
||||
github.com/prometheus/client_model v0.0.0-20170216185247-6f3806018612/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo=
|
||||
github.com/prometheus/common v0.0.0-20181126121408-4724e9255275/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro=
|
||||
github.com/prometheus/procfs v0.0.0-20181204211112-1dc9a6cbc91a/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk=
|
||||
github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo=
|
||||
github.com/prometheus/common v0.0.0-20180801064454-c7de2306084e/go.mod h1:daVV7qP5qjZbuso7PdcryaAu0sAZbrN9i7WWcTMWvro=
|
||||
github.com/prometheus/procfs v0.0.0-20180725123919-05ee40e3a273/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk=
|
||||
github.com/russross/blackfriday v1.5.2/go.mod h1:JO/DiYxRf+HjHt06OyowR9PTA263kcR/rfWxYHBV53g=
|
||||
github.com/ryanuber/columnize v0.0.0-20161220214920-0fbbb3f0e3fb/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts=
|
||||
github.com/satori/go.uuid v0.0.0-20160927100844-b061729afc07/go.mod h1:dA0hQrYB0VpLJoorglMZABFdXlWrHn1NEOzdhQKdks0=
|
||||
github.com/satori/uuid v0.0.0-20160927100844-b061729afc07/go.mod h1:B8HLsPLik/YNn6KKWVMDJ8nzCL8RP5WyfsnmvnAEwIU=
|
||||
github.com/satori/go.uuid v1.2.0/go.mod h1:dA0hQrYB0VpLJoorglMZABFdXlWrHn1NEOzdhQKdks0=
|
||||
github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529/go.mod h1:DxrIzT+xaE7yg65j358z/aeFdxmN0P9QXhEzd20vsDc=
|
||||
github.com/smartystreets/assertions v0.0.0-20190116191733-b6c0e53d7304/go.mod h1:OnSkiWE9lh6wB0YB77sQom3nweQdgAjqCqsofrRNTgc=
|
||||
github.com/smartystreets/goconvey v0.0.0-20181108003508-044398e4856c/go.mod h1:XDJAKZRPZ1CvBcN2aX5YOUTYGHki24fSF0Iv48Ibg0s=
|
||||
github.com/sergi/go-diff v1.0.0/go.mod h1:0CfEIISq7TuYL3j771MWULgwwjU+GofnZX9QAmXWZgo=
|
||||
github.com/shurcooL/component v0.0.0-20170202220835-f88ec8f54cc4/go.mod h1:XhFIlyj5a1fBNx5aJTbKoIq0mNaPvOagO+HjB3EtxrY=
|
||||
github.com/shurcooL/events v0.0.0-20181021180414-410e4ca65f48/go.mod h1:5u70Mqkb5O5cxEA8nxTsgrgLehJeAw6Oc4Ab1c/P1HM=
|
||||
github.com/shurcooL/github_flavored_markdown v0.0.0-20181002035957-2122de532470/go.mod h1:2dOwnU2uBioM+SGy2aZoq1f/Sd1l9OkAeAUvjSyvgU0=
|
||||
github.com/shurcooL/go v0.0.0-20180423040247-9e1955d9fb6e/go.mod h1:TDJrrUr11Vxrven61rcy3hJMUqaf/CLWYhHNPmT14Lk=
|
||||
github.com/shurcooL/go-goon v0.0.0-20170922171312-37c2f522c041/go.mod h1:N5mDOmsrJOB+vfqUK+7DmDyjhSLIIBnXo9lvZJj3MWQ=
|
||||
github.com/shurcooL/gofontwoff v0.0.0-20180329035133-29b52fc0a18d/go.mod h1:05UtEgK5zq39gLST6uB0cf3NEHjETfB4Fgr3Gx5R9Vw=
|
||||
github.com/shurcooL/gopherjslib v0.0.0-20160914041154-feb6d3990c2c/go.mod h1:8d3azKNyqcHP1GaQE/c6dDgjkgSx2BZ4IoEi4F1reUI=
|
||||
github.com/shurcooL/highlight_diff v0.0.0-20170515013008-09bb4053de1b/go.mod h1:ZpfEhSmds4ytuByIcDnOLkTHGUI6KNqRNPDLHDk+mUU=
|
||||
github.com/shurcooL/highlight_go v0.0.0-20181028180052-98c3abbbae20/go.mod h1:UDKB5a1T23gOMUJrI+uSuH0VRDStOiUVSjBTRDVBVag=
|
||||
github.com/shurcooL/home v0.0.0-20181020052607-80b7ffcb30f9/go.mod h1:+rgNQw2P9ARFAs37qieuu7ohDNQ3gds9msbT2yn85sg=
|
||||
github.com/shurcooL/htmlg v0.0.0-20170918183704-d01228ac9e50/go.mod h1:zPn1wHpTIePGnXSHpsVPWEktKXHr6+SS6x/IKRb7cpw=
|
||||
github.com/shurcooL/httperror v0.0.0-20170206035902-86b7830d14cc/go.mod h1:aYMfkZ6DWSJPJ6c4Wwz3QtW22G7mf/PEgaB9k/ik5+Y=
|
||||
github.com/shurcooL/httpfs v0.0.0-20171119174359-809beceb2371/go.mod h1:ZY1cvUeJuFPAdZ/B6v7RHavJWZn2YPVFQ1OSXhCGOkg=
|
||||
github.com/shurcooL/httpgzip v0.0.0-20180522190206-b1c53ac65af9/go.mod h1:919LwcH0M7/W4fcZ0/jy0qGght1GIhqyS/EgWGH2j5Q=
|
||||
github.com/shurcooL/issues v0.0.0-20181008053335-6292fdc1e191/go.mod h1:e2qWDig5bLteJ4fwvDAc2NHzqFEthkqn7aOZAOpj+PQ=
|
||||
github.com/shurcooL/issuesapp v0.0.0-20180602232740-048589ce2241/go.mod h1:NPpHK2TI7iSaM0buivtFUc9offApnI0Alt/K8hcHy0I=
|
||||
github.com/shurcooL/notifications v0.0.0-20181007000457-627ab5aea122/go.mod h1:b5uSkrEVM1jQUspwbixRBhaIjIzL2xazXp6kntxYle0=
|
||||
github.com/shurcooL/octicon v0.0.0-20181028054416-fa4f57f9efb2/go.mod h1:eWdoE5JD4R5UVWDucdOPg1g2fqQRq78IQa9zlOV1vpQ=
|
||||
github.com/shurcooL/reactions v0.0.0-20181006231557-f2e0b4ca5b82/go.mod h1:TCR1lToEk4d2s07G3XGfz2QrgHXg4RJBvjrOozvoWfk=
|
||||
github.com/shurcooL/sanitized_anchor_name v0.0.0-20170918181015-86672fcb3f95/go.mod h1:1NzhyTcUVG4SuEtjjoZeVRXNmyL/1OwPU0+IJeTBvfc=
|
||||
github.com/shurcooL/users v0.0.0-20180125191416-49c67e49c537/go.mod h1:QJTqeLYEDaXHZDBsXlPCDqdhQuJkuw4NOtaxYe3xii4=
|
||||
github.com/shurcooL/webdavfs v0.0.0-20170829043945-18c3829fa133/go.mod h1:hKmq5kWdCj2z2KEozexVbfEZIWiTjhE0+UjmZgPqehw=
|
||||
github.com/sirupsen/logrus v1.1.1/go.mod h1:zrgwTnHtNr00buQ1vSptGe8m1f/BbgsPukg8qsT7A+A=
|
||||
github.com/smartystreets/assertions v0.0.0-20180927180507-b2de0cb4f26d/go.mod h1:OnSkiWE9lh6wB0YB77sQom3nweQdgAjqCqsofrRNTgc=
|
||||
github.com/smartystreets/goconvey v0.0.0-20180222194500-ef6db91d284a/go.mod h1:XDJAKZRPZ1CvBcN2aX5YOUTYGHki24fSF0Iv48Ibg0s=
|
||||
github.com/soheilhy/cmux v0.1.4/go.mod h1:IM3LyeVVIOuxMH7sFAkER9+bJ4dT7Ms6E4xg4kGIyLM=
|
||||
github.com/spf13/afero v1.0.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B0CQ=
|
||||
github.com/spf13/afero v1.1.2 h1:m8/z1t7/fwjysjQRYbP0RD+bUIF/8tJwPdEZsI83ACI=
|
||||
github.com/spf13/afero v1.1.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B0CQ=
|
||||
github.com/spf13/cast v1.3.0 h1:oget//CVOEoFewqQxwr0Ej5yjygnqGkvggSE/gB35Q8=
|
||||
github.com/spf13/cast v1.3.0/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE=
|
||||
github.com/spf13/cobra v0.0.4 h1:S0tLZ3VOKl2Te0hpq8+ke0eSJPfCnNTPiDlsfwi1/NE=
|
||||
github.com/spf13/cobra v0.0.4/go.mod h1:3K3wKZymM7VvHMDS9+Akkh4K60UwM26emMESw8tLCHU=
|
||||
github.com/spf13/jwalterweatherman v1.0.0 h1:XHEdyB+EcvlqZamSM4ZOMGlc93t6AcsBEu9Gc1vn7yk=
|
||||
github.com/spf13/jwalterweatherman v1.0.0/go.mod h1:cQK4TGJAtQXfYWX+Ddv3mKDzgVb68N+wFjFa4jdeBTo=
|
||||
github.com/spf13/pflag v1.0.3 h1:zPAT6CGy6wXeQ7NtTnaTerfKOsV6V6F8agHXFiazDkg=
|
||||
github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
|
||||
github.com/spf13/viper v1.3.2 h1:VUFqw5KcqRf7i70GOzW7N+Q7+gxVBkSSqiXB12+JQ4M=
|
||||
github.com/spf13/viper v1.3.2/go.mod h1:ZiWeW+zYFKm7srdB9IoDzzZXaJaI5eL9QjNiN/DMA2s=
|
||||
github.com/sourcegraph/annotate v0.0.0-20160123013949-f4cad6c6324d/go.mod h1:UdhH50NIW0fCiwBSr0co2m7BnFLdv4fQTgdqdJTHFeE=
|
||||
github.com/sourcegraph/syntaxhighlight v0.0.0-20170531221838-bd320f5d308e/go.mod h1:HuIsMU8RRBOtsCgI77wP899iHVBQpCmg4ErYMZB+2IA=
|
||||
github.com/spf13/afero v1.2.1 h1:qgMbHoJbPbw579P+1zVY+6n4nIFuIchaIjzZ/I/Yq8M=
|
||||
github.com/spf13/afero v1.2.1/go.mod h1:9ZxEEn6pIJ8Rxe320qSDBk6AsU0r9pR7Q4OcevTdifk=
|
||||
github.com/spf13/pflag v1.0.2/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4=
|
||||
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
|
||||
github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
|
||||
github.com/stretchr/testify v1.3.0 h1:TivCn/peBQ7UY8ooIcPgZFpTNSz0Q2U6UrFlUfqbe0Q=
|
||||
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
|
||||
github.com/svanharmelen/jsonapi v0.0.0-20180618144545-0c0828c3f16d/go.mod h1:BSTlc8jOjh0niykqEGVXOLXdi9o0r0kR8tCYiMvjFgw=
|
||||
github.com/tarm/serial v0.0.0-20180830185346-98f6abe2eb07/go.mod h1:kDXzergiv9cbyO7IOYJZWg1U88JhDg3PB6klq9Hg2pA=
|
||||
github.com/terraform-providers/terraform-provider-openstack v1.15.0/go.mod h1:2aQ6n/BtChAl1y2S60vebhyJyZXBsuAI5G4+lHrT1Ew=
|
||||
github.com/ugorji/go v0.0.0-20170107133203-ded73eae5db7/go.mod h1:hnLbHMwcvSihnDhEfx2/BzKp2xb0Y+ErdfYcrs9tkJQ=
|
||||
github.com/ugorji/go/codec v0.0.0-20181204163529-d75b2dcb6bc8/go.mod h1:VFNgLljTbGfSG7qAOspJ7OScBnGdDN/yBr0sguwnwf0=
|
||||
github.com/ulikunitz/xz v0.5.4 h1:zATC2OoZ8H1TZll3FpbX+ikwmadbO699PE06cIkm9oU=
|
||||
github.com/ulikunitz/xz v0.5.4/go.mod h1:2bypXElzHzzJZwzH67Y6wb67pO62Rzfn7BSiF4ABRW8=
|
||||
github.com/xanzy/ssh-agent v0.2.0/go.mod h1:0NyE30eGUDliuLEHJgYte/zncp2zdTStcOnWhgSqHD8=
|
||||
github.com/tmc/grpc-websocket-proxy v0.0.0-20171017195756-830351dc03c6/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U=
|
||||
github.com/ugorji/go v0.0.0-20180813092308-00b869d2f4a5/go.mod h1:hnLbHMwcvSihnDhEfx2/BzKp2xb0Y+ErdfYcrs9tkJQ=
|
||||
github.com/ulikunitz/xz v0.5.5 h1:pFrO0lVpTBXLpYw+pnLj6TbvHuyjXMfjGeCwSqCVwok=
|
||||
github.com/ulikunitz/xz v0.5.5/go.mod h1:2bypXElzHzzJZwzH67Y6wb67pO62Rzfn7BSiF4ABRW8=
|
||||
github.com/vmihailenco/msgpack v3.3.3+incompatible/go.mod h1:fy3FlTQTDXWkZ7Bh6AcGMlsjHatGryHQYUTf1ShIgkk=
|
||||
github.com/vmihailenco/msgpack v4.0.1+incompatible h1:RMF1enSPeKTlXrXdOcqjFUElywVZjjC6pqse21bKbEU=
|
||||
github.com/vmihailenco/msgpack v4.0.1+incompatible/go.mod h1:fy3FlTQTDXWkZ7Bh6AcGMlsjHatGryHQYUTf1ShIgkk=
|
||||
github.com/xanzy/ssh-agent v0.2.1/go.mod h1:mLlQY/MoOhWBj+gOGMQkOeiEvkx+8pJSI+0Bx9h2kr4=
|
||||
github.com/xiang90/probing v0.0.0-20160813154853-07dd2e8dfe18/go.mod h1:UETIi67q53MR2AWcXfiuqkDkRtnGDLqkBTpCHuJHxtU=
|
||||
github.com/xlab/treeprint v0.0.0-20161029104018-1d6e34225557/go.mod h1:ce1O1j6UtZfjr22oyGxGLbauSBp2YVXpARAosm7dHBg=
|
||||
github.com/xordataexchange/crypt v0.0.3-0.20170626215501-b2862e3d0a77/go.mod h1:aYKd//L2LvnjZzWKhF00oedf4jCCReLcmhLdhm1A27Q=
|
||||
github.com/zclconf/go-cty v0.0.0-20180302160414-49fa5e03c418 h1:uZKhc0PzQtIg+6+BqQU1m0zzcIgY2hHJk/Xwf00QUNw=
|
||||
github.com/zclconf/go-cty v0.0.0-20180302160414-49fa5e03c418/go.mod h1:LnDKxj8gN4aatfXUqmUNooaDjvmDcLPbAN3hYBIVoJE=
|
||||
golang.org/x/crypto v0.0.0-20180211211603-9de5f2eaf759/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/crypto v0.0.0-20181203042331-505ab145d0a9 h1:mKdxBk7AujPs8kU4m80U72y/zjbZ3UcXC7dClwKbUI0=
|
||||
golang.org/x/crypto v0.0.0-20181203042331-505ab145d0a9/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/net v0.0.0-20190213061140-3a22650c66bd h1:HuTn7WObtcDo9uEEU7rEqL0jYthdXAmZ6PP+meazmaU=
|
||||
github.com/zclconf/go-cty v0.0.0-20181129180422-88fbe721e0f8/go.mod h1:xnAOWiHeOqg2nWS62VtQ7pbOu17FtxJNW8RLEih+O3s=
|
||||
github.com/zclconf/go-cty v0.0.0-20190426224007-b18a157db9e2/go.mod h1:xnAOWiHeOqg2nWS62VtQ7pbOu17FtxJNW8RLEih+O3s=
|
||||
github.com/zclconf/go-cty v0.0.0-20190516203816-4fecf87372ec h1:MSeYjmyjucsFbecMTxg63ASg23lcSARP/kr9sClTFfk=
|
||||
github.com/zclconf/go-cty v0.0.0-20190516203816-4fecf87372ec/go.mod h1:xnAOWiHeOqg2nWS62VtQ7pbOu17FtxJNW8RLEih+O3s=
|
||||
go.opencensus.io v0.18.0 h1:Mk5rgZcggtbvtAun5aJzAtjKKN/t0R3jJPlWILlv938=
|
||||
go.opencensus.io v0.18.0/go.mod h1:vKdFvxhtzZ9onBp9VKHK8z/sRpBMnKAsufL7wlDrCOA=
|
||||
go.uber.org/atomic v1.3.2/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE=
|
||||
go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0=
|
||||
go.uber.org/zap v1.9.1/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q=
|
||||
go4.org v0.0.0-20180809161055-417644f6feb5/go.mod h1:MkTOUMDaeVYJUOUsaDXIhWPZYa1yOyC1qaOBpL57BhE=
|
||||
golang.org/x/build v0.0.0-20190111050920-041ab4dc3f9d/go.mod h1:OWs+y06UdEOHN4y+MfF/py+xQ/tYqIWW03b70/CG9Rw=
|
||||
golang.org/x/crypto v0.0.0-20180816225734-aabede6cba87/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/crypto v0.0.0-20180904163835-0709b304e793/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/crypto v0.0.0-20181030102418-4d3f4d9ffa16/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/crypto v0.0.0-20181112202954-3d3f9f413869/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/crypto v0.0.0-20190219172222-a4c6cb3142f2/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
|
||||
golang.org/x/crypto v0.0.0-20190222235706-ffb98f73852f/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-20190426145343-a29dc8fdc734 h1:p/H982KKEjUnLJkM3tt/LemDnOc1GiZL5FCVlORJ5zo=
|
||||
golang.org/x/crypto v0.0.0-20190426145343-a29dc8fdc734/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI=
|
||||
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
|
||||
golang.org/x/lint v0.0.0-20180702182130-06c8688daad7/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
|
||||
golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE=
|
||||
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-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20181029044818-c44066c5c816/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20181106065722-10aee1819953/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20181114220301-adae6a3d119a/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
|
||||
golang.org/x/net v0.0.0-20181129055619-fae4c4e3ad76/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/oauth2 v0.0.0-20170928010508-bb50c06baba3/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||
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-20190502183928-7f726cade0ab h1:9RfW3ktsOZxgo9YNbBAjq1FWzc/igwEcUzZz8IXgSbk=
|
||||
golang.org/x/net v0.0.0-20190502183928-7f726cade0ab/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg=
|
||||
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||
golang.org/x/oauth2 v0.0.0-20181017192945-9dcd33a902f4/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||
golang.org/x/oauth2 v0.0.0-20181203162652-d668ce993890/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
|
||||
golang.org/x/oauth2 v0.0.0-20190220154721-9b3c75971fc9 h1:pfyU+l9dEu0vZzDDMsdAKa1gZbJYEn6urYXj/+Xkz7s=
|
||||
golang.org/x/oauth2 v0.0.0-20190220154721-9b3c75971fc9/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw=
|
||||
golang.org/x/perf v0.0.0-20180704124530-6e6d33e29852/go.mod h1:JLpeXjPJfIyPr5TlbXLkXWLhP8nz10XfvxElABhCtcw=
|
||||
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/sys v0.0.0-20181026203630-95b1ffbd15a5/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20181205085412-a5c9d58dba9a h1:1n5lsVfiQW3yfsRGu98756EH1YthsFqr/5mxHduZW2A=
|
||||
golang.org/x/sys v0.0.0-20181205085412-a5c9d58dba9a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg=
|
||||
golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
|
||||
golang.org/x/sys v0.0.0-20180823144017-11551d06cbcc/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
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-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20181029174526-d69651ed3497/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20181213200352-4d1cda033e06/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20190129075346-302c3dd5f1cc/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-20190221075227-b4e8571b14e0/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20190222072716-a9d3bda3a223/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
|
||||
golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/sys v0.0.0-20190502175342-a43fa875dd82 h1:vsphBvatvfbhlb4PO1BYSr9dzugGxJ/SQHoNufZJq1w=
|
||||
golang.org/x/sys v0.0.0-20190502175342-a43fa875dd82/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||
golang.org/x/text v0.3.2 h1:tW2bmiBqwgJj/UpqtC8EpXEZVYOwU0yG4iWbprSVAcs=
|
||||
golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
|
||||
golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||
golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||
golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
|
||||
google.golang.org/api v0.0.0-20171005000305-7a7376eff6a5/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
|
||||
google.golang.org/appengine v0.0.0-20150527042145-b667a5000b08/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
|
||||
google.golang.org/genproto v0.0.0-20171002232614-f676e0f3ac63/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
|
||||
google.golang.org/grpc v0.0.0-20170809211603-7657092a1303/go.mod h1:yo6s7OP7yaDglbqo1J04qKzAhqBH6lvTonzMVmEdcZw=
|
||||
golang.org/x/tools v0.0.0-20180828015842-6cd1fcedba52/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
|
||||
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
|
||||
golang.org/x/tools v0.0.0-20181030000716-a0a13e073c7b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
|
||||
golang.org/x/tools v0.0.0-20190425150028-36563e24a262/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q=
|
||||
google.golang.org/api v0.0.0-20180910000450-7ca32eb868bf/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
|
||||
google.golang.org/api v0.0.0-20181030000543-1d582fd0359e/go.mod h1:4mhQ8q/RsB7i+udVvVy5NUi08OU8ZlA0gRVgrF7VFY0=
|
||||
google.golang.org/api v0.1.0 h1:K6z2u68e86TPdSdefXdzvXgR1zEMa+459vBSfWYAZkI=
|
||||
google.golang.org/api v0.1.0/go.mod h1:UGEZY7KEX120AnNLIHFMKIo4obdJhkp2tPbaPlQx13Y=
|
||||
google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
|
||||
google.golang.org/appengine v1.2.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
|
||||
google.golang.org/appengine v1.3.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
|
||||
google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4=
|
||||
google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
|
||||
google.golang.org/genproto v0.0.0-20180831171423-11092d34479b/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
|
||||
google.golang.org/genproto v0.0.0-20181029155118-b69ba1387ce2/go.mod h1:JiN7NxoALGmiZfu7CAH4rXhgtRTLTxftemlI0sWmxmc=
|
||||
google.golang.org/genproto v0.0.0-20181202183823-bd91e49a0898/go.mod h1:7Ep/1NZk928CDR8SjdVbjWNpdIf6nzjE3BTgJDr2Atg=
|
||||
google.golang.org/genproto v0.0.0-20190201180003-4b09977fb922 h1:mBVYJnbrXLA/ZCBTCe7PtEgAUP+1bg92qTaFoPHdz+8=
|
||||
google.golang.org/genproto v0.0.0-20190201180003-4b09977fb922/go.mod h1:L3J43x8/uS+qIUoksaLKe6OS3nUKxOKuIFz1sl2/jx4=
|
||||
google.golang.org/grpc v1.14.0/go.mod h1:yo6s7OP7yaDglbqo1J04qKzAhqBH6lvTonzMVmEdcZw=
|
||||
google.golang.org/grpc v1.16.0/go.mod h1:0JHn/cJsOMiMfNA9+DeHDlAU7KAAB5GDlYFpa9MZMio=
|
||||
google.golang.org/grpc v1.17.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs=
|
||||
google.golang.org/grpc v1.18.0 h1:IZl7mfBGfbhYx2p2rKRtYgDFw6SBz+kclmxYrCksPPA=
|
||||
google.golang.org/grpc v1.18.0/go.mod h1:6QZJwpn2B+Zp71q/5VxRsJ6NXXVCE5NRUHRo+f3cWCs=
|
||||
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/yaml.v2 v2.0.0-20170407172122-cd8b52f8269e/go.mod h1:JAlM8MvJe8wmxCU4Bli9HhUf9+ttbYbLASfIpnQbh74=
|
||||
gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw=
|
||||
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/cheggaaa/pb.v1 v1.0.27/go.mod h1:V/YB90LKu/1FcN3WVnfiiE5oMCibMjukxqG/qStrOgw=
|
||||
gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys=
|
||||
gopkg.in/inf.v0 v0.9.1/go.mod h1:cWUDdTG/fYaXco+Dcufb5Vnc6Gp2YChqWtbxRZE0mXw=
|
||||
gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw=
|
||||
gopkg.in/yaml.v2 v2.2.1/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
|
||||
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
|
||||
grpc.go4.org v0.0.0-20170609214715-11d0a25b4919/go.mod h1:77eQGdRu53HpSqPFJFmuJdjuHRquDANNeA4x7B8WQ9o=
|
||||
honnef.co/go/tools v0.0.0-20180728063816-88497007e858/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
|
||||
honnef.co/go/tools v0.0.0-20190106161140-3f1c8253044a/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
|
||||
howett.net/plist v0.0.0-20181124034731-591f970eefbb/go.mod h1:vMygbs4qMhSZSc4lCUl2OEE+rDiIIJAIdR4m7MiMcm0=
|
||||
sourcegraph.com/sourcegraph/go-diff v0.5.0/go.mod h1:kuch7UrkMzY0X+p9CRK03kfuPQ2zzQcaEFbx8wA8rck=
|
||||
sourcegraph.com/sqs/pbtypes v0.0.0-20180604144634-d3ebe8f20ae4/go.mod h1:ketZ/q3QxT9HOBeFhu6RdvsftgpsbFHBF5Cas6cDKZ0=
|
||||
|
|
|
@ -1 +0,0 @@
|
|||
|
|
@ -1 +0,0 @@
|
|||
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,5 +1,5 @@
|
|||
data "azurerm_resource_group" "appgateway" {
|
||||
name = "${var.resource_group_name}"
|
||||
name = var.resource_group_name
|
||||
}
|
||||
|
||||
locals {
|
||||
|
@ -9,54 +9,54 @@ locals {
|
|||
}
|
||||
|
||||
resource "azurerm_application_gateway" "appgateway" {
|
||||
name = "${var.appgateway_name}"
|
||||
resource_group_name = "${data.azurerm_resource_group.appgateway.name}"
|
||||
location = "${data.azurerm_resource_group.appgateway.location}"
|
||||
tags = "${var.resource_tags}"
|
||||
name = var.appgateway_name
|
||||
resource_group_name = data.azurerm_resource_group.appgateway.name
|
||||
location = data.azurerm_resource_group.appgateway.location
|
||||
tags = var.resource_tags
|
||||
|
||||
sku {
|
||||
name = "${var.appgateway_sku_name}"
|
||||
tier = "${var.appgateway_tier}"
|
||||
capacity = "${var.appgateway_capacity}"
|
||||
name = var.appgateway_sku_name
|
||||
tier = var.appgateway_tier
|
||||
capacity = var.appgateway_capacity
|
||||
}
|
||||
|
||||
gateway_ip_configuration {
|
||||
name = "${var.appgateway_ipconfig_name}"
|
||||
subnet_id = "${var.virtual_network_subnet_id}"
|
||||
name = var.appgateway_ipconfig_name
|
||||
subnet_id = var.virtual_network_subnet_id
|
||||
}
|
||||
|
||||
frontend_port {
|
||||
name = "${var.appgateway_frontend_port_name}"
|
||||
port = "${var.frontend_http_port}"
|
||||
name = var.appgateway_frontend_port_name
|
||||
port = var.frontend_http_port
|
||||
}
|
||||
|
||||
frontend_ip_configuration {
|
||||
name = "${var.appgateway_frontend_ip_configuration_name}"
|
||||
public_ip_address_id = "${var.public_pip_id}"
|
||||
name = var.appgateway_frontend_ip_configuration_name
|
||||
public_ip_address_id = var.public_pip_id
|
||||
}
|
||||
|
||||
ssl_certificate {
|
||||
name = "${local.ssl_certificate_name}"
|
||||
data = "${var.appgateway_ssl_private_pfx}"
|
||||
name = local.ssl_certificate_name
|
||||
data = var.appgateway_ssl_private_pfx
|
||||
password = ""
|
||||
}
|
||||
|
||||
authentication_certificate {
|
||||
name = "${local.authentication_certificate_name}"
|
||||
data = "${var.appgateway_ssl_public_cert}"
|
||||
name = local.authentication_certificate_name
|
||||
data = var.appgateway_ssl_public_cert
|
||||
}
|
||||
|
||||
backend_address_pool {
|
||||
name = "${var.appgateway_backend_address_pool_name}"
|
||||
fqdns = ["${var.backendpool_fqdns}"]
|
||||
name = var.appgateway_backend_address_pool_name
|
||||
fqdns = var.backendpool_fqdns
|
||||
}
|
||||
|
||||
backend_http_settings {
|
||||
name = "${var.appgateway_backend_http_setting_name}"
|
||||
cookie_based_affinity = "${var.backend_http_cookie_based_affinity}"
|
||||
port = "${var.backend_http_port}"
|
||||
protocol = "${var.backend_http_protocol}"
|
||||
probe_name = "${local.backend_probe_name}"
|
||||
name = var.appgateway_backend_http_setting_name
|
||||
cookie_based_affinity = var.backend_http_cookie_based_affinity
|
||||
port = var.backend_http_port
|
||||
protocol = var.backend_http_protocol
|
||||
probe_name = local.backend_probe_name
|
||||
request_timeout = 1
|
||||
pick_host_name_from_backend_address = true
|
||||
}
|
||||
|
@ -64,43 +64,42 @@ resource "azurerm_application_gateway" "appgateway" {
|
|||
# TODO This is locked into a single api endpoint... We'll need to eventually support multiple endpoints
|
||||
# but the count property is only supported at the resource level.
|
||||
probe {
|
||||
name = "${local.backend_probe_name}"
|
||||
protocol = "${var.backend_http_protocol}"
|
||||
name = local.backend_probe_name
|
||||
protocol = var.backend_http_protocol
|
||||
path = "/"
|
||||
interval = "30"
|
||||
timeout = "30"
|
||||
unhealthy_threshold = "3"
|
||||
interval = 30
|
||||
timeout = 30
|
||||
unhealthy_threshold = 3
|
||||
pick_host_name_from_backend_http_settings = true
|
||||
}
|
||||
|
||||
http_listener {
|
||||
name = "${var.appgateway_listener_name}"
|
||||
frontend_ip_configuration_name = "${var.appgateway_frontend_ip_configuration_name}"
|
||||
frontend_port_name = "${var.appgateway_frontend_port_name}"
|
||||
protocol = "${var.http_listener_protocol}"
|
||||
ssl_certificate_name = "${local.ssl_certificate_name}"
|
||||
name = var.appgateway_listener_name
|
||||
frontend_ip_configuration_name = var.appgateway_frontend_ip_configuration_name
|
||||
frontend_port_name = var.appgateway_frontend_port_name
|
||||
protocol = var.http_listener_protocol
|
||||
ssl_certificate_name = local.ssl_certificate_name
|
||||
}
|
||||
|
||||
waf_configuration {
|
||||
enabled = "true"
|
||||
firewall_mode = "${var.appgateway_waf_config_firewall_mode}"
|
||||
enabled = true
|
||||
firewall_mode = var.appgateway_waf_config_firewall_mode
|
||||
rule_set_type = "OWASP"
|
||||
rule_set_version = "3.0"
|
||||
}
|
||||
|
||||
request_routing_rule {
|
||||
name = "${var.appgateway_request_routing_rule_name}"
|
||||
http_listener_name = "${var.appgateway_listener_name}"
|
||||
rule_type = "${var.request_routing_rule_type}"
|
||||
backend_address_pool_name = "${var.appgateway_backend_address_pool_name}"
|
||||
backend_http_settings_name = "${var.appgateway_backend_http_setting_name}"
|
||||
name = var.appgateway_request_routing_rule_name
|
||||
http_listener_name = var.appgateway_listener_name
|
||||
rule_type = var.request_routing_rule_type
|
||||
backend_address_pool_name = var.appgateway_backend_address_pool_name
|
||||
backend_http_settings_name = var.appgateway_backend_http_setting_name
|
||||
}
|
||||
}
|
||||
|
||||
data "external" "app_gw_health" {
|
||||
depends_on = [
|
||||
"azurerm_application_gateway.appgateway",
|
||||
]
|
||||
depends_on = [azurerm_application_gateway.appgateway]
|
||||
|
||||
program = ["az", "network", "application-gateway", "show-backend-health", "-g", "${data.azurerm_resource_group.appgateway.name}", "-n", "${var.appgateway_name}", "-o", "json", "--query", "backendAddressPools[0].backendHttpSettingsCollection[0].servers[0].{address:address,health:health}"]
|
||||
program = ["az", "network", "application-gateway", "show-backend-health", "-g", data.azurerm_resource_group.appgateway.name, "-n", var.appgateway_name, "-o", "json", "--query", "backendAddressPools[0].backendHttpSettingsCollection[0].servers[0].{address:address,health:health}"]
|
||||
}
|
||||
|
||||
|
|
|
@ -1,22 +1,23 @@
|
|||
output "appgateway_name" {
|
||||
description = "The name of the Application Gateway created"
|
||||
value = "${azurerm_application_gateway.appgateway.name}"
|
||||
value = azurerm_application_gateway.appgateway.name
|
||||
}
|
||||
|
||||
output "appgateway_ipconfig" {
|
||||
description = "The Application Gateway IP Configuration"
|
||||
value = "${azurerm_application_gateway.appgateway.gateway_ip_configuration}"
|
||||
value = azurerm_application_gateway.appgateway.gateway_ip_configuration
|
||||
}
|
||||
|
||||
output "appgateway_frontend_ip_configuration" {
|
||||
description = "The Application Gateway Frontend IP Configuration"
|
||||
value = "${azurerm_application_gateway.appgateway.frontend_ip_configuration}"
|
||||
value = azurerm_application_gateway.appgateway.frontend_ip_configuration
|
||||
}
|
||||
|
||||
output "appgateway_health_probe_backend_status" {
|
||||
value = "${lookup(data.external.app_gw_health.result, "health")}"
|
||||
value = data.external.app_gw_health.result["health"]
|
||||
}
|
||||
|
||||
output "app_gateway_health_probe_backend_address" {
|
||||
value = "${lookup(data.external.app_gw_health.result, "address")}"
|
||||
value = data.external.app_gw_health.result["address"]
|
||||
}
|
||||
|
||||
|
|
|
@ -1,150 +1,149 @@
|
|||
# TODO convert all numeric string to true number scalar types once we're migrated to terraform V12. This
|
||||
# change should take place across both module and template configuration defintions.
|
||||
variable "resource_group_name" {
|
||||
description = "Resource group name that the app gateway will be created in."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "virtual_network_name" {
|
||||
description = "Virtual Network name that the app gateway will be created in."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "virtual_network_subnet_id" {
|
||||
description = "Subnet id that the app gateway will be created in."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "appgateway_name" {
|
||||
description = "The name of the application gateway"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "appgateway_ssl_private_pfx" {
|
||||
description = "PFX certificate"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "appgateway_ssl_public_cert" {
|
||||
description = "The contents of the Authentication Certificate which should be used"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "public_pip_id" {
|
||||
description = "the public ip resource id of the frontend configuration"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "resource_tags" {
|
||||
description = "Map of tags to apply to taggable resources in this module. By default the taggable resources are tagged with the name defined above and this map is merged in"
|
||||
type = "map"
|
||||
type = map(string)
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "appgateway_frontend_port_name" {
|
||||
description = "The Frontend Port Name for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "https-frontend-port"
|
||||
}
|
||||
|
||||
variable "appgateway_sku_name" {
|
||||
description = "The SKU for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "WAF_Medium"
|
||||
}
|
||||
|
||||
variable "appgateway_tier" {
|
||||
description = "The tier of the application gateway. Small/Medium/Large. More details can be found at https://azure.microsoft.com/en-us/pricing/details/application-gateway/"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "WAF"
|
||||
}
|
||||
|
||||
variable "appgateway_capacity" {
|
||||
description = "The capacity of application gateway to be created"
|
||||
type = "string"
|
||||
type = number
|
||||
default = 2
|
||||
}
|
||||
|
||||
variable "appgateway_ipconfig_name" {
|
||||
description = "The IP Config Name for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "subnet"
|
||||
}
|
||||
|
||||
variable "frontend_http_port" {
|
||||
description = "The frontend port for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = number
|
||||
default = 443
|
||||
}
|
||||
|
||||
variable "appgateway_frontend_ip_configuration_name" {
|
||||
description = "The Frontend IP configuration name for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "frontend"
|
||||
}
|
||||
|
||||
variable "appgateway_backend_address_pool_name" {
|
||||
description = "The Backend Addres Pool Name for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "backend_pool"
|
||||
}
|
||||
|
||||
variable "appgateway_backend_http_setting_name" {
|
||||
description = "The Backend Http Settings Name for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "backend_settings"
|
||||
}
|
||||
|
||||
variable "backend_http_cookie_based_affinity" {
|
||||
description = "The Backend Http cookie based affinity for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Disabled"
|
||||
}
|
||||
|
||||
variable "backend_http_port" {
|
||||
description = "The backend port for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = number
|
||||
default = 443
|
||||
}
|
||||
|
||||
variable "backend_http_protocol" {
|
||||
description = "The backend protocol for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Https"
|
||||
}
|
||||
|
||||
variable "http_listener_protocol" {
|
||||
description = "The Http Listener protocol for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Https"
|
||||
}
|
||||
|
||||
variable "appgateway_listener_name" {
|
||||
description = "The Listener Name for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "http_proxy_listener"
|
||||
}
|
||||
|
||||
variable "appgateway_request_routing_rule_name" {
|
||||
description = "The rule name to request routing for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "request_proxy_routing_rule"
|
||||
}
|
||||
|
||||
variable "request_routing_rule_type" {
|
||||
description = "The rule type to request routing for the Appication Gateway to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Basic"
|
||||
}
|
||||
|
||||
variable "appgateway_waf_config_firewall_mode" {
|
||||
description = "The firewall mode on the waf gateway"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Prevention"
|
||||
}
|
||||
|
||||
variable "backendpool_fqdns" {
|
||||
description = "A list of FQDN's which should be part of the Backend Address Pool."
|
||||
type = "list"
|
||||
type = list(string)
|
||||
default = []
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,11 +1,12 @@
|
|||
data "azurerm_resource_group" "appinsights" {
|
||||
name = "${var.service_plan_resource_group_name}"
|
||||
name = var.service_plan_resource_group_name
|
||||
}
|
||||
|
||||
resource "azurerm_application_insights" "appinsights" {
|
||||
name = "${var.appinsights_name}"
|
||||
resource_group_name = "${data.azurerm_resource_group.appinsights.name}"
|
||||
location = "${data.azurerm_resource_group.appinsights.location}"
|
||||
application_type = "${var.appinsights_application_type}"
|
||||
tags = "${var.resource_tags}"
|
||||
name = var.appinsights_name
|
||||
resource_group_name = data.azurerm_resource_group.appinsights.name
|
||||
location = data.azurerm_resource_group.appinsights.location
|
||||
application_type = var.appinsights_application_type
|
||||
tags = var.resource_tags
|
||||
}
|
||||
|
||||
|
|
|
@ -1,10 +1,11 @@
|
|||
output "app_insights_app_id" {
|
||||
description = "The App ID associated with this Application Insights component"
|
||||
value = "${azurerm_application_insights.appinsights.app_id}"
|
||||
value = azurerm_application_insights.appinsights.app_id
|
||||
}
|
||||
|
||||
output "app_insights_instrumentation_key" {
|
||||
description = "The Instrumentation Key for this Application Insights component."
|
||||
value = "${azurerm_application_insights.appinsights.instrumentation_key}"
|
||||
value = azurerm_application_insights.appinsights.instrumentation_key
|
||||
sensitive = true
|
||||
}
|
||||
|
||||
|
|
|
@ -1,20 +1,21 @@
|
|||
variable "service_plan_resource_group_name" {
|
||||
description = "The name of the resource group in which the service plan was created."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "resource_tags" {
|
||||
description = "Map of tags to apply to taggable resources in this module (enter as a set of curly braces containing key-value pairs, as in: {\"tag1\" = \"value1\", \"tag2\" = \"value2\"}). By default the taggable resources are tagged with the name defined above and this map is merged in"
|
||||
type = "map"
|
||||
type = map(string)
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "appinsights_name" {
|
||||
description = "Name of the App Insights to create"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "appinsights_application_type" {
|
||||
description = "Type of the App Insights Application. Valid values are ios for iOS, java for Java web, MobileCenter for App Center, Node.JS for Node.js, other for General, phone for Windows Phone, store for Windows Store and web for ASP.NET."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -4,40 +4,41 @@ locals {
|
|||
}
|
||||
|
||||
resource "azurerm_monitor_action_group" "appmonitoring" {
|
||||
count = "${var.action_group_email_receiver == "" ? 0 : 1}"
|
||||
name = "${var.action_group_name}"
|
||||
resource_group_name = "${var.resource_group_name}"
|
||||
short_name = "${var.action_group_short_name}"
|
||||
count = var.action_group_email_receiver == "" ? 0 : 1
|
||||
name = var.action_group_name
|
||||
resource_group_name = var.resource_group_name
|
||||
short_name = var.action_group_short_name
|
||||
|
||||
email_receiver {
|
||||
name = "${var.action_group_email_receiver_name}"
|
||||
email_address = "${var.action_group_email_receiver}"
|
||||
name = var.action_group_email_receiver_name
|
||||
email_address = var.action_group_email_receiver
|
||||
}
|
||||
}
|
||||
|
||||
resource "azurerm_monitor_metric_alert" "appmonitoring" {
|
||||
count = "${var.action_group_email_receiver == "" ? 0 : 1}"
|
||||
name = "${var.metric_alert_name}"
|
||||
resource_group_name = "${azurerm_monitor_action_group.appmonitoring.resource_group_name}"
|
||||
scopes = ["${var.resource_ids}"]
|
||||
frequency = "${var.metric_alert_frequency}"
|
||||
window_size = "${var.metric_alert_period}"
|
||||
count = var.action_group_email_receiver == "" ? 0 : 1
|
||||
name = var.metric_alert_name
|
||||
resource_group_name = azurerm_monitor_action_group.appmonitoring[0].resource_group_name
|
||||
scopes = var.resource_ids
|
||||
frequency = var.metric_alert_frequency
|
||||
window_size = var.metric_alert_period
|
||||
|
||||
criteria {
|
||||
metric_namespace = "${var.metric_alert_criteria_namespace}"
|
||||
metric_name = "${var.metric_alert_criteria_name}"
|
||||
aggregation = "${var.metric_alert_criteria_aggregation}"
|
||||
operator = "${var.metric_alert_criteria_operator}"
|
||||
threshold = "${var.metric_alert_criteria_threshold}"
|
||||
metric_namespace = var.metric_alert_criteria_namespace
|
||||
metric_name = var.metric_alert_criteria_name
|
||||
aggregation = var.metric_alert_criteria_aggregation
|
||||
operator = var.metric_alert_criteria_operator
|
||||
threshold = var.metric_alert_criteria_threshold
|
||||
|
||||
dimension {
|
||||
name = "${local.scaling_name}"
|
||||
operator = "${local.scaling_operator}"
|
||||
values = "${var.scaling_values}"
|
||||
name = local.scaling_name
|
||||
operator = local.scaling_operator
|
||||
values = var.scaling_values
|
||||
}
|
||||
}
|
||||
|
||||
action {
|
||||
action_group_id = "${azurerm_monitor_action_group.appmonitoring.id}"
|
||||
action_group_id = azurerm_monitor_action_group.appmonitoring[0].id
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
output "rule_resource_id" {
|
||||
description = "The id of a metric alert rule."
|
||||
value = "${azurerm_monitor_metric_alert.appmonitoring.*.id}"
|
||||
value = azurerm_monitor_metric_alert.appmonitoring.*.id
|
||||
}
|
||||
|
||||
|
|
|
@ -1,81 +1,82 @@
|
|||
variable "resource_group_name" {
|
||||
description = "The name of the resource group."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
# action group attributes
|
||||
variable "action_group_name" {
|
||||
description = "The name of the action group."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "action_group_email_receiver" {
|
||||
description = "The e-mail receiver for an alert rule resource."
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "action_group_email_receiver_name" {
|
||||
description = "The e-mail receiver name for an alert group."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "E-mail Receiver"
|
||||
}
|
||||
|
||||
variable "action_group_short_name" {
|
||||
description = "The abbreviated name of the action group."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Notify"
|
||||
}
|
||||
|
||||
# metric alert attributes
|
||||
variable "resource_ids" {
|
||||
description = "Resource Ids to be monitored."
|
||||
type = "list"
|
||||
type = list(string)
|
||||
}
|
||||
|
||||
variable "metric_alert_name" {
|
||||
description = "The display name of a group of metric alert criteria."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_name" {
|
||||
description = "A predefined Azure resource alert monitoring rule name."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_namespace" {
|
||||
description = "A monitored resource namespace that holds metric alert criteria."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_aggregation" {
|
||||
description = "The calculation used for building metric alert criteria."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_operator" {
|
||||
description = "A logical operator used for building metric alert criteria."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_threshold" {
|
||||
description = "The criteria threshold value that activates the metric alert."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "scaling_values" {
|
||||
description = "App instance names made available from app service plan scaling options."
|
||||
type = "list"
|
||||
type = list(string)
|
||||
}
|
||||
|
||||
variable "metric_alert_frequency" {
|
||||
description = "The frequency with which the metric alert checks if the conditions are met."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "PT1M"
|
||||
}
|
||||
|
||||
variable "metric_alert_period" {
|
||||
description = "The look back window over which metric values are checked."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "PT5M"
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -4,35 +4,35 @@ locals {
|
|||
}
|
||||
|
||||
data "azurerm_resource_group" "appsvc" {
|
||||
name = "${var.service_plan_resource_group_name}"
|
||||
name = var.service_plan_resource_group_name
|
||||
}
|
||||
|
||||
data "azurerm_app_service_plan" "appsvc" {
|
||||
name = "${var.service_plan_name}"
|
||||
resource_group_name = "${data.azurerm_resource_group.appsvc.name}"
|
||||
name = var.service_plan_name
|
||||
resource_group_name = data.azurerm_resource_group.appsvc.name
|
||||
}
|
||||
|
||||
resource "azurerm_app_service" "appsvc" {
|
||||
name = "${lower(element(keys(var.app_service_name), count.index))}-${lower(terraform.workspace)}"
|
||||
resource_group_name = "${data.azurerm_resource_group.appsvc.name}"
|
||||
location = "${data.azurerm_resource_group.appsvc.location}"
|
||||
app_service_plan_id = "${data.azurerm_app_service_plan.appsvc.id}"
|
||||
tags = "${var.resource_tags}"
|
||||
count = "${length(keys(var.app_service_name))}"
|
||||
resource_group_name = data.azurerm_resource_group.appsvc.name
|
||||
location = data.azurerm_resource_group.appsvc.location
|
||||
app_service_plan_id = data.azurerm_app_service_plan.appsvc.id
|
||||
tags = var.resource_tags
|
||||
count = length(keys(var.app_service_name))
|
||||
|
||||
app_settings {
|
||||
WEBSITES_ENABLE_APP_SERVICE_STORAGE = "${var.enable_storage}"
|
||||
DOCKER_REGISTRY_SERVER_URL = "${var.docker_registry_server_url}"
|
||||
DOCKER_REGISTRY_SERVER_USERNAME = "${var.docker_registry_server_username}"
|
||||
DOCKER_REGISTRY_SERVER_PASSWORD = "${var.docker_registry_server_password}"
|
||||
APPINSIGHTS_INSTRUMENTATIONKEY = "${var.app_insights_instrumentation_key}"
|
||||
KEYVAULT_URI = "${var.vault_uri}"
|
||||
app_settings = {
|
||||
WEBSITES_ENABLE_APP_SERVICE_STORAGE = var.enable_storage
|
||||
DOCKER_REGISTRY_SERVER_URL = var.docker_registry_server_url
|
||||
DOCKER_REGISTRY_SERVER_USERNAME = var.docker_registry_server_username
|
||||
DOCKER_REGISTRY_SERVER_PASSWORD = var.docker_registry_server_password
|
||||
APPINSIGHTS_INSTRUMENTATIONKEY = var.app_insights_instrumentation_key
|
||||
KEYVAULT_URI = var.vault_uri
|
||||
}
|
||||
|
||||
site_config {
|
||||
linux_fx_version = "${element(values(var.app_service_name), count.index)}"
|
||||
always_on = "${var.site_config_always_on}"
|
||||
virtual_network_name = "${var.vnet_name}"
|
||||
linux_fx_version = element(values(var.app_service_name), count.index)
|
||||
always_on = var.site_config_always_on
|
||||
virtual_network_name = var.vnet_name
|
||||
}
|
||||
|
||||
identity {
|
||||
|
@ -43,26 +43,27 @@ resource "azurerm_app_service" "appsvc" {
|
|||
resource "azurerm_app_service_slot" "appsvc_staging_slot" {
|
||||
name = "staging"
|
||||
app_service_name = "${lower(element(keys(var.app_service_name), count.index))}-${lower(terraform.workspace)}"
|
||||
count = "${length(keys(var.app_service_name))}"
|
||||
location = "${data.azurerm_resource_group.appsvc.location}"
|
||||
resource_group_name = "${data.azurerm_resource_group.appsvc.name}"
|
||||
app_service_plan_id = "${data.azurerm_app_service_plan.appsvc.id}"
|
||||
depends_on = ["azurerm_app_service.appsvc"]
|
||||
count = length(keys(var.app_service_name))
|
||||
location = data.azurerm_resource_group.appsvc.location
|
||||
resource_group_name = data.azurerm_resource_group.appsvc.name
|
||||
app_service_plan_id = data.azurerm_app_service_plan.appsvc.id
|
||||
depends_on = [azurerm_app_service.appsvc]
|
||||
}
|
||||
|
||||
resource "azurerm_template_deployment" "access_restriction" {
|
||||
name = "access_restriction"
|
||||
count = "${var.vnet_name == "" ? 0 : length(keys(var.app_service_name))}"
|
||||
resource_group_name = "${data.azurerm_resource_group.appsvc.name}"
|
||||
count = var.vnet_name == "" ? 0 : length(keys(var.app_service_name))
|
||||
resource_group_name = data.azurerm_resource_group.appsvc.name
|
||||
|
||||
parameters = {
|
||||
service_name = "${lower(element(keys(var.app_service_name), count.index))}-${lower(terraform.workspace)}"
|
||||
vnet_subnet_id = "${var.vnet_subnet_id}"
|
||||
access_restriction_name = "${local.access_restriction_name}"
|
||||
access_restriction_description = "${local.access_restriction_description}"
|
||||
vnet_subnet_id = var.vnet_subnet_id
|
||||
access_restriction_name = local.access_restriction_name
|
||||
access_restriction_description = local.access_restriction_description
|
||||
}
|
||||
|
||||
deployment_mode = "Incremental"
|
||||
template_body = "${file("${path.module}/azuredeploy.json")}"
|
||||
depends_on = ["azurerm_app_service.appsvc"]
|
||||
template_body = file("${path.module}/azuredeploy.json")
|
||||
depends_on = [azurerm_app_service.appsvc]
|
||||
}
|
||||
|
||||
|
|
|
@ -1,19 +1,20 @@
|
|||
output "app_service_uri" {
|
||||
description = "The URL of the app service created"
|
||||
value = ["${azurerm_app_service.appsvc.*.default_site_hostname}"]
|
||||
value = azurerm_app_service.appsvc.*.default_site_hostname
|
||||
}
|
||||
|
||||
output "app_service_ids" {
|
||||
description = "The resource ids of the app service created"
|
||||
value = ["${azurerm_app_service.appsvc.*.id}"]
|
||||
value = azurerm_app_service.appsvc.*.id
|
||||
}
|
||||
|
||||
output "app_service_identity_tenant_id" {
|
||||
description = " The Tenant ID for the Service Principal associated with the Managed Service Identity of this App Service."
|
||||
value = "${azurerm_app_service.appsvc.0.identity.0.tenant_id}"
|
||||
value = azurerm_app_service.appsvc[0].identity[0].tenant_id
|
||||
}
|
||||
|
||||
output "app_service_identity_object_ids" {
|
||||
description = " The Principal IDs for the Service Principal associated with the Managed Service Identity for all App Services."
|
||||
value = ["${azurerm_app_service.appsvc.*.identity.0.principal_id}"]
|
||||
value = azurerm_app_service.appsvc.*.identity.0.principal_id
|
||||
}
|
||||
|
||||
|
|
|
@ -1,75 +1,76 @@
|
|||
variable "service_plan_resource_group_name" {
|
||||
description = "The name of the resource group in which the service plan was created."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "service_plan_name" {
|
||||
description = "The name of the service plan"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "resource_tags" {
|
||||
description = "Map of tags to apply to taggable resources in this module. By default the taggable resources are tagged with the name defined above and this map is merged in"
|
||||
type = "map"
|
||||
type = map(string)
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "app_service_name" {
|
||||
description = "The name of the app service to be created"
|
||||
type = "map"
|
||||
type = map(string)
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "enable_storage" {
|
||||
description = "Determines whether or not a storage is attached to the app service."
|
||||
type = "string"
|
||||
default = "false"
|
||||
type = bool
|
||||
default = false
|
||||
}
|
||||
|
||||
variable "vault_uri" {
|
||||
description = "Specifies the URI of the Key Vault resource. Providing this will create a new app setting called KEYVAULT_URI containing the uri value."
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "docker_registry_server_url" {
|
||||
description = "The docker registry server URL for app service to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "index.docker.io"
|
||||
}
|
||||
|
||||
variable "docker_registry_server_username" {
|
||||
description = "The docker registry server username for app service to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "docker_registry_server_password" {
|
||||
description = "The docker registry server password for app service to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "app_insights_instrumentation_key" {
|
||||
description = "The Instrumentation Key for the Application Insights component used for app service to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "site_config_always_on" {
|
||||
description = "Should the app be loaded at all times? Defaults to false."
|
||||
type = "string"
|
||||
default = "false"
|
||||
type = bool
|
||||
default = false
|
||||
}
|
||||
|
||||
variable "vnet_name" {
|
||||
description = "The vnet integration name."
|
||||
type = "string"
|
||||
description = "The vnet integration name"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "vnet_subnet_id" {
|
||||
description = "The vnet integration subnet gateway identifier."
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,12 +1,13 @@
|
|||
data "azurerm_resource_group" "container_registry" {
|
||||
name = "${var.resource_group_name}"
|
||||
name = var.resource_group_name
|
||||
}
|
||||
|
||||
resource "azurerm_container_registry" "container_registry" {
|
||||
name = "${var.container_registry_name}"
|
||||
resource_group_name = "${data.azurerm_resource_group.container_registry.name}"
|
||||
location = "${data.azurerm_resource_group.container_registry.location}"
|
||||
sku = "${var.container_registry_sku}"
|
||||
admin_enabled = "${var.container_registry_admin_enabled}"
|
||||
tags = "${var.container_registry_tags}"
|
||||
name = var.container_registry_name
|
||||
resource_group_name = data.azurerm_resource_group.container_registry.name
|
||||
location = data.azurerm_resource_group.container_registry.location
|
||||
sku = var.container_registry_sku
|
||||
admin_enabled = var.container_registry_admin_enabled
|
||||
tags = var.container_registry_tags
|
||||
}
|
||||
|
||||
|
|
|
@ -1,15 +1,16 @@
|
|||
output "container_registry_id" {
|
||||
description = "The Container Registry ID."
|
||||
value = "${azurerm_container_registry.container_registry.id}"
|
||||
value = azurerm_container_registry.container_registry.id
|
||||
}
|
||||
|
||||
output "container_registry_login_server" {
|
||||
description = "The URL that can be used to log into the container registry."
|
||||
value = "${azurerm_container_registry.container_registry.login_server}"
|
||||
value = azurerm_container_registry.container_registry.login_server
|
||||
}
|
||||
|
||||
output "container_registry_admin_username" {
|
||||
description = "The Username associated with the Container Registry Admin account - if the admin account is enabled."
|
||||
value = "${azurerm_container_registry.container_registry.admin_username}"
|
||||
value = azurerm_container_registry.container_registry.admin_username
|
||||
sensitive = true
|
||||
}
|
||||
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
variable "resource_group_name" {
|
||||
description = "(Required) The name of the resource group in which to create the Container Registry. Changing this forces a new resource to be created."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "container_registry_name" {
|
||||
description = "(Required) Specifies the name of the Container Registry. Changing this forces a new resource to be created."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "container_registry_admin_enabled" {
|
||||
|
@ -15,12 +15,13 @@ variable "container_registry_admin_enabled" {
|
|||
|
||||
variable "container_registry_sku" {
|
||||
description = "(Optional) The SKU name of the the container registry. Possible values are Basic, Standard and Premium."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Basic"
|
||||
}
|
||||
|
||||
variable "container_registry_tags" {
|
||||
description = "(Optional) A mapping of tags to assign to the resource."
|
||||
type = "map"
|
||||
type = map(string)
|
||||
default = {}
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,22 +1,23 @@
|
|||
data "azurerm_resource_group" "cosmosdb" {
|
||||
name = "${var.service_plan_resource_group_name}"
|
||||
name = var.service_plan_resource_group_name
|
||||
}
|
||||
|
||||
resource "azurerm_cosmosdb_account" "cosmosdb" {
|
||||
name = "${var.cosmosdb_name}"
|
||||
location = "${data.azurerm_resource_group.cosmosdb.location}"
|
||||
resource_group_name = "${data.azurerm_resource_group.cosmosdb.name}"
|
||||
name = var.cosmosdb_name
|
||||
location = data.azurerm_resource_group.cosmosdb.location
|
||||
resource_group_name = data.azurerm_resource_group.cosmosdb.name
|
||||
offer_type = "Standard"
|
||||
kind = "${var.cosmosdb_kind}"
|
||||
kind = var.cosmosdb_kind
|
||||
|
||||
enable_automatic_failover = "${var.cosmosdb_automatic_failover}"
|
||||
enable_automatic_failover = var.cosmosdb_automatic_failover
|
||||
|
||||
consistency_policy {
|
||||
consistency_level = "${var.consistency_level}"
|
||||
consistency_level = var.consistency_level
|
||||
}
|
||||
|
||||
geo_location {
|
||||
location = "${var.primary_replica_location}"
|
||||
location = var.primary_replica_location
|
||||
failover_priority = 0
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,15 +1,16 @@
|
|||
output "cosmosdb_endpoint" {
|
||||
description = "The endpoint used to connect to the CosmosDB account."
|
||||
value = "${azurerm_cosmosdb_account.cosmosdb.endpoint}"
|
||||
value = azurerm_cosmosdb_account.cosmosdb.endpoint
|
||||
}
|
||||
|
||||
output "cosmosdb_primary_master_key" {
|
||||
description = "The Primary master key for the CosmosDB Account."
|
||||
value = "${azurerm_cosmosdb_account.cosmosdb.primary_master_key}"
|
||||
value = azurerm_cosmosdb_account.cosmosdb.primary_master_key
|
||||
sensitive = true
|
||||
}
|
||||
|
||||
output "cosmosdb_connection_strings" {
|
||||
description = "A list of connection strings available for this CosmosDB account."
|
||||
value = "${azurerm_cosmosdb_account.cosmosdb.connection_strings}"
|
||||
value = azurerm_cosmosdb_account.cosmosdb.connection_strings
|
||||
}
|
||||
|
||||
|
|
|
@ -1,16 +1,16 @@
|
|||
variable "service_plan_resource_group_name" {
|
||||
description = "Resource group name that the CosmosDB will be created in."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "cosmosdb_name" {
|
||||
description = "The name that CosmosDB will be created with."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "cosmosdb_kind" {
|
||||
description = "Determines the kind of CosmosDB to create. Can either be 'GlobalDocumentDB' or 'MongoDB'."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "GlobalDocumentDB"
|
||||
}
|
||||
|
||||
|
@ -21,11 +21,12 @@ variable "cosmosdb_automatic_failover" {
|
|||
|
||||
variable "consistency_level" {
|
||||
description = "The Consistency Level to use for this CosmosDB Account. Can be either 'BoundedStaleness', 'Eventual', 'Session', 'Strong' or 'ConsistentPrefix'."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Session"
|
||||
}
|
||||
|
||||
variable "primary_replica_location" {
|
||||
description = "The name of the Azure region to host replicated data."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,17 +1,18 @@
|
|||
data "azurerm_key_vault" "vault" {
|
||||
name = "${var.keyvault_name}"
|
||||
resource_group_name = "${var.resource_group_name}"
|
||||
name = var.keyvault_name
|
||||
resource_group_name = var.resource_group_name
|
||||
}
|
||||
|
||||
data "azurerm_client_config" "current" {}
|
||||
data "azurerm_client_config" "current" {
|
||||
}
|
||||
|
||||
resource "azurerm_key_vault_certificate" "kv_cert_import" {
|
||||
count = "${var.key_vault_cert_import_filepath == "" ? 0 : 1}"
|
||||
name = "${var.key_vault_cert_name}"
|
||||
key_vault_id = "${data.azurerm_key_vault.vault.id}"
|
||||
count = var.key_vault_cert_import_filepath == "" ? 0 : 1
|
||||
name = var.key_vault_cert_name
|
||||
key_vault_id = data.azurerm_key_vault.vault.id
|
||||
|
||||
certificate {
|
||||
contents = "${filebase64("${var.key_vault_cert_import_filepath}")}"
|
||||
contents = filebase64(var.key_vault_cert_import_filepath)
|
||||
password = ""
|
||||
}
|
||||
|
||||
|
@ -28,15 +29,15 @@ resource "azurerm_key_vault_certificate" "kv_cert_import" {
|
|||
}
|
||||
|
||||
secret_properties {
|
||||
content_type = "${var.key_vault_content_type}"
|
||||
content_type = var.key_vault_content_type
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
resource "azurerm_key_vault_certificate" "kv_cert_self_assign" {
|
||||
count = "${var.key_vault_cert_import_filepath == "" ? 1 : 0}"
|
||||
name = "${var.key_vault_cert_name}"
|
||||
key_vault_id = "${data.azurerm_key_vault.vault.id}"
|
||||
count = var.key_vault_cert_import_filepath == "" ? 1 : 0
|
||||
name = var.key_vault_cert_name
|
||||
key_vault_id = data.azurerm_key_vault.vault.id
|
||||
|
||||
certificate_policy {
|
||||
issuer_parameters {
|
||||
|
@ -56,12 +57,12 @@ resource "azurerm_key_vault_certificate" "kv_cert_self_assign" {
|
|||
}
|
||||
|
||||
trigger {
|
||||
days_before_expiry = "${var.key_vault_cert_days_before_expiry}"
|
||||
days_before_expiry = var.key_vault_cert_days_before_expiry
|
||||
}
|
||||
}
|
||||
|
||||
secret_properties {
|
||||
content_type = "${var.key_vault_content_type}"
|
||||
content_type = var.key_vault_content_type
|
||||
}
|
||||
|
||||
x509_certificate_properties {
|
||||
|
@ -79,29 +80,30 @@ resource "azurerm_key_vault_certificate" "kv_cert_self_assign" {
|
|||
]
|
||||
|
||||
subject_alternative_names {
|
||||
dns_names = ["${var.key_vault_cert_alt_names}"]
|
||||
dns_names = var.key_vault_cert_alt_names
|
||||
}
|
||||
|
||||
subject = "CN=${var.key_vault_cert_subject}"
|
||||
validity_in_months = "${var.key_vault_cert_validity_months}"
|
||||
validity_in_months = var.key_vault_cert_validity_months
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
data "external" "public_cert" {
|
||||
depends_on = [
|
||||
"azurerm_key_vault_certificate.kv_cert_self_assign",
|
||||
"azurerm_key_vault_certificate.kv_cert_import",
|
||||
azurerm_key_vault_certificate.kv_cert_self_assign,
|
||||
azurerm_key_vault_certificate.kv_cert_import,
|
||||
]
|
||||
|
||||
program = ["az", "keyvault", "certificate", "show", "--name", "${var.key_vault_cert_name}", "--vault-name", "${var.keyvault_name}", "-o", "json", "--query", "{cer:cer}"]
|
||||
program = ["az", "keyvault", "certificate", "show", "--name", var.key_vault_cert_name, "--vault-name", var.keyvault_name, "-o", "json", "--query", "{cer:cer}"]
|
||||
}
|
||||
|
||||
data "external" "private_pfx" {
|
||||
depends_on = [
|
||||
"azurerm_key_vault_certificate.kv_cert_self_assign",
|
||||
"azurerm_key_vault_certificate.kv_cert_import",
|
||||
azurerm_key_vault_certificate.kv_cert_self_assign,
|
||||
azurerm_key_vault_certificate.kv_cert_import,
|
||||
]
|
||||
|
||||
program = ["az", "keyvault", "secret", "show", "--name", "${var.key_vault_cert_name}", "--vault-name", "${var.keyvault_name}", "-o", "json", "--query", "{value:value}"]
|
||||
program = ["az", "keyvault", "secret", "show", "--name", var.key_vault_cert_name, "--vault-name", var.keyvault_name, "-o", "json", "--query", "{value:value}"]
|
||||
}
|
||||
|
||||
|
|
|
@ -1,17 +1,18 @@
|
|||
output "cert_name" {
|
||||
value = "${var.key_vault_cert_name}"
|
||||
value = var.key_vault_cert_name
|
||||
}
|
||||
|
||||
output "public_cert" {
|
||||
value = "${lookup(data.external.public_cert.result, "cer")}"
|
||||
value = data.external.public_cert.result["cer"]
|
||||
sensitive = true
|
||||
}
|
||||
|
||||
output "private_pfx" {
|
||||
value = "${lookup(data.external.private_pfx.result, "value")}"
|
||||
value = data.external.private_pfx.result["value"]
|
||||
sensitive = true
|
||||
}
|
||||
|
||||
output "vault_id" {
|
||||
value = "${data.azurerm_key_vault.vault.id}"
|
||||
value = data.azurerm_key_vault.vault.id
|
||||
}
|
||||
|
||||
|
|
|
@ -1,51 +1,52 @@
|
|||
variable "keyvault_name" {
|
||||
type = "string"
|
||||
type = string
|
||||
description = "The name of the Key Vault where the Certificate should be created."
|
||||
}
|
||||
|
||||
variable "resource_group_name" {
|
||||
type = "string"
|
||||
type = string
|
||||
description = "Default resource group name that the network will be created in."
|
||||
}
|
||||
|
||||
variable "key_vault_cert_name" {
|
||||
description = "Name of the certifacte to create"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "pfx-certificate"
|
||||
}
|
||||
|
||||
variable "key_vault_cert_alt_names" {
|
||||
type = "list"
|
||||
type = list(string)
|
||||
description = "A list of alternative DNS names (FQDNs) identified by the Certificate. Changing this forces a new resource to be created."
|
||||
default = [""]
|
||||
}
|
||||
|
||||
variable "key_vault_content_type" {
|
||||
type = "string"
|
||||
type = string
|
||||
description = " The Content-Type of the Certificate, such as application/x-pkcs12 for a PFX or application/x-pem-file for a PEM. Changing this forces a new resource to be created."
|
||||
default = "application/x-pkcs12"
|
||||
}
|
||||
|
||||
variable "key_vault_cert_import_filepath" {
|
||||
type = "string"
|
||||
type = string
|
||||
description = "The base64-encoded certificate file path. Changing this forces a new resource to be created."
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "key_vault_cert_subject" {
|
||||
type = "string"
|
||||
type = string
|
||||
description = "The Certificate's Subject. Changing this forces a new resource to be created."
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "key_vault_cert_validity_months" {
|
||||
type = "string"
|
||||
type = number
|
||||
description = "The Certificates Validity Period in Months."
|
||||
default = "12"
|
||||
default = 12
|
||||
}
|
||||
|
||||
variable "key_vault_cert_days_before_expiry" {
|
||||
type = "string"
|
||||
type = number
|
||||
description = "The number of days before the Certificate expires that the action associated with this Trigger should run."
|
||||
default = "30"
|
||||
default = 30
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,11 +1,12 @@
|
|||
resource "azurerm_key_vault_access_policy" "keyvault" {
|
||||
count = "${var.instance_count}"
|
||||
key_vault_id = "${var.vault_id}"
|
||||
count = var.instance_count
|
||||
key_vault_id = var.vault_id
|
||||
|
||||
tenant_id = "${var.tenant_id}"
|
||||
object_id = "${var.object_ids[count.index]}"
|
||||
tenant_id = var.tenant_id
|
||||
object_id = var.object_ids[count.index]
|
||||
|
||||
key_permissions = "${var.key_permissions}"
|
||||
secret_permissions = "${var.secret_permissions}"
|
||||
certificate_permissions = "${var.certificate_permissions}"
|
||||
key_permissions = var.key_permissions
|
||||
secret_permissions = var.secret_permissions
|
||||
certificate_permissions = var.certificate_permissions
|
||||
}
|
||||
|
||||
|
|
|
@ -1,37 +1,38 @@
|
|||
variable "vault_id" {
|
||||
description = "Specifies the name of the Key Vault resource."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "tenant_id" {
|
||||
description = "The Azure Active Directory tenant ID that should be used for authenticating requests to the key vault. Changing this forces a new resource to be created."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "instance_count" {
|
||||
description = "the number of access policies that we need to create. Terraform requires the resource instance count to be known during the plan creation step. This will be removed once we upgrade to TF version 12"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "object_ids" {
|
||||
description = "The object IDs of a user, service principal or security group in the Azure Active Directory tenant for the vault. The object ID must be unique for the list of access policies. Changing this forces a new resource to be created."
|
||||
type = "list"
|
||||
type = list(string)
|
||||
}
|
||||
|
||||
variable "key_permissions" {
|
||||
description = "List of key permissions, must be one or more from the following: backup, create, decrypt, delete, encrypt, get, import, list, purge, recover, restore, sign, unwrapKey, update, verify and wrapKey"
|
||||
type = "list"
|
||||
type = list(string)
|
||||
default = ["create", "delete", "get", "list"]
|
||||
}
|
||||
|
||||
variable "secret_permissions" {
|
||||
type = "list"
|
||||
type = list(string)
|
||||
description = "List of secret permissions, must be one or more from the following: backup, delete, get, list, purge, recover, restore and set."
|
||||
default = ["delete", "get", "set", "list"]
|
||||
}
|
||||
|
||||
variable "certificate_permissions" {
|
||||
type = "list"
|
||||
type = list(string)
|
||||
description = "List of storage permissions, must be one or more from the following: backup, delete, deletesas, get, getsas, list, listsas, purge, recover, regeneratekey, restore, set, setsas and update."
|
||||
default = ["create", "delete", "get", "list"]
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -3,28 +3,30 @@ module "azure-provider" {
|
|||
}
|
||||
|
||||
data "azurerm_resource_group" "kv" {
|
||||
name = "${var.resource_group_name}"
|
||||
name = var.resource_group_name
|
||||
}
|
||||
|
||||
data "azurerm_client_config" "current" {}
|
||||
data "azurerm_client_config" "current" {
|
||||
}
|
||||
|
||||
resource "azurerm_key_vault" "keyvault" {
|
||||
name = "${var.keyvault_name}"
|
||||
location = "${data.azurerm_resource_group.kv.location}"
|
||||
resource_group_name = "${data.azurerm_resource_group.kv.name}"
|
||||
tenant_id = "${data.azurerm_client_config.current.tenant_id}"
|
||||
name = var.keyvault_name
|
||||
location = data.azurerm_resource_group.kv.location
|
||||
resource_group_name = data.azurerm_resource_group.kv.name
|
||||
tenant_id = data.azurerm_client_config.current.tenant_id
|
||||
|
||||
sku {
|
||||
name = "${var.keyvault_sku}"
|
||||
name = var.keyvault_sku
|
||||
}
|
||||
|
||||
access_policy {
|
||||
tenant_id = "${data.azurerm_client_config.current.tenant_id}"
|
||||
object_id = "${data.azurerm_client_config.current.service_principal_object_id}"
|
||||
key_permissions = "${var.keyvault_key_permissions}"
|
||||
secret_permissions = "${var.keyvault_secret_permissions}"
|
||||
certificate_permissions = "${var.keyvault_certificate_permissions}"
|
||||
tenant_id = data.azurerm_client_config.current.tenant_id
|
||||
object_id = data.azurerm_client_config.current.service_principal_object_id
|
||||
key_permissions = var.keyvault_key_permissions
|
||||
secret_permissions = var.keyvault_secret_permissions
|
||||
certificate_permissions = var.keyvault_certificate_permissions
|
||||
}
|
||||
|
||||
tags = "${var.resource_tags}"
|
||||
tags = var.resource_tags
|
||||
}
|
||||
|
||||
|
|
|
@ -1,14 +1,15 @@
|
|||
output "keyvault_id" {
|
||||
description = "The id of the Keyvault"
|
||||
value = "${azurerm_key_vault.keyvault.id}"
|
||||
value = azurerm_key_vault.keyvault.id
|
||||
}
|
||||
|
||||
output "keyvault_uri" {
|
||||
description = "The uri of the keyvault"
|
||||
value = "${azurerm_key_vault.keyvault.vault_uri}"
|
||||
value = azurerm_key_vault.keyvault.vault_uri
|
||||
}
|
||||
|
||||
output "keyvault_name" {
|
||||
description = "The name of the Keyvault"
|
||||
value = "${azurerm_key_vault.keyvault.name}"
|
||||
value = azurerm_key_vault.keyvault.name
|
||||
}
|
||||
|
||||
|
|
|
@ -1,40 +1,41 @@
|
|||
variable "keyvault_name" {
|
||||
description = "Name of the keyvault to create"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "spkeyvault"
|
||||
}
|
||||
|
||||
variable "keyvault_sku" {
|
||||
description = "SKU of the keyvault to create"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "standard"
|
||||
}
|
||||
|
||||
variable "resource_group_name" {
|
||||
type = "string"
|
||||
type = string
|
||||
description = "Default resource group name that the network will be created in."
|
||||
}
|
||||
|
||||
variable "keyvault_key_permissions" {
|
||||
description = "Permissions that the service principal has for accessing keys from KeyVault"
|
||||
type = "list"
|
||||
type = list(string)
|
||||
default = ["create", "delete", "get"]
|
||||
}
|
||||
|
||||
variable "keyvault_secret_permissions" {
|
||||
description = "Permissions that the service principal has for accessing secrets from KeyVault"
|
||||
type = "list"
|
||||
type = list(string)
|
||||
default = ["set", "delete", "get", "list"]
|
||||
}
|
||||
|
||||
variable "keyvault_certificate_permissions" {
|
||||
description = "Permissions that the service principal has for accessing certificates from KeyVault"
|
||||
type = "list"
|
||||
type = list(string)
|
||||
default = ["create", "delete", "get", "list"]
|
||||
}
|
||||
|
||||
variable "resource_tags" {
|
||||
description = "Map of tags to apply to taggable resources in this module. By default the taggable resources are tagged with the name defined above and this map is merged in"
|
||||
type = "map"
|
||||
type = map(string)
|
||||
default = {}
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -21,7 +21,7 @@ resource "azurerm_resource_group" "example" {
|
|||
}
|
||||
```
|
||||
|
||||
### Terraform (Version 0.11.13 or higher)
|
||||
### Terraform (Version 0.12.1 or higher)
|
||||
|
||||
Terraform enables you to safely and predictably create, change, and improve infrastructure. It is an open source tool that codifies APIs into declarative configuration files that can be shared amongst team members, treated as code, edited, reviewed, and versioned. In Cobalt, we use Terraform for all our resource deployments on Azure.
|
||||
|
||||
|
|
|
@ -1,15 +1,12 @@
|
|||
provider "azurerm" {
|
||||
version = "~>1.27.0"
|
||||
}
|
||||
|
||||
terraform {
|
||||
required_version = "~> 0.11.13"
|
||||
version = "~>1.30.1"
|
||||
}
|
||||
|
||||
provider "null" {
|
||||
version = "~>2.0.0"
|
||||
version = "~>2.1.0"
|
||||
}
|
||||
|
||||
provider "azuread" {
|
||||
version = "~>0.4.0"
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,73 +1,73 @@
|
|||
data "azurerm_resource_group" "svcplan" {
|
||||
name = "${var.resource_group_name}"
|
||||
name = var.resource_group_name
|
||||
}
|
||||
|
||||
resource "azurerm_app_service_plan" "svcplan" {
|
||||
name = "${var.service_plan_name}"
|
||||
location = "${data.azurerm_resource_group.svcplan.location}"
|
||||
resource_group_name = "${var.resource_group_name}"
|
||||
kind = "${var.service_plan_kind}"
|
||||
tags = "${var.resource_tags}"
|
||||
reserved = "${var.service_plan_kind == "Linux" ? true : "${var.service_plan_reserved}"}"
|
||||
name = var.service_plan_name
|
||||
location = data.azurerm_resource_group.svcplan.location
|
||||
resource_group_name = var.resource_group_name
|
||||
kind = var.service_plan_kind
|
||||
tags = var.resource_tags
|
||||
reserved = var.service_plan_kind == "Linux" ? true : var.service_plan_reserved
|
||||
|
||||
sku {
|
||||
tier = "${var.service_plan_tier}"
|
||||
size = "${var.service_plan_size}"
|
||||
capacity = "${var.service_plan_capacity}"
|
||||
tier = var.service_plan_tier
|
||||
size = var.service_plan_size
|
||||
capacity = var.service_plan_capacity
|
||||
}
|
||||
}
|
||||
|
||||
resource "azurerm_monitor_autoscale_setting" "app_service_auto_scale" {
|
||||
name = "${var.service_plan_name}-autoscale"
|
||||
resource_group_name = "${var.resource_group_name}"
|
||||
location = "${data.azurerm_resource_group.svcplan.location}"
|
||||
target_resource_id = "${azurerm_app_service_plan.svcplan.id}"
|
||||
resource_group_name = var.resource_group_name
|
||||
location = data.azurerm_resource_group.svcplan.location
|
||||
target_resource_id = azurerm_app_service_plan.svcplan.id
|
||||
|
||||
profile {
|
||||
name = "Scale on CPU usage"
|
||||
|
||||
capacity {
|
||||
default = 1
|
||||
minimum = "${var.autoscale_capacity_minimum}"
|
||||
maximum = "${azurerm_app_service_plan.svcplan.maximum_number_of_workers}"
|
||||
minimum = var.autoscale_capacity_minimum
|
||||
maximum = azurerm_app_service_plan.svcplan.maximum_number_of_workers
|
||||
}
|
||||
|
||||
rule {
|
||||
metric_trigger {
|
||||
metric_name = "${var.autoscale_rule_out_metric_name}"
|
||||
metric_resource_id = "${azurerm_app_service_plan.svcplan.id}"
|
||||
metric_name = var.autoscale_rule_out_metric_name
|
||||
metric_resource_id = azurerm_app_service_plan.svcplan.id
|
||||
time_grain = "PT1M"
|
||||
statistic = "${var.autoscale_rule_out_statistic}"
|
||||
statistic = var.autoscale_rule_out_statistic
|
||||
time_window = "PT5M"
|
||||
time_aggregation = "${var.autoscale_rule_out_statistic}"
|
||||
operator = "${var.autoscale_rule_out_operator}"
|
||||
threshold = "${var.autoscale_rule_out_threshold}"
|
||||
time_aggregation = var.autoscale_rule_out_statistic
|
||||
operator = var.autoscale_rule_out_operator
|
||||
threshold = var.autoscale_rule_out_threshold
|
||||
}
|
||||
|
||||
scale_action {
|
||||
direction = "Increase"
|
||||
type = "ChangeCount"
|
||||
value = "${var.autoscale_rule_out_action_change_count}"
|
||||
value = var.autoscale_rule_out_action_change_count
|
||||
cooldown = "PT10M"
|
||||
}
|
||||
}
|
||||
|
||||
rule {
|
||||
metric_trigger {
|
||||
metric_name = "${var.autoscale_rule_in_metric_name}"
|
||||
metric_resource_id = "${azurerm_app_service_plan.svcplan.id}"
|
||||
metric_name = var.autoscale_rule_in_metric_name
|
||||
metric_resource_id = azurerm_app_service_plan.svcplan.id
|
||||
time_grain = "PT1M"
|
||||
statistic = "${var.autoscale_rule_in_statistic}"
|
||||
statistic = var.autoscale_rule_in_statistic
|
||||
time_window = "PT5M"
|
||||
time_aggregation = "${var.autoscale_rule_in_statistic}"
|
||||
operator = "${var.autoscale_rule_in_operator}"
|
||||
threshold = "${var.autoscale_rule_in_threshold}"
|
||||
time_aggregation = var.autoscale_rule_in_statistic
|
||||
operator = var.autoscale_rule_in_operator
|
||||
threshold = var.autoscale_rule_in_threshold
|
||||
}
|
||||
|
||||
scale_action {
|
||||
direction = "Decrease"
|
||||
type = "ChangeCount"
|
||||
value = "${var.autoscale_rule_in_action_change_count}"
|
||||
value = var.autoscale_rule_in_action_change_count
|
||||
cooldown = "PT1M"
|
||||
}
|
||||
}
|
||||
|
@ -80,3 +80,4 @@ resource "azurerm_monitor_autoscale_setting" "app_service_auto_scale" {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,13 +1,14 @@
|
|||
output "service_plan_name" {
|
||||
description = "The name of the service plan created"
|
||||
value = "${azurerm_app_service_plan.svcplan.name}"
|
||||
value = azurerm_app_service_plan.svcplan.name
|
||||
}
|
||||
|
||||
output "service_plan_kind" {
|
||||
description = "The kind of service plan created"
|
||||
value = "${azurerm_app_service_plan.svcplan.kind}"
|
||||
value = azurerm_app_service_plan.svcplan.kind
|
||||
}
|
||||
|
||||
output "app_service_plan_id" {
|
||||
value = "${azurerm_app_service_plan.svcplan.id}"
|
||||
value = azurerm_app_service_plan.svcplan.id
|
||||
}
|
||||
|
||||
|
|
|
@ -1,111 +1,112 @@
|
|||
variable "resource_group_name" {
|
||||
description = "The name of the resource group in which to create the storage account. Changing this forces a new resource to be created. If omitted, will create a new RG based on the `name` above"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "resource_tags" {
|
||||
description = "Map of tags to apply to taggable resources in this module. By default the taggable resources are tagged with the name defined above and this map is merged in"
|
||||
type = "map"
|
||||
type = map(string)
|
||||
default = {}
|
||||
}
|
||||
|
||||
variable "service_plan_name" {
|
||||
description = "The name of the service plan to be created"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "service_plan_tier" {
|
||||
description = "The tier under which the service plan is created. Details can be found at https://docs.microsoft.com/en-us/azure/app-service/overview-hosting-plans"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Standard"
|
||||
}
|
||||
|
||||
variable "service_plan_size" {
|
||||
description = "The compute and storage needed for the service plan to be deployed. Details can be found at https://azure.microsoft.com/en-us/pricing/details/app-service/windows/"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "S1"
|
||||
}
|
||||
|
||||
variable "service_plan_kind" {
|
||||
description = "The kind of Service Plan to be created. Possible values are Windows/Linux/FunctionApp/App"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Linux"
|
||||
}
|
||||
|
||||
variable "service_plan_capacity" {
|
||||
description = "The capacity of Service Plan to be created."
|
||||
type = "string"
|
||||
default = "1"
|
||||
type = number
|
||||
default = 1
|
||||
}
|
||||
|
||||
variable "service_plan_reserved" {
|
||||
description = "Is the Service Plan to be created reserved. Possible values are true/false"
|
||||
type = "string"
|
||||
default = "true"
|
||||
type = bool
|
||||
default = true
|
||||
}
|
||||
|
||||
variable "autoscale_capacity_minimum" {
|
||||
description = "The minimum number of instances for this resource. Valid values are between 0 and 1000"
|
||||
type = "string"
|
||||
default = "1"
|
||||
type = number
|
||||
default = 1
|
||||
}
|
||||
|
||||
variable "autoscale_rule_out_metric_name" {
|
||||
description = "The name of the scale out rule metric that defines what the rule monitors, such as Percentage CPU for Virtual Machine Scale Sets and CpuPercentage for App Service Plan."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "CpuPercentage"
|
||||
}
|
||||
|
||||
variable "autoscale_rule_out_statistic" {
|
||||
description = "Specifies how the scale out rule metrics from multiple instances are combined. Possible values are Average, Min and Max."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Average"
|
||||
}
|
||||
|
||||
variable "autoscale_rule_out_operator" {
|
||||
description = "Specifies how the scale out rule metrics from multiple instances are combined. Possible values are Average, Min and Max."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "GreaterThan"
|
||||
}
|
||||
|
||||
variable "autoscale_rule_out_threshold" {
|
||||
description = "Specifies the threshold of the scale out rule metric that triggers the scale action."
|
||||
type = "string"
|
||||
default = "70"
|
||||
type = number
|
||||
default = 70
|
||||
}
|
||||
|
||||
variable "autoscale_rule_out_action_change_count" {
|
||||
description = "Specifies the number of instances involved in the scaling action."
|
||||
type = "string"
|
||||
default = "1"
|
||||
type = number
|
||||
default = 1
|
||||
}
|
||||
|
||||
variable "autoscale_rule_in_metric_name" {
|
||||
description = "The name of the scale in rule metric that defines what the rule monitors, such as Percentage CPU for Virtual Machine Scale Sets and CpuPercentage for App Service Plan."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "CpuPercentage"
|
||||
}
|
||||
|
||||
variable "autoscale_rule_in_statistic" {
|
||||
description = "Specifies how the scale in rule metrics from multiple instances are combined. Possible values are Average, Min and Max."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Average"
|
||||
}
|
||||
|
||||
variable "autoscale_rule_in_operator" {
|
||||
description = "Specifies how the scale in rule metrics from multiple instances are combined. Possible values are Average, Min and Max."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "GreaterThan"
|
||||
}
|
||||
|
||||
variable "autoscale_rule_in_threshold" {
|
||||
description = "Specifies the threshold of the scale in rule metric that triggers the scale action."
|
||||
type = "string"
|
||||
default = "25"
|
||||
type = number
|
||||
default = 25
|
||||
}
|
||||
|
||||
variable "autoscale_rule_in_action_change_count" {
|
||||
description = "Specifies the number of instances involved in the scaling action."
|
||||
type = "string"
|
||||
default = "1"
|
||||
type = number
|
||||
default = 1
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -3,23 +3,25 @@ module "azure-provider" {
|
|||
}
|
||||
|
||||
locals {
|
||||
sps_to_create = "${var.create_for_rbac == "true" ? 1 : 0}"
|
||||
sps_to_create = var.create_for_rbac == true ? 1 : 0
|
||||
}
|
||||
|
||||
data "azurerm_subscription" "sp" {}
|
||||
data "azurerm_subscription" "sp" {
|
||||
}
|
||||
|
||||
resource "azuread_application" "sp" {
|
||||
count = "${local.sps_to_create}"
|
||||
name = "${var.service_principal_display_name}"
|
||||
count = local.sps_to_create
|
||||
name = var.service_principal_display_name
|
||||
}
|
||||
|
||||
resource "azuread_service_principal" "sp" {
|
||||
count = "${local.sps_to_create}"
|
||||
application_id = "${azuread_application.sp.application_id}"
|
||||
count = local.sps_to_create
|
||||
application_id = azuread_application.sp[0].application_id
|
||||
}
|
||||
|
||||
resource "azurerm_role_assignment" "sp" {
|
||||
role_definition_name = "${var.role_name}"
|
||||
principal_id = "${var.create_for_rbac == "true" ? azuread_service_principal.sp.object_id : var.service_principle_object_id}"
|
||||
scope = "${var.role_scope}"
|
||||
role_definition_name = var.role_name
|
||||
principal_id = var.create_for_rbac == true ? azuread_service_principal.sp[0].object_id : var.service_principle_object_id
|
||||
scope = var.role_scope
|
||||
}
|
||||
|
||||
|
|
|
@ -1,14 +1,15 @@
|
|||
output "service_principal_object_id" {
|
||||
description = "The ID of the Azure AD Service Principal"
|
||||
value = "${azuread_service_principal.sp.*.object_id}"
|
||||
value = azuread_service_principal.sp.*.object_id
|
||||
}
|
||||
|
||||
output "service_principal_application_id" {
|
||||
description = "The ID of the Azure AD Application"
|
||||
value = "${azuread_service_principal.sp.*.application_id}"
|
||||
value = azuread_service_principal.sp.*.application_id
|
||||
}
|
||||
|
||||
output "service_principal_display_name" {
|
||||
description = "The Display Name of the Azure AD Application associated with this Service Principal"
|
||||
value = "${azuread_service_principal.sp.*.display_name}"
|
||||
value = azuread_service_principal.sp.*.display_name
|
||||
}
|
||||
|
||||
|
|
|
@ -1,26 +1,27 @@
|
|||
variable "create_for_rbac" {
|
||||
description = "Create a new Service Principle"
|
||||
type = "string"
|
||||
default = "true"
|
||||
type = bool
|
||||
default = true
|
||||
}
|
||||
|
||||
variable "display_name" {
|
||||
description = "Display name of the AD application"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "object_id" {
|
||||
description = "Object Id of the service principle to assign a role"
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "role_name" {
|
||||
description = "The name of the role definition to assign a service principle too."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "role_scope" {
|
||||
description = "The scope at which the Role Assignment applies too, such as /subscriptions/0b1f6471-1bf0-4dda-aec3-111122223333"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,43 +1,44 @@
|
|||
data "azurerm_resource_group" "tmrg" {
|
||||
name = "${var.resource_group_name}"
|
||||
name = var.resource_group_name
|
||||
}
|
||||
|
||||
resource "azurerm_traffic_manager_profile" "profile" {
|
||||
name = "${var.traffic_manager_profile_name}"
|
||||
resource_group_name = "${data.azurerm_resource_group.tmrg.name}"
|
||||
name = var.traffic_manager_profile_name
|
||||
resource_group_name = data.azurerm_resource_group.tmrg.name
|
||||
traffic_routing_method = "Weighted"
|
||||
|
||||
dns_config {
|
||||
relative_name = "${var.traffic_manager_dns_name}"
|
||||
relative_name = var.traffic_manager_dns_name
|
||||
ttl = 30
|
||||
}
|
||||
|
||||
monitor_config {
|
||||
protocol = "${var.traffic_manager_monitor_protocol}"
|
||||
port = "${var.traffic_manager_monitor_port}"
|
||||
protocol = var.traffic_manager_monitor_protocol
|
||||
port = var.traffic_manager_monitor_port
|
||||
path = "/"
|
||||
}
|
||||
|
||||
tags = "${var.tags}"
|
||||
tags = var.tags
|
||||
}
|
||||
|
||||
resource "azurerm_public_ip" "pip" {
|
||||
name = "${var.public_ip_name}"
|
||||
location = "${data.azurerm_resource_group.tmrg.location}"
|
||||
resource_group_name = "${data.azurerm_resource_group.tmrg.name}"
|
||||
name = var.public_ip_name
|
||||
location = data.azurerm_resource_group.tmrg.location
|
||||
resource_group_name = data.azurerm_resource_group.tmrg.name
|
||||
allocation_method = "Dynamic"
|
||||
domain_name_label = "${var.public_ip_name}-dns"
|
||||
tags = "${var.tags}"
|
||||
tags = var.tags
|
||||
}
|
||||
|
||||
resource "azurerm_traffic_manager_endpoint" "endpoint" {
|
||||
name = "${var.endpoint_name}-ep"
|
||||
resource_group_name = "${data.azurerm_resource_group.tmrg.name}"
|
||||
profile_name = "${var.traffic_manager_profile_name}"
|
||||
resource_group_name = data.azurerm_resource_group.tmrg.name
|
||||
profile_name = var.traffic_manager_profile_name
|
||||
target = "${var.endpoint_name}-dns"
|
||||
target_resource_id = "${azurerm_public_ip.pip.id}"
|
||||
target_resource_id = azurerm_public_ip.pip.id
|
||||
type = "azureEndpoints"
|
||||
weight = 1
|
||||
|
||||
depends_on = ["azurerm_traffic_manager_profile.profile"]
|
||||
depends_on = [azurerm_traffic_manager_profile.profile]
|
||||
}
|
||||
|
||||
|
|
|
@ -1,11 +1,12 @@
|
|||
output "public_pip_id" {
|
||||
value = "${azurerm_public_ip.pip.id}"
|
||||
value = azurerm_public_ip.pip.id
|
||||
}
|
||||
|
||||
output "tm_fqdn" {
|
||||
value = "${azurerm_traffic_manager_profile.profile.fqdn}"
|
||||
value = azurerm_traffic_manager_profile.profile.fqdn
|
||||
}
|
||||
|
||||
output "public_pip_fqdn" {
|
||||
value = "${azurerm_public_ip.pip.fqdn}"
|
||||
value = azurerm_public_ip.pip.fqdn
|
||||
}
|
||||
|
||||
|
|
|
@ -1,39 +1,40 @@
|
|||
variable "traffic_manager_profile_name" {
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "public_ip_name" {
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "endpoint_name" {
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "resource_group_name" {
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "traffic_manager_dns_name" {
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "traffic_manager_monitor_protocol" {
|
||||
type = "string"
|
||||
type = string
|
||||
default = "https"
|
||||
}
|
||||
|
||||
variable "traffic_manager_monitor_port" {
|
||||
type = "string"
|
||||
default = "443"
|
||||
type = number
|
||||
default = 443
|
||||
}
|
||||
|
||||
variable "tags" {
|
||||
description = "The tags to associate with the public ip address."
|
||||
type = "map"
|
||||
type = map(string)
|
||||
|
||||
default = {
|
||||
tag1 = ""
|
||||
tag2 = ""
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -3,3 +3,4 @@ terraform {
|
|||
key = "terraform.tfstate"
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -3,20 +3,21 @@ module "provider" {
|
|||
}
|
||||
|
||||
resource "azurerm_resource_group" "main" {
|
||||
name = "${var.prefix}"
|
||||
location = "${var.resource_group_location}"
|
||||
name = var.prefix
|
||||
location = var.resource_group_location
|
||||
}
|
||||
|
||||
module "service_plan" {
|
||||
source = "../../modules/providers/azure/service-plan"
|
||||
resource_group_name = "${azurerm_resource_group.main.name}"
|
||||
resource_group_name = azurerm_resource_group.main.name
|
||||
service_plan_name = "${azurerm_resource_group.main.name}-sp"
|
||||
}
|
||||
|
||||
module "app_service" {
|
||||
source = "../../modules/providers/azure/app-service"
|
||||
app_service_name = "${var.app_service_name}"
|
||||
service_plan_name = "${module.service_plan.service_plan_name}"
|
||||
service_plan_resource_group_name = "${azurerm_resource_group.main.name}"
|
||||
docker_registry_server_url = "${var.docker_registry_server_url}"
|
||||
app_service_name = var.app_service_name
|
||||
service_plan_name = module.service_plan.service_plan_name
|
||||
service_plan_resource_group_name = azurerm_resource_group.main.name
|
||||
docker_registry_server_url = var.docker_registry_server_url
|
||||
}
|
||||
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
output "app_service_default_hostname" {
|
||||
value = "http://${element(module.app_service.app_service_uri, 0)}"
|
||||
}
|
||||
|
||||
|
|
|
@ -21,8 +21,8 @@ var tfOptions = &terraform.Options{
|
|||
TerraformDir: "../../",
|
||||
Upgrade: true,
|
||||
Vars: map[string]interface{}{
|
||||
"prefix": prefix,
|
||||
"location": datacenter,
|
||||
"prefix": prefix,
|
||||
"resource_group_location": datacenter,
|
||||
},
|
||||
BackendConfig: map[string]interface{}{
|
||||
"storage_account_name": os.Getenv("TF_VAR_remote_state_account"),
|
||||
|
|
|
@ -10,15 +10,16 @@ import (
|
|||
"github.com/microsoft/cobalt/test-harness/infratests"
|
||||
)
|
||||
|
||||
var workspace = fmt.Sprintf("azure-simple-hw-%s", random.UniqueId())
|
||||
var prefix = fmt.Sprintf("helloworld-unit-tst-%s", random.UniqueId())
|
||||
var datacenter = "eastus"
|
||||
|
||||
var tf_options = &terraform.Options{
|
||||
var tfOptions = &terraform.Options{
|
||||
TerraformDir: "../../",
|
||||
Upgrade: true,
|
||||
Vars: map[string]interface{}{
|
||||
"prefix": prefix,
|
||||
"location": datacenter,
|
||||
"prefix": prefix,
|
||||
"resource_group_location": datacenter,
|
||||
},
|
||||
BackendConfig: map[string]interface{}{
|
||||
"storage_account_name": os.Getenv("TF_VAR_remote_state_account"),
|
||||
|
@ -29,22 +30,28 @@ var tf_options = &terraform.Options{
|
|||
func TestAzureSimple(t *testing.T) {
|
||||
testFixture := infratests.UnitTestFixture{
|
||||
GoTest: t,
|
||||
TfOptions: tf_options,
|
||||
TfOptions: tfOptions,
|
||||
ExpectedResourceCount: 8,
|
||||
PlanAssertions: nil,
|
||||
Workspace: workspace,
|
||||
ExpectedResourceAttributeValues: infratests.ResourceDescription{
|
||||
"azurerm_app_service.appsvc": infratests.AttributeValueMapping{
|
||||
"resource_group_name": prefix,
|
||||
"site_config.0.linux_fx_version": "DOCKER|appsvcsample/static-site:latest",
|
||||
"app_settings.WEBSITES_ENABLE_APP_SERVICE_STORAGE": "false",
|
||||
"module.app_service.azurerm_app_service.appsvc[0]": map[string]interface{}{
|
||||
"resource_group_name": prefix,
|
||||
"app_settings": map[string]interface{}{
|
||||
"WEBSITES_ENABLE_APP_SERVICE_STORAGE": "false",
|
||||
},
|
||||
"site_config": []interface{}{
|
||||
map[string]interface{}{"linux_fx_version": "DOCKER|appsvcsample/static-site:latest"},
|
||||
},
|
||||
},
|
||||
"azurerm_app_service_plan.svcplan": infratests.AttributeValueMapping{
|
||||
"kind": "Linux",
|
||||
"reserved": "true",
|
||||
"sku.0.size": "S1",
|
||||
"sku.0.tier": "Standard",
|
||||
"module.service_plan.azurerm_app_service_plan.svcplan": map[string]interface{}{
|
||||
"kind": "Linux",
|
||||
"reserved": true,
|
||||
"sku": []interface{}{
|
||||
map[string]interface{}{"size": "S1", "tier": "Standard"},
|
||||
},
|
||||
},
|
||||
"azurerm_resource_group.main": infratests.AttributeValueMapping{
|
||||
"azurerm_resource_group.main": map[string]interface{}{
|
||||
"location": datacenter,
|
||||
"name": prefix,
|
||||
},
|
||||
|
|
|
@ -4,16 +4,17 @@ variable "prefix" {
|
|||
|
||||
variable "resource_group_location" {
|
||||
description = "The Azure location where all resources in this example should be created."
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "app_service_name" {
|
||||
description = "The name key value pair where the key is the name assigned to the app service and value is the source container."
|
||||
type = "map"
|
||||
type = map(string)
|
||||
}
|
||||
|
||||
variable "docker_registry_server_url" {
|
||||
description = "The url of the container registry that will be utilized to pull container into the Web Apps for containers"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "https://index.docker.io"
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -1,6 +1,6 @@
|
|||
locals {
|
||||
prefix = "${lower(var.name)}-${lower(terraform.workspace)}"
|
||||
prefix_short = "${format("%.20s", local.prefix)}"
|
||||
prefix_short = format("%.20s", local.prefix)
|
||||
tm_profile_name = "${local.prefix}-tf"
|
||||
vnet_name = "${local.prefix}-vnet"
|
||||
tm_endpoint_name = "${var.resource_group_location}_${var.name}"
|
||||
|
@ -8,57 +8,57 @@ locals {
|
|||
appgateway_name = "${local.prefix}-gateway"
|
||||
public_pip_name = "${local.prefix}-ip"
|
||||
kv_name = "${local.prefix_short}-kv"
|
||||
resource_group_name = "${local.prefix}"
|
||||
resource_group_name = local.prefix
|
||||
}
|
||||
|
||||
resource "azurerm_resource_group" "svcplan" {
|
||||
name = "${local.resource_group_name}"
|
||||
location = "${var.resource_group_location}"
|
||||
name = local.resource_group_name
|
||||
location = var.resource_group_location
|
||||
}
|
||||
|
||||
module "vnet" {
|
||||
source = "github.com/Microsoft/bedrock/cluster/azure/vnet"
|
||||
vnet_name = "${local.vnet_name}"
|
||||
address_space = "${var.address_space}"
|
||||
resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
resource_group_location = "${azurerm_resource_group.svcplan.location}"
|
||||
subnet_names = ["${var.subnet_names}"]
|
||||
subnet_prefixes = ["${var.subnet_prefixes}"]
|
||||
subnet_service_endpoints = "${var.subnet_service_endpoints}"
|
||||
vnet_name = local.vnet_name
|
||||
address_space = var.address_space
|
||||
resource_group_name = azurerm_resource_group.svcplan.name
|
||||
resource_group_location = azurerm_resource_group.svcplan.location
|
||||
subnet_names = var.subnet_names
|
||||
subnet_prefixes = var.subnet_prefixes
|
||||
subnet_service_endpoints = var.subnet_service_endpoints
|
||||
}
|
||||
|
||||
module "keyvault" {
|
||||
source = "../../modules/providers/azure/keyvault"
|
||||
keyvault_name = "${local.kv_name}"
|
||||
resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
keyvault_name = local.kv_name
|
||||
resource_group_name = azurerm_resource_group.svcplan.name
|
||||
}
|
||||
|
||||
module "traffic_manager" {
|
||||
source = "../../modules/providers/azure/traffic-manager"
|
||||
resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
traffic_manager_profile_name = "${local.tm_profile_name}"
|
||||
public_ip_name = "${local.public_pip_name}"
|
||||
endpoint_name = "${local.tm_endpoint_name}"
|
||||
traffic_manager_profile_name = "${local.tm_profile_name}"
|
||||
traffic_manager_dns_name = "${local.tm_dns_name}"
|
||||
resource_group_name = azurerm_resource_group.svcplan.name
|
||||
traffic_manager_profile_name = local.tm_profile_name
|
||||
public_ip_name = local.public_pip_name
|
||||
endpoint_name = local.tm_endpoint_name
|
||||
traffic_manager_dns_name = local.tm_dns_name
|
||||
}
|
||||
|
||||
module "keyvault_certificate" {
|
||||
source = "../../modules/providers/azure/keyvault-cert"
|
||||
keyvault_name = "${module.keyvault.keyvault_name}"
|
||||
resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
key_vault_cert_subject = "${module.traffic_manager.public_pip_fqdn}"
|
||||
key_vault_cert_alt_names = ["${module.app_service.app_service_uri}"]
|
||||
keyvault_name = module.keyvault.keyvault_name
|
||||
resource_group_name = azurerm_resource_group.svcplan.name
|
||||
key_vault_cert_subject = module.traffic_manager.public_pip_fqdn
|
||||
key_vault_cert_alt_names = module.app_service.app_service_uri
|
||||
}
|
||||
|
||||
module "app_gateway" {
|
||||
source = "../../modules/providers/azure/app-gateway"
|
||||
appgateway_name = "${local.appgateway_name}"
|
||||
resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
virtual_network_name = "${module.vnet.vnet_name}"
|
||||
appgateway_ssl_private_pfx = "${module.keyvault_certificate.private_pfx}"
|
||||
appgateway_ssl_public_cert = "${module.keyvault_certificate.public_cert}"
|
||||
public_pip_id = "${module.traffic_manager.public_pip_id}"
|
||||
virtual_network_subnet_id = "${module.vnet.vnet_subnet_ids[0]}"
|
||||
backendpool_fqdns = "${module.app_service.app_service_uri}"
|
||||
appgateway_name = local.appgateway_name
|
||||
resource_group_name = azurerm_resource_group.svcplan.name
|
||||
virtual_network_name = module.vnet.vnet_name
|
||||
appgateway_ssl_private_pfx = module.keyvault_certificate.private_pfx
|
||||
appgateway_ssl_public_cert = module.keyvault_certificate.public_cert
|
||||
public_pip_id = module.traffic_manager.public_pip_id
|
||||
virtual_network_subnet_id = module.vnet.vnet_subnet_ids[0]
|
||||
backendpool_fqdns = module.app_service.app_service_uri
|
||||
}
|
||||
|
||||
|
|
|
@ -9,52 +9,53 @@ module "provider" {
|
|||
|
||||
module "service_plan" {
|
||||
source = "../../modules/providers/azure/service-plan"
|
||||
resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
service_plan_name = "${local.service_plan_name}"
|
||||
resource_group_name = azurerm_resource_group.svcplan.name
|
||||
service_plan_name = local.service_plan_name
|
||||
}
|
||||
|
||||
module "app_service" {
|
||||
source = "../../modules/providers/azure/app-service"
|
||||
app_service_name = "${var.app_service_name}"
|
||||
service_plan_name = "${module.service_plan.service_plan_name}"
|
||||
service_plan_resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
app_insights_instrumentation_key = "${module.app_insight.app_insights_instrumentation_key}"
|
||||
docker_registry_server_url = "${var.docker_registry_server_url}"
|
||||
docker_registry_server_username = "${var.docker_registry_server_username}"
|
||||
docker_registry_server_password = "${var.docker_registry_server_password}"
|
||||
vnet_name = "${local.vnet_name}"
|
||||
vnet_subnet_id = "${module.vnet.vnet_subnet_ids[0]}"
|
||||
vault_uri = "${module.keyvault.keyvault_uri}"
|
||||
app_service_name = var.app_service_name
|
||||
service_plan_name = module.service_plan.service_plan_name
|
||||
service_plan_resource_group_name = azurerm_resource_group.svcplan.name
|
||||
app_insights_instrumentation_key = module.app_insight.app_insights_instrumentation_key
|
||||
docker_registry_server_url = var.docker_registry_server_url
|
||||
docker_registry_server_username = var.docker_registry_server_username
|
||||
docker_registry_server_password = var.docker_registry_server_password
|
||||
vnet_name = local.vnet_name
|
||||
vnet_subnet_id = module.vnet.vnet_subnet_ids[0]
|
||||
vault_uri = module.keyvault.keyvault_uri
|
||||
}
|
||||
|
||||
module "app_insight" {
|
||||
source = "../../modules/providers/azure/app-insights"
|
||||
service_plan_resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
appinsights_name = "${local.app_insights_name}"
|
||||
appinsights_application_type = "${var.application_type}"
|
||||
service_plan_resource_group_name = azurerm_resource_group.svcplan.name
|
||||
appinsights_name = local.app_insights_name
|
||||
appinsights_application_type = var.application_type
|
||||
}
|
||||
|
||||
module "keyvault_appsvc_policy" {
|
||||
source = "../../modules/providers/azure/keyvault-policy"
|
||||
instance_count = "${length(keys(var.app_service_name))}"
|
||||
vault_id = "${module.keyvault_certificate.vault_id}"
|
||||
tenant_id = "${module.app_service.app_service_identity_tenant_id}"
|
||||
object_ids = "${module.app_service.app_service_identity_object_ids}"
|
||||
instance_count = length(keys(var.app_service_name))
|
||||
vault_id = module.keyvault_certificate.vault_id
|
||||
tenant_id = module.app_service.app_service_identity_tenant_id
|
||||
object_ids = module.app_service.app_service_identity_object_ids
|
||||
}
|
||||
|
||||
module "app_monitoring" {
|
||||
source = "../../modules/providers/azure/app-monitoring"
|
||||
resource_group_name = "${azurerm_resource_group.svcplan.name}"
|
||||
resource_ids = ["${module.service_plan.app_service_plan_id}"]
|
||||
action_group_name = "${var.action_group_name}"
|
||||
action_group_email_receiver = "${var.action_group_email_receiver}"
|
||||
metric_alert_name = "${var.metric_alert_name}"
|
||||
metric_alert_frequency = "${var.metric_alert_frequency}"
|
||||
metric_alert_period = "${var.metric_alert_period}"
|
||||
metric_alert_criteria_namespace = "${var.metric_alert_criteria_namespace}"
|
||||
metric_alert_criteria_name = "${var.metric_alert_criteria_name}"
|
||||
metric_alert_criteria_aggregation = "${var.metric_alert_criteria_aggregation}"
|
||||
metric_alert_criteria_operator = "${var.metric_alert_criteria_operator}"
|
||||
metric_alert_criteria_threshold = "${var.metric_alert_criteria_threshold}"
|
||||
scaling_values = "${var.scaling_values}"
|
||||
resource_group_name = azurerm_resource_group.svcplan.name
|
||||
resource_ids = [module.service_plan.app_service_plan_id]
|
||||
action_group_name = var.action_group_name
|
||||
action_group_email_receiver = var.action_group_email_receiver
|
||||
metric_alert_name = var.metric_alert_name
|
||||
metric_alert_frequency = var.metric_alert_frequency
|
||||
metric_alert_period = var.metric_alert_period
|
||||
metric_alert_criteria_namespace = var.metric_alert_criteria_namespace
|
||||
metric_alert_criteria_name = var.metric_alert_criteria_name
|
||||
metric_alert_criteria_aggregation = var.metric_alert_criteria_aggregation
|
||||
metric_alert_criteria_operator = var.metric_alert_criteria_operator
|
||||
metric_alert_criteria_threshold = var.metric_alert_criteria_threshold
|
||||
scaling_values = var.scaling_values
|
||||
}
|
||||
|
||||
|
|
|
@ -3,3 +3,4 @@ terraform {
|
|||
key = "terraform.tfstate"
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,15 +1,16 @@
|
|||
output "app_gateway_health_probe_backend_status" {
|
||||
value = "${module.app_gateway.appgateway_health_probe_backend_status}"
|
||||
value = module.app_gateway.appgateway_health_probe_backend_status
|
||||
}
|
||||
|
||||
output "app_gateway_health_probe_backend_address" {
|
||||
value = "${module.app_gateway.app_gateway_health_probe_backend_address}"
|
||||
value = module.app_gateway.app_gateway_health_probe_backend_address
|
||||
}
|
||||
|
||||
output "tm_fqdn" {
|
||||
value = "${module.traffic_manager.public_pip_fqdn}"
|
||||
value = module.traffic_manager.public_pip_fqdn
|
||||
}
|
||||
|
||||
output "public_cert" {
|
||||
value = "${module.keyvault_certificate.public_cert}"
|
||||
value = module.keyvault_certificate.public_cert
|
||||
}
|
||||
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package test
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"os"
|
||||
"testing"
|
||||
|
||||
|
@ -11,7 +12,7 @@ import (
|
|||
var region = "eastus"
|
||||
var workspace = "azsimple"
|
||||
|
||||
var tf_options = &terraform.Options{
|
||||
var tfOptions = &terraform.Options{
|
||||
TerraformDir: "../../",
|
||||
Upgrade: true,
|
||||
Vars: map[string]interface{}{
|
||||
|
@ -23,72 +24,98 @@ var tf_options = &terraform.Options{
|
|||
},
|
||||
}
|
||||
|
||||
// helper function to parse blocks of JSON into a generic Go map
|
||||
func asMap(t *testing.T, jsonString string) map[string]interface{} {
|
||||
var theMap map[string]interface{}
|
||||
if err := json.Unmarshal([]byte(jsonString), &theMap); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
return theMap
|
||||
}
|
||||
|
||||
func TestTemplate(t *testing.T) {
|
||||
expectedAppServicePlan := asMap(t, `{
|
||||
"name": "cobalt-backend-api-`+workspace+`",
|
||||
"site_config": [{"linux_fx_version": "DOCKER|msftcse/cobalt-azure-simple:0.1"}]
|
||||
}`)
|
||||
|
||||
expectedAppGatewayPlan := asMap(t, `{
|
||||
"authentication_certificate": [{"name": "gateway-public-key"}],
|
||||
"frontend_port": [{"port": 443}],
|
||||
"http_listener": [{"protocol": "Https"}],
|
||||
"backend_http_settings": [{"port": 443, "protocol": "Https"}],
|
||||
"probe": [{"protocol": "Https", "timeout": 30, "unhealthy_threshold": 3}],
|
||||
"sku": [{"capacity": 2, "name": "WAF_Medium", "tier": "WAF"}]
|
||||
}`)
|
||||
|
||||
expectedAutoScalePlan := asMap(t, `{
|
||||
"enabled": true,
|
||||
"notification": [{
|
||||
"email": [{
|
||||
"send_to_subscription_administrator": true,
|
||||
"send_to_subscription_co_administrator": true
|
||||
}]
|
||||
}],
|
||||
"profile": [{
|
||||
"rule": [{
|
||||
"metric_trigger": [{
|
||||
"metric_name": "CpuPercentage",
|
||||
"operator": "GreaterThan",
|
||||
"statistic": "Average",
|
||||
"threshold": 70,
|
||||
"time_aggregation": "Average",
|
||||
"time_grain": "PT1M",
|
||||
"time_window": "PT5M"
|
||||
}],
|
||||
"scale_action": [{
|
||||
"cooldown": "PT10M",
|
||||
"direction": "Increase",
|
||||
"type": "ChangeCount",
|
||||
"value": 1
|
||||
}]
|
||||
},{
|
||||
"metric_trigger": [{
|
||||
"metric_name": "CpuPercentage",
|
||||
"operator": "GreaterThan",
|
||||
"statistic": "Average",
|
||||
"threshold": 25,
|
||||
"time_aggregation": "Average",
|
||||
"time_grain": "PT1M",
|
||||
"time_window": "PT5M"
|
||||
}],
|
||||
"scale_action": [{
|
||||
"cooldown": "PT1M",
|
||||
"direction": "Decrease",
|
||||
"type": "ChangeCount",
|
||||
"value": 1
|
||||
}]
|
||||
}]
|
||||
}]
|
||||
}`)
|
||||
|
||||
testFixture := infratests.UnitTestFixture{
|
||||
GoTest: t,
|
||||
TfOptions: tf_options,
|
||||
TfOptions: tfOptions,
|
||||
Workspace: workspace,
|
||||
PlanAssertions: nil,
|
||||
ExpectedResourceCount: 28,
|
||||
ExpectedResourceAttributeValues: infratests.ResourceDescription{
|
||||
"azurerm_resource_group.svcplan": infratests.AttributeValueMapping{
|
||||
"azurerm_resource_group.svcplan": map[string]interface{}{
|
||||
"location": region,
|
||||
"name": "cobalt-az-simple-" + workspace,
|
||||
},
|
||||
"azurerm_app_service_slot.appsvc_staging_slot": infratests.AttributeValueMapping{
|
||||
"module.app_gateway.data.azurerm_resource_group.appgateway": map[string]interface{}{
|
||||
"name": "cobalt-az-simple-" + workspace,
|
||||
},
|
||||
"module.app_insight.data.azurerm_resource_group.appinsights": map[string]interface{}{
|
||||
"name": "cobalt-az-simple-" + workspace,
|
||||
},
|
||||
"module.app_service.azurerm_app_service_slot.appsvc_staging_slot[0]": map[string]interface{}{
|
||||
"name": "staging",
|
||||
},
|
||||
"azurerm_app_service.appsvc": infratests.AttributeValueMapping{
|
||||
"name": "cobalt-backend-api-" + workspace,
|
||||
"site_config.0.linux_fx_version": "DOCKER|msftcse/cobalt-azure-simple:0.1",
|
||||
},
|
||||
"data.azurerm_resource_group.appgateway": infratests.AttributeValueMapping{
|
||||
"name": "cobalt-az-simple-" + workspace,
|
||||
},
|
||||
"azurerm_application_gateway.appgateway": infratests.AttributeValueMapping{
|
||||
"authentication_certificate.0.name": "gateway-public-key",
|
||||
"frontend_port.0.port": "443",
|
||||
"http_listener.0.protocol": "Https",
|
||||
"backend_http_settings.0.port": "443",
|
||||
"backend_http_settings.0.protocol": "Https",
|
||||
"probe.0.protocol": "Https",
|
||||
"probe.0.timeout": "30",
|
||||
"probe.0.unhealthy_threshold": "3",
|
||||
"sku.0.capacity": "2",
|
||||
"sku.0.name": "WAF_Medium",
|
||||
"sku.0.tier": "WAF",
|
||||
},
|
||||
"data.azurerm_resource_group.appinsights": infratests.AttributeValueMapping{
|
||||
"name": "cobalt-az-simple-" + workspace,
|
||||
},
|
||||
"azurerm_monitor_autoscale_setting.app_service_auto_scale": infratests.AttributeValueMapping{
|
||||
"enabled": "true",
|
||||
"name": "cobalt-az-simple-" + workspace + "-sp-autoscale",
|
||||
"notification.0.email.0.send_to_subscription_administrator": "true",
|
||||
"notification.0.email.0.send_to_subscription_co_administrator": "true",
|
||||
"profile.0.rule.0.metric_trigger.0.metric_name": "CpuPercentage",
|
||||
"profile.0.rule.0.metric_trigger.0.operator": "GreaterThan",
|
||||
"profile.0.rule.0.metric_trigger.0.statistic": "Average",
|
||||
"profile.0.rule.0.metric_trigger.0.threshold": "70",
|
||||
"profile.0.rule.0.metric_trigger.0.time_aggregation": "Average",
|
||||
"profile.0.rule.0.metric_trigger.0.time_grain": "PT1M",
|
||||
"profile.0.rule.0.metric_trigger.0.time_window": "PT5M",
|
||||
"profile.0.rule.0.scale_action.0.cooldown": "PT10M",
|
||||
"profile.0.rule.0.scale_action.0.direction": "Increase",
|
||||
"profile.0.rule.0.scale_action.0.type": "ChangeCount",
|
||||
"profile.0.rule.0.scale_action.0.value": "1",
|
||||
"profile.0.rule.1.metric_trigger.0.metric_name": "CpuPercentage",
|
||||
"profile.0.rule.1.metric_trigger.0.operator": "GreaterThan",
|
||||
"profile.0.rule.1.metric_trigger.0.statistic": "Average",
|
||||
"profile.0.rule.1.metric_trigger.0.threshold": "25",
|
||||
"profile.0.rule.1.metric_trigger.0.time_aggregation": "Average",
|
||||
"profile.0.rule.1.metric_trigger.0.time_grain": "PT1M",
|
||||
"profile.0.rule.1.metric_trigger.0.time_window": "PT5M",
|
||||
"profile.0.rule.1.scale_action.0.cooldown": "PT1M",
|
||||
"profile.0.rule.1.scale_action.0.direction": "Decrease",
|
||||
"profile.0.rule.1.scale_action.0.type": "ChangeCount",
|
||||
"profile.0.rule.1.scale_action.0.value": "1",
|
||||
},
|
||||
"module.app_service.azurerm_app_service.appsvc[0]": expectedAppServicePlan,
|
||||
"module.app_gateway.azurerm_application_gateway.appgateway": expectedAppGatewayPlan,
|
||||
"module.service_plan.azurerm_monitor_autoscale_setting.app_service_auto_scale": expectedAutoScalePlan,
|
||||
},
|
||||
}
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
# Resource Group
|
||||
variable "resource_group_location" {
|
||||
description = "The deployment location of resource group container all the resources"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "application_type" {
|
||||
|
@ -11,17 +11,17 @@ variable "application_type" {
|
|||
|
||||
variable "name" {
|
||||
description = "The name of the deployment. This will be used across the resource created in this solution"
|
||||
type = "string"
|
||||
type = string
|
||||
}
|
||||
|
||||
variable "app_service_name" {
|
||||
description = "The name key value pair where the key is the name assigned to the app service and value is the source container"
|
||||
type = "map"
|
||||
type = map(string)
|
||||
}
|
||||
|
||||
variable "subnet_service_endpoints" {
|
||||
description = "The list of service endpoints that will be given to each subnet"
|
||||
type = "list"
|
||||
type = list(string)
|
||||
default = ["Microsoft.Web"]
|
||||
}
|
||||
|
||||
|
@ -53,67 +53,67 @@ variable "appgateway_http_listener_protocol" {
|
|||
# Monitoring Service
|
||||
variable "action_group_name" {
|
||||
description = "The name of the action group."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Simple Default Action Group"
|
||||
}
|
||||
|
||||
variable "action_group_email_receiver" {
|
||||
description = "The e-mail receiver for an alert rule resource."
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "metric_alert_name" {
|
||||
description = "The display name of a group of metric alert criteria."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Simple Default Metric Alerts"
|
||||
}
|
||||
|
||||
variable "metric_alert_frequency" {
|
||||
description = "The frequency with which the metric alert checks if the conditions are met."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "PT1M"
|
||||
}
|
||||
|
||||
variable "metric_alert_period" {
|
||||
description = "The look back window over which metric values are checked. Value must be greater than 'frequency'."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "PT5M"
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_namespace" {
|
||||
description = "A monitored resource namespace with configurable metric alert criteria."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Microsoft.Web/serverfarms"
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_name" {
|
||||
description = "A predefined Azure resource alert monitoring rule name."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "CpuPercentage"
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_aggregation" {
|
||||
description = "The calculation used for building metric alert criteria."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "Average"
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_operator" {
|
||||
description = "A logical operator used for building metric alert criteria."
|
||||
type = "string"
|
||||
type = string
|
||||
default = "GreaterThan"
|
||||
}
|
||||
|
||||
variable "metric_alert_criteria_threshold" {
|
||||
description = "The criteria threshold value that activates the metric alert."
|
||||
type = "string"
|
||||
default = "50"
|
||||
type = number
|
||||
default = 50
|
||||
}
|
||||
|
||||
variable "scaling_values" {
|
||||
description = "Targets app instances made available from app service plan scaling options."
|
||||
type = "list"
|
||||
type = list(string)
|
||||
default = ["*"]
|
||||
}
|
||||
|
||||
|
@ -121,18 +121,19 @@ variable "scaling_values" {
|
|||
|
||||
variable "docker_registry_server_url" {
|
||||
description = "The url of the container registry that will be utilized to pull container into the Web Apps for containers"
|
||||
type = "string"
|
||||
type = string
|
||||
default = "index.docker.io"
|
||||
}
|
||||
|
||||
variable "docker_registry_server_username" {
|
||||
description = "The username used to authenticate with the container registry"
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
variable "docker_registry_server_password" {
|
||||
description = "The password used to authenticate with the container regitry"
|
||||
type = "string"
|
||||
type = string
|
||||
default = ""
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
|
||||
terraform {
|
||||
required_version = ">= 0.12"
|
||||
}
|
|
@ -199,8 +199,8 @@ Our test harness uses a base docker image to pre-package dependencies like Terra
|
|||
|
||||
##### Script Arguments
|
||||
|
||||
- `-g` | `--go_version`: Golang version specification. This argument drives the version of the `golang` stretch base image. **Defaults** to `1.11`.
|
||||
- `-t` | `--tf_version`: Terraform version specification. This argument drives which terraform version release this image will use.. **Defaults** to `0.11.13`
|
||||
- `-g` | `--go_version`: Golang version specification. This argument drives the version of the `golang` stretch base image. **Defaults** to `1.12.5`.
|
||||
- `-t` | `--tf_version`: Terraform version specification. This argument drives which terraform version release this image will use.. **Defaults** to `0.12.1`
|
||||
|
||||
Keep in mind that the terraform version should align with the version from the provider [module](/infra/modules/providers/azure/provider/main.tf#L6)
|
||||
|
||||
|
|
|
@ -110,8 +110,8 @@ function build_image(){
|
|||
--build-arg tfver=$tf_version
|
||||
}
|
||||
|
||||
declare go_version="1.11"
|
||||
declare tf_version="0.11.13"
|
||||
declare go_version="1.12.5"
|
||||
declare tf_version="0.12.1"
|
||||
|
||||
parseInput "$@"
|
||||
declare docker_img="msftcse/cobalt-test-base"
|
||||
|
|
|
@ -34,7 +34,7 @@ ENV GOPATH $HOME/go
|
|||
ENV GOBIN /usr/local/go
|
||||
|
||||
# Install Terraform
|
||||
ARG tfver=0.11.13
|
||||
ARG tfver=0.12.1
|
||||
ENV TF_VERSION=$tfver
|
||||
RUN wget --quiet https://releases.hashicorp.com/terraform/${TF_VERSION}/terraform_${TF_VERSION}_linux_amd64.zip \
|
||||
&& unzip terraform_${TF_VERSION}_linux_amd64.zip \
|
||||
|
|
|
@ -31,7 +31,7 @@ Golang version specification. This argument drives the version of the `golang` s
|
|||
Terraform version specification. This argument drives which terraform version release this image will use.
|
||||
|
||||
```shell
|
||||
docker build -f "test-harness\docker\base-images\Dockerfile" -t msftcse/cobalt-test-base:1.11 . --build-arg gover=1.11 tfver=0.11.13
|
||||
docker build -f "test-harness\docker\base-images\Dockerfile" -t msftcse/cobalt-test-base:1.12.5 . --build-arg gover=1.12.5 tfver=0.12.1
|
||||
```
|
||||
## Contributing
|
||||
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
This file provides abstractions that simplify the process of integration-testing terraform templates. The goal
|
||||
Package infratests This file provides abstractions that simplify the process of integration-testing terraform templates. The goal
|
||||
is to minimize the boiler plate code required to effectively test terraform templates in order to reduce
|
||||
the effort required to write robust template integration-tests.
|
||||
*/
|
||||
|
|
|
@ -0,0 +1,17 @@
|
|||
/*
|
||||
Package infratests this file provides a model for the JSON representation of a terraform plan. It describes
|
||||
a minimal set of metadata produced by the plan and can be expanded to support other attributes
|
||||
if needed
|
||||
*/
|
||||
package infratests
|
||||
|
||||
// TerraformPlan a JSON schema for the output of `terraform plan <planfile>`
|
||||
type TerraformPlan struct {
|
||||
ResourceChanges []struct {
|
||||
Address string `json:"address"`
|
||||
Change struct {
|
||||
Actions []string `json:"actions"`
|
||||
After map[string]interface{} `json:"after"`
|
||||
} `json:"change"`
|
||||
} `json:"resource_changes"`
|
||||
}
|
|
@ -1,30 +1,28 @@
|
|||
/*
|
||||
This file provides abstractions that simplify the process of unit-testing terraform templates. The goal
|
||||
Package infratests This file provides abstractions that simplify the process of unit-testing terraform templates. The goal
|
||||
is to minimize the boiler plate code required to effectively test terraform templates in order to reduce
|
||||
the effort required to write robust template unit-tests.
|
||||
*/
|
||||
package infratests
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"errors"
|
||||
"fmt"
|
||||
"os"
|
||||
"path"
|
||||
"os/exec"
|
||||
"path/filepath"
|
||||
"testing"
|
||||
|
||||
"github.com/gruntwork-io/terratest/modules/random"
|
||||
"github.com/gruntwork-io/terratest/modules/terraform"
|
||||
terraformCore "github.com/hashicorp/terraform/terraform"
|
||||
)
|
||||
|
||||
// AttributeValueMapping Identifies mapping between attributes and values
|
||||
type AttributeValueMapping map[string]string
|
||||
|
||||
// ResourceDescription Identifies mappings between resources and attributes
|
||||
type ResourceDescription map[string]AttributeValueMapping
|
||||
type ResourceDescription map[string]map[string]interface{}
|
||||
|
||||
// TerraformPlanValidation A function that can run an assertion over a terraform plan
|
||||
type TerraformPlanValidation func(goTest *testing.T, plan *terraformCore.Plan)
|
||||
type TerraformPlanValidation func(goTest *testing.T, plan TerraformPlan)
|
||||
|
||||
// UnitTestFixture Holds metadata required to execute a unit test against a test against a terraform template
|
||||
type UnitTestFixture struct {
|
||||
|
@ -55,7 +53,7 @@ func RunUnitTests(fixture *UnitTestFixture) {
|
|||
defer terraform.RunTerraformCommand(fixture.GoTest, fixture.TfOptions, "workspace", "delete", workspaceName)
|
||||
defer terraform.WorkspaceSelectOrNew(fixture.GoTest, fixture.TfOptions, "default")
|
||||
|
||||
tfPlanFilePath := random.UniqueId() + ".plan"
|
||||
tfPlanFilePath := filepath.FromSlash(fmt.Sprintf("%s/%s.plan", os.TempDir(), random.UniqueId()))
|
||||
terraform.RunTerraformCommand(
|
||||
fixture.GoTest,
|
||||
fixture.TfOptions,
|
||||
|
@ -72,17 +70,7 @@ func RunUnitTests(fixture *UnitTestFixture) {
|
|||
// - The resource <--> attribute <--> attribute value mappings match the parameters from the test fixture
|
||||
// - The plan passes any user-defined assertions
|
||||
func validateTerraformPlanFile(fixture *UnitTestFixture, tfPlanFilePath string) {
|
||||
file, err := os.Open(path.Join(fixture.TfOptions.TerraformDir, tfPlanFilePath))
|
||||
if err != nil {
|
||||
fixture.GoTest.Fatal(err)
|
||||
}
|
||||
defer file.Close()
|
||||
|
||||
plan, err := terraformCore.ReadPlan(file)
|
||||
if err != nil {
|
||||
fixture.GoTest.Fatal(err)
|
||||
}
|
||||
|
||||
plan := parseTerraformPlan(fixture, tfPlanFilePath)
|
||||
validatePlanCreateProperties(fixture, plan)
|
||||
validatePlanResourceKeyValues(fixture, plan)
|
||||
|
||||
|
@ -94,74 +82,86 @@ func validateTerraformPlanFile(fixture *UnitTestFixture, tfPlanFilePath string)
|
|||
}
|
||||
}
|
||||
|
||||
func parseTerraformPlan(fixture *UnitTestFixture, filePath string) TerraformPlan {
|
||||
// Note: when the PR linked below is merged and the new build is used by this codebase,
|
||||
// we can leverage Terratest to run this for us. Currently with large plan outputs,
|
||||
// a buffer overflow will happen in Terratest because the default max character limit
|
||||
// may be exceeded for large plan files:
|
||||
//
|
||||
// - Issue: https://github.com/gruntwork-io/terratest/issues/203
|
||||
// - PR: https://github.com/gruntwork-io/terratest/pull/317
|
||||
//
|
||||
// jsonBytes := []bytes(terraform.RunTerraformCommand(
|
||||
// fixture.GoTest,
|
||||
// fixture.TfOptions,
|
||||
// terraform.FormatArgs(&terraform.Options{}, "show", "-json", filePath)...))
|
||||
cmd := exec.Command("terraform", "show", "-json", filePath)
|
||||
cmd.Dir = fixture.TfOptions.TerraformDir
|
||||
jsonBytes, cmdErr := cmd.Output()
|
||||
if cmdErr != nil {
|
||||
fixture.GoTest.Fatal(cmdErr)
|
||||
}
|
||||
|
||||
fmt.Println("Got terraform plan...", string(jsonBytes))
|
||||
var plan TerraformPlan
|
||||
jsonErr := json.Unmarshal(jsonBytes, &plan)
|
||||
if jsonErr != nil {
|
||||
fixture.GoTest.Fatal(jsonErr)
|
||||
}
|
||||
return plan
|
||||
}
|
||||
|
||||
// Validates high level attributes of a terraform plan creat properties. This includes:
|
||||
// - The plan is not empty
|
||||
// - The plan contains the correct number of resources
|
||||
// - The plan is only creating resources
|
||||
func validatePlanCreateProperties(fixture *UnitTestFixture, plan *terraformCore.Plan) {
|
||||
if plan.Diff.Empty() {
|
||||
// - The plan is not executing any destructive actions
|
||||
func validatePlanCreateProperties(fixture *UnitTestFixture, plan TerraformPlan) {
|
||||
if len(plan.ResourceChanges) == 0 {
|
||||
fixture.GoTest.Fatal(errors.New("Plan diff was unexpectedly empty"))
|
||||
}
|
||||
|
||||
// plans should contain diffs of type `DiffCreate` otherwise the test may accidentally remove resources
|
||||
for _, module := range plan.Diff.Modules {
|
||||
if module.ChangeType() != terraformCore.DiffCreate {
|
||||
fixture.GoTest.Fatal(
|
||||
fmt.Errorf("Plan unexpectedly contained an update of type '%s'", string(module.ChangeType())))
|
||||
}
|
||||
}
|
||||
|
||||
resourceCount := 0
|
||||
for _, module := range plan.Diff.Modules {
|
||||
resourceCount += len(module.Resources)
|
||||
}
|
||||
|
||||
// every plan should have the correct number of resources
|
||||
if resourceCount != fixture.ExpectedResourceCount {
|
||||
if len(plan.ResourceChanges) != fixture.ExpectedResourceCount {
|
||||
fixture.GoTest.Fatal(fmt.Errorf(
|
||||
"Plan unexpectedly had %d resources instead of %d", resourceCount, fixture.ExpectedResourceCount))
|
||||
}
|
||||
}
|
||||
|
||||
// validates that the resource <--> attribute <--> attribute value mappings match the parameters
|
||||
// from the test fixture
|
||||
func validatePlanResourceKeyValues(fixture *UnitTestFixture, plan *terraformCore.Plan) {
|
||||
// collect actual resource attrubte value mappings by iterating over the TF plan
|
||||
seen := ResourceDescription{}
|
||||
for _, module := range plan.Diff.Modules {
|
||||
for resource, resourceDiffs := range module.Resources {
|
||||
seen[resource] = AttributeValueMapping{}
|
||||
for attribute, vals := range resourceDiffs.Attributes {
|
||||
seen[resource][attribute] = vals.New
|
||||
}
|
||||
}
|
||||
"Plan unexpectedly had %d resources instead of %d", len(plan.ResourceChanges), fixture.ExpectedResourceCount))
|
||||
}
|
||||
|
||||
// verify that for each of the expected resource attribute value mappings that the expected
|
||||
// values are found in the terraform plan
|
||||
for resource, expectedMappings := range fixture.ExpectedResourceAttributeValues {
|
||||
_, resourceFound := seen[resource]
|
||||
if !resourceFound {
|
||||
fixture.GoTest.Fatal(fmt.Errorf(
|
||||
"Plan unexpectedly did not contain a change for resource '%s'", resource))
|
||||
}
|
||||
|
||||
for expectedAttr, expectedVal := range expectedMappings {
|
||||
actualVal, attrFound := seen[resource][expectedAttr]
|
||||
if !attrFound {
|
||||
fixture.GoTest.Fatal(fmt.Errorf(
|
||||
"Plan unexpectedly did not contain a change for '%s.%s'", resource, expectedAttr))
|
||||
}
|
||||
|
||||
if expectedVal != actualVal {
|
||||
fixture.GoTest.Fatal(fmt.Errorf(
|
||||
"Plan unexpectedly had value '%s' instead of '%s' for '%s.%s'",
|
||||
actualVal,
|
||||
expectedVal,
|
||||
resource,
|
||||
expectedAttr,
|
||||
))
|
||||
// a unit test should never create a destructive action like deleting a resource
|
||||
allowedActions := map[string]bool{"create": true, "read": true}
|
||||
for _, resource := range plan.ResourceChanges {
|
||||
for _, action := range resource.Change.Actions {
|
||||
if !allowedActions[action] {
|
||||
fixture.GoTest.Fatal(
|
||||
fmt.Errorf("Plan unexpectedly actions other than `create`: %s", resource.Change.Actions))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// verifies that the attribute value mappings for each resource specified by the client exist
|
||||
// as a subset of the actual values defined in the terraform plan.
|
||||
func validatePlanResourceKeyValues(fixture *UnitTestFixture, plan TerraformPlan) {
|
||||
theRealPlanAsMap := planToMap(plan)
|
||||
theExpectedPlanAsMap := resourceDescriptionToMap(fixture.ExpectedResourceAttributeValues)
|
||||
|
||||
if err := verifyTargetsExistInMap(theRealPlanAsMap, theExpectedPlanAsMap); err != nil {
|
||||
fixture.GoTest.Fatal(err)
|
||||
}
|
||||
}
|
||||
|
||||
// transforms the output of `terraform show -json <planfile>` into a generic map
|
||||
func planToMap(plan TerraformPlan) map[string]interface{} {
|
||||
mp := make(map[string]interface{})
|
||||
for _, resource := range plan.ResourceChanges {
|
||||
mp[resource.Address] = resource.Change.After
|
||||
}
|
||||
return mp
|
||||
}
|
||||
|
||||
// transforms a resource description into a generic map
|
||||
func resourceDescriptionToMap(resources ResourceDescription) map[string]interface{} {
|
||||
mp := make(map[string]interface{})
|
||||
for key, value := range resources {
|
||||
mp[key] = value
|
||||
}
|
||||
return mp
|
||||
}
|
||||
|
|
|
@ -0,0 +1,128 @@
|
|||
/*
|
||||
Package infratests This file provides validation utilities that can be used by the core testing constructs
|
||||
*/
|
||||
package infratests
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
)
|
||||
|
||||
// This function validates that a set of search targets exist in a map. The intended use case is to allow
|
||||
// a user of this library to provide a set of *expected values* that should exist within a larger set of
|
||||
// *actual values.* In other words, this is a map equality check that does not care about ordering in keys/lists
|
||||
// and will not fail if the *expected values* are a subset of the *actual values.*
|
||||
//
|
||||
// In the case that the *expected values* are found in the *actual values,* nil will be returned. Otherwise an
|
||||
// error describing the mismatch will be returned.
|
||||
//
|
||||
// Some examples (in pseudo-code):
|
||||
// - Exact Match:
|
||||
// a := {"key1":[{"key2" : "foo"}, {"key2" : "bar"}]}
|
||||
// verifyTargetsExistInMap(a, a) --> nil
|
||||
//
|
||||
// - Subset Match #1:
|
||||
// a := {"key1":[{"key2" : "foo"}, {"key2" : "bar"}]}
|
||||
// b := {"key1":[{"key2" : "foo"}]}
|
||||
// verifyTargetsExistInMap(a, b) --> nil
|
||||
//
|
||||
// - Subset Match #2:
|
||||
// a := {"key1":[{"key2" : "foo"}, {"key2" : "bar"}]}
|
||||
// b := {"key1":[]}
|
||||
// verifyTargetsExistInMap(a, b) --> nil
|
||||
//
|
||||
// - Subset Match #3:
|
||||
// a := {"key1":{"key2": "foo", "key3", "bar"}}
|
||||
// b := {"key1":{"key3", "bar"}}
|
||||
// verifyTargetsExistInMap(a, b) --> nil
|
||||
//
|
||||
// - Mismatch #1:
|
||||
// a := {"key1":{"key2": "foo", "key3", "bar"}}
|
||||
// b := {"key1":[]}
|
||||
// verifyTargetsExistInMap(a, b) --> ERROR: wrong type for key `key1`
|
||||
//
|
||||
// - Mismatch #2:
|
||||
// a := {"key1":{"key2": "foo", "key3", "bar"}}
|
||||
// b := {"key1":{"key4": "foo"}}
|
||||
// verifyTargetsExistInMap(a, b) --> ERROR: `key4` not found
|
||||
//
|
||||
// - Mismatch #3:
|
||||
// a := {"key1":{"key2": "foo", "key3", "bar"}}
|
||||
// b := {"key1":{"key2": "bar"}}
|
||||
// verifyTargetsExistInMap(a, b) --> ERROR: wrong value for `key2`
|
||||
//
|
||||
// The algorithm used to do the equality check is to execute a DFS search in parallel for both maps. In the case
|
||||
// that a mismatch (the values do not match, or the shape of the maps is different in a way that indicates a mismatch)
|
||||
// is identified, the search will be terminated. If no mismatches are found then `nil` is returned
|
||||
func verifyTargetsExistInMap(dataSource map[string]interface{}, searchTargets map[string]interface{}) error {
|
||||
for targetKey := range searchTargets {
|
||||
candidateMatch, candidateExists := dataSource[targetKey]
|
||||
target, targetExists := searchTargets[targetKey]
|
||||
|
||||
// both maps should contain the target search key
|
||||
if !candidateExists || !targetExists {
|
||||
return fmt.Errorf("Unexpectedly could not find key '%s'", targetKey)
|
||||
}
|
||||
|
||||
// the values for the key should be the same type
|
||||
if !isSameType(candidateMatch, target) {
|
||||
return fmt.Errorf("Unexpectedly found type '%T' instead of '%T'", candidateMatch, target)
|
||||
}
|
||||
|
||||
// the key is found and both values are of the same type. time to look for a subset match
|
||||
switch typedTarget := target.(type) {
|
||||
case bool, float32, float64, int, string:
|
||||
if typedTarget != candidateMatch {
|
||||
return fmt.Errorf("Expected %s but got %s", typedTarget, candidateMatch)
|
||||
}
|
||||
case []interface{}:
|
||||
if err := verifyTargetsExistInList(candidateMatch.([]interface{}), typedTarget); err != nil {
|
||||
return err
|
||||
}
|
||||
case map[string]interface{}:
|
||||
if err := verifyTargetsExistInMap(candidateMatch.(map[string]interface{}), typedTarget); err != nil {
|
||||
return err
|
||||
}
|
||||
default:
|
||||
return fmt.Errorf("Comparison for type '%T' in a map not implemented", typedTarget)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// This function has the same semantics as `verifyTargetsExistInMap` (so the documentation will not be repeated)
|
||||
// except that it works for lists.
|
||||
func verifyTargetsExistInList(dataSource []interface{}, searchTargets []interface{}) error {
|
||||
for _, target := range searchTargets {
|
||||
matchFound := false
|
||||
|
||||
switch typedTarget := target.(type) {
|
||||
case bool, float32, float64, int, string:
|
||||
for _, candidateMatch := range dataSource {
|
||||
matchFound = matchFound || typedTarget == candidateMatch
|
||||
}
|
||||
case map[string]interface{}:
|
||||
for _, candidateMatch := range dataSource {
|
||||
if isSameType(candidateMatch, typedTarget) {
|
||||
err := verifyTargetsExistInMap(candidateMatch.(map[string]interface{}), typedTarget)
|
||||
matchFound = matchFound || err == nil
|
||||
}
|
||||
}
|
||||
default:
|
||||
return fmt.Errorf("Comparison for type '%T' in a list not yet implemented", typedTarget)
|
||||
}
|
||||
|
||||
if !matchFound {
|
||||
return fmt.Errorf("Unexpectedly did not find '%s' in '%s'", target, dataSource)
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// return true if the values have the same type, false otherwise
|
||||
func isSameType(a interface{}, b interface{}) bool {
|
||||
return reflect.TypeOf(a) == reflect.TypeOf(b)
|
||||
}
|
|
@ -0,0 +1,89 @@
|
|||
package infratests
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"testing"
|
||||
)
|
||||
|
||||
var tests = []struct {
|
||||
dataSourceJSON string
|
||||
searchTargetsJSON string
|
||||
shouldPass bool
|
||||
}{
|
||||
{
|
||||
`{"key1":[{"key2" : "foo"}, {"key2" : "bar"}]}`,
|
||||
`{"key1":[{"key2" : "foo"}, {"key2" : "bar"}]}`,
|
||||
true,
|
||||
}, {
|
||||
`{"key1":[{"key2" : "foo"}, {"key2" : "bar"}]}`,
|
||||
`{"key1":[{"key2" : "foo"}]}`,
|
||||
true,
|
||||
}, {
|
||||
`{"key1":[{"key2" : "foo"}, {"key2" : "bar"}]}`,
|
||||
`{"key1":[]}`,
|
||||
true,
|
||||
}, {
|
||||
`{"key1":{"key2": "foo", "key3": "bar"}}`,
|
||||
`{"key1":{"key3": "bar"}}`,
|
||||
true,
|
||||
}, {
|
||||
`{"key1":[{"key2" : "foo"}, {"key2" : "bar"}]}`,
|
||||
`{}`,
|
||||
true,
|
||||
}, {
|
||||
`{"key1":{"key2": "foo", "key3": "bar"}}`,
|
||||
`{"key1":[]}`,
|
||||
false, // key has wrong type
|
||||
}, {
|
||||
`{"key1":{"key2": "foo", "key3": "bar"}}`,
|
||||
`{"key1":{"key4": "foo"}}`,
|
||||
false, // key does not exist in data source
|
||||
}, {
|
||||
`{"key1":{"key2": "foo", "key3": "bar"}}`,
|
||||
`{"key1":{"key2": "bar"}}`,
|
||||
false, // key has wrong value
|
||||
}, {
|
||||
`{"key1":[1, 2, 3]}`,
|
||||
`{"key1":[4]}`,
|
||||
false, // list value does not exist in parent
|
||||
}, {
|
||||
`{"key1":[{"key2": "foo"}]}`,
|
||||
`{"key1":[{"key3": "foo"}]}`,
|
||||
false, // list value does not exist in parent
|
||||
}, {
|
||||
`{"key1":[{"key2": "foo"}]}`,
|
||||
`{"key1":[{"key2": "bar"}]}`,
|
||||
false, // list value does not exist in parent
|
||||
},
|
||||
}
|
||||
|
||||
func TestVerifyTargets(t *testing.T) {
|
||||
for _, test := range tests {
|
||||
err := verifyTargetsExistInMap(
|
||||
jsonToMap(t, test.dataSourceJSON),
|
||||
jsonToMap(t, test.searchTargetsJSON))
|
||||
|
||||
// the test should pass but there was an error
|
||||
if test.shouldPass && err != nil {
|
||||
t.Errorf("Search Targets `%s` were unexpectedly not found in Data Source `%s`. %s",
|
||||
test.searchTargetsJSON,
|
||||
test.dataSourceJSON,
|
||||
err)
|
||||
}
|
||||
|
||||
// the test should not pass but there was no error
|
||||
if !test.shouldPass && err == nil {
|
||||
t.Errorf("Search Targets `%s` were unexpectedly found in Data Source `%s`",
|
||||
test.searchTargetsJSON,
|
||||
test.dataSourceJSON)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func jsonToMap(t *testing.T, jsonStr string) map[string]interface{} {
|
||||
var theMap map[string]interface{}
|
||||
if err := json.Unmarshal([]byte(jsonStr), &theMap); err != nil {
|
||||
t.Errorf("Unable to parse JSON `%s`. Error = `%s`", jsonStr, err)
|
||||
}
|
||||
return theMap
|
||||
}
|
|
@ -23,10 +23,16 @@ func RunAllTargets() {
|
|||
mg.Deps(CleanAll)
|
||||
mg.Deps(LintCheckGo)
|
||||
mg.Deps(LintCheckTerraform)
|
||||
mg.Deps(RunTestHarnessUnitTests)
|
||||
mg.Deps(RunUnitTests)
|
||||
mg.Deps(RunIntegrationTests)
|
||||
}
|
||||
|
||||
// RunTestHarnessUnitTests run unit test for the test harness itself
|
||||
func RunTestHarnessUnitTests() error {
|
||||
return sh.RunV("go", "test", "github.com/microsoft/cobalt/test-harness/infratests")
|
||||
}
|
||||
|
||||
// RunUnitTests A build step that runs unit tests
|
||||
func RunUnitTests() error {
|
||||
fmt.Println("INFO: Running unit tests...")
|
||||
|
|
Загрузка…
Ссылка в новой задаче