From 09f1952580d4e40a3aab8b1c4f6bfc8de3ae0b0b Mon Sep 17 00:00:00 2001 From: Joe Lanford Date: Fri, 6 Aug 2021 19:33:12 -0400 Subject: [PATCH] bump to kubernetes 1.22.2, remove support for v1beta1 CRDs and webhooks --- go.mod | 6 +- go.sum | 170 ++++++----- pkg/crd/conv.go | 89 +----- pkg/crd/crd_spec_test.go | 267 ------------------ pkg/crd/gen.go | 150 +--------- pkg/crd/gen_integration_test.go | 16 +- pkg/crd/zz_generated.markerhelp.go | 10 +- pkg/genall/genall.go | 10 +- pkg/schemapatcher/gen.go | 123 +------- pkg/schemapatcher/gen_integration_test.go | 26 +- .../expected/kubebuilder-example-crd.yaml | 40 --- .../kubebuilder-unchanged-crd.v1beta1.yaml | 40 --- .../testdata/expected/legacy-example-crd.yaml | 44 --- .../expected/legacy-unchanged-crd.yaml | 45 --- .../testdata/expected/other-crd.yaml | 13 - .../kubebuilder-example-crd.v1.yaml | 0 .../kubebuilder-example-crd.yaml | 0 .../kubebuilder-unchanged-crd.v1beta1.yaml | 44 --- .../manifests/legacy-example-crd.yaml | 43 --- .../manifests/legacy-unchanged-crd.yaml | 50 ---- .../testdata/manifests/other-crd.yaml | 13 - .../valid/kubebuilder-example-crd.v1.yaml | 40 +++ .../kubebuilder-unchanged-crd.yaml | 0 pkg/schemapatcher/zz_generated.markerhelp.go | 6 +- pkg/webhook/parser.go | 67 ++--- pkg/webhook/parser_integration_test.go | 129 +++++++-- .../cronjob_types.go | 71 +++++ .../manifests.yaml} | 32 ++- .../webhook.go | 50 ++++ .../invalid-sideEffects/cronjob_types.go | 71 +++++ .../invalid-sideEffects/manifests.yaml | 82 ++++++ .../testdata/invalid-sideEffects/webhook.go | 50 ++++ .../cronjob_types.go | 71 +++++ .../manifests.yaml | 82 ++++++ .../invalid-v1beta1NotSupported/webhook.go | 50 ++++ pkg/webhook/testdata/manifests.yaml | 22 ++ pkg/webhook/testdata/valid/cronjob_types.go | 71 +++++ pkg/webhook/testdata/valid/manifests.yaml | 82 ++++++ pkg/webhook/testdata/valid/webhook.go | 50 ++++ pkg/webhook/testdata/webhook.go | 4 +- pkg/webhook/zz_generated.markerhelp.go | 4 +- 41 files changed, 1122 insertions(+), 1111 deletions(-) delete mode 100644 pkg/schemapatcher/testdata/expected/kubebuilder-example-crd.yaml delete mode 100644 pkg/schemapatcher/testdata/expected/kubebuilder-unchanged-crd.v1beta1.yaml delete mode 100644 pkg/schemapatcher/testdata/expected/legacy-example-crd.yaml delete mode 100644 pkg/schemapatcher/testdata/expected/legacy-unchanged-crd.yaml delete mode 100644 pkg/schemapatcher/testdata/expected/other-crd.yaml rename pkg/schemapatcher/testdata/{manifests => invalid}/kubebuilder-example-crd.v1.yaml (100%) rename pkg/schemapatcher/testdata/{manifests => invalid}/kubebuilder-example-crd.yaml (100%) delete mode 100644 pkg/schemapatcher/testdata/manifests/kubebuilder-unchanged-crd.v1beta1.yaml delete mode 100644 pkg/schemapatcher/testdata/manifests/legacy-example-crd.yaml delete mode 100644 pkg/schemapatcher/testdata/manifests/legacy-unchanged-crd.yaml delete mode 100644 pkg/schemapatcher/testdata/manifests/other-crd.yaml create mode 100644 pkg/schemapatcher/testdata/valid/kubebuilder-example-crd.v1.yaml rename pkg/schemapatcher/testdata/{manifests => valid}/kubebuilder-unchanged-crd.yaml (100%) create mode 100644 pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/cronjob_types.go rename pkg/webhook/testdata/{manifests.v1beta1.yaml => invalid-admissionReviewVersionsRequired/manifests.yaml} (63%) create mode 100644 pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/webhook.go create mode 100644 pkg/webhook/testdata/invalid-sideEffects/cronjob_types.go create mode 100644 pkg/webhook/testdata/invalid-sideEffects/manifests.yaml create mode 100644 pkg/webhook/testdata/invalid-sideEffects/webhook.go create mode 100644 pkg/webhook/testdata/invalid-v1beta1NotSupported/cronjob_types.go create mode 100644 pkg/webhook/testdata/invalid-v1beta1NotSupported/manifests.yaml create mode 100644 pkg/webhook/testdata/invalid-v1beta1NotSupported/webhook.go create mode 100644 pkg/webhook/testdata/valid/cronjob_types.go create mode 100644 pkg/webhook/testdata/valid/manifests.yaml create mode 100644 pkg/webhook/testdata/valid/webhook.go diff --git a/go.mod b/go.mod index 4e8d4c1c9..8647f5442 100644 --- a/go.mod +++ b/go.mod @@ -12,8 +12,8 @@ require ( github.com/spf13/pflag v1.0.5 golang.org/x/tools v0.1.5 gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b - k8s.io/api v0.21.3 - k8s.io/apiextensions-apiserver v0.21.3 - k8s.io/apimachinery v0.21.3 + k8s.io/api v0.22.2 + k8s.io/apiextensions-apiserver v0.22.2 + k8s.io/apimachinery v0.22.2 sigs.k8s.io/yaml v1.2.0 ) diff --git a/go.sum b/go.sum index 9edbcdecc..b9b11cdb7 100644 --- a/go.sum +++ b/go.sum @@ -37,13 +37,14 @@ cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohl cloud.google.com/go/storage v1.8.0/go.mod h1:Wv1Oy7z6Yz3DshWRJFhqM/UCfaWIRTdp0RXyy7KQOVs= cloud.google.com/go/storage v1.10.0/go.mod h1:FLPqc6j+Ki4BU591ie1oL6qBQGu2Bl/tZ9ullr3+Kg0= dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU= -github.com/Azure/go-ansiterm v0.0.0-20170929234023-d6e3b3328b78/go.mod h1:LmzpDX56iTiv29bbRTIsUNlaFfuhWRQBWjQdVyAevI8= +github.com/Azure/go-ansiterm v0.0.0-20210608223527-2377c96fe795/go.mod h1:LmzpDX56iTiv29bbRTIsUNlaFfuhWRQBWjQdVyAevI8= +github.com/Azure/go-ansiterm v0.0.0-20210617225240-d185dfc1b5a1/go.mod h1:xomTg63KZ2rFqZQzSB4Vz2SUXa1BpHTVz9L5PTmPC4E= github.com/Azure/go-autorest v14.2.0+incompatible/go.mod h1:r+4oMnoxhatjLLJ6zxSWATqVooLgysK6ZNox3g/xq24= -github.com/Azure/go-autorest/autorest v0.11.12/go.mod h1:eipySxLmqSyC5s5k1CLupqet0PSENBEDP93LQ9a8QYw= -github.com/Azure/go-autorest/autorest/adal v0.9.5/go.mod h1:B7KF7jKIeC9Mct5spmyCB/A8CG/sEz1vwIRGv/bbw7A= +github.com/Azure/go-autorest/autorest v0.11.18/go.mod h1:dSiJPy22c3u0OtOKDNttNgqpNFY/GeWa7GH/Pz56QRA= +github.com/Azure/go-autorest/autorest/adal v0.9.13/go.mod h1:W/MM4U6nLxnIskrw4UwWzlHfGjwUS50aOsc/I3yuU8M= github.com/Azure/go-autorest/autorest/date v0.3.0/go.mod h1:BI0uouVdmngYNUzGWeSYnokU+TrmwEsOqdt8Y6sso74= github.com/Azure/go-autorest/autorest/mocks v0.4.1/go.mod h1:LTp+uSrOhSkaKrUy935gNZuuIPPVsHlr9DSOxSayd+k= -github.com/Azure/go-autorest/logger v0.2.0/go.mod h1:T9E3cAhj2VqvPOtCYAvby9aBXkZmbF5NWuPV8+WeEW8= +github.com/Azure/go-autorest/logger v0.2.1/go.mod h1:T9E3cAhj2VqvPOtCYAvby9aBXkZmbF5NWuPV8+WeEW8= github.com/Azure/go-autorest/tracing v0.6.0/go.mod h1:+vhtPC754Xsa23ID7GlGsrdKBpUA79WCAKPPZVC2DeU= github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU= github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo= @@ -56,11 +57,13 @@ github.com/alecthomas/template v0.0.0-20160405071501-a0175ee3bccc/go.mod h1:LOuy github.com/alecthomas/template v0.0.0-20190718012654-fb15b899a751/go.mod h1:LOuyumcjzFXgccqObfd/Ljyb9UuFJ6TxHnclSeseNhc= github.com/alecthomas/units v0.0.0-20151022065526-2efee857e7cf/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0= github.com/alecthomas/units v0.0.0-20190717042225-c3de453c63f4/go.mod h1:ybxpYRFXyAe+OPACYpWeL0wqObRcbAqCMya13uyzqw0= +github.com/alecthomas/units v0.0.0-20190924025748-f65c72e2690d/go.mod h1:rBZYJk541a8SKzHPHnH3zbiI+7dagKZ0cgpgrD7Fyho= github.com/antihax/optional v1.0.0/go.mod h1:uupD/76wgC+ih3iEmQUL+0Ugr19nfwCT1kdvxnR2qWY= github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/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-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8= github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a/go.mod h1:lB+ZfQJz7igIIfQNfa7Ml4HSf2uFQQRzpGGRXenZAgY= +github.com/benbjohnson/clock v1.0.3/go.mod h1:bGMdMPoPVvcYyt1gHDf4J2KE153Yf9BuiUKYMaxlTDM= github.com/beorn7/perks v0.0.0-20180321164747-3a771d992973/go.mod h1:Dwedo/Wpr24TaqPxmxbtue+5NUziq4I4S80YR8gNf3Q= github.com/beorn7/perks v1.0.0/go.mod h1:KWe93zE9D1o94FZ5RNwFwVgaQK1VOXiVxmqh+CedLV8= github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= @@ -69,6 +72,8 @@ github.com/bketelsen/crypt v0.0.3-0.20200106085610-5cbc8cc4026c/go.mod h1:MKsuJm github.com/bketelsen/crypt v0.0.4/go.mod h1:aI6NrJ0pMGgvZKL1iVgXLnfIFJtfV+bKCoqOes/6LfM= github.com/blang/semver v3.5.1+incompatible/go.mod h1:kRBLl5iJ+tD4TcOOxsy/0fnwebNt5EWlYSAyrTnjyyk= github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= +github.com/certifi/gocertifi v0.0.0-20191021191039-0944d244cd40/go.mod h1:sGbDF6GwGcLpkNXPUTkMRoywsNa/ol15pxFe6ERfguA= +github.com/certifi/gocertifi v0.0.0-20200922220541-2c3bb06c6054/go.mod h1:sGbDF6GwGcLpkNXPUTkMRoywsNa/ol15pxFe6ERfguA= github.com/cespare/xxhash v1.1.0/go.mod h1:XrSqR1VqqWfGrhpAt58auRo0WTKS1nRRg3ghfAqPWnc= github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI= @@ -78,19 +83,17 @@ github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDk github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= github.com/cncf/udpa/go v0.0.0-20200629203442-efcf912fb354/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk= github.com/cncf/udpa/go v0.0.0-20201120205902-5459f2c99403/go.mod h1:WmhPx2Nbnhtbo57+VJT5O0JRkEi1Wbu0z5j0R8u5Hbk= -github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= +github.com/cockroachdb/datadriven v0.0.0-20200714090401-bf6692d28da5/go.mod h1:h6jFvWxBdQXxjopDMZyH2UVceIRfR84bdzbkoKrsWNo= +github.com/cockroachdb/errors v1.2.4/go.mod h1:rQD95gz6FARkaKkQXUksEje/d9a6wBJoCr5oaCLELYA= +github.com/cockroachdb/logtags v0.0.0-20190617123548-eb05cc24525f/go.mod h1:i/u985jwjWRlyHXQbwatDASoW0RMlZ/3i9yJHE2xLkI= github.com/coreos/bbolt v1.3.2/go.mod h1:iRUV2dpdMOn7Bo10OQBFzIJO9kkE559Wcmn+qkEiiKk= github.com/coreos/etcd v3.3.13+incompatible/go.mod h1:uF7uidLiAD3TWHmW31ZFd/JWoc32PjwdhPthX9715RE= github.com/coreos/go-oidc v2.1.0+incompatible/go.mod h1:CgnwVTmzoESiwO9qyAFEMiHoZ1nMCKZlZ9V6mm3/LKc= -github.com/coreos/go-semver v0.2.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= github.com/coreos/go-semver v0.3.0/go.mod h1:nnelYz7RCh+5ahJtPPxZlU+153eP4D4r3EedlOD2RNk= -github.com/coreos/go-systemd v0.0.0-20180511133405-39ca1b05acc7/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= github.com/coreos/go-systemd v0.0.0-20190321100706-95778dfbb74e/go.mod h1:F5haX7vjVVG0kc13fIWeqUViNPyEJxv/OmvnBo0Yme4= github.com/coreos/go-systemd/v22 v22.3.2/go.mod h1:Y58oyj3AT4RCenI/lSvhwexgC+NSVTIJ3seZv2GcEnc= -github.com/coreos/pkg v0.0.0-20160727233714-3ac0863d7acf/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= github.com/coreos/pkg v0.0.0-20180928190104-399ea9e2e55f/go.mod h1:E3G3o1h8I7cfcXa63jLwjI0eiQQMgzzUDFVpN/nH/eA= github.com/cpuguy83/go-md2man/v2 v2.0.0/go.mod h1:maD7wRr/U5Z6m/iR4s+kqSMx2CaBsrgA7czyZG/E6dU= -github.com/creack/pty v1.1.7/go.mod h1:lj5s0c3V2DBrqTV7llrYr5NG6My20zk30Fl46Y7DoTY= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/creack/pty v1.1.11/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -99,7 +102,6 @@ github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSs github.com/dgrijalva/jwt-go v3.2.0+incompatible/go.mod h1:E3ru+11k8xSBh+hMPgOLZmtrrCbhqsmaPHjLKYnJCaQ= github.com/dgryski/go-sip13 v0.0.0-20181026042036-e10d5fee7954/go.mod h1:vAd38F8PWV+bWy6jNmig1y/TA+kYO4g3RSRF0IAv0no= github.com/docopt/docopt-go v0.0.0-20180111231733-ee0de3bc6815/go.mod h1:WwZ+bS3ebgob9U8Nd0kOddGdZWjyMGR8Wziv+TBNwSE= -github.com/dustin/go-humanize v0.0.0-20171111073723-bb3d318650d4/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= github.com/elazarl/goproxy v0.0.0-20180725130230-947c36da3153/go.mod h1:/Zj4wYkgs4iZTTu3o/KG3Itv/qCCa8VVMlb3i9OVuzc= github.com/emicklei/go-restful v0.0.0-20170410110728-ff4f55a20633/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= @@ -111,34 +113,37 @@ github.com/envoyproxy/go-control-plane v0.9.7/go.mod h1:cwu0lG7PUMfa9snN8LXBig5y github.com/envoyproxy/go-control-plane v0.9.9-0.20201210154907-fd9021fe5dad/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk= github.com/envoyproxy/go-control-plane v0.9.9-0.20210217033140-668b12f5399d/go.mod h1:cXg6YxExXjJnVBQHBLXeUAgxn2UodCpnH306RInaBQk= github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= -github.com/evanphx/json-patch v4.9.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= +github.com/evanphx/json-patch v4.11.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= github.com/fatih/color v1.12.0 h1:mRhaKNwANqRgUBGKmnI5ZxEk7QXmjQeCcuYFMX2bfcc= github.com/fatih/color v1.12.0/go.mod h1:ELkj/draVOlAH/xkhN6mQ50Qd0MPOk5AAr3maGEBuJM= +github.com/felixge/httpsnoop v1.0.1/go.mod h1:m8KPJKqk1gH5J9DgRY2ASl2lWCfGKXixSwevea8zH2U= github.com/form3tech-oss/jwt-go v3.2.2+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= +github.com/form3tech-oss/jwt-go v3.2.3+incompatible/go.mod h1:pbq4aXjuKjdthFRnoDwaVPLA+WlJuPGy+QneDUgJi2k= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= github.com/fsnotify/fsnotify v1.4.9 h1:hsms1Qyu0jgnwNXIxa+/V/PDsU6CfLf6CNO8H7IWoS4= github.com/fsnotify/fsnotify v1.4.9/go.mod h1:znqG4EE+3YCdAaPaxE2ZRY/06pZUdp0tY4IgpuI1SZQ= +github.com/getsentry/raven-go v0.2.0/go.mod h1:KungGk8q33+aIAZUIVWZDr2OfAEBsO49PX4NzFV5kcQ= github.com/ghodss/yaml v1.0.0/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= github.com/go-gl/glfw v0.0.0-20190409004039-e6da0acd62b1/go.mod h1:vR7hzQXu2zJy9AVAgeJqvqgH9Q5CA+iKCZ2gyEVpxRU= github.com/go-gl/glfw/v3.3/glfw v0.0.0-20191125211704-12ad95a8df72/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8= github.com/go-gl/glfw/v3.3/glfw v0.0.0-20200222043503-6f7a984d4dc4/go.mod h1:tQ2UAYgL5IevRw8kRxooKSPJfGvJ9fJQFa0TUsXzTg8= github.com/go-kit/kit v0.8.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= github.com/go-kit/kit v0.9.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as= +github.com/go-kit/log v0.1.0/go.mod h1:zbhenjAZHb184qTLMA9ZjW7ThYL0H2mk7Q6pNt4vbaY= github.com/go-logfmt/logfmt v0.3.0/go.mod h1:Qt1PoO58o5twSAckw1HlFXLmHsOX5/0LbT9GBnD5lWE= github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk= +github.com/go-logfmt/logfmt v0.5.0/go.mod h1:wCYkCAKZfumFQihp8CzCvQ3paCTfi41vtzG1KdI/P7A= github.com/go-logr/logr v0.1.0/go.mod h1:ixOQHD9gLJUVQQ2ZOR7zLEifBX6tGkNJF4QyIY7sIas= github.com/go-logr/logr v0.2.0/go.mod h1:z6/tIYblkpsD+a4lm/fGIIU9mZ+XfAiaFtq7xTgseGU= github.com/go-logr/logr v0.4.0 h1:K7/B1jt6fIBQVd4Owv2MqGQClcgf0R266+7C/QjRcLc= github.com/go-logr/logr v0.4.0/go.mod h1:z6/tIYblkpsD+a4lm/fGIIU9mZ+XfAiaFtq7xTgseGU= -github.com/go-openapi/jsonpointer v0.19.2/go.mod h1:3akKfEdA7DF1sugOqz1dVQHBcuDBPKZGEoHC/NkiQRg= github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= -github.com/go-openapi/jsonreference v0.19.2/go.mod h1:jMjeRr2HHw6nAVajTXJ4eiUwohSTlpa0o73RUL1owJc= +github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= github.com/go-openapi/jsonreference v0.19.3/go.mod h1:rjx6GuL8TTa9VaixXglHmQmIL98+wF9xc8zWvFonSJ8= -github.com/go-openapi/spec v0.19.3/go.mod h1:FpwSN1ksY1eteniUU7X0N/BgJ7a4WvBFVA8Lj9mJglo= -github.com/go-openapi/spec v0.19.5/go.mod h1:Hm2Jr4jv8G1ciIAo+frC/Ft+rR2kQDh8JHKHb3gWUSk= -github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= +github.com/go-openapi/jsonreference v0.19.5/go.mod h1:RdybgQwPxbL4UEjuAruzK1x3nE69AqPYEJeo/TWfEeg= github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk= +github.com/go-openapi/swag v0.19.14/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ= github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY= github.com/go-task/slim-sprig v0.0.0-20210107165309-348f09dbbbc0/go.mod h1:fyg7847qk6SyHyPtNmDHnmrv/HOrqktSC+C9fM+CJOE= github.com/gobuffalo/flect v0.2.3 h1:f/ZukRnSNA/DUpSNDadko7Qc0PhGvsew35p/2tu+CRY= @@ -146,14 +151,15 @@ github.com/gobuffalo/flect v0.2.3/go.mod h1:vmkQwuZYhN5Pc4ljYQZzP+1sq+NEkK+lh20j github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA= github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ= github.com/gogo/protobuf v1.2.1/go.mod h1:hp+jE20tsWTFYpLwKvXlhS1hjn+gTNwPg2I6zVXpSg4= +github.com/gogo/protobuf v1.3.1/go.mod h1:SlYgWuQ5SjCEi6WLHjHCa1yvBfUnHcTbrrZtXPKa29o= github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q= github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q= github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b/go.mod h1:SBH7ygxi8pfUlaOkMMuAQtPIUF8ecWP5IEl/CR7VP2Q= -github.com/golang/groupcache v0.0.0-20160516000752-02826c3e7903/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20190129154638-5b532d6fd5ef/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20190702054246-869f871628b6/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20191227052852-215e87163ea7/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= github.com/golang/groupcache v0.0.0-20200121045136-8c9f03a8e57e/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= +github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da/go.mod h1:cIg4eruTrX1D+g88fzRXU5OdNfaM+9IcxsU14FzY7Hc= 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= @@ -182,6 +188,7 @@ github.com/golang/protobuf v1.5.2 h1:ROPKBNFfQgOUMifHyP+KYbvpjbdoFNs+aK7DXlji0Tw github.com/golang/protobuf v1.5.2/go.mod h1:XVQd3VNwM+JqD3oG2Ue2ip4fOMUkwXdXDdiuN0vRsmY= github.com/google/btree v0.0.0-20180813153112-4030bb1f1f0c/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ= github.com/google/btree v1.0.0/go.mod h1:lNA+9X1NB3Zf8V7Ke586lFgjr2dZNuvo3lPJSGZ5JPQ= +github.com/google/btree v1.0.1/go.mod h1:xXMiIv4Fb/0kKde4SpL7qlzvu5cMJDRkFDxJfI9uaxA= github.com/google/go-cmp v0.2.0/go.mod h1:oXzfMopK8JAjlY9xF4vHSVASa0yLyX7SntLO5aqRK0M= github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/go-cmp v0.3.1/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= @@ -213,21 +220,19 @@ github.com/google/pprof v0.0.0-20201203190320-1bf35d6f28c2/go.mod h1:kpwsk12EmLe github.com/google/pprof v0.0.0-20210122040257-d980be63207e/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= github.com/google/pprof v0.0.0-20210226084205-cbba55b83ad5/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= -github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk= -github.com/googleapis/gnostic v0.4.1/go.mod h1:LRhVm6pbyptWbWbuZ38d1eyptfvIytN3ir6b65WBswg= +github.com/googleapis/gnostic v0.5.1/go.mod h1:6U4PtQXGIEt/Z3h5MAT7FNofLnw9vXk2cUuW7uA/OeU= +github.com/googleapis/gnostic v0.5.5/go.mod h1:7+EbHbldMins07ALC74bsA81Ovc97DwqyJO1AENw9kA= github.com/gopherjs/gopherjs v0.0.0-20181017120253-0766667cb4d1/go.mod h1:wJfORRmW1u3UXTncJ5qlYoELFm8eSnnEO6hX4iZ3EWY= -github.com/gorilla/websocket v0.0.0-20170926233335-4201258b820c/go.mod h1:E7qHFY5m1UJ88s3WnNqhKjPHQ0heANvMoAMk2YaljkQ= github.com/gorilla/websocket v1.4.2/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= 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-middleware v1.0.1-0.20190118093823-f849b5445de4/go.mod h1:FiyG127CGDf3tlThmgyCl78X/SZQqEOJBCDaAfeWzPs= +github.com/grpc-ecosystem/go-grpc-middleware v1.3.0/go.mod h1:z0ButlSOZa5vEBq9m2m2hlwIgKw+rp3sdCBRoJY+30Y= github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk= github.com/grpc-ecosystem/grpc-gateway v1.9.0/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY= -github.com/grpc-ecosystem/grpc-gateway v1.9.5/go.mod h1:vNeuVxBJEsws4ogUvrchl83t/GYV9WGTSLVdBhOQFDY= github.com/grpc-ecosystem/grpc-gateway v1.16.0/go.mod h1:BDjrQk3hbvj6Nolgz8mAMFbcEtjT1g+wF4CSlocrBnw= github.com/hashicorp/consul/api v1.1.0/go.mod h1:VmuI/Lkw1nC05EYQWNKwWGbkg+FbDBtguAZLlVdkD9Q= github.com/hashicorp/consul/sdk v0.1.1/go.mod h1:VKf9jXwCTEY1QZP2MOLRhb5i/I/ssyNV1vwHyQBF0x8= @@ -256,8 +261,10 @@ github.com/imdario/mergo v0.3.5/go.mod h1:2EnlNZ0deacrJVfApfmtdGgDfMuh/nq6Ok1EcJ github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM= github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8= github.com/jonboulle/clockwork v0.1.0/go.mod h1:Ii8DK3G1RaLaWxj9trq07+26W01tbo22gdxWY5EU2bo= +github.com/jonboulle/clockwork v0.2.2/go.mod h1:Pkfl5aHPm1nk2H9h0bjmnJD/BcgbGXUBGnn1kMkgxc8= +github.com/josharian/intern v1.0.0/go.mod h1:5DoeVV0s6jJacbCEi61lwdGj/aVlrQvzHFFd8Hwg//Y= +github.com/jpillora/backoff v1.0.0/go.mod h1:J/6gKK9jxlEcS3zixgDgUAsiuZ7yrSoa/FX5e0EB2j4= github.com/json-iterator/go v1.1.6/go.mod h1:+SdeFBvtyEkXs7REEP0seUULqWtbJapLOCVDaaPEHmU= -github.com/json-iterator/go v1.1.7/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/json-iterator/go v1.1.10/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= github.com/json-iterator/go v1.1.11 h1:uVUAXhF2To8cbw/3xN3pxj6kk7TYKs98NIrTqPlMWAQ= github.com/json-iterator/go v1.1.11/go.mod h1:KdQUCv79m/52Kvf8AW2vK1V8akMuk1QjK/uOdHXbAo4= @@ -265,16 +272,18 @@ github.com/jstemmer/go-junit-report v0.0.0-20190106144839-af01ea7f8024/go.mod h1 github.com/jstemmer/go-junit-report v0.9.1/go.mod h1:Brl9GWCQeLvo8nXZwPNNblvFj/XSXhF0NWZEnDohbsk= github.com/jtolds/gls v4.20.0+incompatible/go.mod h1:QJZ7F/aHp+rZTRtaJ1ow/lLfFfVYBRgL+9YlvaHOwJU= github.com/julienschmidt/httprouter v1.2.0/go.mod h1:SYymIcj16QtmaHHD7aYtjjsJG7VTCxuUUipMqKk8s4w= +github.com/julienschmidt/httprouter v1.3.0/go.mod h1:JR6WtHb+2LUe8TCKY3cZOxFyyO8IZAc4RVcycCCAKdM= github.com/kisielk/errcheck v1.1.0/go.mod h1:EZBBE59ingxPouuu3KfxchcWSUPOHkagtvWXihfKN4Q= +github.com/kisielk/errcheck v1.2.0/go.mod h1:/BMXB+zMLi60iA8Vv6Ksmxu/1UDYcXs4uQLJ+jE2L00= github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= +github.com/konsorten/go-windows-terminal-sequences v1.0.3/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ= github.com/kr/fs v0.1.0/go.mod h1:FFnZGqtBN9Gxj7eW1uZ42v5BccTP0vu6NEaFoC2HwRg= github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFBFZlji/RkVcI2GknAs/DXo4wKdlNEc= github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= -github.com/kr/pty v1.1.5/go.mod h1:9r2w37qlBe7rQ6e1fg1S/9xpWHSnaqNdHD3WcMdbPDA= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= @@ -282,15 +291,13 @@ github.com/magiconair/properties v1.8.1/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czP github.com/magiconair/properties v1.8.5/go.mod h1:y3VJvCyxH9uVvJTWEGAELF3aiYNyPKd5NZ3oSwXrF60= github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc= -github.com/mailru/easyjson v0.7.0/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs= +github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU= github.com/mattn/go-colorable v0.1.8 h1:c1ghPdyEDarC70ftn0y+A/Ee++9zz8ljHG1b13eJ0s8= github.com/mattn/go-colorable v0.1.8/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= 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.12 h1:wuysRhFDzyxgEmMf5xjvJ2M9dZoWAXNNr5LSBS7uHXY= github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU= -github.com/mattn/go-runewidth v0.0.2/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU= github.com/matttproud/golang_protobuf_extensions v1.0.1/go.mod h1:D8He9yQNgCq6Z5Ld7szi9bcBfOoFv/3dc6xSMkL2PC0= github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369/go.mod h1:BSXmuO+STAnVfrANrmjBb36TMTDstsz7MSK+HVaYKv4= github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg= @@ -304,7 +311,7 @@ github.com/mitchellh/mapstructure v0.0.0-20160808181253-ca63d7c062ee/go.mod h1:F github.com/mitchellh/mapstructure v1.1.2/go.mod h1:FVVH3fgwuzCH5S8UJGiWEs2h04kUh9fWfEaFds41c1Y= github.com/mitchellh/mapstructure v1.4.1/go.mod h1:bFUtVrKA4DC2yAKiSyO/QUcy7e+RRV2QTWOzhPopBRo= github.com/moby/spdystream v0.2.0/go.mod h1:f7i0iNDQJ059oMTcWxx8MA/zKFIuD/lY+0GqbN2Wy8c= -github.com/moby/term v0.0.0-20201216013528-df9cb8a40635/go.mod h1:FBS0z0QWA44HXygs7VXDUOGoN/1TV3RuWkLO04am3wc= +github.com/moby/term v0.0.0-20210610120745-9d4ed1856297/go.mod h1:vgPCkQMyxTZ7IDy8SXRufE172gr8+K/JE/7hHFxHW3A= github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= @@ -314,6 +321,7 @@ github.com/modern-go/reflect2 v1.0.1/go.mod h1:bx2lNnkwVCuqBIxFjflWJWanXIb3Rllmb github.com/munnerz/goautoneg v0.0.0-20120707110453-a547fc61f48d/go.mod h1:+n7T8mK8HuQTcFwEeznm/DIxMOiR9yIdICNftLE1DvQ= github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822/go.mod h1:+n7T8mK8HuQTcFwEeznm/DIxMOiR9yIdICNftLE1DvQ= github.com/mwitkow/go-conntrack v0.0.0-20161129095857-cc309e4a2223/go.mod h1:qRWi+5nqEBWmkhHvq77mSJWrCKwh8bxhgT7d/eI7P4U= +github.com/mwitkow/go-conntrack v0.0.0-20190716064945-2f068394615f/go.mod h1:qRWi+5nqEBWmkhHvq77mSJWrCKwh8bxhgT7d/eI7P4U= github.com/mxk/go-flowrate v0.0.0-20140419014527-cca7078d478f/go.mod h1:ZdcZmHo+o7JKHSa8/e818NopupXU1YMK5fe1lsApnBw= github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e h1:fD57ERR4JtEqsWbfPhv4DMiApHyliiK5xCTNVSPiaAs= github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno= @@ -321,19 +329,18 @@ github.com/nxadm/tail v1.4.4/go.mod h1:kenIhsEOeOJmVchQTgglprH7qJGnHDVpk1VPCcaMI github.com/nxadm/tail v1.4.8 h1:nPr65rt6Y5JFSKQO7qToXr7pePgD6Gwiw05lkbyAQTE= github.com/nxadm/tail v1.4.8/go.mod h1:+ncqLTQzXmGhMZNUePPaPqPvBxHAIsmXswZKocGu+AU= github.com/oklog/ulid v1.3.1/go.mod h1:CirwcVhetQ6Lv90oh/F+FBtV6XMibvdAFo93nm5qn4U= -github.com/olekukonko/tablewriter v0.0.0-20170122224234-a0225b3f23b5/go.mod h1:vsDQFd/mU46D+Z4whnwzcISnGGzXWMclvtLoiIKAKIo= github.com/onsi/ginkgo v0.0.0-20170829012221-11459a886d9c/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= -github.com/onsi/ginkgo v1.11.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.12.1/go.mod h1:zj2OWP4+oCPe1qIXoGWkgMRwljMUYCdkwsT2108oapk= +github.com/onsi/ginkgo v1.14.0/go.mod h1:iSB4RoI2tjJc9BBv4NKIKWKya62Rps+oPG/Lv9klQyY= github.com/onsi/ginkgo v1.16.4 h1:29JGrr5oVBm5ulCWet69zQkzWipVXIol6ygQUe/EzNc= github.com/onsi/ginkgo v1.16.4/go.mod h1:dX+/inL/fNMqNlz0e9LfyB9TswhZpCVdJM/Z6Vvnwo0= github.com/onsi/gomega v0.0.0-20170829124025-dcabb60a477c/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA= -github.com/onsi/gomega v1.7.0/go.mod h1:ex+gbHU/CVuBBDIJjb2X0qEXbFg53c61hWP/1CpauHY= github.com/onsi/gomega v1.7.1/go.mod h1:XdKZgCCFLUoM/7CFJVPcG8C1xQ1AJ0vpAezJrB7JYyY= github.com/onsi/gomega v1.10.1/go.mod h1:iN09h71vgCQne3DLsj+A5owkum+a2tYe+TOCB1ybHNo= github.com/onsi/gomega v1.14.0 h1:ep6kpPVwmr/nTbklSx2nrLNSIO62DoYAhnPNIMhK8gI= github.com/onsi/gomega v1.14.0/go.mod h1:cIuvLEne0aoVhAgh/O6ac0Op8WWw9H6eYCriF+tEHG0= +github.com/opentracing/opentracing-go v1.1.0/go.mod h1:UkNAQd3GIcIGf0SeVgPpRdFStlNbqXla1AfSYxPUl2o= github.com/pascaldekloe/goe v0.0.0-20180627143212-57f6aae5913c/go.mod h1:lzWF7FIEvWOWxwDKqyGYQf6ZUaNfKdP144TG7ZOy1lc= github.com/pelletier/go-toml v1.2.0/go.mod h1:5z9KED0ma1S8pY6P1sdut58dfprrGBbd/94hg7ilaic= github.com/pelletier/go-toml v1.9.3/go.mod h1:u1nR/EPcESfeI/szUZKdtJ0xRNbUoANCkoOuaOx1Y+c= @@ -350,6 +357,7 @@ github.com/prometheus/client_golang v0.9.1/go.mod h1:7SWBe2y4D6OKWSNQJUaRYU/AaXP github.com/prometheus/client_golang v0.9.3/go.mod h1:/TN21ttK/J9q6uSwhBd54HahCDft0ttaMvbicHlPoso= github.com/prometheus/client_golang v1.0.0/go.mod h1:db9x61etRT2tGnBNRi70OPL5FsnadC4Ky3P0J6CfImo= github.com/prometheus/client_golang v1.7.1/go.mod h1:PY5Wy2awLA44sXw4AOSfFBetzPP4j5+D6mVACh+pe2M= +github.com/prometheus/client_golang v1.11.0/go.mod h1:Z6t4BnS23TR94PD6BsDNk8yVqroYurpAkEiz0P2BEV0= github.com/prometheus/client_model v0.0.0-20180712105110-5c3871d89910/go.mod h1:MbSGuTsp3dbXC40dX6PRTWyKYBIrTGTE9sqQNg2J8bo= github.com/prometheus/client_model v0.0.0-20190129233127-fd36f4220a90/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= @@ -358,11 +366,12 @@ github.com/prometheus/common v0.0.0-20181113130724-41aa239b4cce/go.mod h1:daVV7q github.com/prometheus/common v0.4.0/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= github.com/prometheus/common v0.4.1/go.mod h1:TNfzLD0ON7rHzMJeJkieUDPYmFC7Snx/y86RQel1bk4= github.com/prometheus/common v0.10.0/go.mod h1:Tlit/dnDKsSWFlCLTWaA1cyBgKHSMdTB80sz/V91rCo= +github.com/prometheus/common v0.26.0/go.mod h1:M7rCNAaPfAosfx8veZJCuw84e35h3Cfd9VFqTh1DIvc= github.com/prometheus/procfs v0.0.0-20181005140218-185b4288413d/go.mod h1:c3At6R/oaqEKCNdg8wHV1ftS6bRYblBhIjjI8uT2IGk= github.com/prometheus/procfs v0.0.0-20190507164030-5867b95ac084/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= github.com/prometheus/procfs v0.0.2/go.mod h1:TjEm7ze935MbeOT/UhFTIMYKhuLP4wbCsTZCD3I8kEA= github.com/prometheus/procfs v0.1.3/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU= -github.com/prometheus/procfs v0.2.0/go.mod h1:lV6e/gmhEcM9IjHGsFOCxxuZ+z1YqCvr4OA4YeYWdaU= +github.com/prometheus/procfs v0.6.0/go.mod h1:cz+aTbrPOrUb4q7XlbU9ygM+/jj0fzG6c1xBZuNvfVA= github.com/prometheus/tsdb v0.7.1/go.mod h1:qhTCs0VvXwvX/y3TZrWD7rabWM+ijKTux40TwIPHuXU= github.com/rogpeppe/fastuuid v0.0.0-20150106093220-6724a57986af/go.mod h1:XWv6SoW27p1b0cqNHllgS5HIMJraePCO15w5zCzIWYg= github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6LYCDYWNEvQ= @@ -373,32 +382,33 @@ github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529/go.mod h1:DxrIzT+xaE7yg github.com/shurcooL/sanitized_anchor_name v1.0.0/go.mod h1:1NzhyTcUVG4SuEtjjoZeVRXNmyL/1OwPU0+IJeTBvfc= github.com/sirupsen/logrus v1.2.0/go.mod h1:LxeOpSwHxABJmUn/MG1IvRgCAasNZTLOkJPxbbu5VWo= github.com/sirupsen/logrus v1.4.2/go.mod h1:tLMulIdttU9McNUspp0xgXVQah82FyeX6MwdIuYE2rE= +github.com/sirupsen/logrus v1.6.0/go.mod h1:7uNnSEd1DgxDLC74fIahvMZmmYsHGZGEOFrfsX/uA88= github.com/sirupsen/logrus v1.7.0/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= +github.com/sirupsen/logrus v1.8.1/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= github.com/smartystreets/assertions v0.0.0-20180927180507-b2de0cb4f26d/go.mod h1:OnSkiWE9lh6wB0YB77sQom3nweQdgAjqCqsofrRNTgc= github.com/smartystreets/goconvey v1.6.4/go.mod h1:syvi0/a8iFYH4r/RixwvyeAJjdLS9QV7WQ/tjFTllLA= github.com/soheilhy/cmux v0.1.4/go.mod h1:IM3LyeVVIOuxMH7sFAkER9+bJ4dT7Ms6E4xg4kGIyLM= +github.com/soheilhy/cmux v0.1.5/go.mod h1:T7TcVDs9LWfQgPlPsdngu6I6QIoyIFZDDC6sNE1GqG0= github.com/spaolacci/murmur3 v0.0.0-20180118202830-f09979ecbc72/go.mod h1:JwIasOWyU6f++ZhiEuf87xNszmSA2myDM2Kzu9HwQUA= github.com/spf13/afero v1.1.2/go.mod h1:j4pytiNVoe2o6bmDsKpLACNPDBIoEAkihy7loJ1B0CQ= github.com/spf13/afero v1.2.2/go.mod h1:9ZxEEn6pIJ8Rxe320qSDBk6AsU0r9pR7Q4OcevTdifk= github.com/spf13/afero v1.6.0/go.mod h1:Ai8FlHk4v/PARR026UzYexafAt9roJ7LcLMAmO6Z93I= github.com/spf13/cast v1.3.0/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE= github.com/spf13/cast v1.3.1/go.mod h1:Qx5cxh0v+4UWYiBimWS+eyWzqEqokIECu5etghLkUJE= -github.com/spf13/cobra v0.0.3/go.mod h1:1l0Ry5zgKvJasoi3XT1TypsSe7PqH0Sj9dhYf7v3XqQ= -github.com/spf13/cobra v1.1.1/go.mod h1:WnodtKOvamDL/PwE2M4iKs8aMDBZ5Q5klgD3qfVJQMI= +github.com/spf13/cobra v1.1.3/go.mod h1:pGADOWyqRD/YMrPZigI/zbliZ2wVD/23d+is3pSWzOo= github.com/spf13/cobra v1.2.1 h1:+KmjbUw1hriSNMF55oPrkZcb27aECyrj8V2ytv7kWDw= github.com/spf13/cobra v1.2.1/go.mod h1:ExllRjgxM/piMAM+3tAZvg8fsklGAf3tPfi+i8t68Nk= github.com/spf13/jwalterweatherman v1.0.0/go.mod h1:cQK4TGJAtQXfYWX+Ddv3mKDzgVb68N+wFjFa4jdeBTo= github.com/spf13/jwalterweatherman v1.1.0/go.mod h1:aNWZUN0dPAAO/Ljvb5BEdw96iTZ0EXowPYD95IqWIGo= github.com/spf13/pflag v0.0.0-20170130214245-9ff6c6923cff/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= -github.com/spf13/pflag v1.0.1/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= github.com/spf13/pflag v1.0.5 h1:iy+VFUOCP1a+8yFto/drg2CJ5u0yRoB7fZw3DKv/JXA= github.com/spf13/pflag v1.0.5/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= github.com/spf13/viper v1.7.0/go.mod h1:8WkrPz2fc9jxqZNCJI/76HCieCp4Q8HaLFoCha5qpdg= github.com/spf13/viper v1.8.1/go.mod h1:o0Pch8wJ9BVSWGQMbra6iw0oQ5oktSIBaujf1rJH9Ns= +github.com/stoewer/go-strcase v1.2.0/go.mod h1:IBiWB2sKIp3wVVQ3Y035++gc+knqhUQag1KpM8ahLw8= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.1.1/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -github.com/stretchr/objx v0.2.0/go.mod h1:qt09Ya8vawLte6SNmTgCsAVtYtaKzEcn8ATUoHMkEqE= github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= @@ -407,9 +417,8 @@ github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/ github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY= github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69rRypqCw= -github.com/tmc/grpc-websocket-proxy v0.0.0-20170815181823-89b8d40f7ca8/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= github.com/tmc/grpc-websocket-proxy v0.0.0-20190109142713-0ad062ec5ee5/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= -github.com/urfave/cli v1.20.0/go.mod h1:70zkFmudgCuE/ngEzBv17Jvp/497gISqfk5gWijbERA= +github.com/tmc/grpc-websocket-proxy v0.0.0-20201229170055-e5319fda7802/go.mod h1:ncp9v5uamzpCO7NfCPTXjqaC+bZgJeR0sMTm6dMHP7U= github.com/xiang90/probing v0.0.0-20190116061207-43a291ad63a2/go.mod h1:UETIi67q53MR2AWcXfiuqkDkRtnGDLqkBTpCHuJHxtU= github.com/yuin/goldmark v1.1.25/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= @@ -417,12 +426,14 @@ github.com/yuin/goldmark v1.1.32/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9de github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= github.com/yuin/goldmark v1.3.5/go.mod h1:mwnBkeHKe2W/ZEtQ+71ViKU8L12m81fl3OWwC1Zlc8k= go.etcd.io/bbolt v1.3.2/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= -go.etcd.io/bbolt v1.3.3/go.mod h1:IbVyRI1SCnLcuJnV2u8VeU0CEYM7e686BmAb1XKL+uU= -go.etcd.io/bbolt v1.3.5/go.mod h1:G5EMThwa9y8QZGBClrRx5EY+Yw9kAhnjy3bSjsnlVTQ= -go.etcd.io/etcd v0.5.0-alpha.5.0.20200910180754-dd1b699fc489/go.mod h1:yVHk9ub3CSBatqGNg7GRmsnfLWtoW60w4eDYfh7vHDg= +go.etcd.io/bbolt v1.3.6/go.mod h1:qXsaaIqmgQH0T+OPdb99Bf+PKfBBQVAdyD6TY9G8XM4= go.etcd.io/etcd/api/v3 v3.5.0/go.mod h1:cbVKeC6lCfl7j/8jBhAK6aIYO9XOjdptoxU/nLQcPvs= go.etcd.io/etcd/client/pkg/v3 v3.5.0/go.mod h1:IJHfcCEKxYu1Os13ZdwCwIUTUVGYTSAM3YSwc9/Ac1g= go.etcd.io/etcd/client/v2 v2.305.0/go.mod h1:h9puh54ZTgAKtEbut2oe9P4L/oqKCVB6xsXlzd7alYQ= +go.etcd.io/etcd/client/v3 v3.5.0/go.mod h1:AIKXXVX/DQXtfTEqBryiLTUXwON+GuvO6Z7lLS/oTh0= +go.etcd.io/etcd/pkg/v3 v3.5.0/go.mod h1:UzJGatBQ1lXChBkQF0AuAtkRQMYnHubxAEYIrC3MSsE= +go.etcd.io/etcd/raft/v3 v3.5.0/go.mod h1:UFOHSIvO/nKwd4lhkwabrTD3cqW5yVyYYf/KlD00Szc= +go.etcd.io/etcd/server/v3 v3.5.0/go.mod h1:3Ah5ruV+M+7RZr0+Y/5mNLwC+eQlni+mQmOVdCRJoS4= go.opencensus.io v0.21.0/go.mod h1:mSImk1erAIZhrmZN+AvHh14ztQfjbGwt4TtuofqLduU= go.opencensus.io v0.22.0/go.mod h1:+kGneAE2xo2IficOXnaByMWTGM9T73dGwxeWcUqIpI8= go.opencensus.io v0.22.2/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= @@ -430,9 +441,21 @@ go.opencensus.io v0.22.3/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= go.opencensus.io v0.22.4/go.mod h1:yxeiOL68Rb0Xd1ddK5vPZ/oVn4vY4Ynel7k9FzqtOIw= go.opencensus.io v0.22.5/go.mod h1:5pWMHQbX5EPX2/62yrJeAkowc+lfs/XD7Uxpq3pI6kk= go.opencensus.io v0.23.0/go.mod h1:XItmlyltB5F7CS4xOC1DcqMoFqwtC6OG2xF7mCv7P7E= -go.uber.org/atomic v1.3.2/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= +go.opentelemetry.io/contrib v0.20.0/go.mod h1:G/EtFaa6qaN7+LxqfIAT3GiZa7Wv5DTBUzl5H4LY0Kc= +go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.20.0/go.mod h1:oVGt1LRbBOBq1A5BQLlUg9UaU/54aiHw8cgjV3aWZ/E= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.20.0/go.mod h1:2AboqHi0CiIZU0qwhtUfCYD1GeUzvvIXWNkhDt7ZMG4= +go.opentelemetry.io/otel v0.20.0/go.mod h1:Y3ugLH2oa81t5QO+Lty+zXf8zC9L26ax4Nzoxm/dooo= +go.opentelemetry.io/otel/exporters/otlp v0.20.0/go.mod h1:YIieizyaN77rtLJra0buKiNBOm9XQfkPEKBeuhoMwAM= +go.opentelemetry.io/otel/metric v0.20.0/go.mod h1:598I5tYlH1vzBjn+BTuhzTCSb/9debfNp6R3s7Pr1eU= +go.opentelemetry.io/otel/oteltest v0.20.0/go.mod h1:L7bgKf9ZB7qCwT9Up7i9/pn0PWIa9FqQ2IQ8LoxiGnw= +go.opentelemetry.io/otel/sdk v0.20.0/go.mod h1:g/IcepuwNsoiX5Byy2nNV0ySUF1em498m7hBWC279Yc= +go.opentelemetry.io/otel/sdk/export/metric v0.20.0/go.mod h1:h7RBNMsDJ5pmI1zExLi+bJK+Dr8NQCh0qGhm1KDnNlE= +go.opentelemetry.io/otel/sdk/metric v0.20.0/go.mod h1:knxiS8Xd4E/N+ZqKmUPf3gTTZ4/0TjTXukfxjzSTpHE= +go.opentelemetry.io/otel/trace v0.20.0/go.mod h1:6GjCW8zgDjwGHGa6GkyeB8+/5vjT16gUEi0Nf1iBdgw= +go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI= go.uber.org/atomic v1.4.0/go.mod h1:gD2HeocX3+yG+ygLZcrzQJaqmWj9AIm7n08wl/qW/PE= go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc= +go.uber.org/goleak v1.1.10/go.mod h1:8a7PlsEVH3e/a/GLqe5IIrQx6GzcnRmZEufDUTk4A7A= go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0= go.uber.org/multierr v1.6.0/go.mod h1:cdWPpRnG4AhwMwsgIHip0KRBQjJy5kYEpYjJxpXp9iU= go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q= @@ -442,7 +465,6 @@ golang.org/x/crypto v0.0.0-20181029021203-45a5f77698d3/go.mod h1:6SG95UA2DQfeDnf golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= golang.org/x/crypto v0.0.0-20190510104115-cbcb75029529/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190605123033-f99c8df09eb5/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= -golang.org/x/crypto v0.0.0-20190611184440-5c40567a22f8/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20190820162420-60c769a6c586/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20191011191535-87dc89f01550/go.mod h1:yigFU9vqHzYiE8UmvKecakEJjdnWj3jj499lnFckfCI= golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPhUkYOs5KpL4U8rLKemX1yGLhDgUto= @@ -480,7 +502,6 @@ golang.org/x/mod v0.1.1-0.20191105210325-c90efee705ee/go.mod h1:QqPTAvyqsEbceGzB golang.org/x/mod v0.1.1-0.20191107180719-034126e5016b/go.mod h1:QqPTAvyqsEbceGzBzNggFXnrqF1CaUcvgkdR5Ot7KZg= golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= -golang.org/x/mod v0.3.1-0.20200828183125-ce943fd02449/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.4.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.4.1/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.4.2 h1:Gz96sIWK3OalVv/I/qNygP42zyoKp3xptRVCWRFEBvo= @@ -503,7 +524,6 @@ golang.org/x/net v0.0.0-20190613194153-d28f0bde5980/go.mod h1:z5CRVTTTmAJ677TzLL golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190628185345-da137c7871d7/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190724013045-ca1201d0de80/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= -golang.org/x/net v0.0.0-20190813141303-74dc4d7220e7/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20190827160401-ba9fcec4b297/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20191209160850-c0dbc17a3553/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20200114155413-6afb5195e5aa/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= @@ -523,14 +543,15 @@ golang.org/x/net v0.0.0-20200822124328-c89045814202/go.mod h1:/O7V0waA8r7cgGh81R golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20201031054903-ff519b6c9102/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20201110031124-69a78807bb2b/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= +golang.org/x/net v0.0.0-20201202161906-c7110b5ffcbb/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= golang.org/x/net v0.0.0-20201209123823-ac852fbbde11/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= -golang.org/x/net v0.0.0-20210224082022-3d97a244fca7/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.0.0-20210316092652-d523dce5a7f4/go.mod h1:RBQZq4jEuRlivfhVLdyRGr576XBO4/greRjx4P4O3yc= golang.org/x/net v0.0.0-20210405180319-a5a99cb37ef4/go.mod h1:p54w0d4576C0XHj96bSt6lcn1PtDYWL6XObtHCRCNQM= -golang.org/x/net v0.0.0-20210428140749-89ef3d95e781 h1:DzZ89McO9/gWPsQXS/FVKAlG02ZjaQ6AlZRBimEYOd0= golang.org/x/net v0.0.0-20210428140749-89ef3d95e781/go.mod h1:OJAsFXCWl8Ukc7SiCT/9KSuxbyM7479/AVlXFRxuMCk= +golang.org/x/net v0.0.0-20210520170846-37e1c6afe023 h1:ADo5wSpq2gqaCGQWzk7S5vd//0iyyLeAratkEoG5dLE= +golang.org/x/net v0.0.0-20210520170846-37e1c6afe023/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -568,10 +589,8 @@ golang.org/x/sys v0.0.0-20190422165155-953cdadca894/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20190502145724-3ef323f4f1fd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190507160741-ecd444e8653b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190606165138-5da285871e9c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190616124812-15dcb6c0061f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190624142023-c5567b49c5d0/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190726091711-fc99dfbffb4e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20190826190057-c7b8b68b1456/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190904154756-749cb33beabd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191001151750-bb3f8db39f24/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20191005200804-aed5e4c7ecf9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -592,17 +611,21 @@ golang.org/x/sys v0.0.0-20200331124033-c3d80250170d/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20200501052902-10377860bb8e/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200511232937-7e40ca221e25/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200515095857-1151b9dac4a9/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200519105757-fe76b779f299/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200523222454-059865788121/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200615200032-f1bc736245b1/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200625212154-ddb9806d33ae/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200803210538-64077c9b5642/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200831180312-196b9ba8737a/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200905004654-be1d3432aa8f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20200923182605-d9f96fdee20d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20201201145000-ef89a241ccb3/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210104204734-6f8348627aad/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210112080510-489259a85091/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210119212857-b64e53b001e4/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= +golang.org/x/sys v0.0.0-20210124154548-22da62e12c0c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210220050731-9a76102bfb43/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210305230114-8fe3ee5dd75b/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210315160823-c6e025ad8005/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -610,9 +633,10 @@ golang.org/x/sys v0.0.0-20210320140829-1e4c9ba3b0c4/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210403161142-5e06dd20ab57/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210426230700-d19ff857e887/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210510120138-977fb7262007 h1:gG67DSER+11cZvqIMb8S8bt0vZtiN6xWYARwirrOSfE= golang.org/x/sys v0.0.0-20210510120138-977fb7262007/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210603081109-ebe580a85c40/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20210616094352-59db8d763f22 h1:RqytpXGR1iVNX7psjB3ff8y7sNFinVFvkx1c8SjBkio= +golang.org/x/sys v0.0.0-20210616094352-59db8d763f22/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210220032956-6a3ed077a48d/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= @@ -625,13 +649,14 @@ golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.6 h1:aRYxNxv6iGQlyVaZmk6ZgYEDa+Jg18DxebPSrd6bg1M= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -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= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20210220033141-f8bda1e9f3ba/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= +golang.org/x/time v0.0.0-20210723032227-1f47c861a9ac/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/tools v0.0.0-20180221164845-07fd8470d635/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-20181030221726-6c7e314b6563/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY= golang.org/x/tools v0.0.0-20190311212946-11955173bddd/go.mod h1:LCzVGOaR6xXOjkQ3onu1FJEFr0SW1gC7cKk1uF8kGRs= @@ -642,13 +667,13 @@ golang.org/x/tools v0.0.0-20190425150028-36563e24a262/go.mod h1:RgjU9mgBXZiqYHBn golang.org/x/tools v0.0.0-20190506145303-2d16b83fe98c/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= golang.org/x/tools v0.0.0-20190524140312-2c0ae7006135/go.mod h1:RgjU9mgBXZiqYHBnxXauZ1Gv1EHHAz9KjViQ78xBX0Q= golang.org/x/tools v0.0.0-20190606124116-d0a3d012864b/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= -golang.org/x/tools v0.0.0-20190614205625-5aca471b1d59/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190621195816-6e04913cbbac/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190624222133-a101b041ded4/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190628153133-6cdbf07be9d0/go.mod h1:/rFqwRUd4F7ZHNgwSSTFct+R/Kf4OFW1sUzUTQQTgfc= golang.org/x/tools v0.0.0-20190816200558-6889da9d5479/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20190911174233-4f2ddba30aff/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191012152004-8de300cfc20a/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.0.0-20191108193012-7d206e10da11/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191112195655-aa38f8e97acc/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191113191852-77e3bb0ad9e7/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20191115202509-3a792d9c32b2/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= @@ -743,6 +768,7 @@ google.golang.org/genproto v0.0.0-20200228133532-8c2c7df3a383/go.mod h1:55QSHmfG google.golang.org/genproto v0.0.0-20200305110556-506484158171/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= google.golang.org/genproto v0.0.0-20200312145019-da6875a35672/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= google.golang.org/genproto v0.0.0-20200331122359-1ee6d9798940/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= +google.golang.org/genproto v0.0.0-20200423170343-7949de9c1215/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= google.golang.org/genproto v0.0.0-20200430143042-b979b6f78d84/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= google.golang.org/genproto v0.0.0-20200511104702-f5ebc3bea380/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= google.golang.org/genproto v0.0.0-20200513103714-09dca8ec2884/go.mod h1:55QSHmfGQM9UVYDPBsyGGes0y52j32PQ3BqQfXhyH3c= @@ -753,8 +779,8 @@ google.golang.org/genproto v0.0.0-20200729003335-053ba62fc06f/go.mod h1:FWY/as6D google.golang.org/genproto v0.0.0-20200804131852-c06518451d9c/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20200825200019-8632dd797987/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20200904004341-0bd0a958aa1d/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= +google.golang.org/genproto v0.0.0-20201019141844-1ed22bb0c154/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20201109203340-2640f1f9cdfb/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= -google.golang.org/genproto v0.0.0-20201110150050-8816d57aaa9a/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20201201144952-b05cb90ed32e/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20201210142538-e3217bee35cc/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= google.golang.org/genproto v0.0.0-20201214200347-8c77b98c765d/go.mod h1:FWY/as6DDZQgahTzZj3fqbO1CbirC29ZNUFHwi0/+no= @@ -783,6 +809,7 @@ google.golang.org/grpc v1.34.0/go.mod h1:WotjhfgOW/POjDeRt8vscBtXq+2VjORFy659qA5 google.golang.org/grpc v1.35.0/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU= google.golang.org/grpc v1.36.0/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU= google.golang.org/grpc v1.36.1/go.mod h1:qjiiYl8FncCW8feJPdyg3v6XW24KsRHe+dy9BAGRRjU= +google.golang.org/grpc v1.37.0/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQdJfM= google.golang.org/grpc v1.38.0/go.mod h1:NREThFqKR1f3iQ6oBuvc5LadQuXVGo9rkm5ZGrQdJfM= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= @@ -803,7 +830,6 @@ gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8 gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f h1:BLraFXnmrev5lT+xlilqcH8XK9/i0At2xKjWk4p6zsU= gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/cheggaaa/pb.v1 v1.0.25/go.mod h1:V/YB90LKu/1FcN3WVnfiiE5oMCibMjukxqG/qStrOgw= gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI= gopkg.in/fsnotify.v1 v1.4.7/go.mod h1:Tz8NjZHkW78fSQdbUxIjBTcgA1z1m8ZHf0WmKUhAMys= gopkg.in/inf.v0 v0.9.1 h1:73M5CoZyi3ZLMOyDlQh031Cx6N9NDJ2Vvfl76EDAgDc= @@ -826,6 +852,7 @@ gopkg.in/yaml.v2 v2.3.0/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v3 v3.0.0-20200615113413-eeeca48fe776/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo= gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gotest.tools/v3 v3.0.2/go.mod h1:3SzNCllyD9/Y+b5r9JIKQ474KzkZyqLqEfYqMsX94Bk= @@ -837,32 +864,31 @@ honnef.co/go/tools v0.0.0-20190523083050-ea95bdfd59fc/go.mod h1:rf3lG4BRIbNafJWh honnef.co/go/tools v0.0.1-2019.2.3/go.mod h1:a3bituU0lyd329TUQxRnasdCoJDkEUEAqEt0JzvZhAg= honnef.co/go/tools v0.0.1-2020.1.3/go.mod h1:X/FiERA/W4tHapMX5mGpAtMSVEeEUOyHaw9vFzvIQ3k= honnef.co/go/tools v0.0.1-2020.1.4/go.mod h1:X/FiERA/W4tHapMX5mGpAtMSVEeEUOyHaw9vFzvIQ3k= -k8s.io/api v0.21.3 h1:cblWILbLO8ar+Fj6xdDGr603HRsf8Wu9E9rngJeprZQ= -k8s.io/api v0.21.3/go.mod h1:hUgeYHUbBp23Ue4qdX9tR8/ANi/g3ehylAqDn9NWVOg= -k8s.io/apiextensions-apiserver v0.21.3 h1:+B6biyUWpqt41kz5x6peIsljlsuwvNAp/oFax/j2/aY= -k8s.io/apiextensions-apiserver v0.21.3/go.mod h1:kl6dap3Gd45+21Jnh6utCx8Z2xxLm8LGDkprcd+KbsE= -k8s.io/apimachinery v0.21.3 h1:3Ju4nvjCngxxMYby0BimUk+pQHPOQp3eCGChk5kfVII= -k8s.io/apimachinery v0.21.3/go.mod h1:H/IM+5vH9kZRNJ4l3x/fXP/5bOPJaVP/guptnZPeCFI= -k8s.io/apiserver v0.21.3/go.mod h1:eDPWlZG6/cCCMj/JBcEpDoK+I+6i3r9GsChYBHSbAzU= -k8s.io/client-go v0.21.3/go.mod h1:+VPhCgTsaFmGILxR/7E1N0S+ryO010QBeNCv5JwRGYU= -k8s.io/code-generator v0.21.3/go.mod h1:K3y0Bv9Cz2cOW2vXUrNZlFbflhuPvuadW6JdnN6gGKo= -k8s.io/component-base v0.21.3/go.mod h1:kkuhtfEHeZM6LkX0saqSK8PbdO7A0HigUngmhhrwfGQ= +k8s.io/api v0.22.2 h1:M8ZzAD0V6725Fjg53fKeTJxGsJvRbk4TEm/fexHMtfw= +k8s.io/api v0.22.2/go.mod h1:y3ydYpLJAaDI+BbSe2xmGcqxiWHmWjkEeIbiwHvnPR8= +k8s.io/apiextensions-apiserver v0.22.2 h1:zK7qI8Ery7j2CaN23UCFaC1hj7dMiI87n01+nKuewd4= +k8s.io/apiextensions-apiserver v0.22.2/go.mod h1:2E0Ve/isxNl7tWLSUDgi6+cmwHi5fQRdwGVCxbC+KFA= +k8s.io/apimachinery v0.22.2 h1:ejz6y/zNma8clPVfNDLnPbleBo6MpoFy/HBiBqCouVk= +k8s.io/apimachinery v0.22.2/go.mod h1:O3oNtNadZdeOMxHFVxOreoznohCpy0z6mocxbZr7oJ0= +k8s.io/apiserver v0.22.2/go.mod h1:vrpMmbyjWrgdyOvZTSpsusQq5iigKNWv9o9KlDAbBHI= +k8s.io/client-go v0.22.2/go.mod h1:sAlhrkVDf50ZHx6z4K0S40wISNTarf1r800F+RlCF6U= +k8s.io/code-generator v0.22.2/go.mod h1:eV77Y09IopzeXOJzndrDyCI88UBok2h6WxAlBwpxa+o= +k8s.io/component-base v0.22.2/go.mod h1:5Br2QhI9OTe79p+TzPe9JKNQYvEKbq9rTJDWllunGug= k8s.io/gengo v0.0.0-20200413195148-3a45101e95ac/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0= k8s.io/gengo v0.0.0-20201214224949-b6c5ce23f027/go.mod h1:FiNAH4ZV3gBg2Kwh89tzAEV2be7d5xI0vBa/VySYy3E= k8s.io/klog/v2 v2.0.0/go.mod h1:PBfzABfn139FHAV07az/IF9Wp1bkk3vpT2XSJ76fSDE= k8s.io/klog/v2 v2.2.0/go.mod h1:Od+F08eJP+W3HUb4pSrPpgp9DGU4GzlpG/TmITuYh/Y= -k8s.io/klog/v2 v2.8.0 h1:Q3gmuM9hKEjefWFFYF0Mat+YyFJvsUyYuwyNNJ5C9Ts= -k8s.io/klog/v2 v2.8.0/go.mod h1:hy9LJ/NvuK+iVyP4Ehqva4HxZG/oXyIS3n3Jmire4Ec= -k8s.io/kube-openapi v0.0.0-20210305001622-591a79e4bda7/go.mod h1:wXW5VT87nVfh/iLV8FpR2uDvrFyomxbtb1KivDbvPTE= -k8s.io/utils v0.0.0-20201110183641-67b214c5f920 h1:CbnUZsM497iRC5QMVkHwyl8s2tB3g7yaSHkYPkpgelw= -k8s.io/utils v0.0.0-20201110183641-67b214c5f920/go.mod h1:jPW/WVKK9YHAvNhRxK0md/EJ228hCsBRufyofKtW8HA= +k8s.io/klog/v2 v2.9.0 h1:D7HV+n1V57XeZ0m6tdRkfknthUaM06VFbWldOFh8kzM= +k8s.io/klog/v2 v2.9.0/go.mod h1:hy9LJ/NvuK+iVyP4Ehqva4HxZG/oXyIS3n3Jmire4Ec= +k8s.io/kube-openapi v0.0.0-20210421082810-95288971da7e/go.mod h1:vHXdDvt9+2spS2Rx9ql3I8tycm3H9FDfdUoIuKCefvw= +k8s.io/utils v0.0.0-20210819203725-bdf08cb9a70a h1:8dYfu/Fc9Gz2rNJKB9IQRGgQOh2clmRzNIPPY1xLY5g= +k8s.io/utils v0.0.0-20210819203725-bdf08cb9a70a/go.mod h1:jPW/WVKK9YHAvNhRxK0md/EJ228hCsBRufyofKtW8HA= rsc.io/binaryregexp v0.2.0/go.mod h1:qTv7/COck+e2FymRvadv62gMdZztPaShugOCi3I+8D8= rsc.io/quote/v3 v3.1.0/go.mod h1:yEA65RcK8LyAZtP9Kv3t0HmxON59tX3rD+tICJqUlj0= rsc.io/sampler v1.3.0/go.mod h1:T1hPZKmBbMNahiBKFy5HrXp6adAjACjK9JXDnKaTXpA= -sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.0.19/go.mod h1:LEScyzhFmoF5pso/YSeBstl57mOzx9xlU9n85RGrDQg= +sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.0.22/go.mod h1:LEScyzhFmoF5pso/YSeBstl57mOzx9xlU9n85RGrDQg= sigs.k8s.io/structured-merge-diff/v4 v4.0.2/go.mod h1:bJZC9H9iH24zzfZ/41RGcq60oK1F7G282QMXDPYydCw= sigs.k8s.io/structured-merge-diff/v4 v4.1.2 h1:Hr/htKFmJEbtMgS/UD0N+gtgctAqz81t3nu+sPzynno= sigs.k8s.io/structured-merge-diff/v4 v4.1.2/go.mod h1:j/nl6xW8vLS49O8YvXW1ocPhZawJtm+Yrr7PPRQ0Vg4= -sigs.k8s.io/yaml v1.1.0/go.mod h1:UJmg0vDUVViEyp3mgSv9WPwZCDxu4rQW1olrI1uml+o= sigs.k8s.io/yaml v1.2.0 h1:kr/MCeFWJWTwyaHoR9c8EjH9OumOmoF9YGiZd7lFm/Q= sigs.k8s.io/yaml v1.2.0/go.mod h1:yfXDCHCao9+ENCvLSE62v9VSji2MKu5jeNfTrofGhJc= diff --git a/pkg/crd/conv.go b/pkg/crd/conv.go index e429db5cc..374e02c37 100644 --- a/pkg/crd/conv.go +++ b/pkg/crd/conv.go @@ -6,7 +6,6 @@ import ( apiextinternal "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions" apiext "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1" apiextv1beta1 "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1beta1" - "k8s.io/apimachinery/pkg/api/equality" "k8s.io/apimachinery/pkg/runtime" "k8s.io/apimachinery/pkg/runtime/schema" ) @@ -22,13 +21,15 @@ func init() { if err := apiext.AddToScheme(conversionScheme); err != nil { panic("must be able to add apiextensions/v1 to the CRD conversion Scheme") } - if err := apiextv1beta1.AddToScheme(conversionScheme); err != nil { - panic("must be able to add apiextensions/v1beta1 to the CRD conversion Scheme") - } } // AsVersion converts a CRD from the canonical internal form (currently v1) to some external form. func AsVersion(original apiext.CustomResourceDefinition, gv schema.GroupVersion) (runtime.Object, error) { + // TODO: Do we need to keep maintaining this conversion function + // post 1.22 when only CRDv1 is served by the apiserver? + if gv == apiextv1beta1.SchemeGroupVersion { + return nil, fmt.Errorf("apiVersion %q is not supported", gv.String()) + } // We can use the internal versions an existing conversions from kubernetes, since they're not in k/k itself. // This punts the problem of conversion down the road for a future maintainer (or future instance of @directxman12) // when we have to support older versions that get removed, or when API machinery decides to yell at us for this @@ -40,83 +41,3 @@ func AsVersion(original apiext.CustomResourceDefinition, gv schema.GroupVersion) return conversionScheme.ConvertToVersion(intVer, gv) } - -// mergeIdenticalSubresources checks to see if subresources are identical across -// all versions, and if so, merges them into a top-level version. -// -// This assumes you're not using trivial versions. -func mergeIdenticalSubresources(crd *apiextv1beta1.CustomResourceDefinition) { - subres := crd.Spec.Versions[0].Subresources - for _, ver := range crd.Spec.Versions { - if ver.Subresources == nil || !equality.Semantic.DeepEqual(subres, ver.Subresources) { - // either all nil, or not identical - return - } - } - - // things are identical if we've gotten this far, so move the subresources up - // and discard the identical per-version ones - crd.Spec.Subresources = subres - for i := range crd.Spec.Versions { - crd.Spec.Versions[i].Subresources = nil - } -} - -// mergeIdenticalSchemata checks to see if schemata are identical across -// all versions, and if so, merges them into a top-level version. -// -// This assumes you're not using trivial versions. -func mergeIdenticalSchemata(crd *apiextv1beta1.CustomResourceDefinition) { - schema := crd.Spec.Versions[0].Schema - for _, ver := range crd.Spec.Versions { - if ver.Schema == nil || !equality.Semantic.DeepEqual(schema, ver.Schema) { - // either all nil, or not identical - return - } - } - - // things are identical if we've gotten this far, so move the schemata up - // to a single schema and discard the identical per-version ones - crd.Spec.Validation = schema - for i := range crd.Spec.Versions { - crd.Spec.Versions[i].Schema = nil - } -} - -// mergeIdenticalPrinterColumns checks to see if schemata are identical across -// all versions, and if so, merges them into a top-level version. -// -// This assumes you're not using trivial versions. -func mergeIdenticalPrinterColumns(crd *apiextv1beta1.CustomResourceDefinition) { - cols := crd.Spec.Versions[0].AdditionalPrinterColumns - for _, ver := range crd.Spec.Versions { - if len(ver.AdditionalPrinterColumns) == 0 || !equality.Semantic.DeepEqual(cols, ver.AdditionalPrinterColumns) { - // either all nil, or not identical - return - } - } - - // things are identical if we've gotten this far, so move the printer columns up - // and discard the identical per-version ones - crd.Spec.AdditionalPrinterColumns = cols - for i := range crd.Spec.Versions { - crd.Spec.Versions[i].AdditionalPrinterColumns = nil - } -} - -// MergeIdenticalVersionInfo makes sure that components of the Versions field that are identical -// across all versions get merged into the top-level fields in v1beta1. -// -// This is required by the Kubernetes API server validation. -// -// The reason is that a v1beta1 -> v1 -> v1beta1 conversion cycle would need to -// round-trip identically, v1 doesn't have top-level subresources, and without -// this restriction it would be ambiguous how a v1-with-identical-subresources -// converts into a v1beta1). -func MergeIdenticalVersionInfo(crd *apiextv1beta1.CustomResourceDefinition) { - if len(crd.Spec.Versions) > 0 { - mergeIdenticalSubresources(crd) - mergeIdenticalSchemata(crd) - mergeIdenticalPrinterColumns(crd) - } -} diff --git a/pkg/crd/crd_spec_test.go b/pkg/crd/crd_spec_test.go index 4e802eeca..600e26542 100644 --- a/pkg/crd/crd_spec_test.go +++ b/pkg/crd/crd_spec_test.go @@ -18,275 +18,8 @@ package crd_test import ( . "github.com/onsi/ginkgo" - . "github.com/onsi/gomega" - apiextlegacy "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1beta1" - - "sigs.k8s.io/controller-tools/pkg/crd" ) var _ = Describe("CRD Generation", func() { - Describe("Utilities", func() { - Describe("MergeIdenticalVersionInfo", func() { - It("should replace per-version schemata with a top-level schema if only one version", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - Storage: true, - Schema: &apiextlegacy.CustomResourceValidation{ - OpenAPIV3Schema: &apiextlegacy.JSONSchemaProps{ - Required: []string{"foo"}, - Type: "object", - Properties: map[string]apiextlegacy.JSONSchemaProps{"foo": {Type: "string"}}, - }, - }, - }, - }, - }, - } - crd.MergeIdenticalVersionInfo(spec) - Expect(spec.Spec.Validation).To(Equal(&apiextlegacy.CustomResourceValidation{ - OpenAPIV3Schema: &apiextlegacy.JSONSchemaProps{ - Required: []string{"foo"}, - Type: "object", - Properties: map[string]apiextlegacy.JSONSchemaProps{"foo": {Type: "string"}}, - }, - })) - Expect(spec.Spec.Versions).To(Equal([]apiextlegacy.CustomResourceDefinitionVersion{ - {Name: "v1", Storage: true}, - })) - }) - It("should replace per-version schemata with a top-level schema if all are identical", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - Schema: &apiextlegacy.CustomResourceValidation{ - OpenAPIV3Schema: &apiextlegacy.JSONSchemaProps{ - Required: []string{"foo"}, - Type: "object", - Properties: map[string]apiextlegacy.JSONSchemaProps{"foo": {Type: "string"}}, - }, - }, - }, - { - Name: "v2", - Storage: true, - Schema: &apiextlegacy.CustomResourceValidation{ - OpenAPIV3Schema: &apiextlegacy.JSONSchemaProps{ - Required: []string{"foo"}, - Type: "object", - Properties: map[string]apiextlegacy.JSONSchemaProps{"foo": {Type: "string"}}, - }, - }, - }, - }, - }, - } - crd.MergeIdenticalVersionInfo(spec) - Expect(spec.Spec.Validation).To(Equal(&apiextlegacy.CustomResourceValidation{ - OpenAPIV3Schema: &apiextlegacy.JSONSchemaProps{ - Required: []string{"foo"}, - Type: "object", - Properties: map[string]apiextlegacy.JSONSchemaProps{"foo": {Type: "string"}}, - }, - })) - Expect(spec.Spec.Versions).To(Equal([]apiextlegacy.CustomResourceDefinitionVersion{ - {Name: "v1"}, {Name: "v2", Storage: true}, - })) - }) - - It("shouldn't merge different schemata", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - Schema: &apiextlegacy.CustomResourceValidation{ - OpenAPIV3Schema: &apiextlegacy.JSONSchemaProps{ - Type: "object", - Properties: map[string]apiextlegacy.JSONSchemaProps{"foo": {Type: "string"}}, - }, - }, - }, - { - Name: "v2", - Storage: true, - Schema: &apiextlegacy.CustomResourceValidation{ - OpenAPIV3Schema: &apiextlegacy.JSONSchemaProps{ - Required: []string{"foo"}, - Type: "object", - Properties: map[string]apiextlegacy.JSONSchemaProps{"foo": {Type: "string"}}, - }, - }, - }, - }, - }, - } - orig := spec.DeepCopy() - crd.MergeIdenticalVersionInfo(spec) - Expect(spec).To(Equal(orig)) - }) - - It("should replace per-version subresources with top-level subresources if only one version", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - Storage: true, - Subresources: &apiextlegacy.CustomResourceSubresources{ - Status: &apiextlegacy.CustomResourceSubresourceStatus{}, - }, - }, - }, - }, - } - - crd.MergeIdenticalVersionInfo(spec) - Expect(spec.Spec.Subresources).To(Equal(&apiextlegacy.CustomResourceSubresources{ - Status: &apiextlegacy.CustomResourceSubresourceStatus{}, - })) - Expect(spec.Spec.Versions).To(Equal([]apiextlegacy.CustomResourceDefinitionVersion{ - {Name: "v1", Storage: true}, - })) - }) - - It("should replace per-version subresources with top-level subresources if all are identical", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - Subresources: &apiextlegacy.CustomResourceSubresources{ - Status: &apiextlegacy.CustomResourceSubresourceStatus{}, - }, - }, - { - Name: "v2", - Storage: true, - Subresources: &apiextlegacy.CustomResourceSubresources{ - Status: &apiextlegacy.CustomResourceSubresourceStatus{}, - }, - }, - }, - }, - } - - crd.MergeIdenticalVersionInfo(spec) - Expect(spec.Spec.Subresources).To(Equal(&apiextlegacy.CustomResourceSubresources{ - Status: &apiextlegacy.CustomResourceSubresourceStatus{}, - })) - Expect(spec.Spec.Versions).To(Equal([]apiextlegacy.CustomResourceDefinitionVersion{ - {Name: "v1"}, {Name: "v2", Storage: true}, - })) - }) - - It("shouldn't merge different subresources", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - Subresources: &apiextlegacy.CustomResourceSubresources{ - Status: &apiextlegacy.CustomResourceSubresourceStatus{}, - }, - }, - { - Name: "v2", - Storage: true, - }, - }, - }, - } - orig := spec.DeepCopy() - crd.MergeIdenticalVersionInfo(spec) - Expect(spec).To(Equal(orig)) - }) - - It("should replace per-version printer columns with top-level printer columns if only one version", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - Storage: true, - AdditionalPrinterColumns: []apiextlegacy.CustomResourceColumnDefinition{ - {Name: "Cheddar", JSONPath: ".spec.cheddar"}, - {Name: "Parmesan", JSONPath: ".status.parmesan"}, - }, - }, - }, - }, - } - - crd.MergeIdenticalVersionInfo(spec) - Expect(spec.Spec.AdditionalPrinterColumns).To(Equal([]apiextlegacy.CustomResourceColumnDefinition{ - {Name: "Cheddar", JSONPath: ".spec.cheddar"}, - {Name: "Parmesan", JSONPath: ".status.parmesan"}, - })) - Expect(spec.Spec.Versions).To(Equal([]apiextlegacy.CustomResourceDefinitionVersion{ - {Name: "v1", Storage: true}, - })) - }) - - It("should replace per-version printer columns with top-level printer columns if all are identical", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - AdditionalPrinterColumns: []apiextlegacy.CustomResourceColumnDefinition{ - {Name: "Cheddar", JSONPath: ".spec.cheddar"}, - {Name: "Parmesan", JSONPath: ".status.parmesan"}, - }, - }, - { - Name: "v2", - Storage: true, - AdditionalPrinterColumns: []apiextlegacy.CustomResourceColumnDefinition{ - {Name: "Cheddar", JSONPath: ".spec.cheddar"}, - {Name: "Parmesan", JSONPath: ".status.parmesan"}, - }, - }, - }, - }, - } - - crd.MergeIdenticalVersionInfo(spec) - Expect(spec.Spec.AdditionalPrinterColumns).To(Equal([]apiextlegacy.CustomResourceColumnDefinition{ - {Name: "Cheddar", JSONPath: ".spec.cheddar"}, - {Name: "Parmesan", JSONPath: ".status.parmesan"}, - })) - Expect(spec.Spec.Versions).To(Equal([]apiextlegacy.CustomResourceDefinitionVersion{ - {Name: "v1"}, {Name: "v2", Storage: true}, - })) - }) - It("shouldn't merge different printer columns", func() { - spec := &apiextlegacy.CustomResourceDefinition{ - Spec: apiextlegacy.CustomResourceDefinitionSpec{ - Versions: []apiextlegacy.CustomResourceDefinitionVersion{ - { - Name: "v1", - AdditionalPrinterColumns: []apiextlegacy.CustomResourceColumnDefinition{ - {Name: "Cheddar", JSONPath: ".spec.cheddar"}, - {Name: "Parmesan", JSONPath: ".status.parmesan"}, - }, - }, - { - Name: "v2", - Storage: true, - }, - }, - }, - } - orig := spec.DeepCopy() - crd.MergeIdenticalVersionInfo(spec) - Expect(spec).To(Equal(orig)) - }) - }) - }) }) diff --git a/pkg/crd/gen.go b/pkg/crd/gen.go index dd154c549..995987462 100644 --- a/pkg/crd/gen.go +++ b/pkg/crd/gen.go @@ -20,10 +20,8 @@ import ( "fmt" "go/ast" "go/types" - "os" apiext "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1" - apiextlegacy "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1beta1" "k8s.io/apimachinery/pkg/runtime/schema" crdmarkers "sigs.k8s.io/controller-tools/pkg/crd/markers" @@ -33,31 +31,16 @@ import ( "sigs.k8s.io/controller-tools/pkg/version" ) +// The identifier for v1 CustomResourceDefinitions. +const v1 = "v1" + // The default CustomResourceDefinition version to generate. -const defaultVersion = "v1" +const defaultVersion = v1 // +controllertools:marker:generateHelp // Generator generates CustomResourceDefinition objects. type Generator struct { - // TrivialVersions indicates that we should produce a single-version CRD. - // - // Single "trivial-version" CRDs are compatible with older (pre 1.13) - // Kubernetes API servers. The storage version's schema will be used as - // the CRD's schema. - // - // Only works with the v1beta1 CRD version. - TrivialVersions bool `marker:",optional"` - - // PreserveUnknownFields indicates whether or not we should turn off pruning. - // - // Left unspecified, it'll default to true when only a v1beta1 CRD is - // generated (to preserve compatibility with older versions of this tool), - // or false otherwise. - // - // It's required to be false for v1 CRDs. - PreserveUnknownFields *bool `marker:",optional"` - // AllowDangerousTypes allows types which are usually omitted from CRD generation // because they are not recommended. // @@ -78,6 +61,8 @@ type Generator struct { // CRDVersions specifies the target API versions of the CRD type itself to // generate. Defaults to v1. // + // Currently, the only supported value is v1. + // // The first version listed will be assumed to be the "default" version and // will not get a version suffix in the output filename. // @@ -146,38 +131,8 @@ func (g Generator) Generate(ctx *genall.GenerationContext) error { versionedCRDs[i] = conv } - if g.TrivialVersions { - for i, crd := range versionedCRDs { - if crdVersions[i] == "v1beta1" { - toTrivialVersions(crd.(*apiextlegacy.CustomResourceDefinition)) - } - } - } - - // *If* we're only generating v1beta1 CRDs, default to `preserveUnknownFields: (unset)` - // for compatibility purposes. In any other case, default to false, since that's - // the sensible default and is required for v1. - v1beta1Only := len(crdVersions) == 1 && crdVersions[0] == "v1beta1" - switch { - case (g.PreserveUnknownFields == nil || *g.PreserveUnknownFields) && v1beta1Only: - crd := versionedCRDs[0].(*apiextlegacy.CustomResourceDefinition) - crd.Spec.PreserveUnknownFields = nil - case g.PreserveUnknownFields == nil, g.PreserveUnknownFields != nil && !*g.PreserveUnknownFields: - // it'll be false here (coming from v1) -- leave it as such - default: - return fmt.Errorf("you may only set PreserveUnknownFields to true with v1beta1 CRDs") - } - for i, crd := range versionedCRDs { - // defaults are not allowed to be specified in v1beta1 CRDs and - // decriptions are not allowed on the metadata regardless of version - // strip them before writing to a file - if crdVersions[i] == "v1beta1" { - removeDefaultsFromSchemas(crd.(*apiextlegacy.CustomResourceDefinition)) - removeDescriptionFromMetadataLegacy(crd.(*apiextlegacy.CustomResourceDefinition)) - } else { - removeDescriptionFromMetadata(crd.(*apiext.CustomResourceDefinition)) - } + removeDescriptionFromMetadata(crd.(*apiext.CustomResourceDefinition)) var fileName string if i == 0 { fileName = fmt.Sprintf("%s_%s.yaml", crdRaw.Spec.Group, crdRaw.Spec.Names.Plural) @@ -212,71 +167,6 @@ func removeDescriptionFromMetadataProps(v *apiext.JSONSchemaProps) { } } -func removeDescriptionFromMetadataLegacy(crd *apiextlegacy.CustomResourceDefinition) { - if crd.Spec.Validation != nil { - removeDescriptionFromMetadataPropsLegacy(crd.Spec.Validation.OpenAPIV3Schema) - } - for _, versionSpec := range crd.Spec.Versions { - if versionSpec.Schema != nil { - removeDescriptionFromMetadataPropsLegacy(versionSpec.Schema.OpenAPIV3Schema) - } - } -} - -func removeDescriptionFromMetadataPropsLegacy(v *apiextlegacy.JSONSchemaProps) { - if m, ok := v.Properties["metadata"]; ok { - meta := &m - if meta.Description != "" { - meta.Description = "" - v.Properties["metadata"] = m - - } - } -} - -// removeDefaultsFromSchemas will remove all instances of default values being -// specified across all defined API versions -func removeDefaultsFromSchemas(crd *apiextlegacy.CustomResourceDefinition) { - if crd.Spec.Validation != nil { - removeDefaultsFromSchemaProps(crd.Spec.Validation.OpenAPIV3Schema) - } - - for _, versionSpec := range crd.Spec.Versions { - if versionSpec.Schema != nil { - removeDefaultsFromSchemaProps(versionSpec.Schema.OpenAPIV3Schema) - } - } -} - -// removeDefaultsFromSchemaProps will recurse into JSONSchemaProps to remove -// all instances of default values being specified -func removeDefaultsFromSchemaProps(v *apiextlegacy.JSONSchemaProps) { - if v == nil { - return - } - - if v.Default != nil { - fmt.Fprintln(os.Stderr, "Warning: default unsupported in CRD version v1beta1, v1 required. Removing defaults.") - } - - // nil-out the default field - v.Default = nil - for name, prop := range v.Properties { - // iter var reference is fine -- we handle the persistence of the modfications on the line below - //nolint:gosec - removeDefaultsFromSchemaProps(&prop) - v.Properties[name] = prop - } - if v.Items != nil { - removeDefaultsFromSchemaProps(v.Items.Schema) - for i := range v.Items.JSONSchemas { - props := v.Items.JSONSchemas[i] - removeDefaultsFromSchemaProps(&props) - v.Items.JSONSchemas[i] = props - } - } -} - // FixTopLevelMetadata resets the schema for the top-level metadata field which is needed for CRD validation func FixTopLevelMetadata(crd apiext.CustomResourceDefinition) { for _, v := range crd.Spec.Versions { @@ -289,32 +179,6 @@ func FixTopLevelMetadata(crd apiext.CustomResourceDefinition) { } } -// toTrivialVersions strips out all schemata except for the storage schema, -// and moves that up into the root object. This makes the CRD compatible -// with pre 1.13 clusters. -func toTrivialVersions(crd *apiextlegacy.CustomResourceDefinition) { - var canonicalSchema *apiextlegacy.CustomResourceValidation - var canonicalSubresources *apiextlegacy.CustomResourceSubresources - var canonicalColumns []apiextlegacy.CustomResourceColumnDefinition - for i, ver := range crd.Spec.Versions { - if ver.Storage == true { - canonicalSchema = ver.Schema - canonicalSubresources = ver.Subresources - canonicalColumns = ver.AdditionalPrinterColumns - } - crd.Spec.Versions[i].Schema = nil - crd.Spec.Versions[i].Subresources = nil - crd.Spec.Versions[i].AdditionalPrinterColumns = nil - } - if canonicalSchema == nil { - return - } - - crd.Spec.Validation = canonicalSchema - crd.Spec.Subresources = canonicalSubresources - crd.Spec.AdditionalPrinterColumns = canonicalColumns -} - // addAttribution adds attribution info to indicate controller-gen tool was used // to generate this CRD definition along with the version info. func addAttribution(crd *apiext.CustomResourceDefinition) { diff --git a/pkg/crd/gen_integration_test.go b/pkg/crd/gen_integration_test.go index 2134e8335..bfaaec73f 100644 --- a/pkg/crd/gen_integration_test.go +++ b/pkg/crd/gen_integration_test.go @@ -26,6 +26,7 @@ import ( "github.com/google/go-cmp/cmp" . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" + "sigs.k8s.io/controller-tools/pkg/crd" crdmarkers "sigs.k8s.io/controller-tools/pkg/crd/markers" "sigs.k8s.io/controller-tools/pkg/genall" @@ -53,7 +54,7 @@ var _ = Describe("CRD Generation proper defaulting", func() { Expect(err).NotTo(HaveOccurred()) Expect(pkgs).To(HaveLen(1)) - By("settup up the context") + By("setup up the context") reg := &markers.Registry{} Expect(crdmarkers.Register(reg)).To(Succeed()) out = &outputRule{ @@ -67,21 +68,12 @@ var _ = Describe("CRD Generation proper defaulting", func() { } }) - It("should strip v1beta1 CRDs of default fields and metadata description", func() { + It("should fail to generate v1beta1 CRDs", func() { By("calling Generate") gen := &crd.Generator{ CRDVersions: []string{"v1beta1"}, } - Expect(gen.Generate(ctx)).NotTo(HaveOccurred()) - - By("loading the desired YAML") - expectedFile, err := ioutil.ReadFile(filepath.Join(genDir, "bar.example.com_foos.v1beta1.yaml")) - Expect(err).NotTo(HaveOccurred()) - expectedFile = fixAnnotations(expectedFile) - - By("comparing the two") - Expect(out.buf.String()).To(Equal(string(expectedFile)), cmp.Diff(out.buf.String(), string(expectedFile))) - + Expect(gen.Generate(ctx)).To(MatchError(`apiVersion "apiextensions.k8s.io/v1beta1" is not supported`)) }) It("should not strip v1 CRDs of default fields and metadata description", func() { diff --git a/pkg/crd/zz_generated.markerhelp.go b/pkg/crd/zz_generated.markerhelp.go index 4b008f594..5e30a191b 100644 --- a/pkg/crd/zz_generated.markerhelp.go +++ b/pkg/crd/zz_generated.markerhelp.go @@ -32,14 +32,6 @@ func (Generator) Help() *markers.DefinitionHelp { Details: "", }, FieldHelp: map[string]markers.DetailedHelp{ - "TrivialVersions": { - Summary: "indicates that we should produce a single-version CRD. ", - Details: "Single \"trivial-version\" CRDs are compatible with older (pre 1.13) Kubernetes API servers. The storage version's schema will be used as the CRD's schema. \n Only works with the v1beta1 CRD version.", - }, - "PreserveUnknownFields": { - Summary: "indicates whether or not we should turn off pruning. ", - Details: "Left unspecified, it'll default to true when only a v1beta1 CRD is generated (to preserve compatibility with older versions of this tool), or false otherwise. \n It's required to be false for v1 CRDs.", - }, "AllowDangerousTypes": { Summary: "allows types which are usually omitted from CRD generation because they are not recommended. ", Details: "Currently the following additional types are allowed when this is true: float32 float64 \n Left unspecified, the default is false", @@ -50,7 +42,7 @@ func (Generator) Help() *markers.DefinitionHelp { }, "CRDVersions": { Summary: "specifies the target API versions of the CRD type itself to generate. Defaults to v1. ", - Details: "The first version listed will be assumed to be the \"default\" version and will not get a version suffix in the output filename. \n You'll need to use \"v1\" to get support for features like defaulting, along with an API server that supports it (Kubernetes 1.16+).", + Details: "Currently, the only supported value is v1. \n The first version listed will be assumed to be the \"default\" version and will not get a version suffix in the output filename. \n You'll need to use \"v1\" to get support for features like defaulting, along with an API server that supports it (Kubernetes 1.16+).", }, "GenerateEmbeddedObjectMeta": { Summary: "specifies if any embedded ObjectMeta in the CRD should be generated", diff --git a/pkg/genall/genall.go b/pkg/genall/genall.go index 0206a4afa..2cf4ec7e7 100644 --- a/pkg/genall/genall.go +++ b/pkg/genall/genall.go @@ -100,6 +100,8 @@ type Runtime struct { GenerationContext // OutputRules defines how to output artifacts for each Generator. OutputRules OutputRules + // ErrorWriter defines where to write error messages. + ErrorWriter io.Writer } // GenerationContext defines the common information needed for each Generator @@ -188,8 +190,12 @@ func (g Generators) ForRoots(rootPaths ...string) (*Runtime, error) { func (r *Runtime) Run() bool { // TODO(directxman12): we could make this parallel, // but we'd need to ensure all underlying machinery is threadsafe + + if r.ErrorWriter == nil { + r.ErrorWriter = os.Stderr + } if len(r.Generators) == 0 { - fmt.Fprintln(os.Stderr, "no generators to run") + fmt.Fprintln(r.ErrorWriter, "no generators to run") return true } @@ -205,7 +211,7 @@ func (r *Runtime) Run() bool { } if err := (*gen).Generate(&ctx); err != nil { - fmt.Fprintln(os.Stderr, err) + fmt.Fprintln(r.ErrorWriter, err) hadErrs = true } } diff --git a/pkg/schemapatcher/gen.go b/pkg/schemapatcher/gen.go index f9b197a59..6aec36ca6 100644 --- a/pkg/schemapatcher/gen.go +++ b/pkg/schemapatcher/gen.go @@ -23,7 +23,6 @@ import ( "gopkg.in/yaml.v3" apiext "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1" - apiextlegacy "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1beta1" "k8s.io/apimachinery/pkg/api/equality" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime/schema" @@ -54,7 +53,6 @@ import ( // patches. var ( - legacyAPIExtVersion = apiextlegacy.SchemeGroupVersion.String() currentAPIExtVersion = apiext.SchemeGroupVersion.String() ) @@ -62,18 +60,8 @@ var ( // Generator patches existing CRDs with new schemata. // -// For legacy (v1beta1) single-version CRDs, it will simply replace the global schema. -// -// For legacy (v1beta1) multi-version CRDs, and any v1 CRDs, it will replace -// schemata of existing versions and *clear the schema* from any versions not -// specified in the Go code. It will *not* add new versions, or remove old -// ones. -// -// For legacy multi-version CRDs with identical schemata, it will take care of -// lifting the per-version schema up to the global schema. -// // It will generate output for each "CRD Version" (API version of the CRD type -// itself) , e.g. apiextensions/v1beta1 and apiextensions/v1) available. +// itself) , e.g. apiextensions/v1) available. type Generator struct { // ManifestsPath contains the CustomResourceDefinition YAML files. ManifestsPath string `marker:"manifests"` @@ -259,67 +247,13 @@ type partialCRD struct { CRDVersion string } -// setGlobalSchema sets the global schema for the v1beta1 apiext version in -// this set (if present, as per partialCRD.setGlobalSchema), and sets the -// versioned schemas (as per setVersionedSchemata) for the v1 version. +// setGlobalSchema sets the versioned schemas (as per setVersionedSchemata). func (e *partialCRDSet) setGlobalSchema() error { - // there's no easy way to get a "random" key from a go map :-/ - var schema apiext.JSONSchemaProps - for ver := range e.NewSchemata { - schema = e.NewSchemata[ver] - break - } for _, crdInfo := range e.CRDVersions { - switch crdInfo.CRDVersion { - case legacyAPIExtVersion: - if err := crdInfo.setGlobalSchema(schema); err != nil { - return err - } - case currentAPIExtVersion: - // just set the schemata as normal for non-legacy versions - if err := crdInfo.setVersionedSchemata(e.NewSchemata); err != nil { - return err - } - } - } - return nil -} - -// setGlobalSchema sets the global schema to one of the schemata -// for this CRD. All schemata must be identical for this to be a valid operation. -func (e *partialCRD) setGlobalSchema(newSchema apiext.JSONSchemaProps) error { - if e.CRDVersion != legacyAPIExtVersion { - // no global schema, nothing to do - return fmt.Errorf("cannot set global schema on non-legacy CRD versions") - } - schema, err := legacySchema(newSchema) - if err != nil { - return fmt.Errorf("failed to convert schema to legacy form: %w", err) - } - schemaNodeTree, err := yamlop.ToYAML(schema) - if err != nil { - return err - } - schemaNodeTree = schemaNodeTree.Content[0] // get rid of the document node - yamlop.SetStyle(schemaNodeTree, 0) // clear the style so it defaults to auto-style-choice - - if err := yamlop.SetNode(e.Yaml, *schemaNodeTree, "spec", "validation", "openAPIV3Schema"); err != nil { - return err - } - - versions, found, err := e.getVersionsNode() - if err != nil { - return err - } - if !found { - return nil - } - for i, verNode := range versions.Content { - if err := yamlop.DeleteNode(verNode, "schema"); err != nil { - return fmt.Errorf("spec.versions[%d]: %w", i, err) + if err := crdInfo.setVersionedSchemata(e.NewSchemata); err != nil { + return err } } - return nil } @@ -382,16 +316,7 @@ func (e *partialCRD) setVersionedSchemata(newSchemata map[string]apiext.JSONSche return fmt.Errorf("spec.versions[%d]: %w", i, err) } } else { - // TODO(directxman12): if this gets to be more than 2 versions, use polymorphism to clean this up - var verSchema interface{} = newSchema - if e.CRDVersion == legacyAPIExtVersion { - verSchema, err = legacySchema(newSchema) - if err != nil { - return fmt.Errorf("failed to convert schema to legacy form: %w", err) - } - } - - schemaNodeTree, err := yamlop.ToYAML(verSchema) + schemaNodeTree, err := yamlop.ToYAML(newSchema) if err != nil { return fmt.Errorf("failed to convert schema to YAML: %w", err) } @@ -433,7 +358,10 @@ func crdsFromDirectory(ctx *genall.GenerationContext, dir string) (map[schema.Gr if err := kyaml.Unmarshal(rawContent, &typeMeta); err != nil { continue } - if !isSupportedAPIExtGroupVer(typeMeta.APIVersion) || typeMeta.Kind != "CustomResourceDefinition" { + if !isSupportedAPIExtGroupVer(typeMeta.APIVersion) { + return nil, fmt.Errorf("load %q: apiVersion %q not supported", filepath.Join(dir, fileInfo.Name()), typeMeta.APIVersion) + } + if typeMeta.Kind != "CustomResourceDefinition" { continue } @@ -443,14 +371,9 @@ func crdsFromDirectory(ctx *genall.GenerationContext, dir string) (map[schema.Gr continue } groupKind := schema.GroupKind{Group: actualCRD.Spec.Group, Kind: actualCRD.Spec.Names.Kind} - var versions map[string]struct{} - if len(actualCRD.Spec.Versions) == 0 { - versions = map[string]struct{}{actualCRD.Spec.Version: {}} - } else { - versions = make(map[string]struct{}, len(actualCRD.Spec.Versions)) - for _, ver := range actualCRD.Spec.Versions { - versions[ver.Name] = struct{}{} - } + versions := make(map[string]struct{}, len(actualCRD.Spec.Versions)) + for _, ver := range actualCRD.Spec.Versions { + versions[ver.Name] = struct{}{} } // then actually unmarshal in a manner that preserves ordering, etc @@ -480,9 +403,9 @@ func crdsFromDirectory(ctx *genall.GenerationContext, dir string) (map[schema.Gr } // isSupportedAPIExtGroupVer checks if the given string-form group-version -// is one of the known apiextensions versions (v1, v1beta1). +// is one of the known apiextensions versions (v1). func isSupportedAPIExtGroupVer(groupVer string) bool { - return groupVer == currentAPIExtVersion || groupVer == legacyAPIExtVersion + return groupVer == currentAPIExtVersion } // crdIsh is a merged blob of CRD fields that looks enough like all versions of @@ -502,23 +425,5 @@ type crdIsh struct { Versions []struct { Name string `json:"name"` } `json:"versions"` - Version string `json:"version"` } `json:"spec"` } - -// legacySchema jumps through some hoops to convert a v1 schema to a v1beta1 schema. -func legacySchema(origSchema apiext.JSONSchemaProps) (apiextlegacy.JSONSchemaProps, error) { - shellCRD := apiext.CustomResourceDefinition{} - shellCRD.APIVersion = currentAPIExtVersion - shellCRD.Kind = "CustomResourceDefinition" - shellCRD.Spec.Versions = []apiext.CustomResourceDefinitionVersion{ - {Schema: &apiext.CustomResourceValidation{OpenAPIV3Schema: origSchema.DeepCopy()}}, - } - - legacyCRD, err := crdgen.AsVersion(shellCRD, apiextlegacy.SchemeGroupVersion) - if err != nil { - return apiextlegacy.JSONSchemaProps{}, err - } - - return *legacyCRD.(*apiextlegacy.CustomResourceDefinition).Spec.Validation.OpenAPIV3Schema, nil -} diff --git a/pkg/schemapatcher/gen_integration_test.go b/pkg/schemapatcher/gen_integration_test.go index 3bdb7f421..d1c8485d6 100644 --- a/pkg/schemapatcher/gen_integration_test.go +++ b/pkg/schemapatcher/gen_integration_test.go @@ -30,6 +30,29 @@ import ( ) var _ = Describe("CRD Patching From Parsing to Editing", func() { + It("should fail to load legacy CRDs", func() { + By("switching into testdata to appease go modules") + cwd, err := os.Getwd() + Expect(err).NotTo(HaveOccurred()) + Expect(os.Chdir("./testdata")).To(Succeed()) // go modules are directory-sensitive + defer func() { Expect(os.Chdir(cwd)).To(Succeed()) }() + + By("loading the generation runtime") + var crdSchemaGen genall.Generator = &Generator{ + ManifestsPath: "./invalid", + } + rt, err := genall.Generators{&crdSchemaGen}.ForRoots("./...") + Expect(err).NotTo(HaveOccurred()) + + outputDir, err := ioutil.TempDir("", "controller-tools-test") + Expect(err).NotTo(HaveOccurred()) + defer os.RemoveAll(outputDir) + rt.OutputRules.Default = genall.OutputToDirectory(outputDir) + + By("running the generator") + Expect(rt.Run()).To(BeTrue(), "unexpectedly succeeded") + }) + It("should properly generate and patch the test CRDs", func() { // TODO(directxman12): I've ported these over from @sttts's tests, // but they should really probably not be writing to an actual filesystem @@ -42,7 +65,7 @@ var _ = Describe("CRD Patching From Parsing to Editing", func() { By("loading the generation runtime") var crdSchemaGen genall.Generator = &Generator{ - ManifestsPath: "./manifests", + ManifestsPath: "./valid", } rt, err := genall.Generators{&crdSchemaGen}.ForRoots("./...") Expect(err).NotTo(HaveOccurred()) @@ -51,6 +74,7 @@ var _ = Describe("CRD Patching From Parsing to Editing", func() { Expect(err).NotTo(HaveOccurred()) defer os.RemoveAll(outputDir) rt.OutputRules.Default = genall.OutputToDirectory(outputDir) + rt.ErrorWriter = GinkgoWriter By("running the generator") Expect(rt.Run()).To(BeFalse(), "unexpectedly had errors") diff --git a/pkg/schemapatcher/testdata/expected/kubebuilder-example-crd.yaml b/pkg/schemapatcher/testdata/expected/kubebuilder-example-crd.yaml deleted file mode 100644 index bcf83aacc..000000000 --- a/pkg/schemapatcher/testdata/expected/kubebuilder-example-crd.yaml +++ /dev/null @@ -1,40 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: example.kubebuilder.schemapatcher.controller-tools.sigs.k8s.io -spec: - group: kubebuilder.schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Example - singular: example - plural: examples - listKind: ExampleList - version: v1 - validation: - openAPIV3Schema: - description: Example is a kind with schema changes. - type: object - required: - - spec - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation of an object. Servers should convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this object represents. Servers may infer this from the endpoint the client submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - type: object - required: - - bar - - foo - properties: - bar: - description: foo contains foo. - type: string - foo: - description: foo contains foo. - type: string diff --git a/pkg/schemapatcher/testdata/expected/kubebuilder-unchanged-crd.v1beta1.yaml b/pkg/schemapatcher/testdata/expected/kubebuilder-unchanged-crd.v1beta1.yaml deleted file mode 100644 index 4c39743c0..000000000 --- a/pkg/schemapatcher/testdata/expected/kubebuilder-unchanged-crd.v1beta1.yaml +++ /dev/null @@ -1,40 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: unchanged.kubebuilder.schemapatcher.controller-tools.sigs.k8s.io -spec: - group: kubebuilder.schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Unchanged - singular: unchanged - plural: unchangeds - listKind: UnchangedList - version: v1 - validation: - openAPIV3Schema: - description: Unchanged is a kind without schema changes. - type: object - required: - - spec - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation of an object. Servers should convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this object represents. Servers may infer this from the endpoint the client submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - type: object - required: - - bar - - foo - properties: - bar: - description: foo contains foo. - type: string - foo: - description: foo contains foo. - type: string diff --git a/pkg/schemapatcher/testdata/expected/legacy-example-crd.yaml b/pkg/schemapatcher/testdata/expected/legacy-example-crd.yaml deleted file mode 100644 index 83dba9e3b..000000000 --- a/pkg/schemapatcher/testdata/expected/legacy-example-crd.yaml +++ /dev/null @@ -1,44 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: example.legacy.schemapatcher.controller-tools.sigs.k8s.io - # ensure that comments and annotations are left in place - annotations: - firstkey: firstval - secondkey: secondval -spec: - group: legacy.schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Example - singular: example - plural: examples - listKind: ExampleList - version: v1 - validation: - openAPIV3Schema: - description: Example is a kind with schema changes. - type: object - required: - - spec - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation of an object. Servers should convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this object represents. Servers may infer this from the endpoint the client submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - type: object - required: - - bar - - foo - properties: - bar: - description: foo contains foo. - type: string - foo: - description: foo contains foo. - type: string diff --git a/pkg/schemapatcher/testdata/expected/legacy-unchanged-crd.yaml b/pkg/schemapatcher/testdata/expected/legacy-unchanged-crd.yaml deleted file mode 100644 index 34252814a..000000000 --- a/pkg/schemapatcher/testdata/expected/legacy-unchanged-crd.yaml +++ /dev/null @@ -1,45 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: unchanged.legacy.schemapatcher.controller-tools.sigs.k8s.io - # ensure that comments and annotations are left in place - # (note the space above this comment -- go-yaml isn't perfect preseving whitespace) - annotations: - firstkey: firstval - secondkey: secondval -spec: - group: legacy.schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Unchanged - singular: unchanged - plural: unchangeds - listKind: UnchangedList - version: v1 - validation: - openAPIV3Schema: - description: Unchanged is a kind without schema changes. - type: object - required: - - spec - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation of an object. Servers should convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this object represents. Servers may infer this from the endpoint the client submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - type: object - required: - - bar - - foo - properties: - bar: - description: foo contains foo. - type: string - foo: - description: foo contains foo. - type: string diff --git a/pkg/schemapatcher/testdata/expected/other-crd.yaml b/pkg/schemapatcher/testdata/expected/other-crd.yaml deleted file mode 100644 index da1b19400..000000000 --- a/pkg/schemapatcher/testdata/expected/other-crd.yaml +++ /dev/null @@ -1,13 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: other.schemapatcher.controller-tools.sigs.k8s.io -spec: - group: schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Other - singular: other - plural: others - listKind: OtherList - version: v1 diff --git a/pkg/schemapatcher/testdata/manifests/kubebuilder-example-crd.v1.yaml b/pkg/schemapatcher/testdata/invalid/kubebuilder-example-crd.v1.yaml similarity index 100% rename from pkg/schemapatcher/testdata/manifests/kubebuilder-example-crd.v1.yaml rename to pkg/schemapatcher/testdata/invalid/kubebuilder-example-crd.v1.yaml diff --git a/pkg/schemapatcher/testdata/manifests/kubebuilder-example-crd.yaml b/pkg/schemapatcher/testdata/invalid/kubebuilder-example-crd.yaml similarity index 100% rename from pkg/schemapatcher/testdata/manifests/kubebuilder-example-crd.yaml rename to pkg/schemapatcher/testdata/invalid/kubebuilder-example-crd.yaml diff --git a/pkg/schemapatcher/testdata/manifests/kubebuilder-unchanged-crd.v1beta1.yaml b/pkg/schemapatcher/testdata/manifests/kubebuilder-unchanged-crd.v1beta1.yaml deleted file mode 100644 index ec4d2a104..000000000 --- a/pkg/schemapatcher/testdata/manifests/kubebuilder-unchanged-crd.v1beta1.yaml +++ /dev/null @@ -1,44 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: unchanged.kubebuilder.schemapatcher.controller-tools.sigs.k8s.io -spec: - group: kubebuilder.schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Unchanged - singular: unchanged - plural: unchangeds - listKind: UnchangedList - version: v1 - validation: - openAPIV3Schema: - description: Unchanged is a kind without schema changes. - type: object - required: - - spec - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - type: object - required: - - bar - - foo - properties: - bar: - description: foo contains foo. - type: string - foo: - description: foo contains foo. - type: string diff --git a/pkg/schemapatcher/testdata/manifests/legacy-example-crd.yaml b/pkg/schemapatcher/testdata/manifests/legacy-example-crd.yaml deleted file mode 100644 index 02d9a549b..000000000 --- a/pkg/schemapatcher/testdata/manifests/legacy-example-crd.yaml +++ /dev/null @@ -1,43 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: example.legacy.schemapatcher.controller-tools.sigs.k8s.io - # ensure that comments and annotations are left in place - annotations: - firstkey: firstval - secondkey: secondval -spec: - group: legacy.schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Example - singular: example - plural: examples - listKind: ExampleList - version: v1 - validation: - openAPIV3Schema: - description: Example is a kind with schema changes. - type: object - required: - - spec - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation of an object. Servers should convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this object represents. Servers may infer this from the endpoint the client submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - type: object - required: - - bar - properties: - bar: - description: foo contains foo. - type: string - foo: - description: foo contains foo. - type: string diff --git a/pkg/schemapatcher/testdata/manifests/legacy-unchanged-crd.yaml b/pkg/schemapatcher/testdata/manifests/legacy-unchanged-crd.yaml deleted file mode 100644 index 3caa090fb..000000000 --- a/pkg/schemapatcher/testdata/manifests/legacy-unchanged-crd.yaml +++ /dev/null @@ -1,50 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: unchanged.legacy.schemapatcher.controller-tools.sigs.k8s.io - - # ensure that comments and annotations are left in place - # (note the space above this comment -- go-yaml isn't perfect preseving whitespace) - annotations: - firstkey: firstval - secondkey: secondval -spec: - group: legacy.schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Unchanged - singular: unchanged - plural: unchangeds - listKind: UnchangedList - version: v1 - validation: - openAPIV3Schema: - description: Unchanged is a kind without schema changes. - type: object - required: - - spec - properties: - apiVersion: - description: 'APIVersion defines the versioned schema of this representation - of an object. Servers should convert recognized schemas to the latest - internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/api-conventions.md#resources' - type: string - kind: - description: 'Kind is a string value representing the REST resource this - object represents. Servers may infer this from the endpoint the client - submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/api-conventions.md#types-kinds' - type: string - metadata: - type: object - spec: - type: object - required: - - bar - - foo - properties: - bar: - description: foo contains foo. - type: string - foo: - description: foo contains foo. - type: string diff --git a/pkg/schemapatcher/testdata/manifests/other-crd.yaml b/pkg/schemapatcher/testdata/manifests/other-crd.yaml deleted file mode 100644 index da1b19400..000000000 --- a/pkg/schemapatcher/testdata/manifests/other-crd.yaml +++ /dev/null @@ -1,13 +0,0 @@ -apiVersion: apiextensions.k8s.io/v1beta1 -kind: CustomResourceDefinition -metadata: - name: other.schemapatcher.controller-tools.sigs.k8s.io -spec: - group: schemapatcher.controller-tools.sigs.k8s.io - scope: Cluster - names: - kind: Other - singular: other - plural: others - listKind: OtherList - version: v1 diff --git a/pkg/schemapatcher/testdata/valid/kubebuilder-example-crd.v1.yaml b/pkg/schemapatcher/testdata/valid/kubebuilder-example-crd.v1.yaml new file mode 100644 index 000000000..0d651dfc2 --- /dev/null +++ b/pkg/schemapatcher/testdata/valid/kubebuilder-example-crd.v1.yaml @@ -0,0 +1,40 @@ +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + name: example.kubebuilder.schemapatcher.controller-tools.sigs.k8s.io +spec: + group: kubebuilder.schemapatcher.controller-tools.sigs.k8s.io + scope: Cluster + names: + kind: Example + singular: example + plural: examples + listKind: ExampleList + versions: + - name: v1 + schema: + openAPIV3Schema: + description: Example is a kind with schema changes. + type: object + required: + - spec + properties: + apiVersion: + description: 'APIVersion defines the versioned schema of this representation of an object. Servers should convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources' + type: string + kind: + description: 'Kind is a string value representing the REST resource this object represents. Servers may infer this from the endpoint the client submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds' + type: string + metadata: + type: object + spec: + type: object + required: + - bar + properties: + bar: + description: foo contains foo. + type: string + foo: + description: foo contains foo. + type: string diff --git a/pkg/schemapatcher/testdata/manifests/kubebuilder-unchanged-crd.yaml b/pkg/schemapatcher/testdata/valid/kubebuilder-unchanged-crd.yaml similarity index 100% rename from pkg/schemapatcher/testdata/manifests/kubebuilder-unchanged-crd.yaml rename to pkg/schemapatcher/testdata/valid/kubebuilder-unchanged-crd.yaml diff --git a/pkg/schemapatcher/zz_generated.markerhelp.go b/pkg/schemapatcher/zz_generated.markerhelp.go index 36cc0cba8..96950a9d1 100644 --- a/pkg/schemapatcher/zz_generated.markerhelp.go +++ b/pkg/schemapatcher/zz_generated.markerhelp.go @@ -29,7 +29,7 @@ func (Generator) Help() *markers.DefinitionHelp { Category: "", DetailedHelp: markers.DetailedHelp{ Summary: "patches existing CRDs with new schemata. ", - Details: "For legacy (v1beta1) single-version CRDs, it will simply replace the global schema. \n For legacy (v1beta1) multi-version CRDs, and any v1 CRDs, it will replace schemata of existing versions and *clear the schema* from any versions not specified in the Go code. It will *not* add new versions, or remove old ones. \n For legacy multi-version CRDs with identical schemata, it will take care of lifting the per-version schema up to the global schema. \n It will generate output for each \"CRD Version\" (API version of the CRD type itself) , e.g. apiextensions/v1beta1 and apiextensions/v1) available.", + Details: "It will generate output for each \"CRD Version\" (API version of the CRD type itself) , e.g. apiextensions/v1) available.", }, FieldHelp: map[string]markers.DetailedHelp{ "ManifestsPath": { @@ -40,6 +40,10 @@ func (Generator) Help() *markers.DefinitionHelp { Summary: "specifies the maximum description length for fields in CRD's OpenAPI schema. ", Details: "0 indicates drop the description for all fields completely. n indicates limit the description to at most n characters and truncate the description to closest sentence boundary if it exceeds n characters.", }, + "GenerateEmbeddedObjectMeta": { + Summary: "specifies if any embedded ObjectMeta in the CRD should be generated", + Details: "", + }, }, } } diff --git a/pkg/webhook/parser.go b/pkg/webhook/parser.go index 30d1360da..f3434e1ab 100644 --- a/pkg/webhook/parser.go +++ b/pkg/webhook/parser.go @@ -36,7 +36,8 @@ import ( // The default {Mutating,Validating}WebhookConfiguration version to generate. const ( - defaultWebhookVersion = "v1" + v1 = "v1" + defaultWebhookVersion = v1 ) var ( @@ -47,7 +48,7 @@ var ( // supportedWebhookVersions returns currently supported API version of {Mutating,Validating}WebhookConfiguration. func supportedWebhookVersions() []string { - return []string{defaultWebhookVersion, "v1beta1"} + return []string{defaultWebhookVersion} } // +controllertools:marker:generateHelp:category=Webhook @@ -104,14 +105,12 @@ type Config struct { Path string // WebhookVersions specifies the target API versions of the {Mutating,Validating}WebhookConfiguration objects - // itself to generate. Defaults to v1. + // itself to generate. The only supported value is v1. Defaults to v1. WebhookVersions []string `marker:"webhookVersions,optional"` // AdmissionReviewVersions is an ordered list of preferred `AdmissionReview` // versions the Webhook expects. - // For generating v1 {Mutating,Validating}WebhookConfiguration, this is mandatory. - // For generating v1beta1 {Mutating,Validating}WebhookConfiguration, this is optional, and default to v1beta1. - AdmissionReviewVersions []string `marker:"admissionReviewVersions,optional"` + AdmissionReviewVersions []string `marker:"admissionReviewVersions"` } // verbToAPIVariant converts a marker's verb to the proper value for the API. @@ -331,9 +330,8 @@ func (Generator) Generate(ctx *genall.GenerationContext) error { versionedWebhooks := make(map[string][]interface{}, len(supportedWebhookVersions)) for _, version := range supportedWebhookVersions { if cfgs, ok := mutatingCfgs[version]; ok { - // All webhook config versions in supportedWebhookVersions have the same general form, with a few - // stricter requirements for v1. Since no conversion scheme exists for webhook configs, the v1 - // type can be used for all versioned types in this context. + // The only possible version in supportedWebhookVersions is v1, + // so use it for all versioned types in this context. objRaw := &admissionregv1.MutatingWebhookConfiguration{} objRaw.SetGroupVersionKind(schema.GroupVersionKind{ Group: admissionregv1.SchemeGroupVersion.Group, @@ -342,28 +340,24 @@ func (Generator) Generate(ctx *genall.GenerationContext) error { }) objRaw.SetName("mutating-webhook-configuration") objRaw.Webhooks = cfgs - switch version { - case admissionregv1.SchemeGroupVersion.Version: - for i := range objRaw.Webhooks { - // SideEffects is required in admissionregistration/v1, if this is not set or set to `Some` or `Known`, - // return an error - if err := checkSideEffectsForV1(objRaw.Webhooks[i].SideEffects); err != nil { - return err - } - // AdmissionReviewVersions is required in admissionregistration/v1, if this is not set, - // return an error - if len(objRaw.Webhooks[i].AdmissionReviewVersions) == 0 { - return fmt.Errorf("AdmissionReviewVersions is mandatory for v1 {Mutating,Validating}WebhookConfiguration") - } + for i := range objRaw.Webhooks { + // SideEffects is required in admissionregistration/v1, if this is not set or set to `Some` or `Known`, + // return an error + if err := checkSideEffectsForV1(objRaw.Webhooks[i].SideEffects); err != nil { + return err + } + // AdmissionReviewVersions is required in admissionregistration/v1, if this is not set, + // return an error + if len(objRaw.Webhooks[i].AdmissionReviewVersions) == 0 { + return fmt.Errorf("AdmissionReviewVersions is mandatory for v1 {Mutating,Validating}WebhookConfiguration") } } versionedWebhooks[version] = append(versionedWebhooks[version], objRaw) } if cfgs, ok := validatingCfgs[version]; ok { - // All webhook config versions in supportedWebhookVersions have the same general form, with a few - // stricter requirements for v1. Since no conversion scheme exists for webhook configs, the v1 - // type can be used for all versioned types in this context. + // The only possible version in supportedWebhookVersions is v1, + // so use it for all versioned types in this context. objRaw := &admissionregv1.ValidatingWebhookConfiguration{} objRaw.SetGroupVersionKind(schema.GroupVersionKind{ Group: admissionregv1.SchemeGroupVersion.Group, @@ -372,19 +366,16 @@ func (Generator) Generate(ctx *genall.GenerationContext) error { }) objRaw.SetName("validating-webhook-configuration") objRaw.Webhooks = cfgs - switch version { - case admissionregv1.SchemeGroupVersion.Version: - for i := range objRaw.Webhooks { - // SideEffects is required in admissionregistration/v1, if this is not set or set to `Some` or `Known`, - // return an error - if err := checkSideEffectsForV1(objRaw.Webhooks[i].SideEffects); err != nil { - return err - } - // AdmissionReviewVersions is required in admissionregistration/v1, if this is not set, - // return an error - if len(objRaw.Webhooks[i].AdmissionReviewVersions) == 0 { - return fmt.Errorf("AdmissionReviewVersions is mandatory for v1 {Mutating,Validating}WebhookConfiguration") - } + for i := range objRaw.Webhooks { + // SideEffects is required in admissionregistration/v1, if this is not set or set to `Some` or `Known`, + // return an error + if err := checkSideEffectsForV1(objRaw.Webhooks[i].SideEffects); err != nil { + return err + } + // AdmissionReviewVersions is required in admissionregistration/v1, if this is not set, + // return an error + if len(objRaw.Webhooks[i].AdmissionReviewVersions) == 0 { + return fmt.Errorf("AdmissionReviewVersions is mandatory for v1 {Mutating,Validating}WebhookConfiguration") } } versionedWebhooks[version] = append(versionedWebhooks[version], objRaw) diff --git a/pkg/webhook/parser_integration_test.go b/pkg/webhook/parser_integration_test.go index a5b549a87..e91302707 100644 --- a/pkg/webhook/parser_integration_test.go +++ b/pkg/webhook/parser_integration_test.go @@ -26,7 +26,6 @@ import ( . "github.com/onsi/ginkgo" . "github.com/onsi/gomega" admissionregv1 "k8s.io/api/admissionregistration/v1" - admissionregv1beta1 "k8s.io/api/admissionregistration/v1beta1" "sigs.k8s.io/yaml" "sigs.k8s.io/controller-tools/pkg/genall" @@ -35,19 +34,108 @@ import ( "sigs.k8s.io/controller-tools/pkg/webhook" ) +// TODO(directxman12): test generation across multiple versions (right +// now, we're trusting k/k's conversion code, though, which is probably +// fine for the time being) var _ = Describe("Webhook Generation From Parsing to CustomResourceDefinition", func() { assertSame := func(actual, expected interface{}) { ExpectWithOffset(1, actual).To(Equal(expected), "type not as expected, check pkg/webhook/testdata/README.md for more details.\n\nDiff:\n\n%s", cmp.Diff(actual, expected)) } + It("should fail generating a v1beta1 webhook", func() { + By("switching into testdata to appease go modules") + cwd, err := os.Getwd() + Expect(err).NotTo(HaveOccurred()) + Expect(os.Chdir("./testdata/invalid-v1beta1NotSupported")).To(Succeed()) // go modules are directory-sensitive + defer func() { Expect(os.Chdir(cwd)).To(Succeed()) }() + + By("loading the roots") + pkgs, err := loader.LoadRoots(".") + Expect(err).NotTo(HaveOccurred()) + Expect(pkgs).To(HaveLen(1)) + + By("setting up the parser") + reg := &markers.Registry{} + Expect(reg.Register(webhook.ConfigDefinition)).To(Succeed()) + + By("requesting that the manifest be generated") + outputDir, err := ioutil.TempDir("", "webhook-integration-test") + Expect(err).NotTo(HaveOccurred()) + defer os.RemoveAll(outputDir) + genCtx := &genall.GenerationContext{ + Collector: &markers.Collector{Registry: reg}, + Roots: pkgs, + OutputRule: genall.OutputToDirectory(outputDir), + } + err = webhook.Generator{}.Generate(genCtx) + Expect(err).To(MatchError("unsupported webhook version: v1beta1")) + }) + + It("should fail without admissionReviewVersions specified", func() { + By("switching into testdata to appease go modules") + cwd, err := os.Getwd() + Expect(err).NotTo(HaveOccurred()) + Expect(os.Chdir("./testdata/invalid-admissionReviewVersionsRequired")).To(Succeed()) // go modules are directory-sensitive + defer func() { Expect(os.Chdir(cwd)).To(Succeed()) }() + + By("loading the roots") + pkgs, err := loader.LoadRoots(".") + Expect(err).NotTo(HaveOccurred()) + Expect(pkgs).To(HaveLen(1)) + + By("setting up the parser") + reg := &markers.Registry{} + Expect(reg.Register(webhook.ConfigDefinition)).To(Succeed()) + + By("requesting that the manifest be generated") + outputDir, err := ioutil.TempDir("", "webhook-integration-test") + Expect(err).NotTo(HaveOccurred()) + defer os.RemoveAll(outputDir) + genCtx := &genall.GenerationContext{ + Collector: &markers.Collector{Registry: reg}, + Roots: pkgs, + OutputRule: genall.OutputToDirectory(outputDir), + } + Expect(webhook.Generator{}.Generate(genCtx)).To(Succeed()) + Expect(genCtx.Roots).To(HaveLen(1)) + Expect(genCtx.Roots[0].Errors).To(HaveLen(1)) + Expect(genCtx.Roots[0].Errors[0].Error()).To(ContainSubstring(`missing argument "admissionReviewVersions"`)) + }) + + It("should fail with invalid side effects", func() { + By("switching into testdata to appease go modules") + cwd, err := os.Getwd() + Expect(err).NotTo(HaveOccurred()) + Expect(os.Chdir("./testdata/invalid-sideEffects")).To(Succeed()) // go modules are directory-sensitive + defer func() { Expect(os.Chdir(cwd)).To(Succeed()) }() + + By("loading the roots") + pkgs, err := loader.LoadRoots(".") + Expect(err).NotTo(HaveOccurred()) + Expect(pkgs).To(HaveLen(1)) + + By("setting up the parser") + reg := &markers.Registry{} + Expect(reg.Register(webhook.ConfigDefinition)).To(Succeed()) + + By("requesting that the manifest be generated") + outputDir, err := ioutil.TempDir("", "webhook-integration-test") + Expect(err).NotTo(HaveOccurred()) + defer os.RemoveAll(outputDir) + genCtx := &genall.GenerationContext{ + Collector: &markers.Collector{Registry: reg}, + Roots: pkgs, + OutputRule: genall.OutputToDirectory(outputDir), + } + err = webhook.Generator{}.Generate(genCtx) + Expect(err).To(MatchError("SideEffects should not be set to `Some` or `Unknown` for v1 {Mutating,Validating}WebhookConfiguration")) + }) + It("should properly generate the webhook definition", func() { - // TODO(directxman12): test generation across multiple versions (right - // now, we're trusting k/k's conversion code, though, which is probably - // fine for the time being) By("switching into testdata to appease go modules") cwd, err := os.Getwd() Expect(err).NotTo(HaveOccurred()) - Expect(os.Chdir("./testdata")).To(Succeed()) // go modules are directory-sensitive + Expect(os.Chdir("./testdata/valid")).To(Succeed()) // go modules are directory-sensitive defer func() { Expect(os.Chdir(cwd)).To(Succeed()) }() By("loading the roots") @@ -63,11 +151,15 @@ var _ = Describe("Webhook Generation From Parsing to CustomResourceDefinition", outputDir, err := ioutil.TempDir("", "webhook-integration-test") Expect(err).NotTo(HaveOccurred()) defer os.RemoveAll(outputDir) - Expect(webhook.Generator{}.Generate(&genall.GenerationContext{ + genCtx := &genall.GenerationContext{ Collector: &markers.Collector{Registry: reg}, Roots: pkgs, OutputRule: genall.OutputToDirectory(outputDir), - })).To(Succeed()) + } + Expect(webhook.Generator{}.Generate(genCtx)).To(Succeed()) + for _, r := range genCtx.Roots { + Expect(r.Errors).To(HaveLen(0)) + } By("loading the generated v1 YAML") actualFile, err := ioutil.ReadFile(path.Join(outputDir, "manifests.yaml")) @@ -82,32 +174,9 @@ var _ = Describe("Webhook Generation From Parsing to CustomResourceDefinition", By("comparing the two") assertSame(actualMutating, expectedMutating) assertSame(actualValidating, expectedValidating) - - By("loading the generated v1beta1 YAML") - actualFile, err = ioutil.ReadFile(path.Join(outputDir, "manifests.v1beta1.yaml")) - Expect(err).NotTo(HaveOccurred()) - actualMutatingV1beta1, actualValidatingV1beta1 := unmarshalBothV1beta1(actualFile) - - By("loading the desired v1beta1 YAML") - expectedFile, err = ioutil.ReadFile("manifests.v1beta1.yaml") - Expect(err).NotTo(HaveOccurred()) - expectedMutatingV1beta1, expectedValidatingV1beta1 := unmarshalBothV1beta1(expectedFile) - - By("comparing the two") - assertSame(actualMutatingV1beta1, expectedMutatingV1beta1) - assertSame(actualValidatingV1beta1, expectedValidatingV1beta1) }) }) -func unmarshalBothV1beta1(in []byte) (mutating admissionregv1beta1.MutatingWebhookConfiguration, validating admissionregv1beta1.ValidatingWebhookConfiguration) { - documents := bytes.Split(in, []byte("\n---\n"))[1:] - ExpectWithOffset(1, documents).To(HaveLen(2), "expected two documents in file, found %d", len(documents)) - - ExpectWithOffset(1, yaml.UnmarshalStrict(documents[0], &mutating)).To(Succeed(), "expected the first document in the file to be a mutating webhook configuration") - ExpectWithOffset(1, yaml.UnmarshalStrict(documents[1], &validating)).To(Succeed(), "expected the second document in the file to be a validating webhook configuration") - return -} - func unmarshalBothV1(in []byte) (mutating admissionregv1.MutatingWebhookConfiguration, validating admissionregv1.ValidatingWebhookConfiguration) { documents := bytes.Split(in, []byte("\n---\n"))[1:] ExpectWithOffset(1, documents).To(HaveLen(2), "expected two documents in file, found %d", len(documents)) diff --git a/pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/cronjob_types.go b/pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/cronjob_types.go new file mode 100644 index 000000000..4a95bf52a --- /dev/null +++ b/pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/cronjob_types.go @@ -0,0 +1,71 @@ +/* + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +//go:generate ../../../../.run-controller-gen.sh webhook paths=. output:dir=. + +// +groupName=testdata.kubebuilder.io +// +versionName=v1 +package cronjob + +import ( + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + +// EDIT THIS FILE! THIS IS SCAFFOLDING FOR YOU TO OWN! +// NOTE: json tags are required. Any new fields you add must have json tags for the fields to be serialized. + +// CronJobSpec defines the desired state of CronJob +type CronJobSpec struct { + // The schedule in Cron format, see https://en.wikipedia.org/wiki/Cron. + Schedule string `json:"schedule"` +} + +// CronJobStatus defines the observed state of CronJob +type CronJobStatus struct { + // INSERT ADDITIONAL STATUS FIELD - define observed state of cluster + // Important: Run "make" to regenerate code after modifying this file + + // Information when was the last time the job was successfully scheduled. + // +optional + LastScheduleTime *metav1.Time `json:"lastScheduleTime,omitempty"` +} + +// +kubebuilder:object:root=true +// +kubebuilder:subresource:status +// +kubebuilder:resource:singular=mycronjob + +// CronJob is the Schema for the cronjobs API +type CronJob struct { + /* + */ + metav1.TypeMeta `json:",inline"` + metav1.ObjectMeta `json:"metadata,omitempty"` + + Spec CronJobSpec `json:"spec,omitempty"` + Status CronJobStatus `json:"status,omitempty"` +} + +// +kubebuilder:object:root=true + +// CronJobList contains a list of CronJob +type CronJobList struct { + metav1.TypeMeta `json:",inline"` + metav1.ListMeta `json:"metadata,omitempty"` + Items []CronJob `json:"items"` +} + +func init() { + SchemeBuilder.Register(&CronJob{}, &CronJobList{}) +} diff --git a/pkg/webhook/testdata/manifests.v1beta1.yaml b/pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/manifests.yaml similarity index 63% rename from pkg/webhook/testdata/manifests.v1beta1.yaml rename to pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/manifests.yaml index 7c26713d3..8a579ae92 100644 --- a/pkg/webhook/testdata/manifests.v1beta1.yaml +++ b/pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/manifests.yaml @@ -1,6 +1,6 @@ --- -apiVersion: admissionregistration.k8s.io/v1beta1 +apiVersion: admissionregistration.k8s.io/v1 kind: MutatingWebhookConfiguration metadata: creationTimestamp: null @@ -30,13 +30,37 @@ webhooks: sideEffects: None --- -apiVersion: admissionregistration.k8s.io/v1beta1 +apiVersion: admissionregistration.k8s.io/v1 kind: ValidatingWebhookConfiguration metadata: creationTimestamp: null name: validating-webhook-configuration webhooks: -- admissionReviewVersions: null +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /validate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: validation.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: None +- admissionReviewVersions: + - v1 + - v1beta1 clientConfig: service: name: webhook-service @@ -55,4 +79,4 @@ webhooks: - UPDATE resources: - cronjobs - sideEffects: Some + sideEffects: NoneOnDryRun diff --git a/pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/webhook.go b/pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/webhook.go new file mode 100644 index 000000000..4275ad3ed --- /dev/null +++ b/pkg/webhook/testdata/invalid-admissionReviewVersionsRequired/webhook.go @@ -0,0 +1,50 @@ +/* + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package cronjob + +import ( + "k8s.io/apimachinery/pkg/runtime" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/webhook" +) + +func (c *CronJob) SetupWebhookWithManager(mgr ctrl.Manager) error { + return ctrl.NewWebhookManagedBy(mgr). + For(c). + Complete() +} + +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=None +// +kubebuilder:webhook:verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=NoneOnDryRun,admissionReviewVersions=v1;v1beta1 +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/mutate-testdata-kubebuilder-io-v1-cronjob,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=default.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 + +var _ webhook.Defaulter = &CronJob{} +var _ webhook.Validator = &CronJob{} + +func (c *CronJob) Default() { +} + +func (c *CronJob) ValidateCreate() error { + return nil +} + +func (c *CronJob) ValidateUpdate(_ runtime.Object) error { + return nil +} + +func (c *CronJob) ValidateDelete() error { + return nil +} diff --git a/pkg/webhook/testdata/invalid-sideEffects/cronjob_types.go b/pkg/webhook/testdata/invalid-sideEffects/cronjob_types.go new file mode 100644 index 000000000..4a95bf52a --- /dev/null +++ b/pkg/webhook/testdata/invalid-sideEffects/cronjob_types.go @@ -0,0 +1,71 @@ +/* + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +//go:generate ../../../../.run-controller-gen.sh webhook paths=. output:dir=. + +// +groupName=testdata.kubebuilder.io +// +versionName=v1 +package cronjob + +import ( + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + +// EDIT THIS FILE! THIS IS SCAFFOLDING FOR YOU TO OWN! +// NOTE: json tags are required. Any new fields you add must have json tags for the fields to be serialized. + +// CronJobSpec defines the desired state of CronJob +type CronJobSpec struct { + // The schedule in Cron format, see https://en.wikipedia.org/wiki/Cron. + Schedule string `json:"schedule"` +} + +// CronJobStatus defines the observed state of CronJob +type CronJobStatus struct { + // INSERT ADDITIONAL STATUS FIELD - define observed state of cluster + // Important: Run "make" to regenerate code after modifying this file + + // Information when was the last time the job was successfully scheduled. + // +optional + LastScheduleTime *metav1.Time `json:"lastScheduleTime,omitempty"` +} + +// +kubebuilder:object:root=true +// +kubebuilder:subresource:status +// +kubebuilder:resource:singular=mycronjob + +// CronJob is the Schema for the cronjobs API +type CronJob struct { + /* + */ + metav1.TypeMeta `json:",inline"` + metav1.ObjectMeta `json:"metadata,omitempty"` + + Spec CronJobSpec `json:"spec,omitempty"` + Status CronJobStatus `json:"status,omitempty"` +} + +// +kubebuilder:object:root=true + +// CronJobList contains a list of CronJob +type CronJobList struct { + metav1.TypeMeta `json:",inline"` + metav1.ListMeta `json:"metadata,omitempty"` + Items []CronJob `json:"items"` +} + +func init() { + SchemeBuilder.Register(&CronJob{}, &CronJobList{}) +} diff --git a/pkg/webhook/testdata/invalid-sideEffects/manifests.yaml b/pkg/webhook/testdata/invalid-sideEffects/manifests.yaml new file mode 100644 index 000000000..8a579ae92 --- /dev/null +++ b/pkg/webhook/testdata/invalid-sideEffects/manifests.yaml @@ -0,0 +1,82 @@ + +--- +apiVersion: admissionregistration.k8s.io/v1 +kind: MutatingWebhookConfiguration +metadata: + creationTimestamp: null + name: mutating-webhook-configuration +webhooks: +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /mutate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: default.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: None + +--- +apiVersion: admissionregistration.k8s.io/v1 +kind: ValidatingWebhookConfiguration +metadata: + creationTimestamp: null + name: validating-webhook-configuration +webhooks: +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /validate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: validation.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: None +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /validate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: validation.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: NoneOnDryRun diff --git a/pkg/webhook/testdata/invalid-sideEffects/webhook.go b/pkg/webhook/testdata/invalid-sideEffects/webhook.go new file mode 100644 index 000000000..70c05446a --- /dev/null +++ b/pkg/webhook/testdata/invalid-sideEffects/webhook.go @@ -0,0 +1,50 @@ +/* + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package cronjob + +import ( + "k8s.io/apimachinery/pkg/runtime" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/webhook" +) + +func (c *CronJob) SetupWebhookWithManager(mgr ctrl.Manager) error { + return ctrl.NewWebhookManagedBy(mgr). + For(c). + Complete() +} + +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=Some,admissionReviewVersions=v1;v1beta1 +// +kubebuilder:webhook:verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=NoneOnDryRun,admissionReviewVersions=v1;v1beta1 +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/mutate-testdata-kubebuilder-io-v1-cronjob,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=default.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 + +var _ webhook.Defaulter = &CronJob{} +var _ webhook.Validator = &CronJob{} + +func (c *CronJob) Default() { +} + +func (c *CronJob) ValidateCreate() error { + return nil +} + +func (c *CronJob) ValidateUpdate(_ runtime.Object) error { + return nil +} + +func (c *CronJob) ValidateDelete() error { + return nil +} diff --git a/pkg/webhook/testdata/invalid-v1beta1NotSupported/cronjob_types.go b/pkg/webhook/testdata/invalid-v1beta1NotSupported/cronjob_types.go new file mode 100644 index 000000000..4a95bf52a --- /dev/null +++ b/pkg/webhook/testdata/invalid-v1beta1NotSupported/cronjob_types.go @@ -0,0 +1,71 @@ +/* + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +//go:generate ../../../../.run-controller-gen.sh webhook paths=. output:dir=. + +// +groupName=testdata.kubebuilder.io +// +versionName=v1 +package cronjob + +import ( + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + +// EDIT THIS FILE! THIS IS SCAFFOLDING FOR YOU TO OWN! +// NOTE: json tags are required. Any new fields you add must have json tags for the fields to be serialized. + +// CronJobSpec defines the desired state of CronJob +type CronJobSpec struct { + // The schedule in Cron format, see https://en.wikipedia.org/wiki/Cron. + Schedule string `json:"schedule"` +} + +// CronJobStatus defines the observed state of CronJob +type CronJobStatus struct { + // INSERT ADDITIONAL STATUS FIELD - define observed state of cluster + // Important: Run "make" to regenerate code after modifying this file + + // Information when was the last time the job was successfully scheduled. + // +optional + LastScheduleTime *metav1.Time `json:"lastScheduleTime,omitempty"` +} + +// +kubebuilder:object:root=true +// +kubebuilder:subresource:status +// +kubebuilder:resource:singular=mycronjob + +// CronJob is the Schema for the cronjobs API +type CronJob struct { + /* + */ + metav1.TypeMeta `json:",inline"` + metav1.ObjectMeta `json:"metadata,omitempty"` + + Spec CronJobSpec `json:"spec,omitempty"` + Status CronJobStatus `json:"status,omitempty"` +} + +// +kubebuilder:object:root=true + +// CronJobList contains a list of CronJob +type CronJobList struct { + metav1.TypeMeta `json:",inline"` + metav1.ListMeta `json:"metadata,omitempty"` + Items []CronJob `json:"items"` +} + +func init() { + SchemeBuilder.Register(&CronJob{}, &CronJobList{}) +} diff --git a/pkg/webhook/testdata/invalid-v1beta1NotSupported/manifests.yaml b/pkg/webhook/testdata/invalid-v1beta1NotSupported/manifests.yaml new file mode 100644 index 000000000..8a579ae92 --- /dev/null +++ b/pkg/webhook/testdata/invalid-v1beta1NotSupported/manifests.yaml @@ -0,0 +1,82 @@ + +--- +apiVersion: admissionregistration.k8s.io/v1 +kind: MutatingWebhookConfiguration +metadata: + creationTimestamp: null + name: mutating-webhook-configuration +webhooks: +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /mutate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: default.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: None + +--- +apiVersion: admissionregistration.k8s.io/v1 +kind: ValidatingWebhookConfiguration +metadata: + creationTimestamp: null + name: validating-webhook-configuration +webhooks: +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /validate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: validation.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: None +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /validate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: validation.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: NoneOnDryRun diff --git a/pkg/webhook/testdata/invalid-v1beta1NotSupported/webhook.go b/pkg/webhook/testdata/invalid-v1beta1NotSupported/webhook.go new file mode 100644 index 000000000..f717d4ed3 --- /dev/null +++ b/pkg/webhook/testdata/invalid-v1beta1NotSupported/webhook.go @@ -0,0 +1,50 @@ +/* + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package cronjob + +import ( + "k8s.io/apimachinery/pkg/runtime" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/webhook" +) + +func (c *CronJob) SetupWebhookWithManager(mgr ctrl.Manager) error { + return ctrl.NewWebhookManagedBy(mgr). + For(c). + Complete() +} + +// +kubebuilder:webhook:webhookVersions=v1beta1,verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 +// +kubebuilder:webhook:verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=NoneOnDryRun,admissionReviewVersions=v1;v1beta1 +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/mutate-testdata-kubebuilder-io-v1-cronjob,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=default.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 + +var _ webhook.Defaulter = &CronJob{} +var _ webhook.Validator = &CronJob{} + +func (c *CronJob) Default() { +} + +func (c *CronJob) ValidateCreate() error { + return nil +} + +func (c *CronJob) ValidateUpdate(_ runtime.Object) error { + return nil +} + +func (c *CronJob) ValidateDelete() error { + return nil +} diff --git a/pkg/webhook/testdata/manifests.yaml b/pkg/webhook/testdata/manifests.yaml index 285be0243..8a579ae92 100644 --- a/pkg/webhook/testdata/manifests.yaml +++ b/pkg/webhook/testdata/manifests.yaml @@ -36,6 +36,28 @@ metadata: creationTimestamp: null name: validating-webhook-configuration webhooks: +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /validate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: validation.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: None - admissionReviewVersions: - v1 - v1beta1 diff --git a/pkg/webhook/testdata/valid/cronjob_types.go b/pkg/webhook/testdata/valid/cronjob_types.go new file mode 100644 index 000000000..4a95bf52a --- /dev/null +++ b/pkg/webhook/testdata/valid/cronjob_types.go @@ -0,0 +1,71 @@ +/* + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +//go:generate ../../../../.run-controller-gen.sh webhook paths=. output:dir=. + +// +groupName=testdata.kubebuilder.io +// +versionName=v1 +package cronjob + +import ( + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + +// EDIT THIS FILE! THIS IS SCAFFOLDING FOR YOU TO OWN! +// NOTE: json tags are required. Any new fields you add must have json tags for the fields to be serialized. + +// CronJobSpec defines the desired state of CronJob +type CronJobSpec struct { + // The schedule in Cron format, see https://en.wikipedia.org/wiki/Cron. + Schedule string `json:"schedule"` +} + +// CronJobStatus defines the observed state of CronJob +type CronJobStatus struct { + // INSERT ADDITIONAL STATUS FIELD - define observed state of cluster + // Important: Run "make" to regenerate code after modifying this file + + // Information when was the last time the job was successfully scheduled. + // +optional + LastScheduleTime *metav1.Time `json:"lastScheduleTime,omitempty"` +} + +// +kubebuilder:object:root=true +// +kubebuilder:subresource:status +// +kubebuilder:resource:singular=mycronjob + +// CronJob is the Schema for the cronjobs API +type CronJob struct { + /* + */ + metav1.TypeMeta `json:",inline"` + metav1.ObjectMeta `json:"metadata,omitempty"` + + Spec CronJobSpec `json:"spec,omitempty"` + Status CronJobStatus `json:"status,omitempty"` +} + +// +kubebuilder:object:root=true + +// CronJobList contains a list of CronJob +type CronJobList struct { + metav1.TypeMeta `json:",inline"` + metav1.ListMeta `json:"metadata,omitempty"` + Items []CronJob `json:"items"` +} + +func init() { + SchemeBuilder.Register(&CronJob{}, &CronJobList{}) +} diff --git a/pkg/webhook/testdata/valid/manifests.yaml b/pkg/webhook/testdata/valid/manifests.yaml new file mode 100644 index 000000000..8a579ae92 --- /dev/null +++ b/pkg/webhook/testdata/valid/manifests.yaml @@ -0,0 +1,82 @@ + +--- +apiVersion: admissionregistration.k8s.io/v1 +kind: MutatingWebhookConfiguration +metadata: + creationTimestamp: null + name: mutating-webhook-configuration +webhooks: +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /mutate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: default.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: None + +--- +apiVersion: admissionregistration.k8s.io/v1 +kind: ValidatingWebhookConfiguration +metadata: + creationTimestamp: null + name: validating-webhook-configuration +webhooks: +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /validate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: validation.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: None +- admissionReviewVersions: + - v1 + - v1beta1 + clientConfig: + service: + name: webhook-service + namespace: system + path: /validate-testdata-kubebuilder-io-v1-cronjob + failurePolicy: Fail + matchPolicy: Equivalent + name: validation.cronjob.testdata.kubebuilder.io + rules: + - apiGroups: + - testdata.kubebuiler.io + apiVersions: + - v1 + operations: + - CREATE + - UPDATE + resources: + - cronjobs + sideEffects: NoneOnDryRun diff --git a/pkg/webhook/testdata/valid/webhook.go b/pkg/webhook/testdata/valid/webhook.go new file mode 100644 index 000000000..d964c493a --- /dev/null +++ b/pkg/webhook/testdata/valid/webhook.go @@ -0,0 +1,50 @@ +/* + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package cronjob + +import ( + "k8s.io/apimachinery/pkg/runtime" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/webhook" +) + +func (c *CronJob) SetupWebhookWithManager(mgr ctrl.Manager) error { + return ctrl.NewWebhookManagedBy(mgr). + For(c). + Complete() +} + +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 +// +kubebuilder:webhook:verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=NoneOnDryRun,admissionReviewVersions=v1;v1beta1 +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/mutate-testdata-kubebuilder-io-v1-cronjob,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=default.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 + +var _ webhook.Defaulter = &CronJob{} +var _ webhook.Validator = &CronJob{} + +func (c *CronJob) Default() { +} + +func (c *CronJob) ValidateCreate() error { + return nil +} + +func (c *CronJob) ValidateUpdate(_ runtime.Object) error { + return nil +} + +func (c *CronJob) ValidateDelete() error { + return nil +} diff --git a/pkg/webhook/testdata/webhook.go b/pkg/webhook/testdata/webhook.go index 17ab8f415..d964c493a 100644 --- a/pkg/webhook/testdata/webhook.go +++ b/pkg/webhook/testdata/webhook.go @@ -27,9 +27,9 @@ func (c *CronJob) SetupWebhookWithManager(mgr ctrl.Manager) error { Complete() } -// +kubebuilder:webhook:webhookVersions=v1beta1,verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=Some +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 // +kubebuilder:webhook:verbs=create;update,path=/validate-testdata-kubebuilder-io-v1-cronjob,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=validation.cronjob.testdata.kubebuilder.io,sideEffects=NoneOnDryRun,admissionReviewVersions=v1;v1beta1 -// +kubebuilder:webhook:webhookVersions=v1;v1beta1,verbs=create;update,path=/mutate-testdata-kubebuilder-io-v1-cronjob,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=default.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 +// +kubebuilder:webhook:webhookVersions=v1,verbs=create;update,path=/mutate-testdata-kubebuilder-io-v1-cronjob,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=testdata.kubebuiler.io,resources=cronjobs,versions=v1,name=default.cronjob.testdata.kubebuilder.io,sideEffects=None,admissionReviewVersions=v1;v1beta1 var _ webhook.Defaulter = &CronJob{} var _ webhook.Validator = &CronJob{} diff --git a/pkg/webhook/zz_generated.markerhelp.go b/pkg/webhook/zz_generated.markerhelp.go index 15e9158ce..5e4e02f86 100644 --- a/pkg/webhook/zz_generated.markerhelp.go +++ b/pkg/webhook/zz_generated.markerhelp.go @@ -73,11 +73,11 @@ func (Config) Help() *markers.DefinitionHelp { Details: "", }, "WebhookVersions": { - Summary: "specifies the target API versions of the {Mutating,Validating}WebhookConfiguration objects itself to generate. Defaults to v1.", + Summary: "specifies the target API versions of the {Mutating,Validating}WebhookConfiguration objects itself to generate. The only supported value is v1. Defaults to v1.", Details: "", }, "AdmissionReviewVersions": { - Summary: "is an ordered list of preferred `AdmissionReview` versions the Webhook expects. For generating v1 {Mutating,Validating}WebhookConfiguration, this is mandatory. For generating v1beta1 {Mutating,Validating}WebhookConfiguration, this is optional, and default to v1beta1.", + Summary: "is an ordered list of preferred `AdmissionReview` versions the Webhook expects.", Details: "", }, },